Home > mml > at > readmad.m

readmad

PURPOSE ^

READMAD reads the file output of MAD commands

SYNOPSIS ^

function [ATLATTICE, Twiss] = readmad(FILENAME)

DESCRIPTION ^

READMAD reads the file output of MAD commands
 TWISS, STRUCTURE, SURVEY.

 READMAD reads the MAD file header to determine the number of elements
 in the lattice, symmetry flag, the number of supperperiods etc.

 Then it interprets the entry for each element in the MAD output file.
 The topology of the lattice is completely determined by
 Length, Bending Angle, and Ttilt Angle in each element

 READMAD uses MAD TYPES and the values of to determine
 which pass-method function in AT to use.

 MAD TYPE      |  AT PassMethod
 ----------------------------------
 DRIFT         |  DriftPass
 SBEND         |  BendLinearPass, BendLinearFringeTiltPass, BndMPoleSymplectic4Pass
 QUADRUPOLE    |  QualdLinearPass
 SEXTUPOLE     |  StrMPoleSymplectic4Pass
 OCTUPOLE      |  StrMPoleSymplectic4Pass
 MULTIPOLE     |  !!! Not implemented, in future - ThinMPolePass
 RFCAVITY      |  CavityPass
 KICKER        |  CorrectorPass
 HKICKER       |  CorrectorPass
 VKICKER       |  CorrectorPass
 MONITOR       |  IdentityPass
 HMONITOR      |  IdentityPass
 VMONITOR      |  IdentityPass
 MARKER        |  IdentityPass
 -----------------------------------
 all others    |  Length=0 -> IdentityPass, Length~=0 -> DriftPass

CROSS-REFERENCE INFORMATION ^

This function calls: This function is called by:

SUBFUNCTIONS ^

SOURCE CODE ^

0001 function [ATLATTICE, Twiss] = readmad(FILENAME)
0002 %READMAD reads the file output of MAD commands
0003 % TWISS, STRUCTURE, SURVEY.
0004 %
0005 % READMAD reads the MAD file header to determine the number of elements
0006 % in the lattice, symmetry flag, the number of supperperiods etc.
0007 %
0008 % Then it interprets the entry for each element in the MAD output file.
0009 % The topology of the lattice is completely determined by
0010 % Length, Bending Angle, and Ttilt Angle in each element
0011 %
0012 % READMAD uses MAD TYPES and the values of to determine
0013 % which pass-method function in AT to use.
0014 %
0015 % MAD TYPE      |  AT PassMethod
0016 % ----------------------------------
0017 % DRIFT         |  DriftPass
0018 % SBEND         |  BendLinearPass, BendLinearFringeTiltPass, BndMPoleSymplectic4Pass
0019 % QUADRUPOLE    |  QualdLinearPass
0020 % SEXTUPOLE     |  StrMPoleSymplectic4Pass
0021 % OCTUPOLE      |  StrMPoleSymplectic4Pass
0022 % MULTIPOLE     |  !!! Not implemented, in future - ThinMPolePass
0023 % RFCAVITY      |  CavityPass
0024 % KICKER        |  CorrectorPass
0025 % HKICKER       |  CorrectorPass
0026 % VKICKER       |  CorrectorPass
0027 % MONITOR       |  IdentityPass
0028 % HMONITOR      |  IdentityPass
0029 % VMONITOR      |  IdentityPass
0030 % MARKER        |  IdentityPass
0031 % -----------------------------------
0032 % all others    |  Length=0 -> IdentityPass, Length~=0 -> DriftPass
0033 
0034 Twiss = [];
0035 
0036 [fid, errmsg]  = fopen(FILENAME,'r');
0037 if fid==-1
0038     error('Could not open file');
0039 end
0040 
0041 warnlevel = warning;
0042 warning on
0043 
0044 global READMADCAVITYFLAG
0045 READMADCAVITYFLAG = 0;
0046 
0047 LINE1 = fgetl(fid);
0048 LINE2 = fgetl(fid);
0049 
0050 S = LINE1(9:16);
0051 nonspaceindex = find(~isspace(S) & (S~=0));
0052 MADFILETYPE = S(nonspaceindex);
0053 % The possiblilites for MADFILETYPE are
0054 % TWISS,SURVEY,STRUCTUR,ENVELOPE
0055 
0056 
0057 NSUPER = str2double(LINE1(41:48));
0058 
0059 S = LINE1(56);
0060 SYMFLAG = eq(S,'T');
0061 
0062 NPOS = str2double(LINE1(57:64));
0063 
0064 disp(['   MAD output file: ',FILENAME]);
0065 disp(['   MAD file type:           ',MADFILETYPE]);
0066 disp(['   Symmetry flag:           ',num2str(SYMFLAG)]);
0067 disp(['   Number of superperiods:  ',num2str(NSUPER)]);
0068 disp(['   Number of elements :     ',num2str(NPOS)]);
0069 
0070 
0071 % Allocate cell array to store AT lattice
0072 % MAD files heve one extra entry for the beginning of the lattice
0073 ATNumElements = NPOS-1;
0074 ATLATTICE = cell(1,ATNumElements);
0075 
0076 
0077 switch MADFILETYPE
0078     case {'STRUCTUR','SURVEY'}
0079         NumLinesPerElement = 4;
0080     case {'TWISS','CHROM'}
0081         NumLinesPerElement = 5;
0082     case 'ENVELOPE'
0083         NumLinesPerElement = 8;
0084 end
0085 
0086 ELEMENTDATA = cell(1,NumLinesPerElement);
0087 
0088 % Skip the INITIAL element in MAD file
0089 for i = 1:NumLinesPerElement;
0090     LINE = fgetl(fid);
0091 end
0092 
0093 for i = 1:ATNumElements
0094     % Read the first 2 lines of the element entry
0095     for j= 1:NumLinesPerElement
0096         ELEMENTDATA{j}=fgetl(fid);
0097     end
0098 
0099     ATLATTICE{i}=mad2at(ELEMENTDATA,MADFILETYPE);
0100 
0101     if strcmpi(MADFILETYPE, 'TWISS')
0102         Twiss.Alpha(i,1) = str2double(ELEMENTDATA{3}([1:16]));
0103         Twiss.Beta(i,1)  = str2double(ELEMENTDATA{3}([1:16]+16));
0104         Twiss.Mu(i,1)    = str2double(ELEMENTDATA{3}([1:16]+16*2));
0105         Twiss.d(i,1)     = str2double(ELEMENTDATA{3}([1:16]+16*3));
0106         Twiss.dp(i,1)    = str2double(ELEMENTDATA{3}([1:16]+16*4));
0107 
0108         Twiss.Alpha(i,2) = str2double(ELEMENTDATA{4}([1:16]));
0109         Twiss.Beta(i,2)  = str2double(ELEMENTDATA{4}([1:16]+16));
0110         Twiss.Mu(i,2)    = str2double(ELEMENTDATA{4}([1:16]+16*2));
0111         Twiss.d(i,2)     = str2double(ELEMENTDATA{4}([1:16]+16*3));
0112         Twiss.dp(i,2)    = str2double(ELEMENTDATA{4}([1:16]+16*4));
0113 
0114         Twiss.a(i,1)    = str2double(ELEMENTDATA{5}([1:16]));
0115         Twiss.Px(i,1)   = str2double(ELEMENTDATA{5}([1:16]+16));
0116         Twiss.y(i,1)    = str2double(ELEMENTDATA{5}([1:16]+16*2));
0117         Twiss.Py(i,1)   = str2double(ELEMENTDATA{5}([1:16]+16*3));
0118         Twiss.s(i,1) = str2double(ELEMENTDATA{5}([1:16]+16*4));
0119     end
0120 end
0121 
0122 % Add a marker to the end
0123 ATLATTICE{end+1}.FamName = 'EndMarker';
0124 ATLATTICE{end}.Length  = 0;
0125 ATLATTICE{end}.MADType = 'MARK';
0126 ATLATTICE{end}.PassMethod = 'IdentityPass';
0127 
0128 
0129 fclose(fid);
0130 warning(warnlevel);
0131 
0132 % disp(' ');
0133 % disp(['AT cell array was successfully created from MAD output file ',FILENAME]);
0134 % disp('Some information may be not available in MAD otput files')
0135 % disp('Some elements may have to be further modified to be consistent with AT element models')
0136 % disp(' ');
0137 % %disp('For RF cavities READMAD creates elements that use DriftPass or IdentityPass (if Length ==0)');
0138 % disp('For RF cavities READMAD creates elements that use CavityPass');
0139 % disp('Use CAVITYON(ENERGY) [eV] in order to turn them into cavities');
0140 
0141 % Compute total length and RF frequency
0142 L0_tot = findspos(ATLATTICE, length(ATLATTICE)+1);
0143 fprintf('   Total length = %.6f m  \n', L0_tot)
0144 %fprintf('   RF = %.6f MHz (should be 499.640349 Hz)\n', HarmNumber*C0/L0_tot/1e6)
0145 
0146 
0147 % Some AT passmethods requires Energy to be an field
0148 % ATLATTICE = setcellstruct(ATLATTICE, 'Energy', 1:length(ATLATTICE), Energy);
0149 
0150 
0151 % ---------------------------------------------------------------------------
0152 
0153 function atelement = mad2at(elementdata,madfiletype)
0154 global READMADCAVITYFLAG
0155 MADTYPE = elementdata{1}(1:4);
0156 atelement.FamName = deblank(elementdata{1}(5:20));
0157 atelement.Length  = str2double(elementdata{1}(21:32));
0158 atelement.MADType = MADTYPE;
0159 %atelement.Type    = deblank(elementdata{1}(98:113));
0160 %atelement.Energy  = str2double(elementdata{1}(115:130)) * 1e9;  % MAD uses GeV
0161 
0162 
0163 % Type specific
0164 switch MADTYPE
0165     case 'DRIF'
0166         atelement.FamName = 'DRIFT';
0167         atelement.PassMethod = 'DriftPass';
0168     
0169     case {'MARK','MONI','HMON','VMON'}
0170         atelement.PassMethod = 'IdentityPass';
0171     
0172     case {'KICK','HKIC','VKIC'}
0173         %atelement.FamName = 'COR';
0174         atelement.KickAngle = [0 0];
0175         atelement.PassMethod = 'CorrectorPass';
0176     
0177     case 'RFCA'
0178         % Note MAD determines the RF frequency from the harmonic number HARMON
0179         % defined by MAD stetement BEAM, and the total length of the closed orbit
0180         if ~READMADCAVITYFLAG
0181             %warning('MAD lattice contains RF cavities')
0182             READMADCAVITYFLAG = 1;
0183         end
0184         atelement.Frequency = 1e6*str2double(elementdata{2}(17:32)); % MAD uses MHz
0185         atelement.Voltage   = 1e6*str2double(elementdata{2}(33:48));
0186         atelement.PhaseLag  =     str2double(elementdata{2}(49:64));
0187         if atelement.Length
0188             atelement.PassMethod = 'CavityPass';
0189         else
0190             atelement.PassMethod = 'CavityPass';
0191         end
0192 
0193     case 'SBEN'
0194         K1 = str2double(elementdata{1}(49:64));
0195         K2 = str2double(elementdata{1}(65:80));
0196         atelement.BendingAngle = str2double(elementdata{1}(33:48));
0197         atelement.ByError = 0;
0198         atelement.MaxOrder = 3;
0199         atelement.NumIntSteps = 10;
0200         atelement.TiltAngle     = str2double(elementdata{2}(1:16));
0201         atelement.EntranceAngle = str2double(elementdata{2}(17:32));
0202         atelement.ExitAngle     = str2double(elementdata{2}(33:48));
0203         %     atelement.ExitAngle     = atelement.EntranceAngle;
0204         atelement.K = K1;
0205         atelement.PolynomB = [0 K1 K2 0];
0206         atelement.PolynomA = [0 0 0 0];
0207         atelement.T1 = zeros(1,6);
0208         atelement.T2 = zeros(1,6);
0209         atelement.R1 = eye(6);
0210         atelement.R2 = eye(6);
0211         if atelement.BendingAngle
0212             if K2
0213                 atelement.PassMethod = 'BndMPoleSymplectic4Pass';
0214             elseif atelement.TiltAngle
0215                 atelement.PassMethod = 'BendLinearFringeTiltPass';
0216             else
0217                 %atelement.PassMethod = 'BndMPoleSymplectic4Pass';
0218                 atelement.PassMethod = 'BendLinearPass';
0219             end
0220 
0221         else
0222             if K2
0223                 atelement.PassMethod = 'StrMPoleSymplectic4Pass';
0224             elseif K1
0225                 atelement.PassMethod = 'QuadLinearPass';
0226             else
0227                 atelement.PassMethod = 'DriftPass';
0228             end
0229         end
0230 
0231     case 'QUAD'
0232         K1 = str2double(elementdata{1}(49:64));
0233         atelement.MaxOrder = 3;
0234         atelement.NumIntSteps = 10;
0235         atelement.K = K1;
0236         atelement.PolynomB = [0 K1 0 0];
0237         atelement.PolynomA = [0 0 0 0];
0238         atelement.T1 = zeros(1,6);
0239         atelement.T2 = zeros(1,6);
0240         TILT = str2double(elementdata{2}(1:16));
0241         atelement.R1 = mksrollmat(TILT);
0242         atelement.R2 = mksrollmat(-TILT);
0243         atelement.PassMethod = 'QuadLinearPass';
0244         %atelement.PassMethod = 'StrMPoleSymplectic4Pass';
0245 
0246     case 'SEXT'
0247         % MAD multipole strength coefficients K(n) are defined without 1/n!
0248         % Adjust to match AT
0249         K2 = str2double(elementdata{1}(65:80))/2;
0250         atelement.MaxOrder = 3;
0251         atelement.NumIntSteps = 10;
0252         atelement.PolynomB = [0 0 K2 0];
0253         atelement.PolynomA = [0 0 0 0];
0254         atelement.T1 = zeros(1,6);
0255         atelement.T2 = zeros(1,6);
0256         TILT = str2double(elementdata{2}(1:16));
0257         atelement.R1 = mksrollmat(TILT);
0258         atelement.R2 = mksrollmat(-TILT);
0259         atelement.PassMethod = 'StrMPoleSymplectic4Pass';
0260 
0261     case 'OCTU'
0262         % MAD multipole strength coefficients K(n) are defined without 1/n!
0263         % Adjust to match AT
0264         K3 = str2double(elementdata{2}(17:32))/6;
0265         atelement.MaxOrder = 3 ;
0266         atelement.NumIntSteps = 10;
0267         atelement.PolynomB = [0 0 0 K3];
0268         atelement.PolynomA = [0 0 0 0];
0269         atelement.T1 = zeros(1,6);
0270         atelement.T2 = zeros(1,6);
0271         TILT = str2double(elementdata{2}(1:16));
0272         atelement.R1 = mksrollmat(TILT);
0273         atelement.R2 = mksrollmat(-TILT);
0274         atelement.PassMethod = 'StrMPoleSymplectic4Pass';
0275 
0276     otherwise
0277         if atelement.Length
0278             atelement.PassMethod = 'DriftPass';
0279         else
0280             atelement.PassMethod = 'IdentityPass';
0281         end
0282 end

Generated on Fri 01-Aug-2008 10:57:33 by m2html © 2003