camacmap.cpp

Go to the documentation of this file.
00001 /*
00002     This software is Copyright by the Board of Trustees of Michigan
00003     State University (c) Copyright 2005.
00004 
00005     You may use this software under the terms of the GNU public license
00006     (GPL).  The terms of this license are described at:
00007 
00008      http://www.gnu.org/licenses/gpl.txt
00009 
00010      Author:
00011              Ron Fox
00012              NSCL
00013              Michigan State University
00014              East Lansing, MI 48824-1321
00015 */
00016 
00017 static const char* Copyright= "(C) Copyright Michigan State University 2002, All rights reserved";/*
00018 ** camacmap.c:
00019 **   Contains daq interfaces to the Bit3/CBD8210 branch highway device.
00020 **   Access to the CAMAC crate is via pointer dereferences into a virtual
00021 **   address space which maps to the CAMAC space as follows:
00022 **     base + |bbb|ccc|nnnnn|aaaa|fffff|w|0
00023 **   (each letter in the set above is a bit) where:
00024 **     bbb   - Is the branch to reference
00025 **     ccc   - Is a crate within the branch (note that the VME controller
00026 **             registers live in crate 0.
00027 **     nnnnn - Is the CAMAC slot.
00028 **     aaaa  - Is the subaddress within the slot.
00029 **     fffff - Is the function code to execute in the selected module.
00030 **     w     - Is 1 for word accesses, and 0 is for longword (24 bit) access.
00031 **
00032 ** Author:
00033 **     Ron Fox
00034 **     NSCL
00035 **     Michigan State University
00036 **     East Lansing, MI 48824-1321
00037 **     (c) Copyright NSCL 1999 All rights reserved.
00038 **
00039 ** Acknowledgements:
00040 **    Natalie Kruszinska at Nikhef who wrote the Bit 3 device driver,
00041 **    Eric Kasten at NSCL who made it work and gave me code samples on which
00042 **                to base this file.
00043 */
00044 /*
00045    $Header$
00046 
00047    Change log:
00048 
00049    $Log$
00050    Revision 8.3  2006/01/05 17:30:31  ron-fox
00051    Work around some issues with rethrowing exceptions across constructors
00052    in shared objects...bouncing back and forth.  Exceptions caught by
00053    ReadoutStateMachine are now reported at that level before being rethrown.
00054 
00055    Revision 8.2  2005/06/24 11:30:38  ron-fox
00056    Bring the entire world onto the 8.2 line
00057 
00058    Revision 4.2  2004/11/16 15:24:48  ron-fox
00059    - Port to the gnu 3.x compiler set.
00060    - Integrate buid of tests.
00061    - Integrate build of docos.
00062 
00063    Revision 1.2  2004/11/16 15:23:29  ron-fox
00064    - Port -> gcc/g++ 3.x
00065    - Support integrated test building.
00066    - Support integrated doxygen docu7mentation building.
00067 
00068    Revision 1.1  2003/12/03 19:29:05  ron-fox
00069     Add generic CAMAC support to the library.
00070 
00071    Revision 3.1  2003/03/22 04:03:46  ron-fox
00072    Added SBS/Bit3 device driver.
00073 
00074    Revision 2.1  2003/02/11 16:44:58  ron-fox
00075    Retag to version 2.1 to remove the weird branch I accidently made.
00076 
00077    Revision 1.2  2003/02/05 18:06:17  ron-fox
00078    Catch up on drift between Readout and the snapshot from which we started
00079    the port to autotools.
00080 
00081    Revision 2.7  2002/12/30 18:46:57  fox
00082    Support the WIENER VC/CC32 crate controller hardware thanks to
00083    Dave Caussyn at FSU (caussyn@nucmar.physics.fsu.edu)
00084 
00085    Revision 2.6  2002/11/20 16:03:09  fox
00086    Support multiple VME crates and CAMAC Branches spread across the multiple VME
00087    crates.
00088 
00089    Revision 2.5  2002/10/22 12:37:23  fox
00090    Straighten out dates in copyright notices in files.
00091 
00092 // Revision 2.4  2002/10/10  12:54:25  fox
00093 // Remove multiple copyright strings.
00094 //
00095 // Revision 2.3  2002/10/09  11:27:46  fox
00096 // Add copyright/license stamp.
00097 //
00098 // Revision 2.2  2002/07/02  15:12:23  fox
00099 // Go to 2.xx based releases (recover from client crash too).
00100 //
00101 // Revision 2.1  2002/07/02  15:05:34  fox
00102 // Transition to 2.1 releases
00103 //
00104 // Revision 1.1  2002/07/01  17:37:01  fox
00105 // - Made camacmap.c ->camacmap.cpp
00106 // - The world use CVMEInterface:: rather than direct device access to abstract
00107 //   VME crate access.
00108 //
00109 */
00110 #include <config.h>
00111 
00112 #include <stdlib.h>
00113 #include <stdio.h>
00114 #include <string.h>
00115 #include <signal.h>
00116 #include <setjmp.h>
00117 #include <unistd.h>
00118 #include <errno.h>
00119 #include <sys/types.h>
00120 #include <sys/stat.h>
00121 #include <sys/wait.h>
00122 #include <sys/mman.h>
00123 #include <time.h>
00124 #include <sys/time.h>
00125 #include <fcntl.h>
00126 #include <ctype.h>
00127 #include <sys/ioctl.h>
00128 #include <math.h>
00129 #include <assert.h>
00130 #include <CVMEInterface.h>
00131 #include <camac.h>
00132 #include <Iostream.h>
00133 
00134 #include <CVMEInterface.h>
00135 
00136 #ifdef HAVE_STD_NAMESPACE
00137 using namespace std;
00138 #endif
00139 
00140 #define VMECRATES      16
00141 #define BRANCHESINCRATE 8 
00142 
00143 
00144 #define DEF_SIGNAL SIGUSR1
00145 #define DEF_VECTOR -1
00146 #define DEF_IRQ    2
00147 
00148 
00149 /* This stuff is all pretty obsolete I'm guessing.  - RF */
00150 
00151 #define PAGE_SIZE 4096
00152 #define SLOT_SIZE 2048
00153 #define SLOTS_PER_CRATE 25
00154 #define PAGES_PER_CRATE ((SLOTS_PER_CRATE*SLOT_SIZE)/PAGE_SIZE) 
00155 #define BRANCHES        8
00156 #define CRATES_PER_BRANCH 8
00157 
00158 
00159 static char *pCopyright = "(c) NSCL 1999, All rights reserved\n";
00160 
00161  
00162 /*===================================================================*/
00163 void*
00164 daq_OpenCamacDriver()
00165 {
00166   /*  Opens the CAMAC device.  The user can use the fd returned by
00167   **  this call to to call the other functions in this module:
00168   **  
00169   ** Returns:
00170   **     -1            - IF failure, error in errno.
00171   **    otherwise      - the file id open on the device.
00172   */
00173 
00174   return CVMEInterface::Open(CVMEInterface::A24);
00175 }
00176 
00177 
00178 /*===================================================================*/
00179 void*
00180 daq_MapCamacSpace(void* fid)
00181 {
00182   /*  Maps the entire CAMAC branch highway space and returns a pointer
00183   **  to it to the caller.  The branch highway space is assumed to consist
00184   **  of 8 branches with 8 crates all located  contiguously in VME space.
00185   **  NOTE:  It will be the responsibility of the user of this spaced to
00186   **  ensure that the branches and crates referenced actually exist.
00187   **
00188   ** Formal Parameters:
00189   **    int fid  [in]:
00190   **       File id open on the VME A24/D16 device, returned from a call to
00191   **       daq_OpenCamacDriver().
00192   ** Returns:
00193   **   Pointer to the CAMAC highway space Virtual address or NULL if
00194   **   the map failed.
00195   */
00196    void *mbuf;
00197    unsigned long base;
00198 
00199    base = (1<<23);              /* This is the entire branch base. */
00200 
00201    base = (base&(~(PAGE_SIZE-1))); /* Probably  not needed for full br map */
00202 
00203    mbuf = CVMEInterface::Map(fid, base,
00204                              (unsigned long)(BRANCHES*CRATES_PER_BRANCH* 
00205                                              PAGE_SIZE*PAGES_PER_CRATE));
00206    return(mbuf);  
00207 }
00208 
00209 /*===================================================================*/
00210 void
00211 daq_UnmapCamacSpace(void* fd, void* pSpace)
00212 {
00213   /* Unmaps the CAMAC address space mapped with daq_MapCamacSpace
00214   ** the mapping is assumed to be the entire size of the CAMAC space 
00215   ** which is BRANCHES*CRATES_PER_BRANCH contiguous crates.
00216   **
00217   ** Formal Parameters:
00218   **
00219   **   int   fd [in]:
00220   **      File descriptor open on the vme driver.
00221   **   void* pSpace [in]:
00222   **      Pointer returned from daq_MapCamacSpace.
00223   */
00224 
00225   CVMEInterface::Unmap(fd, pSpace,
00226                             (unsigned long)(BRANCHES*CRATES_PER_BRANCH* 
00227                                             PAGE_SIZE*PAGES_PER_CRATE));
00228                                         
00229 
00230 }
00231 /*===================================================================*/
00232 void
00233 daq_CloseCamacDriver(void* fid)
00234 {
00235   /*  Closes the file id open on the CAMAC device.
00236   **  
00237   **  int fid [in]:
00238   **     File id returned from the call to daq_OpenCamacDriver.
00239   */
00240 
00241   CVMEInterface::Close(fid);
00242 }
00243 
00259 static void*   vmeFds[VMECRATES];
00260        void*   pBranchBases[VMECRATES*BRANCHESINCRATE];  // static init to NULL
00261 void CESBranchAccess(int nBranch)
00262 {
00263   int nVme    = nBranch >> 3;   // Extract the VME crate and the
00264   int nB      = nBranch & 0x7;  // branch inside the crate.
00265 
00266   // Note that failures in the map are probably unrecoverable.  So we
00267   // allow the exceptions signalled to propagate back up the call stack
00268   // where hopefully smoeone has installed a last chance handler prior to exit.
00269 
00270   assert((void*)NULL == (void*)0);              // Assumption about init values of ptr array.
00271   assert(nBranch < VMECRATES*BRANCHESINCRATE);  // in range branch.
00272 
00273   //  If the pointer does not exist, then it needs to be mapped:
00274 
00275   if(pBranchBases[nBranch] == (void*)NULL) {
00276     if (vmeFds[nVme] == (void*) NULL) { // Need to open the device:
00277       vmeFds[nVme] = CVMEInterface::Open(CVMEInterface::Standard, nVme);
00278     }
00279     // Map the memory:
00280     
00281     try { 
00282 
00283       long nBase = 0x800000 + (nB <<CAMB);
00284       pBranchBases[nBranch] = CVMEInterface::Map(vmeFds[nVme], nBase,
00285                                                (1L << CAMB));
00286     }
00287     catch (...) {
00288       cerr << "CVMEInterface::Map threw... rethrowing\n";
00289       throw;
00290     }
00291   }
00292 }
00302 void WIENERBranchAccess(int nBranch)
00303 {
00304   int nVme        =  nBranch >> 3;      // 8 crates == crates / vme crate.
00305   int nController =  nBranch & 0x7;     // This is the crate #.
00306 
00307   assert ((void*) NULL == (void*)0);    // Assume the pointers init to null.
00308   assert(nBranch < VMECRATES*BRANCHESINCRATE);
00309 
00310   // Map the crate if the pointer is still NULL:
00311 
00312   if(pBranchBases[nBranch] == (void*)NULL) {
00313     if(vmeFds[nVme] == (void*)NULL) { // Need to open the device...
00314       vmeFds[nVme]  = CVMEInterface::Open(CVMEInterface::Standard, nVme);
00315     }
00316   
00317     // Map the memory for a crate...
00318     // The crates are at : 0x800000 + ((nB *  0x20) << CAMN)
00319     
00320     long nBase = 0x800000 + ((nController * 0x20) << CAMN);
00321     pBranchBases[nBranch] = CVMEInterface::Map(vmeFds[nVme], nBase,
00322                                                0x20 << CAMN);
00323   }
00324 }
00325 
00326    

Generated on Wed Sep 17 08:38:09 2008 for NSCL Device support. by  doxygen 1.5.1