| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

In This Package:

MagneticFieldSvc.cpp

Go to the documentation of this file.
00001 // $Id: MagneticFieldSvc.cpp,v 1.43 2009/01/26 12:58:07 cattanem Exp $
00002 
00003 // Include files
00004 #include "GaudiKernel/SvcFactory.h"
00005 #include "GaudiKernel/ISvcLocator.h"
00006 #include "GaudiKernel/MsgStream.h"
00007 #include "GaudiKernel/SystemOfUnits.h"
00008 
00009 #include "MagneticFieldSvc.h"
00010 #include "MagnetCondLocations.h"
00011 #include "IMagFieldTool.h"
00012 
00013 #include "GaudiKernel/Vector3DTypes.h"
00014 #include "GaudiKernel/Point3DTypes.h"
00015 #include "GaudiKernel/IUpdateManagerSvc.h"
00016 #include "GaudiKernel/IToolSvc.h"
00017 
00018 #include <cstdlib>
00019 #include <fstream>
00020 
00030 DECLARE_SERVICE_FACTORY( MagneticFieldSvc );
00031 
00032 //=============================================================================
00033 // Standard constructor, initializes variables
00034 //=============================================================================
00035 MagneticFieldSvc::MagneticFieldSvc( const std::string& name, 
00036                                     ISvcLocator* svc ) : Service( name, svc ),
00037                                                          m_mapFromOptions(false),
00038                                                          m_scaleFromOptions(false),
00039                                                          m_mapFilesUpPtr(0),
00040                                                          m_mapFilesDownPtr(0),
00041                                                          m_scaleUpPtr(0),
00042                                                          m_scaleDownPtr(0),
00043                                                          m_currentPtr(0),
00044                                                          m_fieldTool(0),
00045                                                          m_DC06FieldUp(0),
00046                                                          m_DC06FieldDown(0),
00047                                                          m_RealFieldUp(0),
00048                                                          m_RealFieldDown(0),
00049                                                          m_updMgrSvc(0),
00050                                                          m_toolSvc(0)
00051 {
00052 
00053   m_constFieldVector.push_back( 0. );
00054   m_constFieldVector.push_back( 0. );
00055   m_constFieldVector.push_back( 0. );
00056 
00057   if( std::getenv("FIELDMAPROOT") != NULL ) {
00058     m_mapFilePath  = getenv("FIELDMAPROOT");
00059     m_mapFilePath += "/cdf/";
00060   }
00061   else
00062     m_mapFilePath  = "";
00063   
00064   declareProperty( "NominalCurrent", m_nominalCurrent = 5850, 
00065                    "Nominal magnet current in Amps" );
00066   declareProperty( "FieldMapPath",  m_mapFilePath, 
00067                    "Directory where field map files are located, including trailing separator" );
00068   declareProperty( "UseConditions", m_UseConditions = true );
00069   declareProperty( "UseSetCurrent", m_UseSetCurrent = false );
00070   declareProperty( "FieldMapFiles", m_mapFileNames, 
00071                    "Vector of file names for the field map. If set, over-rides CondDB value" );
00072   declareProperty( "ScaleFactor",   m_scaleFactor = 9999.,
00073                    "Factor by which to rescale the field map. If set, over-rides CondDB value" );
00074   declareProperty( "Polarity",      m_polarity = 0,
00075                    "Polarity of the magnet. If set, over-rides CondDB value" );
00076   
00077   declareProperty( "UseConstantField",    m_useConstField = false );
00078   declareProperty( "ConstantFieldVector", m_constFieldVector );
00079 
00080   // Obsolete properties, will be removed soon, do not use!
00081   declareProperty( "UseRealMap",    m_useRealMap   = false );
00082   declareProperty( "FieldMapFile",  m_filename     = "" );
00083   declareProperty( "FieldMapFileQ1",m_qfilename[0] = "" );
00084   declareProperty( "FieldMapFileQ2",m_qfilename[1] = "" );
00085   declareProperty( "FieldMapFileQ3",m_qfilename[2] = "" );
00086   declareProperty( "FieldMapFileQ4",m_qfilename[3] = "" );
00087   declareProperty( "CondPath", m_condPath = "" );
00088   
00089 }
00090 //=============================================================================
00091 // Standard destructor
00092 //=============================================================================
00093 MagneticFieldSvc::~MagneticFieldSvc()
00094 {
00095 }
00096 
00097 //=============================================================================
00098 // Initialize
00099 //=============================================================================
00100 StatusCode MagneticFieldSvc::initialize()
00101 {
00102   
00103   MsgStream log(msgSvc(), name());
00104   StatusCode status = Service::initialize();
00105   if( status.isFailure() ) return status;
00106 
00107   // Backward compatibility of old options
00108   if( m_filename != "" || m_qfilename[0] != "" || m_qfilename[1] != ""
00109                        || m_qfilename[2] != "" || m_qfilename[3] != "") {
00110     if( m_mapFileNames.size() > 0 ) {
00111       log << MSG::ERROR << "Both old and new style FieldMapFile options set, don't know what to do!" << endmsg;
00112       return StatusCode::FAILURE;
00113     }
00114     else if( m_filename != "" && m_qfilename[0] == "" && m_qfilename[1] == ""
00115                               && m_qfilename[2] == "" && m_qfilename[3] == "") {
00116       log << MSG::WARNING << "Using obsolete DC06 option FieldMapFile, please change to FieldMapFiles" << endmsg;
00117       m_mapFileNames.push_back( m_filename );
00118     }
00119     else if( m_filename == "" && m_qfilename[0] != "" && m_qfilename[1] != ""
00120                               && m_qfilename[2] != "" && m_qfilename[3] != "") {
00121       log << MSG::WARNING << "Using obsolete real map options FieldMapFileQ*, please change to FieldMapFiles" << endmsg;
00122       m_mapFileNames.push_back( m_qfilename[0] );
00123       m_mapFileNames.push_back( m_qfilename[1] );
00124       m_mapFileNames.push_back( m_qfilename[2] );
00125       m_mapFileNames.push_back( m_qfilename[3] );
00126     }
00127     else {
00128       log << MSG::ERROR << "Using invalid combination of FieldMapFile and FieldMapfileQ* options" << endmsg;
00129       return StatusCode::FAILURE;
00130     }
00131   }
00132   if( m_condPath != "" )
00133     log << MSG::WARNING << "Obsolete property CondPath given but has no effect" << endmsg;
00134 
00135   // Tool service, for access to the Field map tool(s)
00136   status = service("ToolSvc", m_toolSvc );
00137   if ( status.isFailure() ) {
00138     log << MSG::ERROR << "Cannot find the ToolSvc" << endmsg;
00139     return status;
00140   }
00141 
00142   if( m_useConstField ) {
00143     // Constant field requested, do not use any field map
00144     log << MSG::WARNING << "using constant magnetic field with field vector "
00145         << m_constFieldVector << " (Tesla)" << endmsg;
00146     return StatusCode::SUCCESS;
00147   }
00148   
00149   if( m_UseConditions ) {
00150     // Normal case, use conditions database
00151     status = initializeWithCondDB();
00152   }
00153   else {
00154     status = initializeWithoutCondDB();
00155   }
00156   
00157   return status;  
00158 }
00159 
00160 //=============================================================================
00161 // Finalize
00162 //=============================================================================
00163 StatusCode MagneticFieldSvc::finalize()
00164 {
00165   StatusCode sc = StatusCode::SUCCESS;
00166   // release the used tools
00167   if ( m_DC06FieldUp   ) { sc = sc && m_toolSvc->releaseTool(m_DC06FieldUp);   }
00168   if ( m_DC06FieldDown ) { sc = sc && m_toolSvc->releaseTool(m_DC06FieldDown); }
00169   if ( m_RealFieldUp   ) { sc = sc && m_toolSvc->releaseTool(m_RealFieldUp);   }
00170   if ( m_RealFieldDown ) { sc = sc && m_toolSvc->releaseTool(m_RealFieldDown); }
00171   // base clase finalize
00172   return sc && Service::finalize();
00173 }
00174 
00175 //=============================================================================
00176 bool MagneticFieldSvc::useRealMap() const
00177 //=============================================================================
00178 {
00179   if( m_mapFileNames.size() == 4 )
00180     return true;
00181   else
00182     return false;
00183 }
00184 
00185 //=============================================================================
00186 StatusCode MagneticFieldSvc::initializeWithCondDB() 
00187 //=============================================================================
00188 {
00189   MsgStream log(msgSvc(), name());
00190 
00191   StatusCode status = service("UpdateManagerSvc",m_updMgrSvc);
00192   if ( status.isFailure() ) {
00193     log << MSG::ERROR << "Cannot find the UpdateManagerSvc" << endmsg;
00194     return status;
00195   }
00196 
00197   // Polarity and current
00198   if( m_UseSetCurrent ) {
00199     m_updMgrSvc->registerCondition( this, MagnetCondLocations::Set,
00200                                     &MagneticFieldSvc::i_updateConditions, m_currentPtr );
00201   }
00202   else {
00203     m_updMgrSvc->registerCondition( this, MagnetCondLocations::Measured,
00204                                     &MagneticFieldSvc::i_updateConditions, m_currentPtr );
00205   }
00206 
00207   // FieldMap file name(s). If not over-ridden by options, get from CondDB
00208   m_mapFromOptions = false;
00209   if( m_mapFileNames.size() != 0 ) {
00210     log << MSG::WARNING 
00211         << "Requested condDB but using manually set field map file name(s) = "
00212         << m_mapFileNames << endmsg;
00213     m_mapFromOptions = true;
00214   }
00215   else {
00216     m_updMgrSvc->registerCondition( this, MagnetCondLocations::FieldMapFilesUp,
00217                                     &MagneticFieldSvc::i_updateConditions, m_mapFilesUpPtr );
00218 
00219     m_updMgrSvc->registerCondition( this, MagnetCondLocations::FieldMapFilesDown,
00220                                     &MagneticFieldSvc::i_updateConditions, m_mapFilesDownPtr );
00221   }
00222   
00223 
00224   // Scaling factor. If not over-ridden by options, get it from CondDB
00225   m_scaleFromOptions = false;
00226   if( m_scaleFactor < 9998. ) {
00227     log << MSG::WARNING 
00228         << "Requested condDB but using manually set scale factor = "
00229         << m_scaleFactor << endmsg;
00230     m_scaleFromOptions = true;
00231   }
00232   else {
00233     m_updMgrSvc->registerCondition( this, MagnetCondLocations::ScaleUp,
00234                                     &MagneticFieldSvc::i_updateConditions, m_scaleUpPtr );
00235 
00236     m_updMgrSvc->registerCondition( this, MagnetCondLocations::ScaleDown,
00237                                     &MagneticFieldSvc::i_updateConditions, m_scaleDownPtr );
00238   }
00239   
00240   // Initialize the service using the current conditions values
00241   return m_updMgrSvc->update(this);
00242 
00243 }
00244 
00245 //=============================================================================
00246 StatusCode MagneticFieldSvc::initializeWithoutCondDB() 
00247 //=============================================================================
00248 {
00249 
00250   MsgStream log(msgSvc(), name());
00251   log << MSG::WARNING << "Not using CondDB, entirely steered by options" << endmsg;
00252   
00253   if( m_mapFileNames.size() == 0 ) {
00254     log << MSG::ERROR << "Field Map filename(s) not set" << endmsg;
00255     return StatusCode::FAILURE;
00256   }
00257   m_mapFromOptions = true;
00258 
00259   if( m_scaleFactor > 9998. ) {
00260     m_scaleFactor = 1.;
00261     log << MSG::DEBUG << "Scale factor set to default = " << m_scaleFactor << endmsg;
00262   }
00263   m_scaleFromOptions = true;
00264   
00265   // Value of polarity irrelevant when using options
00266   // Parse the file via the appropriate tool
00267   return updateTool( 1 );
00268 }
00269 
00270 //=============================================================================
00271 // QueryInterface
00272 //=============================================================================
00273 StatusCode MagneticFieldSvc::queryInterface( const InterfaceID& riid, 
00274                                              void** ppvInterface      ) 
00275 {
00276   if ( IMagneticFieldSvc::interfaceID().versionMatch(riid) ) {
00277     *ppvInterface = (IMagneticFieldSvc*)this;
00278     addRef();
00279     return StatusCode::SUCCESS;
00280   } else if ( ILHCbMagnetSvc::interfaceID().versionMatch(riid) ) {
00281     *ppvInterface = (ILHCbMagnetSvc*)this;
00282     addRef();
00283     return StatusCode::SUCCESS;
00284   }
00285   return Service::queryInterface(riid,ppvInterface);
00286 }
00287 
00288 //=============================================================================
00289 // FieldVector: find the magnetic field value at a given point in space
00290 //=============================================================================
00291 StatusCode MagneticFieldSvc::fieldVector(const Gaudi::XYZPoint&  r,
00292                                                Gaudi::XYZVector& bf ) const {
00293 
00294   if( m_useConstField ) {
00295     bf.SetXYZ( m_constFieldVector[0]*Gaudi::Units::tesla,
00296                m_constFieldVector[1]*Gaudi::Units::tesla,
00297                m_constFieldVector[2]*Gaudi::Units::tesla );
00298     return StatusCode::SUCCESS;
00299   }
00300 
00301   // Forward request to the tool
00302   m_fieldTool->fieldVector( r, bf );
00303   return StatusCode::SUCCESS;
00304   
00305 }
00306 
00307 //=============================================================================
00308 StatusCode MagneticFieldSvc::i_updateConditions() 
00309 //=============================================================================
00310 {
00311   MsgStream log(msgSvc(), name());
00312   log << MSG::DEBUG << "updateConditions called" << endmsg;
00313 
00314   int polarity;
00315   if( m_polarity != 0 ) {
00316     log << MSG::WARNING 
00317         << "Requested condDB but using manually set polarity = " << m_polarity << endmsg;
00318     polarity = m_polarity;
00319   }
00320   else
00321     polarity = m_currentPtr->param<int>("Polarity");
00322   
00323   // Update the scale factor
00324   if( !m_scaleFromOptions ) {
00325     double current = m_currentPtr->param<double>("Current");
00326     
00327     // ******* Check I have the correct convention!!
00328     std::vector<double> coeffs;
00329     if( polarity > 0 )
00330       coeffs = m_scaleUpPtr->param<std::vector<double> >("Coeffs");
00331     else
00332       coeffs = m_scaleDownPtr->param<std::vector<double> >("Coeffs");
00333   
00334     m_scaleFactor = coeffs[0] + ( coeffs[1]*(current/m_nominalCurrent) );
00335   }
00336    
00337   // Update the field map file
00338   if( !m_mapFromOptions ) {
00339     m_mapFileNames.clear();
00340     
00341     // ******* Check I have the correct convention!!
00342     std::vector<std::string> files;
00343     if( polarity > 0 )
00344       files = m_mapFilesUpPtr->param<std::vector<std::string> >("Files");
00345     else
00346       files = m_mapFilesDownPtr->param<std::vector<std::string> >("Files");
00347 
00348     for ( std::vector<std::string>::const_iterator iF = files.begin(); iF != files.end(); ++iF ) {
00349       m_mapFileNames.push_back( m_mapFilePath + *iF );
00350     }
00351   }
00352   
00353   log << MSG::DEBUG << "Field map files updated: " << m_mapFileNames << endmsg;
00354   log << MSG::DEBUG << "Scale factor updated: "    << m_scaleFactor << endmsg;
00355 
00356   // Finally update the appropriate tool
00357   return updateTool( polarity );
00358 }
00359 
00360 //=============================================================================
00361 StatusCode MagneticFieldSvc::updateTool( int polarity )
00362 //=============================================================================
00363 {
00364   // Depending on the polarity and the type of field map, update the tool
00365   MsgStream log(msgSvc(), name());
00366 
00367   if( polarity == 0 ) {
00368     polarity = 1;
00369     log << MSG::INFO << "Polarity not set, using default = 1 (UP) " << endmsg;
00370   }
00371 
00372   if(  m_mapFileNames.size() == 1 ) {
00373     // DC06 case
00374     if( polarity > 0 ) {
00375       if( 0 == m_DC06FieldUp ) {
00376         StatusCode sc = m_toolSvc->retrieveTool( "MagFieldToolDC06",
00377                                                  "MagToolDC06Up",
00378                                                  m_DC06FieldUp, this );
00379         if( sc.isFailure() ) {
00380           log << MSG::ERROR << "Could not retrieve MagToolDC06Up" << endmsg;
00381           return sc;
00382         }
00383       }
00384       m_fieldTool = m_DC06FieldUp;
00385     }
00386     else {
00387       if( 0 == m_DC06FieldDown ) {
00388         StatusCode sc = m_toolSvc->retrieveTool( "MagFieldToolDC06",
00389                                                  "MagToolDC06Down",
00390                                                  m_DC06FieldDown, this );
00391         if( sc.isFailure() ) {
00392           log << MSG::ERROR << "Could not retrieve MagToolDC06Down" << endmsg;
00393           return sc;
00394         }
00395       }
00396       m_fieldTool = m_DC06FieldDown;
00397     }
00398   }
00399   else if( m_mapFileNames.size() == 4 ) {
00400     // Real map case
00401     if( polarity > 0 ) {
00402       if( 0 == m_RealFieldUp ) {
00403         StatusCode sc = m_toolSvc->retrieveTool( "MagFieldTool",
00404                                                  "MagToolRealUp",
00405                                                  m_RealFieldUp, this );
00406         if( sc.isFailure() ) {
00407           log << MSG::ERROR << "Could not retrieve MagToolRealUp" << endmsg;
00408           return sc;
00409         }
00410       }
00411       m_fieldTool = m_RealFieldUp;
00412     }
00413     else {
00414       if( 0 == m_RealFieldDown ) {
00415         StatusCode sc = m_toolSvc->retrieveTool( "MagFieldTool",
00416                                                  "MagToolRealDown",
00417                                                  m_RealFieldDown, this );
00418         if( sc.isFailure() ) {
00419           log << MSG::ERROR << "Could not retrieve MagToolRealDown" << endmsg;
00420           return sc;
00421         }
00422       }
00423       m_fieldTool = m_RealFieldDown;
00424     }
00425   }
00426   else {
00427     log << MSG::ERROR 
00428         << "Wrong number of field map files, don't know what to do" << endmsg;
00429     return StatusCode::FAILURE;
00430   }
00431 
00432   if ( !m_fieldTool ) 
00433   {
00434     log << MSG::ERROR
00435         << "Null FieldTool pointer | polarity = " << polarity
00436         << ", # FieldMap Files = " << m_mapFileNames.size() 
00437         << endmsg;
00438     return StatusCode::FAILURE;
00439   }
00440 
00441   // Update the Tool
00442   return m_fieldTool->updateMap( m_mapFileNames, m_scaleFactor );
00443 }
| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

Generated on Mon Apr 11 20:04:54 2011 for Magnet by doxygen 1.4.7