00001
00002
00003
00005
00006 #include <assert.h>
00007 #include <sys/time.h>
00008 #include <sys/resource.h>
00009 #include <sys/ioctl.h>
00010 #include <sys/types.h>
00011 #include <sys/stat.h>
00012 #include <string.h>
00013 #include <sched.h>
00014 #include <unistd.h>
00015 #include <fcntl.h>
00016 #define HANDLE int
00017 #define FALSE 0
00018 #define DWORD long
00019 #define _ASSERT assert
00020 #define REALTIME_PRIORITY_CLASS 1
00021 #define GetCurrentProcess getpid
00022 #define LOBYTE(x) ((x) & 0xff)
00023 #define HIBYTE(x) ((x >> 8) & 0xff)
00024
00025 #define MIRQ1 0x21
00026 #define MIRQ2 0xA1
00027
00028 #include "time.h"
00029
00030
00031 #include "CameraIO_Linux.h"
00032 #include "ApogeeLinux.h"
00033
00034 const int NUM_POSITIONS = 6;
00035 const int NUM_STEPS_PER_FILTER = 48;
00036 const int STEP_DELAY = 10;
00037
00038 const unsigned char Steps[] = { 0x10, 0x30, 0x20, 0x60, 0x40, 0xc0, 0x80, 0x90 };
00039 const int NUM_STEPS = sizeof ( Steps );
00040
00042
00044
00045 CCameraIO::CCameraIO()
00046 {
00047 InitDefaults();
00048
00049 m_TDI = false;
00050
00051 m_Shutter = false;
00052 m_FilterPosition = 0;
00053 m_FilterStepPos = 0;
00054
00055 m_WaitingforImage = false;
00056 m_WaitingforLine = false;
00057
00058 m_WaitingforTrigger = false;
00059 m_Status = Camera_Status_Idle;
00060 m_CoolerStatus = Camera_CoolerStatus_Off;
00061
00062 m_ExposureBinX = 0;
00063 m_ExposureBinY = 0;
00064 m_ExposureStartX = 0;
00065 m_ExposureStartY = 0;
00066 m_ExposureNumX = 0;
00067 m_ExposureNumY = 0;
00068 m_ExposureColumns = 0;
00069 m_ExposureRows = 0;
00070 m_ExposureSkipC = 0;
00071 m_ExposureSkipR = 0;
00072 m_ExposureHFlush = 0;
00073 m_ExposureVFlush = 0;
00074 m_ExposureBIC = 0;
00075 m_ExposureBIR = 0;
00076 m_ExposureAIC = 0;
00077 m_ExposureRemainingLines = 0;
00078 m_ExposureAIR = 0;
00079
00080 m_RegShadow[ Reg_Command ] = 0;
00081 m_RegShadow[ Reg_Timer ] = 0;
00082 m_RegShadow[ Reg_VBinning ] = 0;
00083 m_RegShadow[ Reg_AICCounter ] = 0;
00084 m_RegShadow[ Reg_TempSetPoint ] = 0;
00085 m_RegShadow[ Reg_PixelCounter ] = 0;
00086 m_RegShadow[ Reg_LineCounter ] = 0;
00087 m_RegShadow[ Reg_BICCounter ] = 0;
00088
00089 m_FastShutterBits_Mode = 0;
00090 m_FastShutterBits_Test = 0;
00091 m_IRQMask = 0;
00092 saveIRQS = 0;
00093
00094 }
00095
00096 CCameraIO::~CCameraIO()
00097 {
00098
00099
00100 close(fileHandle);
00101 }
00102
00104
00105
00106 int GetPriorityClass ( HANDLE )
00107 {
00108 int i;
00109 i = sched_getscheduler(0);
00110 return(i);
00111 }
00112
00113 int SetPriorityClass ( HANDLE , int hPriority)
00114 {
00115 int i;
00116 sched_param p;
00117
00118 if (hPriority) {
00119 i = sched_setscheduler(0,SCHED_RR,&p);
00120 } else {
00121 i = sched_setscheduler(0,SCHED_OTHER,&p);
00122 }
00123 return(i);
00124 }
00125
00126 void Sleep (int hTime)
00127 {
00128 timespec t;
00129 t.tv_sec= 0;
00130 t.tv_nsec = hTime*1000000;
00131
00132 }
00133
00134
00135
00136 void ATLTRACE (char * )
00137 {
00138 }
00139
00140
00141 void CCameraIO::Reset()
00142 {
00143 unsigned short val = 0;
00144 Read( Reg_CommandReadback, val );
00145 m_RegShadow[ Reg_Command ] = val;
00146
00147
00148 m_RegShadow[ Reg_Command ] &= ~RegBit_FIFOCache;
00149 m_RegShadow[ Reg_Command ] &= ~RegBit_TDIMode;
00150
00151 m_RegShadow[ Reg_Command ] |= RegBit_ResetSystem;
00152 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00153
00154 m_RegShadow[ Reg_Command ] &= ~RegBit_ResetSystem;
00155 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00156
00157 m_WaitingforImage = false;
00158 m_WaitingforLine = false;
00159 m_WaitingforTrigger = false;
00160 }
00161
00162 void CCameraIO::AuxOutput( unsigned char val )
00163 {
00164
00165 m_RegShadow[ Reg_TempSetPoint ] &= ~( RegBitMask_PortControl << RegBitShift_PortControl );
00166
00167
00168 m_RegShadow[ Reg_TempSetPoint ] |= val << RegBitShift_PortControl;
00169
00170 Write( Reg_TempSetPoint, m_RegShadow[ Reg_TempSetPoint ] );
00171 }
00172
00173
00174 void CCameraIO::RegWrite( short reg, unsigned short val )
00175 {
00176 Write( reg, val );
00177
00178
00179 switch ( reg )
00180 {
00181 case Reg_Command:
00182 m_RegShadow[ Reg_Command ] = val;
00183 break;
00184 case Reg_Timer:
00185 m_RegShadow[ Reg_Timer ] = val;
00186 break;
00187 case Reg_VBinning:
00188 m_RegShadow[ Reg_VBinning ] = val;
00189 break;
00190 case Reg_AICCounter:
00191 m_RegShadow[ Reg_AICCounter ] = val;
00192 break;
00193 case Reg_TempSetPoint:
00194 m_RegShadow[ Reg_TempSetPoint ] = val;
00195 break;
00196 case Reg_PixelCounter:
00197 m_RegShadow[ Reg_PixelCounter ] = val;
00198 break;
00199 case Reg_LineCounter:
00200 m_RegShadow[ Reg_LineCounter ] = val;
00201 break;
00202 case Reg_BICCounter:
00203 m_RegShadow[ Reg_BICCounter ] = val;
00204 break;
00205 default:
00206 _ASSERT( FALSE );
00207 }
00208 }
00209
00210
00211 void CCameraIO::RegRead( short reg, unsigned short& val )
00212 {
00213 Read( reg, val );
00214 }
00215
00216 bool CCameraIO::FilterHome()
00217 {
00218 HANDLE hProcess(0);
00219 DWORD Class(0);
00220
00221 if ( m_HighPriority )
00222 {
00223 hProcess = GetCurrentProcess();
00224 Class = GetPriorityClass ( hProcess );
00225 SetPriorityClass ( hProcess, REALTIME_PRIORITY_CLASS );
00226 }
00227
00228
00229 m_FilterPosition = 0;
00230 int Safety = 0;
00231 for (int I = 0; I < NUM_POSITIONS * NUM_STEPS_PER_FILTER * 2; I++)
00232 {
00233
00234 m_FilterStepPos += 1;
00235 if (m_FilterStepPos >= NUM_STEPS) m_FilterStepPos = 0;
00236 unsigned char Step = Steps[ m_FilterStepPos ];
00237
00238 AuxOutput( Step );
00239 Sleep ( STEP_DELAY );
00240
00241
00242 unsigned short val = 0;
00243 Read( Reg_Status, val );
00244 if ( val & RegBit_GotTrigger )
00245 {
00246
00247 if (I < NUM_STEPS_PER_FILTER)
00248 {
00249 if (++Safety > NUM_STEPS_PER_FILTER * 2)
00250 {
00251
00252 if ( m_HighPriority ) SetPriorityClass ( hProcess, Class );
00253 return false;
00254 }
00255 I = 0;
00256 continue;
00257 }
00258
00259
00260 for (int J = 0; J < NUM_STEPS_PER_FILTER; J++)
00261 {
00262
00263 m_FilterStepPos += 1;
00264 if (m_FilterStepPos >= NUM_STEPS) m_FilterStepPos = 0;
00265 unsigned char Step = Steps[ m_FilterStepPos ];
00266
00267 AuxOutput( Step );
00268 Sleep ( STEP_DELAY );
00269
00270 val = 0;
00271 Read( Reg_Status, val );
00272 if ( val & RegBit_GotTrigger )
00273 {
00274 Sleep ( 10 );
00275
00276 val = 0;
00277 Read( Reg_Status, val );
00278 if ( val & RegBit_GotTrigger )
00279 {
00280
00281 if ( m_HighPriority ) SetPriorityClass ( hProcess, Class );
00282 return true;
00283 }
00284 }
00285 }
00286
00287
00288 if ( m_HighPriority ) SetPriorityClass ( hProcess, Class );
00289 return true;
00290 }
00291 }
00292
00293
00294 if ( m_HighPriority ) SetPriorityClass ( hProcess, Class );
00295 return false;
00296 }
00297
00298 void CCameraIO::FilterSet( short Slot )
00299 {
00300
00301 int Pos = Slot - m_FilterPosition;
00302 if (Pos < 0) Pos += NUM_POSITIONS;
00303
00304 HANDLE hProcess(0);
00305 DWORD Class(0);
00306
00307 if ( m_HighPriority )
00308 {
00309 hProcess = GetCurrentProcess();
00310 Class = GetPriorityClass ( hProcess );
00311 SetPriorityClass ( hProcess, REALTIME_PRIORITY_CLASS );
00312 }
00313
00314 for (int I = 0; I < Pos; I++)
00315 {
00316
00317 for (int J = 0; J < NUM_STEPS_PER_FILTER; J++)
00318 {
00319 m_FilterStepPos += 1;
00320 if (m_FilterStepPos >= NUM_STEPS) m_FilterStepPos = 0;
00321 unsigned char Step = Steps[ m_FilterStepPos ];
00322
00323 AuxOutput( Step );
00324 Sleep ( STEP_DELAY );
00325 }
00326 }
00327
00328 if ( m_HighPriority ) SetPriorityClass ( hProcess, Class );
00329
00330 m_FilterPosition = Slot;
00331 }
00332
00334
00335
00336 bool CCameraIO::Expose( double Duration, bool Light )
00337 {
00338 if ( !m_TDI && ( Duration < m_MinExposure || Duration > m_MaxExposure ) ) return false;
00339
00340
00341 if ( m_Columns < 1 || m_Columns > MAXCOLUMNS ) return false;
00342 m_ExposureColumns = m_Columns;
00343
00344 if ( m_Rows < 1 || m_Rows > MAXROWS ) return false;
00345 m_ExposureRows = m_Rows;
00346
00347 if ( m_SkipC < 0 ) return false;
00348 m_ExposureSkipC = m_SkipC;
00349
00350 if ( m_SkipR < 0 ) return false;
00351 m_ExposureSkipR = m_SkipR;
00352
00353 if ( m_HFlush < 1 || m_HFlush > MAXHBIN ) return false;
00354 m_ExposureHFlush = m_HFlush;
00355
00356 if ( m_VFlush < 1 || m_VFlush > MAXVBIN ) return false;
00357 m_ExposureVFlush = m_VFlush;
00358
00359 if ( m_BIC < 1 || m_BIC > MAXCOLUMNS ) return false;
00360 m_ExposureBIC = m_BIC;
00361
00362 if ( m_BIR < 1 || m_BIR > MAXROWS ) return false;
00363 m_ExposureBIR = m_BIR;
00364
00365
00366 if ( m_BinX < 1 || m_BinX > MAXHBIN ) return false;
00367 m_ExposureBinX = m_BinX;
00368
00369 if ( m_StartX < 0 || m_StartX >= MAXCOLUMNS ) return false;
00370 m_ExposureStartX = m_StartX;
00371
00372 if ( m_NumX < 1 || m_NumX * m_BinX > m_ImgColumns ) return false;
00373 m_ExposureNumX = m_NumX;
00374
00375
00376 unsigned short BIC = m_ExposureBIC + m_ExposureStartX;
00377 unsigned short RawPixelCount = m_ExposureNumX * m_ExposureBinX;
00378 m_ExposureAIC = m_ExposureColumns - BIC - RawPixelCount;
00379
00380 if ( m_BinY < 1 || m_BinY > MAXVBIN ) return false;
00381 m_ExposureBinY = m_BinY;
00382
00383 unsigned short VBin(0), row_offset(0);
00384
00385 if ( m_TDI )
00386 {
00387 row_offset = (unsigned short) (Duration * 1000 + 0.5);
00388 Duration = 0.0;
00389 }
00390 else
00391 {
00392 if ( m_StartY < 0 || m_StartX >= MAXROWS ) return false;
00393 m_ExposureStartY = m_StartY;
00394
00395 if ( m_NumY < 1 || m_NumY * m_BinY > m_ImgRows ) return false;
00396 m_ExposureNumY = m_NumY;
00397
00398 unsigned short BIR = m_ExposureBIR + m_ExposureStartY;
00399 if ( BIR >= MAXROWS ) return false;
00400 m_ExposureAIR = m_ExposureRows - BIR - m_ExposureNumY * m_ExposureBinY;
00401
00402 if ( m_VFlush > BIR )
00403 {
00404 VBin = BIR;
00405 m_ExposureRemainingLines = 0;
00406 }
00407 else
00408 {
00409 VBin = m_VFlush;
00410 m_ExposureRemainingLines = BIR % VBin;
00411 }
00412 row_offset = BIR - m_ExposureRemainingLines;
00413 }
00414
00415 StopFlushing();
00416 Reset();
00417
00418 LoadColumnLayout( m_ExposureAIC, BIC, (unsigned short) m_ExposureNumX + m_ExposureSkipC );
00419 LoadTimerAndBinning( Duration, (unsigned short) m_ExposureHFlush, VBin );
00420 LoadLineCounter( row_offset );
00421
00422 if ( m_TDI )
00423 {
00424
00425 m_RegShadow[ Reg_Command ] |= RegBit_TDIMode;
00426
00427
00428 m_RegShadow[ Reg_Command ] &= ~RegBit_FIFOCache;
00429
00430
00431 if ( Light )
00432 m_RegShadow[ Reg_Command ] |= RegBit_ShutterOverride;
00433 else
00434 m_RegShadow[ Reg_Command ] &= ~RegBit_ShutterOverride;
00435
00436 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00437
00438
00439 m_Shutter = Light;
00440 m_WaitingforTrigger = false;
00441 m_WaitingforLine = false;
00442 }
00443 else
00444 {
00445
00446 if ( Light )
00447 m_RegShadow[ Reg_Command ] |= RegBit_ShutterEnable;
00448 else
00449 m_RegShadow[ Reg_Command ] &= ~RegBit_ShutterEnable;
00450
00451 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00452
00453
00454 unsigned short val = 0;
00455 Read( Reg_CommandReadback, val );
00456 if ( val & RegBit_ShutterOverride )
00457 m_Shutter = true;
00458 else
00459 m_Shutter = Light;
00460
00461 if ( ( val & RegBit_TriggerEnable ) )
00462 m_WaitingforTrigger = true;
00463 else
00464 m_WaitingforTrigger = false;
00465
00466
00467 m_RegShadow[ Reg_Command ] |= RegBit_StartTimer;
00468 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00469
00470 m_RegShadow[ Reg_Command ] &= ~RegBit_StartTimer;
00471 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00472
00473 m_WaitingforImage = true;
00474 }
00475
00476 return true;
00477 }
00478
00479
00480
00481
00482
00483
00484
00485
00486
00487
00488
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498
00499
00500 bool CCameraIO::GetImage( unsigned short* pImageData, short& xSize, short& ySize )
00501 {
00502 int i;
00503 unsigned short BIC = m_ExposureBIC + m_ExposureStartX;
00504
00505
00506 m_WaitingforTrigger = false;
00507 m_WaitingforLine = false;
00508
00509 if ( m_WaitingforImage )
00510 {
00511 m_WaitingforImage = false;
00512
00514
00515 clock_t StopTime = clock() + long( m_Timeout * CLOCKS_PER_SEC );
00516 while ( true )
00517 {
00518 unsigned short val = 0;
00519 Read( Reg_Status, val );
00520 if ( ( val & RegBit_FrameDone ) != 0 ) break;
00521
00522 if ( clock() > StopTime ) return false;
00523 }
00524 }
00525
00526
00527
00529
00530 unsigned short val = 0;
00531 Read( Reg_CommandReadback, val );
00532 if ( !( val & RegBit_ShutterOverride ) ) m_Shutter = false;
00533
00534 StopFlushing();
00535 LoadColumnLayout( m_ExposureAIC, BIC, (unsigned short) m_ExposureNumX + m_ExposureSkipC );
00536
00537 if ( m_ExposureRemainingLines > 0 )
00538 {
00539 LoadTimerAndBinning( 0.0, m_ExposureHFlush, m_ExposureRemainingLines );
00540
00542
00543 m_RegShadow[ Reg_Command ] |= RegBit_StartNextLine;
00544 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00545
00546 m_RegShadow[ Reg_Command ] &= ~RegBit_StartNextLine;
00547 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00549
00551
00552 clock_t StopTime = clock() + CLOCKS_PER_SEC;
00553 while ( true )
00554 {
00555 unsigned short val = 0;
00556 Read( Reg_Status, val );
00557 if ( ( val & RegBit_LineDone ) != 0 ) break;
00558
00559 if ( clock() > StopTime )
00560 {
00561 Flush();
00562 return false;
00563 }
00564 }
00565 }
00566
00567 LoadTimerAndBinning( 0.0, m_ExposureBinX, m_ExposureBinY );
00568
00569 bool ret = false;
00570
00571
00572 if ( pImageData != NULL )
00573 {
00574 HANDLE hProcess(0);
00575 DWORD Class(0);
00576
00577 if ( m_HighPriority )
00578 {
00579 hProcess = GetCurrentProcess();
00580 Class = GetPriorityClass ( hProcess );
00581 SetPriorityClass ( hProcess, REALTIME_PRIORITY_CLASS );
00582 }
00583
00584 m_RegShadow[ Reg_Command ] |= RegBit_FIFOCache;
00585 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00586
00587 long XPixels = long( m_ExposureNumX );
00588 long SkipPixels = long( m_ExposureSkipC );
00589 for (i = 0; i < m_ExposureSkipR; i++)
00590 {
00591 if ( ReadLine( SkipPixels, XPixels, pImageData ) ) break;
00592 }
00593
00594 if ( i == m_ExposureSkipR )
00595 {
00596 long YPixels = long( m_ExposureNumY );
00597 unsigned short* pLineBuffer = pImageData;
00598 for (i = 0; i < YPixels; i++)
00599 {
00600 if ( ReadLine( SkipPixels, XPixels, pLineBuffer ) ) break;
00601 pLineBuffer += XPixels;
00602 }
00603
00604 if ( i == YPixels ) ret = true;
00605 }
00606
00607 m_RegShadow[ Reg_Command ] &= ~RegBit_FIFOCache;
00608 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00609
00610
00611 if ( m_HighPriority ) SetPriorityClass ( hProcess, Class );
00612 }
00613
00614
00615
00616 if ( ret )
00617 {
00618 Flush( m_ExposureAIR );
00619
00620 xSize = m_ExposureNumX;
00621 ySize = m_ExposureNumY;
00622
00623 if ( m_DataBits == 16 )
00624 {
00625 unsigned short *Ptr = pImageData;
00626 short *Ptr2 = (short *) pImageData;
00627 long Size = m_ExposureNumX * m_ExposureNumY;
00628 for (i = 0; i < Size; i++)
00629 {
00630 *Ptr++ = (unsigned short) *Ptr2++ + 32768 ;
00631 }
00632 }
00633
00634 }
00635 else
00636 {
00637 xSize = 0;
00638 ySize = 0;
00639 }
00640
00641 Flush();
00642
00643 return ret;
00644 }
00645
00647
00648
00649 bool CCameraIO::DigitizeLine()
00650 {
00652
00653
00654 StopFlushing();
00655
00656 unsigned short BIC = m_ExposureBIC + m_ExposureStartX;
00657 LoadColumnLayout( m_ExposureAIC, BIC, (unsigned short) m_ExposureNumX + m_ExposureSkipC );
00658 LoadTimerAndBinning( 0.0, m_ExposureBinX, m_ExposureBinY );
00659
00660
00661 m_RegShadow[ Reg_Command ] &= ~RegBit_FIFOCache;
00663
00665
00666 m_RegShadow[ Reg_Command ] |= RegBit_StartNextLine;
00667 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00668
00669 m_RegShadow[ Reg_Command ] &= ~RegBit_StartNextLine;
00670 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00672
00673 m_WaitingforLine = true;
00674 return true;
00675 }
00676
00677 bool CCameraIO::GetLine( unsigned short* pLineData, short& xSize )
00678 {
00679 int i;
00680
00681 if ( m_WaitingforLine )
00682 {
00683 m_WaitingforLine = false;
00684
00686
00687 clock_t StopTime = clock() + CLOCKS_PER_SEC;
00688 while ( true )
00689 {
00690 unsigned short val = 0;
00691 Read( Reg_Status, val );
00692 if ( ( val & RegBit_LineDone ) != 0 ) break;
00693
00694 if ( clock() > StopTime )
00695 {
00696 Flush();
00697 return false;
00698 }
00699 }
00700 }
00701
00702 bool ret = false;
00703
00704
00705
00706
00707 if ( pLineData != NULL )
00708 {
00709 HANDLE hProcess(0);
00710 DWORD Class(0);
00711
00712 if ( m_HighPriority )
00713 {
00714 hProcess = GetCurrentProcess();
00715 Class = GetPriorityClass ( hProcess );
00716 SetPriorityClass ( hProcess, REALTIME_PRIORITY_CLASS );
00717 }
00718
00719 long XPixels = long( m_ExposureNumX );
00720 long SkipPixels = long( m_ExposureSkipC );
00721
00722 if ( ReadLine( SkipPixels, XPixels, pLineData ) )
00723 {
00724 xSize = 0;
00725 ret = false;
00726 }
00727 else
00728 {
00729 xSize = m_ExposureNumX;
00730
00731 if ( m_DataBits == 16 )
00732 {
00733 unsigned short *Ptr = pLineData;
00734 short *Ptr2 = (short *) pLineData;
00735 long Size = m_ExposureNumX;
00736 for (i = 0; i < Size; i++)
00737 {
00738 *Ptr++ = (unsigned short) *Ptr2++ + 32768 ;
00739 }
00740 }
00741
00742 ret = true;
00743 }
00744
00745
00746 if ( m_HighPriority ) SetPriorityClass ( hProcess, Class );
00747 }
00748
00749
00750 return ret;
00751 }
00752
00754
00755
00756 bool CCameraIO::Snap( double Duration, bool Light, unsigned short* pImageData, short& xSize, short& ySize )
00757 {
00758
00759
00760
00761 bool ret = Expose( Duration, Light );
00762 if ( !ret ) return false;
00763
00764 if ( m_WaitingforTrigger )
00765 {
00766 Camera_Status stat;
00767 while ( true )
00768 {
00769 stat = read_Status();
00770 if ( stat == Camera_Status_Exposing ) break;
00771 Sleep( 220 );
00772 }
00773 m_WaitingforTrigger = false;
00774 }
00775
00776
00777
00778 clock_t StopTime = clock() + long( ( 1.2 * Duration + m_Timeout ) * CLOCKS_PER_SEC );
00779 while ( true )
00780 {
00781 Camera_Status stat = read_Status();
00782 if ( stat == Camera_Status_ImageReady ) break;
00783
00784 if ( clock() > StopTime ) return false;
00785 Sleep( 220 );
00786 }
00787
00788 return GetImage( pImageData, xSize, ySize );
00789 }
00790
00792
00793
00794 Camera_Status CCameraIO::read_Status()
00795 {
00796 unsigned short val = 0;
00797 Read( Reg_Status, val );
00798
00799 if ( val & RegBit_Exposing )
00800 {
00801 ATLTRACE( "Exposing\r\n" );
00802 m_WaitingforTrigger = false;
00803 m_Status = Camera_Status_Exposing;
00804 }
00805
00806 else if ( m_WaitingforTrigger )
00807 m_Status = Camera_Status_Waiting;
00808
00809 else if ( m_WaitingforImage && ( val & RegBit_FrameDone ) )
00810 {
00811 ATLTRACE( "ImageReady\r\n" );
00812 m_WaitingforImage = false;
00813 m_Status = Camera_Status_ImageReady;
00814 }
00815
00816 else if ( m_WaitingforLine && ( val & RegBit_LineDone ) )
00817 {
00818 ATLTRACE( "LineReady\r\n" );
00819 m_WaitingforLine = false;
00820 m_Status = Camera_Status_LineReady;
00821 }
00822 else if ( m_WaitingforImage || m_WaitingforLine )
00823 {
00824 ATLTRACE( "Flushing\r\n" );
00825 m_Status = Camera_Status_Flushing;
00826 }
00827 else
00828 m_Status = Camera_Status_Idle;
00829
00830 return m_Status;
00831 }
00832
00833 bool CCameraIO::read_Present()
00834 {
00835
00836
00837
00838
00839
00840
00841
00842
00843
00844
00845
00846
00847
00848
00849
00850
00851
00852 unsigned short val = 0;
00853 Read( Reg_CommandReadback, val );
00854 m_RegShadow[ Reg_Command ] = val;
00855
00856 bool TriggerEnabled = ( val & RegBit_TriggerEnable ) != 0;
00857
00858 m_RegShadow[ Reg_Command ] &= ~RegBit_TriggerEnable;
00859 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00860
00861 Read( Reg_CommandReadback, val );
00862 if ( val & RegBit_TriggerEnable ) return false;
00863
00864 m_RegShadow[ Reg_Command ] |= RegBit_TriggerEnable;
00865 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00866
00867 Read( Reg_CommandReadback, val );
00868 if ( !(val & RegBit_TriggerEnable) ) return false;
00869
00870 m_RegShadow[ Reg_Command ] &= ~RegBit_TriggerEnable;
00871 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00872
00873 Read( Reg_CommandReadback, val );
00874 if ( val & RegBit_TriggerEnable ) return false;
00875
00876 if ( TriggerEnabled )
00877 {
00878 m_RegShadow[ Reg_Command ] |= RegBit_TriggerEnable;
00879 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00880 }
00881 return true;
00882 }
00883
00884 bool CCameraIO::read_Shutter()
00885 {
00886 unsigned short regval = 0;
00887 Read( Reg_Status, regval );
00888 if ( !( regval & RegBit_Exposing ) )
00889 {
00890
00891 regval = 0;
00892 Read( Reg_CommandReadback, regval );
00893 if ( !( regval & RegBit_ShutterOverride ) )
00894
00895 m_Shutter = false;
00896 }
00897
00898 return m_Shutter;
00899 }
00900
00901 bool CCameraIO::read_ForceShutterOpen()
00902 {
00903 unsigned short val = 0;
00904 Read( Reg_CommandReadback, val );
00905 return ( ( val & RegBit_ShutterOverride ) != 0 );
00906 }
00907
00908 void CCameraIO::write_ForceShutterOpen( bool val )
00909 {
00910 if ( val )
00911 {
00912 m_RegShadow[ Reg_Command ] |= RegBit_ShutterOverride;
00913 m_Shutter = true;
00914 }
00915 else
00916 {
00917 m_RegShadow[ Reg_Command ] &= ~RegBit_ShutterOverride;
00918
00919 unsigned short regval = 0;
00920 Read( Reg_Status, regval );
00921 if ( ( regval & RegBit_Exposing ) )
00922 {
00923
00924
00925
00926
00927
00928
00929 regval = 0;
00930 Read( Reg_CommandReadback, regval );
00931 if ( !( regval & RegBit_ShutterEnable ) ) m_Shutter = false;
00932 }
00933 else
00934 {
00935
00936 m_Shutter = false;
00937 }
00938 }
00939 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00940 }
00941
00942
00943
00944 bool CCameraIO::read_LongCable()
00945 {
00946 unsigned short val = 0;
00947 Read( Reg_CommandReadback, val );
00948 return ( ( val & RegBit_CableLength ) != 0 );
00949 }
00950
00951 void CCameraIO::write_Shutter( bool val )
00952 {
00953 if ( val )
00954 m_RegShadow[ Reg_Command ] |= RegBit_ShutterEnable;
00955 else
00956 m_RegShadow[ Reg_Command ] &= ~RegBit_ShutterEnable;
00957
00958 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00959 }
00960
00961 void CCameraIO::write_LongCable( bool val )
00962 {
00963 if ( val )
00964 m_RegShadow[ Reg_Command ] |= RegBit_CableLength;
00965 else
00966 m_RegShadow[ Reg_Command ] &= ~RegBit_CableLength;
00967
00968 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
00969 }
00970
00971
00972 short CCameraIO::read_Mode()
00973 {
00974 return ( ( m_RegShadow[ Reg_LineCounter ] >> RegBitShift_Mode ) & RegBitMask_Mode );
00975 }
00976
00977 void CCameraIO::write_Mode( short val )
00978 {
00979
00980 m_RegShadow[ Reg_LineCounter ] &= ~( RegBitMask_Mode << RegBitShift_Mode );
00981
00982
00983 m_RegShadow[ Reg_LineCounter ] |= ( (unsigned short) val & RegBitMask_Mode ) << RegBitShift_Mode;
00984
00985 Write( Reg_LineCounter, m_RegShadow[ Reg_LineCounter ] );
00986 }
00987
00988 short CCameraIO::read_TestBits()
00989 {
00990 return ( ( m_RegShadow[ Reg_BICCounter ] >> RegBitShift_Test ) & RegBitMask_Test );
00991 }
00992
00993 void CCameraIO::write_TestBits( short val )
00994 {
00995
00996 m_RegShadow[ Reg_BICCounter ] &= ~( RegBitMask_Test << RegBitShift_Test );
00997
00998
00999 m_RegShadow[ Reg_BICCounter ] |= ( (unsigned short) val & RegBitMask_Test ) << RegBitShift_Test;
01000
01001 Write( Reg_BICCounter, m_RegShadow[ Reg_BICCounter ] );
01002 }
01003
01004
01005 short CCameraIO::read_Test2Bits()
01006 {
01007 return ( ( m_RegShadow[ Reg_AICCounter ] >> RegBitShift_Test2 ) & RegBitMask_Test2 );
01008 }
01009
01010 void CCameraIO::write_Test2Bits( short val )
01011 {
01012
01013 m_RegShadow[ Reg_AICCounter ] &= ~( RegBitMask_Test2 << RegBitShift_Test2 );
01014
01015
01016 m_RegShadow[ Reg_AICCounter ] |= ( (unsigned short) val & RegBitMask_Test2 ) << RegBitShift_Test2;
01017
01018 Write( Reg_AICCounter, m_RegShadow[ Reg_AICCounter ] );
01019 }
01020
01021 bool CCameraIO::read_FastReadout()
01022 {
01023 unsigned short val = 0;
01024 Read( Reg_CommandReadback , val );
01025 return ( ( val & RegBit_Focus ) != 0 );
01026 }
01027
01028 void CCameraIO::write_FastReadout( bool val )
01029 {
01030 if ( val )
01031 m_RegShadow[ Reg_Command ] |= RegBit_Focus;
01032 else
01033 m_RegShadow[ Reg_Command ] &= ~RegBit_Focus;
01034
01035 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01036 }
01037
01038 bool CCameraIO::read_UseTrigger()
01039 {
01040 unsigned short val = 0;
01041 Read( Reg_CommandReadback , val );
01042 return ( ( val & RegBit_TriggerEnable ) != 0 );
01043 }
01044
01045 void CCameraIO::write_UseTrigger( bool val )
01046 {
01047 if ( val )
01048 m_RegShadow[ Reg_Command ] |= RegBit_TriggerEnable;
01049 else
01050 m_RegShadow[ Reg_Command ] &= ~RegBit_TriggerEnable;
01051
01052 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01053 }
01054
01056
01057
01058 double CCameraIO::read_CoolerSetPoint()
01059 {
01060
01061 short DACunits = short( ( m_RegShadow[ Reg_TempSetPoint ] >> RegBitShift_TempSetPoint ) & RegBitMask_TempSetPoint );
01062 return ( DACunits - m_TempCalibration ) / m_TempScale;
01063 }
01064
01065 void CCameraIO::write_CoolerSetPoint( double val )
01066 {
01067
01068 m_RegShadow[ Reg_TempSetPoint ] &= ~( RegBitMask_TempSetPoint << RegBitShift_TempSetPoint );
01069
01070
01071 unsigned short DACunits = (unsigned )( m_TempScale * val ) + m_TempCalibration ;
01072
01073
01074 m_RegShadow[ Reg_TempSetPoint ] |= ( DACunits & RegBitMask_TempSetPoint ) << RegBitShift_TempSetPoint;
01075
01076 Write( Reg_TempSetPoint, m_RegShadow[ Reg_TempSetPoint ] );
01077 }
01078
01079 Camera_CoolerStatus CCameraIO::read_CoolerStatus()
01080 {
01081 unsigned short val = 0;
01082 Read( Reg_CommandReadback, val );
01083
01084 if ( val & RegBit_CoolerEnable )
01085 {
01086 unsigned short val2 = 0;
01087 Read( Reg_Status, val2 );
01088
01089 if ( val & RegBit_CoolerShutdown )
01090 {
01091 if ( val2 & RegBit_ShutdownComplete )
01092 m_CoolerStatus = Camera_CoolerStatus_AtAmbient;
01093 else
01094 m_CoolerStatus = Camera_CoolerStatus_RampingToAmbient;
01095 }
01096 else
01097 {
01098 if ( val2 & RegBit_TempAtMax )
01099 m_CoolerStatus = Camera_CoolerStatus_AtMax;
01100 else if ( val2 & RegBit_TempAtMin )
01101 m_CoolerStatus = Camera_CoolerStatus_AtMin;
01102 else if ( val2 & RegBit_TempAtSetPoint )
01103 m_CoolerStatus = Camera_CoolerStatus_AtSetPoint;
01104
01105 else if ( m_CoolerStatus == Camera_CoolerStatus_AtSetPoint )
01106 m_CoolerStatus = Camera_CoolerStatus_Correcting;
01107 else
01108 m_CoolerStatus = Camera_CoolerStatus_RampingToSetPoint;
01109 }
01110 }
01111 else
01112 m_CoolerStatus = Camera_CoolerStatus_Off;
01113
01114 return m_CoolerStatus;
01115 }
01116
01117 Camera_CoolerMode CCameraIO::read_CoolerMode()
01118 {
01119 unsigned short val = 0;
01120 Read( Reg_CommandReadback, val );
01121
01122 if ( val & RegBit_CoolerShutdown )
01123 return Camera_CoolerMode_Shutdown;
01124 else if ( val & RegBit_CoolerEnable )
01125 return Camera_CoolerMode_On;
01126 else
01127 return Camera_CoolerMode_Off;
01128 }
01129
01130 void CCameraIO::write_CoolerMode( Camera_CoolerMode val )
01131 {
01132 switch ( val )
01133 {
01134 case Camera_CoolerMode_Off:
01135 m_RegShadow[ Reg_Command ] &= ~( RegBit_CoolerEnable );
01136 m_RegShadow[ Reg_Command ] &= ~( RegBit_CoolerShutdown );
01137 break;
01138 case Camera_CoolerMode_On:
01139 m_RegShadow[ Reg_Command ] |= RegBit_CoolerEnable;
01140 break;
01141 case Camera_CoolerMode_Shutdown:
01142 m_RegShadow[ Reg_Command ] |= RegBit_CoolerShutdown;
01143 break;
01144 default:
01145 return;
01146 }
01147
01148 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01149 }
01150
01151 double CCameraIO::read_Temperature()
01152 {
01153 if ( m_TempScale == 0.0 )
01154 return 0.0;
01155 else
01156 {
01157 unsigned short val = 0;
01158 Read( Reg_TempData, val );
01159
01160 short DACunits = short( ( val >> RegBitShift_TempData ) & RegBitMask_TempData );
01161
01162 return ( DACunits - m_TempCalibration ) / m_TempScale;
01163 }
01164 }
01165
01166
01167 void CCameraIO::LoadLineCounter( unsigned short rows )
01168 {
01170
01171
01172 m_RegShadow[ Reg_LineCounter ] &= ~( RegBitMask_LineCounter << RegBitShift_LineCounter );
01173
01174 m_RegShadow[ Reg_LineCounter ] |= ( rows & RegBitMask_LineCounter ) << RegBitShift_LineCounter;
01175
01176 Write( Reg_LineCounter, m_RegShadow[ Reg_LineCounter ] );
01178 }
01179
01180
01181 void CCameraIO::LoadColumnLayout( unsigned short aic, unsigned short bic, unsigned short pixels )
01182 {
01184
01185
01186 m_RegShadow[ Reg_AICCounter ] &= ~( RegBitMask_AICCounter << RegBitShift_AICCounter );
01187
01188 m_RegShadow[ Reg_AICCounter ] |= ( aic & RegBitMask_AICCounter ) << RegBitShift_AICCounter;
01189
01190 Write( Reg_AICCounter, m_RegShadow[ Reg_AICCounter ] );
01192
01194
01195
01196 m_RegShadow[ Reg_BICCounter ] &= ~( RegBitMask_BICCounter << RegBitShift_BICCounter );
01197
01198 m_RegShadow[ Reg_BICCounter ] |= ( bic & RegBitMask_BICCounter ) << RegBitShift_BICCounter;
01199
01200 Write( Reg_BICCounter, m_RegShadow[ Reg_BICCounter ] );
01202
01204
01205
01206 m_RegShadow[ Reg_PixelCounter ] &= ~( RegBitMask_PixelCounter << RegBitShift_PixelCounter );
01207
01208 m_RegShadow[ Reg_PixelCounter ] |= ( pixels & RegBitMask_PixelCounter ) << RegBitShift_PixelCounter;
01209
01210 Write( Reg_PixelCounter, m_RegShadow[ Reg_PixelCounter ] );
01212 }
01213
01214
01215
01216
01217
01218 void CCameraIO::LoadTimerAndBinning( double Duration, unsigned short HBin, unsigned short VBin )
01219 {
01221
01222
01223 m_RegShadow[ Reg_PixelCounter ] &= ~( RegBitMask_HBinning << RegBitShift_HBinning );
01224
01225 m_RegShadow[ Reg_PixelCounter ] |= ( ( HBin - 1 ) & RegBitMask_HBinning ) << RegBitShift_HBinning;
01226
01227 Write( Reg_PixelCounter, m_RegShadow[ Reg_PixelCounter ] );
01229
01231
01232 if ( Duration > 0.0 )
01233 {
01234 if ( Duration > m_MaxExposure ) Duration = m_MaxExposure;
01235
01236 long valTimer;
01237 if ( m_FastShutter && Duration <= 1048.575 )
01238 {
01239 valTimer = long( ( Duration * 1000 ) + 0.5 );
01240 m_RegShadow[ Reg_LineCounter ] |= ( m_FastShutterBits_Mode & RegBitMask_Mode ) << RegBitShift_Mode;
01241 m_RegShadow[ Reg_BICCounter ] |= ( m_FastShutterBits_Test & RegBitMask_Test ) << RegBitShift_Test;
01242 }
01243 else
01244 {
01245 valTimer = long( ( Duration * 100 ) + 0.5 );
01246 if ( m_FastShutter )
01247 {
01248 m_RegShadow[ Reg_LineCounter ] &= ~( m_FastShutterBits_Mode & RegBitMask_Mode ) << RegBitShift_Mode;
01249 m_RegShadow[ Reg_BICCounter ] &= ~( m_FastShutterBits_Test & RegBitMask_Test ) << RegBitShift_Test;
01250 }
01251 }
01252
01253 if ( m_FastShutter )
01254 {
01255 Write( Reg_LineCounter, m_RegShadow[ Reg_LineCounter ] );
01256 Write( Reg_BICCounter, m_RegShadow[ Reg_BICCounter ] );
01257 }
01258
01259 if ( valTimer <= 0 ) valTimer = 1;
01260
01261 unsigned short valTimerLow = (unsigned short) (valTimer & 0x0000FFFF);
01262 unsigned short valTimerHigh = (unsigned short) (valTimer >> 16);
01263
01264
01265 m_RegShadow[ Reg_Command ] |= RegBit_TimerLoad;
01266 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01267
01268
01269 m_RegShadow[ Reg_Timer ] = 0;
01270
01271 m_RegShadow[ Reg_Timer ] |= ( valTimerLow & RegBitMask_Timer )<< RegBitShift_Timer;
01272 Write( Reg_Timer, m_RegShadow[ Reg_Timer ] );
01273
01274
01275 m_RegShadow[ Reg_VBinning ] = 0;
01276
01277
01278 m_RegShadow[ Reg_VBinning ] |= ( VBin & RegBitMask_VBinning ) << RegBitShift_VBinning;
01279 m_RegShadow[ Reg_VBinning ] |= ( valTimerHigh & RegBitMask_Timer2 ) << RegBitShift_Timer2;
01280 Write( Reg_VBinning, m_RegShadow[ Reg_VBinning ] );
01281
01282
01283 m_RegShadow[ Reg_Command ] &= ~RegBit_TimerLoad;
01284 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01286 }
01287 else
01288 {
01289
01290 m_RegShadow[ Reg_VBinning ] &= ~( RegBitMask_VBinning << RegBitShift_VBinning );
01291
01292
01293 m_RegShadow[ Reg_VBinning ] |= ( VBin & RegBitMask_VBinning ) << RegBitShift_VBinning;
01294 Write( Reg_VBinning, m_RegShadow[ Reg_VBinning ] );
01295 }
01296
01297 }
01298
01299
01300 void CCameraIO::Flush( short Rows )
01301 {
01302 if ( Rows == 0 ) return;
01303
01304 unsigned short AIC = (unsigned short) ( m_Columns - m_BIC - m_ImgColumns );
01305 unsigned short Pixels = (unsigned short) ( m_ImgColumns / m_HFlush );
01306 if ( m_ImgColumns % m_HFlush > 0 ) Pixels++;
01307 LoadColumnLayout( AIC, (unsigned short) m_BIC, Pixels );
01308
01309 LoadTimerAndBinning( 0.0, m_HFlush, m_VFlush );
01310
01311 if ( Rows > 0 )
01312 {
01313 LoadLineCounter( (unsigned short) Rows );
01314 StartFlushing();
01315
01317
01318 clock_t StopTime = clock() + long( m_Timeout * CLOCKS_PER_SEC );
01319 while ( true )
01320 {
01321 unsigned short val = 0;
01322 Read( Reg_Status, val );
01323 if ( ( val & RegBit_FrameDone ) != 0 ) break;
01324
01325 if ( clock() > StopTime ) break;
01326 }
01327 }
01328 else
01329 {
01330 LoadLineCounter( (unsigned short) m_ImgRows );
01331 StartFlushing();
01332 }
01333 }
01334
01335 void CCameraIO::StartFlushing()
01336 {
01338
01339 m_RegShadow[ Reg_Command ] |= RegBit_StartFlushing;
01340 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01341
01342 m_RegShadow[ Reg_Command ] &= ~RegBit_StartFlushing;
01343 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01345 }
01346
01347 void CCameraIO::StopFlushing()
01348 {
01350
01351 m_RegShadow[ Reg_Command ] |= RegBit_StopFlushing;
01352 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01353
01354 m_RegShadow[ Reg_Command ] &= ~RegBit_StopFlushing;
01355 Write( Reg_Command, m_RegShadow[ Reg_Command ] );
01357 }
01358
01359
01360
01361
01362