1 | function [DeltaRF, RFnew, frf] = findrf1(DeltaRF, BPMFamily, BPMList, FileName) |
---|
2 | %FINDRF1 - Finds the RF frequency that minimizes the horizontal dispersion |
---|
3 | % [DeltaRF, RFnew, frf] = findrf1(DeltaRFvec, BPMFamily, BPMList, FileName) |
---|
4 | % |
---|
5 | % INPUTS |
---|
6 | % 1. DeltaRFvec - Vector of RF changes {Default or empty: [-.2% -.1% 0% .1% .2%] energy change} |
---|
7 | % 2. BPMFamily - Family name {Default or empty: 'BPMx'} |
---|
8 | % 3. BPMList - Device or element list of BPMs {Default or empty: all} |
---|
9 | % 4. FileName to save data (data in structure 'frf') {Default or empty: don't save data} |
---|
10 | % |
---|
11 | % OUTPUTS |
---|
12 | % 1. DeltaRF - Change in RF |
---|
13 | % 2. RFnew - Zero crossing of the fit |
---|
14 | % 3. frf - RF structure containing all the measurement data |
---|
15 | % |
---|
16 | % NOTES |
---|
17 | % 1. The RF frequency that minimized the dispersion maybe not be the |
---|
18 | % optimal RF frequency. The ALS found that choosing an RF frequency which |
---|
19 | % minimizes the energy shift due to the horizontal corrector magnets |
---|
20 | % to be a more robust and repeatable solution. |
---|
21 | % 2. This function measures the dispersion, hence changes the RF frequency! |
---|
22 | % rmdisp will basically do the same thing as findrf1 without changing the |
---|
23 | % RF frequency. However, findrf1 gives more control over the fit range for |
---|
24 | % the RF change and allows for more noise reduction in the fit. That said, |
---|
25 | % rmdisp is usually just fine to use. |
---|
26 | % 3. Beware of the magnitude of DeltaRFvec for nonlinear accelerators. |
---|
27 | % |
---|
28 | % See also findrf rmdisp plotcm |
---|
29 | % |
---|
30 | % Written by Greg Portmann |
---|
31 | |
---|
32 | |
---|
33 | ChangeRFFlag = 1; |
---|
34 | DisplayFlag = 1; |
---|
35 | |
---|
36 | |
---|
37 | % Starting Point |
---|
38 | RF0 = getrf('Struct'); |
---|
39 | |
---|
40 | |
---|
41 | if nargin < 1 |
---|
42 | DeltaRF = []; |
---|
43 | end |
---|
44 | if isempty(DeltaRF) |
---|
45 | %DeltaRF = getfamilydata('DeltaRFChro'); |
---|
46 | if isempty(DeltaRF) |
---|
47 | DeltaRF = getrf * getmcf * [-.002 -.001 0 .001 .002]; % .2% energy change |
---|
48 | %DeltaRF = getrf * getmcf * [-.006 -.003 0 .003 .006]; % .6% energy change |
---|
49 | %DeltaRF = [-400 -200 0 200 400]; % Hz |
---|
50 | %if strcmpi(RF0.UnitsString, 'Hz') |
---|
51 | %elseif strcmpi(RF0.UnitsString, 'MHz') |
---|
52 | % DeltaRF = DeltaRF * 1e-6; % MHz |
---|
53 | %else |
---|
54 | % error('RF units unknown, hence default input frequency cannot be choosen.'); |
---|
55 | %end |
---|
56 | end |
---|
57 | end |
---|
58 | if nargin < 2 |
---|
59 | BPMFamily = ''; |
---|
60 | end |
---|
61 | if isempty(BPMFamily) |
---|
62 | BPMFamily = 'BPMx'; |
---|
63 | end |
---|
64 | if nargin < 3 |
---|
65 | BPMList = family2dev(BPMFamily); |
---|
66 | end |
---|
67 | if isempty(BPMList) |
---|
68 | BPMList = family2dev(BPMFamily); |
---|
69 | end |
---|
70 | if nargin < 4 |
---|
71 | FileName = []; |
---|
72 | end |
---|
73 | |
---|
74 | |
---|
75 | BPMDelay = getfamilydata('BPMDelay'); |
---|
76 | if isempty(BPMDelay) |
---|
77 | BPMDelay = 0; |
---|
78 | end |
---|
79 | |
---|
80 | |
---|
81 | Xoffset = getoffset(BPMFamily, BPMList); |
---|
82 | Xgolden = getgolden(BPMFamily, BPMList); |
---|
83 | |
---|
84 | |
---|
85 | % Get Dispersion |
---|
86 | Dx = measdisp([], BPMFamily, BPMList); |
---|
87 | |
---|
88 | |
---|
89 | for i = 1:length(DeltaRF) |
---|
90 | fprintf(' %d. Setting RF to %f [%s] \n', i, RF0.Data + DeltaRF(i), RF0.UnitsString); |
---|
91 | setrf(RF0.Data + DeltaRF(i)); |
---|
92 | sleep(BPMDelay); |
---|
93 | x(:,i) = getam(BPMFamily, BPMList) - Xoffset; |
---|
94 | rf(1,i) = getrf; |
---|
95 | end |
---|
96 | |
---|
97 | |
---|
98 | % Set RF back to starting point |
---|
99 | setrf(RF0); |
---|
100 | |
---|
101 | |
---|
102 | % Find LS fit to the line |
---|
103 | y = x' * Dx; % Dot product of Dx and the X orbit |
---|
104 | X = [ones(max(size(rf)),1) rf']; |
---|
105 | %b = inv(X'*X)*X'*y; |
---|
106 | b = X \ y; |
---|
107 | RFnew = -b(1) / b(2); |
---|
108 | |
---|
109 | |
---|
110 | rf1 = linspace(rf(1),rf(max(size(rf))),100); |
---|
111 | yfit = b(1) + b(2)*rf1; |
---|
112 | |
---|
113 | DeltaRF = RFnew - RF0.Data; |
---|
114 | |
---|
115 | |
---|
116 | %figure |
---|
117 | clf reset |
---|
118 | plot(rf1,yfit, 'b', rf,y,'og', RFnew,0,'xr'); |
---|
119 | grid on |
---|
120 | xlabel('RF Frequency [MHz]'); |
---|
121 | ylabel('Dot product of Dx and Hor. Orbit'); |
---|
122 | title(sprintf('FIT: %g + %g * RF, \\DeltaRF = %g', b(1), b(2), DeltaRF)); |
---|
123 | |
---|
124 | |
---|
125 | |
---|
126 | % Set the RF frequency |
---|
127 | if ChangeRFFlag |
---|
128 | % fprintf('\n Starting RF = %f [%s]\n', RF0.Data, RF0.UnitsString); |
---|
129 | % fprintf(' Zero crossing of the RF = %f Delta RF = %g [%s]\n', RFnew, DeltaRF, RF0.UnitsString); |
---|
130 | % answer = input(' Do you want to set the RF frequence now (n/y)? ','s'); |
---|
131 | % if strcmp(answer, 'y') == 1 |
---|
132 | % setrf(RFnew); |
---|
133 | % fprintf(' New RF frequency = %f [%s]\n', getrf, RF0.UnitsString); |
---|
134 | % fprintf(' Measurement complete.\n'); |
---|
135 | % else |
---|
136 | % fprintf(' Measurement complete. No change to the RF frequency.\n'); |
---|
137 | % end |
---|
138 | if ~isempty(DeltaRF) |
---|
139 | if DisplayFlag |
---|
140 | answer = inputdlg({strvcat(strvcat(strvcat(sprintf('Recommend new RF Freqenecy is %g %s', RFnew, RF0.UnitsString), sprintf('Delta RF is %g %s', DeltaRF, RF0.UnitsString)), ' '),'Change the RF frequency?')},'FINDFR1',1,{sprintf('%g',DeltaRF)}); |
---|
141 | if isempty(answer) |
---|
142 | fprintf(' No change was made to the RF frequency.\n'); |
---|
143 | return |
---|
144 | end |
---|
145 | DeltaRF = str2num(answer{1}); |
---|
146 | end |
---|
147 | steprf(DeltaRF); |
---|
148 | if DisplayFlag |
---|
149 | fprintf(' RF frequency change by %f %s.\n', DeltaRF, RFUnitsString); |
---|
150 | end |
---|
151 | else |
---|
152 | error('RF frequency not changed because of a calculation problem.'); |
---|
153 | end |
---|
154 | end |
---|
155 | |
---|
156 | |
---|
157 | if ~isempty(FileName) %save file |
---|
158 | frf.TimeStamp = clock; |
---|
159 | frf.CreatedBy = 'findrf'; |
---|
160 | frf.FileName = FileName; |
---|
161 | frf.x = x; |
---|
162 | frf.rf = rf; |
---|
163 | frf.Dx = Dx; |
---|
164 | frf.RF0 = RF0; |
---|
165 | frf.RFnew = RFnew; |
---|
166 | frf.DeltaRF = DeltaRF; |
---|
167 | frf.BPMFamily = BPMFamily; |
---|
168 | frf.BPMList = BPMList; |
---|
169 | frf.Xgolden = Xgolden; |
---|
170 | frf.Xoffset = Xoffset; |
---|
171 | save(FileName, 'frf'); |
---|
172 | fprintf(' Data saved to %s.mat in directory %s.\n', FileName, pwd); |
---|
173 | end |
---|
174 | |
---|
175 | |
---|
176 | |
---|