#include <stdio.h>#include "stg2.h"#include "extintf.h"#include "rcs_prnt.hh"Include dependency graph for stg2.c:

Go to the source code of this file.
Defines | |
| #define | __attribute__(x) |
| #define | STG_MAX_AXIS 4 |
| #define | _outp(port, val) outb(val,port) |
| #define | outp(port, val) outb(val,port) |
| #define | _inp(port) inb(port) |
| #define | inp(port) inb(port) |
| #define | _inpw(port) inw(port) |
| #define | _outpw(port, val) outw(val,port) |
| #define | fOutP(port, val) _outp(port,val) |
| #define | fOutPW(port, val) _outpw(port, val) |
| #define | fInP(port) _inp(port) |
| #define | fInPW(port) _inpw(port) |
| #define | STG_INIT_WAIT 1000 |
| #define | STG_ADC_WAIT_USEC 20 |
| #define | HOME_0 0x00000001 |
| #define | MIN_LIM_0 0x00000002 |
| #define | MAX_LIM_0 0x00000004 |
| #define | FAULT_0 0x00000008 |
| #define | HOME_1 0x00000010 |
| #define | MIN_LIM_1 0x00000020 |
| #define | MAX_LIM_1 0x00000040 |
| #define | FAULT_1 0x00000080 |
| #define | HOME_2 0x00000100 |
| #define | MIN_LIM_2 0x00000200 |
| #define | MAX_LIM_2 0x00000400 |
| #define | FAULT_2 0x00000800 |
| #define | HOME_3 0x00001000 |
| #define | MIN_LIM_3 0x00002000 |
| #define | MAX_LIM_3 0x00004000 |
| #define | FAULT_3 0x00008000 |
Functions | |
| char | __attribute__ ((unused)) ident[]="$Id |
| unsigned char | inb (unsigned int port) |
| void | outb (unsigned char byte, unsigned int port) |
| unsigned short | inw (unsigned int port) |
| void | outw (unsigned short word, unsigned int port) |
| void | ServoToGoConstructor (STG_STRUCT *stg, unsigned short wRequestedIrq) |
| void | ServoToGoDestructor (STG_STRUCT *stg) |
| void | SetIrq (STG_STRUCT *stg, unsigned short wRequestedIrq) |
| unsigned short | BaseFind (STG_STRUCT *stg) |
| unsigned short | BrdtstOK (STG_STRUCT *stg, unsigned short BaseAddress) |
| void | Initialize (STG_STRUCT *stg, unsigned short wRequestedIrq) |
| void | StartADC (STG_STRUCT *stg, unsigned short wAxis) |
| short | SpinReadADC (STG_STRUCT *stg, unsigned short wAxis) |
| long | ReadADC (STG_STRUCT *stg, unsigned short wAxis, short *counts) |
| void | EncoderInit (STG_STRUCT *stg) |
| void | SelectInterruptPeriod (STG_STRUCT *stg, long lPeriodSelect) |
| unsigned short | BaseAddress (STG_STRUCT *stg) |
| void | RawDAC (STG_STRUCT *stg, unsigned short nAxis, long lCounts) |
| void | EncReadAll (STG_STRUCT *stg, LONGBYTE *lbEnc) |
| void | ResetIndexLatch (STG_STRUCT *stg) |
| void | ResetIndexLatches (STG_STRUCT *stg, unsigned char byLatchBits) |
| void | SelectIndexAxis (STG_STRUCT *stg, unsigned char byAxis, unsigned char byPol) |
| void | SelectIndexOrExtLatch (STG_STRUCT *stg, unsigned char bySelectBits) |
| void | EnableCounterLatchOnIndexOrExt (STG_STRUCT *stg, unsigned char bySelectBits) |
| unsigned char | CurrentIRR (STG_STRUCT *stg) |
| unsigned short | IndexPulseLatch (STG_STRUCT *stg) |
| unsigned char | GetIndexLatches (STG_STRUCT *stg) |
| unsigned long | RawDI (STG_STRUCT *stg) |
| void | RawDO (STG_STRUCT *stg, unsigned long lOutBits) |
| void | RawDOPort (STG_STRUCT *stg, unsigned char byBitNumber, unsigned char bySet0or1, unsigned short nPort) |
| short | PortBits2Index (short nPort) |
| void | DioDirection (STG_STRUCT *stg, const unsigned short nSwDir) |
| void | SetDDir (STG_STRUCT *stg, unsigned short nSwDir) |
| void | MotSim (STG_STRUCT *stg) |
| void | AutoZeroAdc (STG_STRUCT *stg) |
| void | DontAutoZeroAdc (STG_STRUCT *stg) |
| void | CalADC (STG_STRUCT *stg) |
| void | SetEncoderCounts (STG_STRUCT *stg, unsigned short nAxis, long lCounts) |
| void | EncoderLatch (STG_STRUCT *stg) |
| void | EncoderResetAddr (STG_STRUCT *stg) |
| unsigned char | GetSELDI (STG_STRUCT *stg) |
| unsigned char | GetIDLEN (STG_STRUCT *stg) |
| unsigned char | GetCNTRL0 (STG_STRUCT *stg) |
| unsigned char | GetCNTRL1 (STG_STRUCT *stg) |
| void | ResetWatchdogLatch (STG_STRUCT *stg) |
| unsigned char | GetBRDTST (STG_STRUCT *stg) |
| unsigned short | GetBoardPresence (STG_STRUCT *stg) |
| unsigned short | GetAxes (STG_STRUCT *stg) |
| unsigned short | GetIrq (STG_STRUCT *stg) |
| unsigned short | GetAddr (STG_STRUCT *stg) |
| unsigned short | GetModel (STG_STRUCT *stg) |
| short | IndexPulse (STG_STRUCT *stg) |
| void | StopTimer (STG_STRUCT *stg) |
| void | Timer2Delay (STG_STRUCT *stg, unsigned short counts) |
| void | StartTimer2TerminalCount (STG_STRUCT *stg, unsigned short count) |
| void | StartTimer2RTI (STG_STRUCT *stg, unsigned short count) |
| unsigned short | ReadTimer2TerminalCount (STG_STRUCT *stg) |
| short | PollTimer2 (STG_STRUCT *stg) |
| void | MaskTimer2Interrupt (STG_STRUCT *stg) |
| void | UnMaskTimer2Interrupt (STG_STRUCT *stg) |
| void | StartInterrupts (STG_STRUCT *stg) |
| void | StopInterrupts (STG_STRUCT *stg) |
| int | stgMotInit (const char *stuff) |
| int | stgMotQuit (void) |
| int | stgAdcNum (void) |
| int | stgAdcStart (int adc) |
| void | stgAdcWait (void) |
| int | stgAdcRead (int adc, double *volts) |
| int | stgDacNum (void) |
| int | stgDacWrite (int dac, double volts) |
| int | stgDacWriteAll (int max, double *volts) |
| unsigned int | stgEncoderIndexModel (void) |
| int | stgEncoderSetIndexModel (unsigned int model) |
| int | stgEncoderNum (void) |
| int | stgEncoderRead (int encoder, double *counts) |
| int | stgEncoderReadAll (int max, double *counts) |
| int | stgEncoderResetIndex (int encoder) |
| int | stgEncoderReadLatch (int encoder, int *flag) |
| int | stgEncoderReadLevel (int encoder, int *flag) |
| int | stgMaxLimitSwitchRead (int axis, int *flag) |
| int | stgMinLimitSwitchRead (int axis, int *flag) |
| int | stgHomeSwitchRead (int axis, int *flag) |
| int | stgAmpEnable (int axis, int enable) |
| int | stgAmpFault (int axis, int *flag) |
| int | stgDioInit (const char *stuff) |
| int | stgDioQuit (void) |
| int | stgDioMaxInputs (void) |
| int | stgDioMaxOutputs (void) |
| int | stgDioRead (int index, int *value) |
| int | stgDioWrite (int index, int value) |
| int | stgDioCheck (int index, int *value) |
| int | stgDioByteRead (int index, unsigned char *byte) |
| int | stgDioShortRead (int index, unsigned short *sh) |
| int | stgDioWordRead (int index, unsigned int *word) |
| int | stgDioByteWrite (int index, unsigned char byte) |
| int | stgDioShortWrite (int index, unsigned short sh) |
| int | stgDioWordWrite (int index, unsigned int word) |
| int | stgDioByteCheck (int index, unsigned char *byte) |
| int | stgDioShortCheck (int index, unsigned short *sh) |
| int | stgDioWordCheck (int index, unsigned int *word) |
| int | stgAioInit (const char *stuff) |
| int | stgAioQuit (void) |
| int | stgAioMaxInputs (void) |
| int | stgAioMaxOutputs (void) |
| int | stgAioStart (int index) |
| void | stgAioWait (void) |
| int | stgAioRead (int index, double *volts) |
| int | stgAioWrite (int index, double volts) |
| int | stgAioCheck (int index, double *volts) |
| int | stgModel () |
Variables | |
| const int | aPortOffset_1 [] = {DIO_A, DIO_B, DIO_C, DIO_D} |
| const int | aPortOffset_2 [] = {PORT_A, PORT_B, PORT_C, PORT_D} |
| STG_STRUCT | theStg |
| double | checkedOutputs [STG_MAX_AXIS] |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Definition at line 233 of file stg2.c. Referenced by AutoZeroAdc(), BrdtstOK(), CalADC(), CurrentIRR(), DontAutoZeroAdc(), GetBRDTST(), GetCNTRL0(), GetCNTRL1(), GetIDLEN(), GetIndexLatches(), GetSELDI(), MaskTimer2Interrupt(), PollTimer2(), RawDI(), RawDIAll(), RawDIBitPort(), RawDIPort(), RawDOBitValPort(), RawDOPort(), ReadADC(), ReadTimer2TerminalCount(), ResetIndexLatch(), ResetWatchdogLatch(), SelectIndexAxis(), SelectIndexAxisWithPolarity(), SetDDir(), SpinReadADC(), StartADC(), StopInterrupts(), and UnMaskTimer2Interrupt().
|
|
|
Definition at line 234 of file stg2.c. Referenced by EncReadAll(), EncoderInit(), ReadADC(), SpinReadADC(), and StartADC().
|
|
|
Definition at line 231 of file stg2.c. Referenced by AutoZeroAdc(), CalADC(), CurrentIRR(), DioDirection(), DioDirection2(), DontAutoZeroAdc(), EnableCounterLatchOnIndexOrExt(), EncoderInit(), Initialize(), MaskTimer2Interrupt(), PollTimer2(), RawDO(), RawDOAll(), RawDOBitValPort(), RawDOBytePort(), RawDOPort(), ReadTimer2TerminalCount(), ResetIndexLatches(), ResetWatchdogLatch(), SelectIndexAxis(), SelectIndexAxisWithPolarity(), SelectIndexOrExtLatch(), SelectInterruptPeriod(), ServoToGoConstructor(), SetDDir(), SetEncoderCounts(), SetIrq(), StartADC(), StartInterrupts(), StartTimer2RTI(), StartTimer2TerminalCount(), StopInterrupts(), StopTimer(), and UnMaskTimer2Interrupt().
|
|
|
Definition at line 232 of file stg2.c. Referenced by EncReadAll(), EncoderInit(), EncoderLatch(), EncoderResetAddr(), RawDAC(), and StartADC().
|
|
|
|
|
|
|
|
|
Definition at line 1394 of file stg2.c. 01395 {
01396 /* set the Analog to Digital converter to autozero on each conversion */
01397
01398 if (stg->wModel == MODEL1)
01399 fOutP(stg->wBaseAddress + INTC, fInP(stg->wBaseAddress + INTC) & ~AUTOZERO);
01400 else /* MODEL2 */
01401 fOutP(stg->wBaseAddress + CNTRL0, fInP(stg->wBaseAddress + CNTRL0) | CNTRL0_AZ);
01402 }
|
|
|
Definition at line 870 of file stg2.c. 00871 {
00872 return stg->wBaseAddress;
00873 };
|
|
|
Definition at line 363 of file stg2.c. 00364 {
00365 short i;
00366 unsigned short io_add;
00367
00368 for (i = 15; i >= 0; i--) /* search all possible addresses */
00369 {
00370 io_add = i * 0x20 + 0x200;
00371 if ( BrdtstOK(stg,
00372 io_add) )
00373 return io_add;
00374 }
00375 return(0);
00376 }
|
|
||||||||||||
|
Definition at line 386 of file stg2.c. 00387 {
00388 unsigned short BrdtstAddress;
00389 unsigned short SerSeq, HighNibble;
00390 int j;
00391
00392 BrdtstAddress = BaseAddress + BRDTST;
00393
00394 SerSeq = 0;
00395 for (j = 7; j >= 0; j--)
00396 {
00397 HighNibble = fInP(BrdtstAddress) >> 4;
00398 if (HighNibble & 8) /* is SER set */
00399 {
00400 /* shift bit to position specifed by Q2, Q1, Q0 */
00401 /* which are the lower three bits. Put bit in SerSeq. */
00402 SerSeq |= 1 << (HighNibble & 7);
00403 }
00404 }
00405 if (SerSeq == 0x75) /* SER sequence is 01110101 */
00406 {
00407 stg->wModel = MODEL1;
00408 return 1; /*true */
00409 }
00410 if (SerSeq == 0x74) /* SER sequence is 01110100 */
00411 {
00412 stg->wModel = MODEL2;
00413 return 1; /* true */
00414 }
00415 /* stg->wModel = MODEL_NO_ID; */
00416 return 0; /* false */
00417 }
|
|
|
Definition at line 1414 of file stg2.c. 01415 {
01416 /* Start calibration cycle on ADC chip */
01417
01418 unsigned char Cntrl0;
01419
01420 if (stg->wModel == MODEL2) /* this function only in Model 2 board. */
01421 {
01422 Cntrl0 = fInP(stg->wBaseAddress + CNTRL0) & 0x07; /* save irq */
01423 fOutP(stg->wBaseAddress + CNTRL0, Cntrl0); /* cal is low */
01424 /* cal pulse should be 60 ns. The ISA bus is 10 MHz. or 100 ns. */
01425 /* so we can just set it back high. */
01426 fOutP(stg->wBaseAddress + CNTRL0, Cntrl0 | 0x08); /* cal is high */
01427 }
01428 }
|
|
|
Definition at line 1094 of file stg2.c. 01095 {
01096 fOutP(stg->wBaseAddress + OCW3, 0x0a); /* IRR on next read */
01097 return fInP(stg->wBaseAddress + IRRreg);
01098 }
|
|
||||||||||||
|
Definition at line 1271 of file stg2.c. 01272 {
01273 unsigned char byHwDir; /* direction bits for hardware */
01274 unsigned long lCurrentData;
01275
01276 if (stg->wNoBoardFlag == NO_BOARD)
01277 {
01278 return;
01279 }
01280
01281 /* get the current data in the I/O ports. We'll replace it when we're */
01282 /* done. When you change a port to output, it will start at what the */
01283 /* input was (usually high). This way, bits won't change (except for a */
01284 /* glitch) when a port is set to output. */
01285
01286 lCurrentData = RawDI(stg);
01287
01288 byHwDir = 0x9b; /* initially all ports input */
01289
01290 if (nSwDir & STG_PORT_A) /* check the bit for A out */
01291 byHwDir &= ~A_DIR_BIT; /* if output, set bit to 0 */
01292 if (nSwDir & STG_PORT_B)
01293 byHwDir &= ~B_DIR_BIT;
01294 if (nSwDir & STG_PORT_C_LO)
01295 byHwDir &= ~C_LOW_DIR_BIT;
01296 if (nSwDir & STG_PORT_C_HI)
01297 byHwDir &= ~C_HI_DIR_BIT;
01298
01299 fOutP(stg->wBaseAddress + ABC_DIR, byHwDir); /* set direction for A, B and C */
01300
01301 SetDDir(stg, nSwDir);
01302 stg->wSaveDirs = nSwDir; /* save, mostly for other function */
01303 RawDO(stg, lCurrentData);
01304 }
|
|
|
Definition at line 1404 of file stg2.c. 01405 {
01406 /* set the Analog to Digital converter to NOT autozero */
01407
01408 if (stg->wModel == MODEL1)
01409 fOutP(stg->wBaseAddress + INTC, fInP(stg->wBaseAddress + INTC) | AUTOZERO);
01410 else /* MODEL2 */
01411 fOutP(stg->wBaseAddress + CNTRL0, fInP(stg->wBaseAddress + CNTRL0) & ~CNTRL0_AZ);
01412 }
|
|
||||||||||||
|
Definition at line 1083 of file stg2.c. 01084 {
01085 /* routine for Model 2 */
01086 fOutP(stg->wBaseAddress + IDLEN, bySelectBits);
01087 }
|
|
||||||||||||
|
Definition at line 934 of file stg2.c. 00935 {
00936 WORDBYTE wbTransfer;
00937 /* static unsigned char byOldByte2[MAX_AXIS]; */
00938 /* static unsigned char byEncHighByte[MAX_AXIS]; */
00939 short i;
00940
00941 if (stg->wNoBoardFlag == NO_BOARD)
00942 {
00943 for (i = 0; i < 8; i++)
00944 {
00945 lbEnc[i].Long = stg->lSimEnc[i];
00946 }
00947 return;
00948 }
00949
00950 /* Disable interrupts here? No, the timer will latch new data in the */
00951 /* hardware anyway. Maybe we should stop the timer? In an interrupt */
00952 /* service routine, you're synchronized with the timer; so the readings */
00953 /* will never change while you're reading them. If you're polling, you */
00954 /* would first latch the encoder counts with the EncoderLatch() function. */
00955 /* But, the timer could latch the counts again, in the middle of the read. */
00956 /* A critical section will help in some extreme cases. */
00957
00958 /* reset counter internal addr ptr to point to first byte */
00959 /* BUG FIX-- don't go past 4 axes on 4 axis board */
00960 fOutPW(stg->wBaseAddress + CNT0_C, 0x0101);
00961 fOutPW(stg->wBaseAddress + CNT2_C, 0x0101);
00962 if (stg->wAxesInSys > 4) {
00963 fOutPW(stg->wBaseAddress + CNT4_C, 0x0101);
00964 fOutPW(stg->wBaseAddress + CNT6_C, 0x0101);
00965 }
00966
00967 for (i = 0; i < 3; i++) /* 24 bits means get 3 bytes each */
00968 {
00969 wbTransfer.Word = fInPW(stg->wBaseAddress + CNT0_D);
00970
00971 lbEnc[0].Byte[i] = wbTransfer.Byte.high;
00972 lbEnc[1].Byte[i] = wbTransfer.Byte.low;
00973
00974 wbTransfer.Word = fInPW(stg->wBaseAddress + CNT2_D);
00975
00976 lbEnc[2].Byte[i] = wbTransfer.Byte.high;
00977 lbEnc[3].Byte[i] = wbTransfer.Byte.low;
00978
00979 /* BUG FIX-- index rolls off end and kills stack if you
00980 have a 4 axis board after this point */
00981 if (stg->wAxesInSys < 8)
00982 {
00983 continue;
00984 }
00985
00986 wbTransfer.Word = fInPW(stg->wBaseAddress + CNT4_D);
00987
00988 lbEnc[4].Byte[i] = wbTransfer.Byte.high;
00989 lbEnc[5].Byte[i] = wbTransfer.Byte.low;
00990
00991 wbTransfer.Word = fInPW(stg->wBaseAddress + CNT6_D);
00992
00993 lbEnc[6].Byte[i] = wbTransfer.Byte.high;
00994 lbEnc[7].Byte[i] = wbTransfer.Byte.low;
00995 }
00996
00997 /* maintain the high byte, to extend the counter to 32 bits */
00998 /* */
00999 /* base decisions to increment or decrement the high byte */
01000 /* on the highest 2 bits of the 24 bit value. To get the */
01001 /* highest 2 bits, use 0xc0 as a mask on byte [2] (the third */
01002 /* byte). */
01003
01004 for (i = 0; i < MAX_AXIS; i++)
01005 {
01006 /* check for -1 to 0 transition */
01007
01008 if ( ( (stg->byOldByte2[i] & 0xc0) == 0xc0 ) /* 11xxxxxx */
01009 && ( (lbEnc[i].Byte[2] & 0xc0) == 0 ) /* 00xxxxxx */
01010 )
01011 stg->byEncHighByte[i]++;
01012
01013 /* check for 0 to -1 transition */
01014
01015 if ( ( (stg->byOldByte2[i] & 0xc0) == 0 ) /* 00xxxxxx */
01016 && ( (lbEnc[i].Byte[2] & 0xc0) == 0xc0 ) /* 11xxxxxx */
01017 )
01018 stg->byEncHighByte[i]--;
01019
01020 lbEnc[i].Byte[3] = stg->byEncHighByte[i];
01021 stg->byOldByte2[i] = lbEnc[i].Byte[2]; /* current byte 2 becomes old one */
01022 }
01023 };
|
|
|
Definition at line 636 of file stg2.c. 00637 {
00638 unsigned short wAdd, uplim; /* for BUG FIX below */
00639 #if 0
00640 /* These variables are used only in the if 0'd out sections below. */
00641 unsigned short wA;
00642 unsigned short const wTestPat = 0x5aa5;
00643 LONGBYTE enc[MAX_AXIS]; /* BUG FIX-- was hard-coded 8 */
00644 #endif
00645
00646 if (stg->wNoBoardFlag == NO_BOARD)
00647 {
00648 stg->wAxesInSys = MAX_AXIS;
00649 return;
00650 }
00651
00652 /* It is possible that the encoder counts are being held by battery */
00653 /* backup, so we'll read the encoders, and save the values */
00654 /* Then we'll initialize the encoder chips, since it's more likely that */
00655 /* the ecoders were not kept alive by battery and need to be initialized */
00656
00657 #if 0
00658 /* FIXME-- we need to read all the encoders here, so temporarily set
00659 wAxesInSys to MAX_AXIS */
00660 stg->wAxesInSys = MAX_AXIS;
00661 EncReadAll(stg, enc);
00662 stg->wAxesInSys = 0;
00663 #endif
00664
00665 /* probably the right thing is to sign extend the 24 bits, so, instead */
00666 /* of a 24 bit unsigned count, we have +/- 23 bits. */
00667
00668 /* for ( i = 0; i < 8; i++) */
00669 /* { */
00670 /* byEncHighByte[i] = enc[i].Byte[2] & 0x80 ? 0xff : 0; */
00671 /* byOldByte2[i] = enc[i].Byte[2]; */
00672 /* } */
00673
00674 /* FIXME-- we don't yet have wAxesInSys, so we'll have to go to the max */
00675 uplim = stg->wBaseAddress + CNT6_C;
00676
00677 for (wAdd = stg->wBaseAddress + CNT0_C; wAdd <= uplim; wAdd +=4)
00678 {
00679 /* we're going to be slick and do two chips at a time, that's why */
00680 /* the registers are arranged data, data, control, control. You */
00681 /* can do two at a time, by using word operations, instead of */
00682 /* byte operations. Not a big deal for initializing, but reading is */
00683 /* done pretty often. */
00684
00685 fOutPW(wAdd, 0x2020); /* master reset */
00686
00687 /* Set Counter Command Register - Input Control, OL Load (P3), */
00688 /* and Enable Inputs A and B (INA/B). */
00689
00690 fOutPW(wAdd, 0x6868);
00691
00692 /* Set Counter Command Register - Output Control */
00693
00694 fOutPW(wAdd, 0x8080);
00695
00696 /* Set Counter Command Register - Quadrature */
00697
00698 fOutPW(wAdd, 0xc3c3);
00699
00700 fOutPW(wAdd, 0x0404); /* reset counter to zero */
00701 }
00702
00703 /* Figure out how many axes are on the card */
00704
00705 #if 0
00706 /* FIXME-- we don't yet have wAxesInSys, so we'll have to go to the max */
00707 uplim = stg->wBaseAddress + CNT6_D;
00708
00709 for (wA = stg->wBaseAddress + CNT0_D; wA <= uplim; wA +=4)
00710 {
00711 /* reset address pointer */
00712
00713 fOutPW(wA + 2, 0x0101);
00714
00715 /* write a pattern to the preset register */
00716
00717 fOutPW(wA, wTestPat);
00718 fOutPW(wA, wTestPat);
00719 fOutPW(wA, wTestPat);
00720
00721 /* transfer the preset register to the count register */
00722
00723 fOutPW(wA + 2, 0x0909);
00724
00725 /* transfer counter to output latch */
00726
00727 fOutPW(wA + 2, 0x0202);
00728
00729 /* read the output latch and see if it matches */
00730
00731 if (fInPW(wA) != wTestPat)
00732 break;
00733 if (fInPW(wA) != wTestPat)
00734 break;
00735 if (fInPW(wA) != wTestPat)
00736 break;
00737
00738 /* now replace the values that you saved previously, in case the */
00739 /* encoder was battery backed up */
00740
00741 fOutP(wA, enc[stg->wAxesInSys].Byte[0]);
00742 fOutP(wA, enc[stg->wAxesInSys].Byte[1]);
00743 fOutP(wA, enc[stg->wAxesInSys].Byte[2]);
00744
00745 fOutP(wA + 1, enc[stg->wAxesInSys + 1].Byte[0]);
00746 fOutP(wA + 1, enc[stg->wAxesInSys + 1].Byte[1]);
00747 fOutP(wA + 1, enc[stg->wAxesInSys + 1].Byte[2]);
00748
00749 /* transfer the preset register to the count register */
00750
00751 fOutPW(wA + 2, 0x0909);
00752
00753 stg->wAxesInSys += 2;
00754
00755 /* write zeros to preset register, we don't want to do a master reset */
00756 /* (MRST), because then we would need to re-initialize the counter */
00757
00758 /* fOutPW(wA, 0); */
00759 /* fOutPW(wA, 0); */
00760 /* fOutPW(wA, 0); */
00761
00762 /* reset counter, BRW and CRY and address pointer (RADR) */
00763
00764 /* fOutPW(wA + 2, 0x0505); */
00765 }
00766 #else
00767 stg->wAxesInSys = 4;
00768 #endif
00769 };
|
|
|
Definition at line 1464 of file stg2.c. 01465 {
01466 if (stg->wNoBoardFlag == NO_BOARD)
01467 {
01468 return;
01469 }
01470
01471 /* normally you'll have the timer latch the data in hardware, but */
01472 /* if the timer isn't running, we need to latch it ourselves. */
01473
01474 /* BUG FIX-- don't go past 4 axes on 4 axis board */
01475 fOutPW(stg->wBaseAddress + CNT0_C, 0x0303);
01476 fOutPW(stg->wBaseAddress + CNT2_C, 0x0303);
01477 if (stg->wAxesInSys > 4) {
01478 fOutPW(stg->wBaseAddress + CNT4_C, 0x0303);
01479 fOutPW(stg->wBaseAddress + CNT6_C, 0x0303);
01480 }
01481 };
|
|
|
Definition at line 1488 of file stg2.c. 01489 {
01490 if (stg->wNoBoardFlag == NO_BOARD)
01491 {
01492 return;
01493 }
01494
01495 /* This function resets all the counter's internal address pointers to point */
01496 /* to the first byte in the 3 byte sequence */
01497
01498 /* BUG FIX-- don't go past 4 axes on 4 axis board */
01499 fOutPW(stg->wBaseAddress + CNT0_C, 0x0101);
01500 fOutPW(stg->wBaseAddress + CNT2_C, 0x0101);
01501 if (stg->wAxesInSys > 4) {
01502 fOutPW(stg->wBaseAddress + CNT4_C, 0x0101);
01503 fOutPW(stg->wBaseAddress + CNT6_C, 0x0101);
01504 }
01505 };
|
|
|
Definition at line 1556 of file stg2.c. 01557 {
01558 return stg->wBaseAddress;
01559 };
|
|
|
Definition at line 1546 of file stg2.c. 01547 {
01548 return stg->wAxesInSys;
01549 };
|
|
|
Definition at line 1536 of file stg2.c. 01537 {
01538 return fInP(stg->wBaseAddress + BRDTST);
01539 }
|
|
|
Definition at line 1541 of file stg2.c. 01542 {
01543 return stg->wNoBoardFlag;
01544 };
|
|
|
Definition at line 1517 of file stg2.c. 01518 {
01519 return fInP(stg->wBaseAddress + CNTRL0);
01520 }
|
|
|
Definition at line 1522 of file stg2.c. 01523 {
01524 return fInP(stg->wBaseAddress + CNTRL1);
01525 }
|
|
|
Definition at line 1512 of file stg2.c. 01513 {
01514 return fInP(stg->wBaseAddress + IDLEN);
01515 }
|
|
|
Definition at line 1129 of file stg2.c. 01130 {
01131 /* routine for Model 2 board */
01132
01133 return fInP(stg->wBaseAddress + IDL);
01134 }
|
|
|
Definition at line 1551 of file stg2.c. 01552 {
01553 return stg->wIrq;
01554 };
|
|
|
Definition at line 1561 of file stg2.c. 01562 {
01563 return stg->wModel;
01564 };
|
|
|
Definition at line 1507 of file stg2.c. 01508 {
01509 return fInP(stg->wBaseAddress + SELDI);
01510 }
|
|
|
Definition at line 1571 of file stg2.c. 01572 {
01573 /* poll for the index pulse of the axis that was previously set up. */
01574 /* Normally you would look at the latched pulse. This function will */
01575 /* probably only get used during testing. */
01576
01577 unsigned char byIRR, byAxisMask;
01578
01579 byIRR = CurrentIRR(stg);
01580 byAxisMask = (stg->byIndexPollAxis & 1) ? IXODD : IXEVN; /* even or odd axis? */
01581
01582 /* The raw index pulse isn't inverted by the hardware if the index pulse is */
01583 /* low active (only the latched pulse is). For consistancy, we'll invert */
01584 /* the pulse in software. */
01585
01586 if (stg->byIndexPulsePolarity == 0) /* if pulse is low true */
01587 byIRR ^= byAxisMask; /* flip bit */
01588
01589 if (byIRR & byAxisMask) /* check index pulse */
01590 return 1;
01591 return 0;
01592 }
|
|
|
Definition at line 1105 of file stg2.c. 01106 {
01107 /* routine for Model 1 board */
01108
01109 /* poll the latched index pulse of the axis that was previously set up */
01110
01111 unsigned char byIRR, byAxisMask;
01112
01113 byIRR = CurrentIRR(stg);
01114 byAxisMask = (stg->byIndexPollAxis & 1) ? LIXODD : LIXEVN; /* even or odd axis? */
01115 if (byIRR & byAxisMask) /* check latched index pulse */
01116 return 1;
01117 return 0;
01118
01119 /* */
01120 /* a faster, but messier way */
01121 /* */
01122 /*fOutP(stg->wBaseAddress + OCW3, 0x0a); // IRR on next read */
01123 /* */
01124 /*return ( fInP(stg->wBaseAddress + IRR) */
01125 /* & ( (stg->byIndexPollAxis & 1) ? LIXODD : LIXEVN ) // mask for even or odd */
01126 /* ); */
01127 }
|
|
||||||||||||
|
Definition at line 424 of file stg2.c. 00425 {
00426 /*
00427 * First find the the base I/O address of the board.
00428 *
00429 * only do this in the DOS example. It's dangerous under 95, and can't be
00430 * done under NT
00431 */
00432 if(FIND_STG_BASE_ADDRESS)
00433 {
00434 stg->wBaseAddress = BaseFind(stg);
00435 if (stg->wBaseAddress == 0)
00436 {
00437 stg->wNoBoardFlag = NO_BOARD;
00438 }
00439 else /* BUG FIX-- need an else */
00440 {
00441 stg->wNoBoardFlag = BOARD_PRESENT;
00442 }
00443 #if !defined(rtlinux) && !defined(rtai)
00444 printf("Servo To Go Board IO address = 0x%X\n",stg->wBaseAddress);
00445 #endif
00446 STG_BASE_ADDRESS = stg->wBaseAddress;
00447 }
00448 else
00449 {
00450 stg->wBaseAddress = STG_BASE_ADDRESS;
00451 }
00452
00453
00454 /*
00455 * Initialize the interrupt controller
00456 */
00457 if (stg->wModel == MODEL1)
00458 {
00459 fOutP(stg->wBaseAddress + MIO_2, 0x92); /* initialize INTC as output reg. */
00460 /* sets port D to input since we have */
00461 /* to set it to something. */
00462 SetIrq(stg, wRequestedIrq); /* selects the IRQ in INTC. Now, if a stray */
00463 /* interrupt is issued (see below) it will */
00464 /* go to an interrupt that isn't enabled on */
00465 /* the motherboard yet (if your system is */
00466 /* set up correctly). */
00467 fOutP(stg->wBaseAddress + ICW1, 0x1a ); /* initialize 82C59 as single chip, */
00468 /* level triggered */
00469 fOutP(stg->wBaseAddress + ICW2, 0x00 ); /* icw2 - not used, must write */
00470 /* could issue stray interrupt here - danger! */
00471 fOutP(stg->wBaseAddress + OCW1, 0xff); /* mask off all interrupt sources (the */
00472 /* interrupt on the motherboard isn't */
00473 /* enabled yet, you do that when you install */
00474 /* your interrupt handler.). */
00475 }
00476 else /* must be a Model 2 */
00477 {
00478 fOutP(stg->wBaseAddress + MIO_2, 0x8b); /* initialize CNTRL0 as output reg. */
00479 /* BRDTST to input. */
00480 /* sets port D, high and low, to input */
00481 /* since we have to set it to something. */
00482 SetIrq(stg, wRequestedIrq); /* selects the IRQ in CNTRL0. Now, if a stray */
00483 /* interrupt is issued (see below) it will */
00484 /* go to an interrupt that isn't enabled on */
00485 /* the motherboard yet (if your system is */
00486 /* set up correctly). */
00487 }
00488 };
|
|
|
Definition at line 1708 of file stg2.c. 01709 {
01710 if (stg->wNoBoardFlag == NO_BOARD)
01711 {
01712 return;
01713 }
01714
01715 if (stg->wModel == MODEL1)
01716 fOutP(stg->wBaseAddress + OCW1, CurrentIRR(stg) | TP2);
01717 else /* Model 2 */
01718 /* we want to save the state of the slave mode, and set the */
01719 /* high nibble bits high, so you don't reset any latches. */
01720 /* bit pattern: 1111x000 where x is don't change */
01721 fOutP(stg->wBaseAddress + CNTRL1,
01722 (fInP(stg->wBaseAddress + CNTRL1) & CNTRL1_NOT_SLAVE) | 0xf0);
01723 }
|
|
|
Definition at line 1369 of file stg2.c. 01370 {
01371 static long lState_1[MAX_AXIS] = {0}; /* state variables */
01372 long lScaledUp;
01373 const short nScale = 10;
01374 int nAxis;
01375
01376 for (nAxis = 0; nAxis < MAX_AXIS; nAxis++)
01377 {
01378 /* The input is guaranteed to be +/- 12 bits */
01379 /* Scale up state so we don't loose resolution */
01380 lScaledUp = stg->lSimDac[nAxis] << nScale;
01381
01382 /* note: I assume right shift is sign preserving (for signed value) */
01383
01384 /* lag */
01385 lState_1[nAxis] += (lScaledUp - lState_1[nAxis]) >> (4 + nAxis); /*lint !e704 */
01386 /* ^^^^^^^ time constant */
01387 /* is different for each axis */
01388
01389 /* integrator (shift out the scale factor and then some) */
01390 stg->lSimEnc[nAxis] += lState_1[nAxis] >> (nScale + 1); /*lint !e704 */
01391 }
01392 }
|
|
|
Definition at line 1671 of file stg2.c. 01672 {
01673 if (stg->wNoBoardFlag == NO_BOARD)
01674 {
01675 return 0;
01676 }
01677
01678 if (stg->wModel == MODEL1)
01679 return !(CurrentIRR(stg) & TP2); /* mask selects bit for TP2 */
01680 else /* MODEL 2 */
01681 {
01682 unsigned char byRegCntrl1, byNewCntrl1;
01683
01684 byRegCntrl1 = fInP(stg->wBaseAddress + CNTRL1);
01685 if (byRegCntrl1 & CNTRL1_INT_T2)
01686 {
01687 /* If it's set, we want to reset the latch, by writing a zero */
01688 /* to CNTRL1_INT_T2. */
01689
01690 /* When we write to CNTRL1, we don't want to change SLAVE, IEN_G2 */
01691 /* IEN_T2, or IEN_T0 -- the lower 4 bits. So, we start with */
01692
01693 byNewCntrl1 = byRegCntrl1 & 0x0f; /* (0000xxxx) */
01694
01695 /* We don't want to reset WDTOUT, INT_G2, or INT_T0--we only want */
01696 /* to reset ...T2. (1101xxxx) */
01697
01698 byNewCntrl1 |= CNTRL1_WDTOUT | CNTRL1_INT_G2 | CNTRL1_INT_T0;
01699
01700 fOutP(stg->wBaseAddress + CNTRL1, byNewCntrl1); /* reset bit */
01701
01702 return 1; /* true */
01703 }
01704 }
01705 return 0; /* false */
01706 }
|
|
|
Definition at line 1228 of file stg2.c. 01229 {
01230 int nPortIndex = 9;
01231
01232 switch(nPort)
01233 {
01234 case STG_PORT_A:
01235 nPortIndex = 0;
01236 break;
01237 case STG_PORT_B:
01238 nPortIndex = 1;
01239 break;
01240 case STG_PORT_C_LO:
01241 case STG_PORT_C_HI:
01242 case STG_PORT_C:
01243 nPortIndex = 2;
01244 break;
01245 case STG_PORT_D_LO:
01246 case STG_PORT_D_HI:
01247 case STG_PORT_D:
01248 nPortIndex = 3;
01249 break;
01250 }
01251 return nPortIndex;
01252 }
|
|
||||||||||||||||
|
Definition at line 880 of file stg2.c. 00881 {
00882 if (stg->wNoBoardFlag == NO_BOARD)
00883 {
00884 return;
00885 }
00886
00887 if ( nAxis > 7 ) /* is axis within range? */
00888 return;
00889
00890
00891 /* input / output: */
00892 /* */
00893 /* lCounts (decimal) ... -lCounts ... +0x1000 ... volts */
00894 /* */
00895 /* 0x1000 (4096) 0xfffff000 0 +10 */
00896 /*out 0 0 0x1000 0 */
00897 /* 0xfffff001 (-4095) 0xfff 0x1fff -10 */
00898
00899 /* So, the domain might be different than you expected. I expected: */
00900 /* 0xf000 (-4096) to 0xfff (4095), rather than */
00901 /* 0xf001 (-4095) to 0x1000 (4096) */
00902
00903 /* reverse slope so positive counts give positive voltage */
00904 lCounts = - lCounts;
00905
00906 /* shift for DAC */
00907 lCounts += 0x1000;
00908
00909 if (lCounts > 0x1FFF) /* clamp + output */
00910 {
00911 lCounts = 0x1FFF;
00912 }
00913 if (lCounts < 0) /* clamp - output */
00914 {
00915 lCounts = 0;
00916 }
00917
00918 if (stg->wNoBoardFlag == NO_BOARD) /* are we simulating? */
00919 {
00920 stg->lSimDac[nAxis] = lCounts;
00921 return;
00922 }
00923
00924 /* nCounts = (USHORT) (lCounts + 0x1000); // correct range for DAC */
00925
00926 fOutPW(stg->wBaseAddress + DAC_0 + (nAxis << 1), (unsigned short)lCounts);
00927 };
|
|
|
Definition at line 1142 of file stg2.c. 01143 {
01144 IO32 xInBits;
01145
01146 if (stg->wNoBoardFlag == NO_BOARD)
01147 {
01148 xInBits.all = 0;
01149 return(xInBits.all);
01150 }
01151
01152 if (stg->wModel == MODEL1)
01153 {
01154 xInBits.port.A = fInP(stg->wBaseAddress + DIO_A);
01155 xInBits.port.B = fInP(stg->wBaseAddress + DIO_B);
01156 xInBits.port.C = fInP(stg->wBaseAddress + DIO_C);
01157 xInBits.port.D = fInP(stg->wBaseAddress + DIO_D);
01158 }
01159 else /* Model 2 */
01160 {
01161 xInBits.port.A = fInP(stg->wBaseAddress + PORT_A);
01162 xInBits.port.B = fInP(stg->wBaseAddress + PORT_B);
01163 xInBits.port.C = fInP(stg->wBaseAddress + PORT_C);
01164 xInBits.port.D = fInP(stg->wBaseAddress + PORT_D);
01165 }
01166 return (xInBits.all);
01167 };
|
|
||||||||||||
|
Definition at line 1175 of file stg2.c. 01176 {
01177 if (stg->wNoBoardFlag == NO_BOARD)
01178 {
01179 return;
01180 }
01181 if (stg->wModel == MODEL1)
01182 {
01183 fOutP(stg->wBaseAddress + DIO_A, ((IO32 *)&lOutBits)->port.A);
01184 fOutP(stg->wBaseAddress + DIO_B, ((IO32 *)&lOutBits)->port.B);
01185 fOutP(stg->wBaseAddress + DIO_C, ((IO32 *)&lOutBits)->port.C);
01186 fOutP(stg->wBaseAddress + DIO_D, ((IO32 *)&lOutBits)->port.D);
01187 }
01188 else /* Model 2 */
01189 {
01190 fOutP(stg->wBaseAddress + PORT_A, ((IO32 *)&lOutBits)->port.A);
01191 fOutP(stg->wBaseAddress + PORT_B, ((IO32 *)&lOutBits)->port.B);
01192 fOutP(stg->wBaseAddress + PORT_C, ((IO32 *)&lOutBits)->port.C);
01193 fOutP(stg->wBaseAddress + PORT_D, ((IO32 *)&lOutBits)->port.D);
01194 }
01195 };
|
|
||||||||||||||||||||
|
Definition at line 1197 of file stg2.c. 01198 {
01199 unsigned nOffset;
01200 unsigned char byData;
01201
01202 if (stg->wNoBoardFlag == NO_BOARD)
01203 {
01204 return;
01205 }
01206
01207 if (nPort > 3)
01208 return;
01209
01210 if (stg->wModel == MODEL1)
01211 nOffset = aPortOffset_1[nPort];
01212 else /* Model 2 */
01213 nOffset = aPortOffset_2[nPort];
01214
01215 byData = fInP(stg->wBaseAddress + nOffset);
01216 if (bySet0or1 == 1)
01217 byData |= 1 << byBitNumber;
01218 else
01219 byData &= ~(1u << byBitNumber);
01220 fOutP(stg->wBaseAddress + nOffset, byData);
01221 };
|
|
||||||||||||||||
|
Definition at line 588 of file stg2.c. 00589 {
00590 if (stg->wNoBoardFlag == NO_BOARD)
00591 {
00592 return STG_SUCCESS;
00593 }
00594
00595 if (wAxis > 7)
00596 return STG_FAILURE;
00597
00598 if (stg->wModel == MODEL1)
00599 {
00600 if ( !(CurrentIRR(stg) & 0x08) ) /* is the conversion done? */
00601 return STG_FAILURE; /* no, return failure */
00602
00603 /* conversion is done, get counts. */
00604 /* *counts = fInPW(stg->wBaseAddress + ADC_0 + (wAxis << 1)); */
00605 /* *counts = fInPW(stg->wBaseAddress + ADC_1); // debug */
00606 }
00607 else /* Model 2 */
00608 {
00609 /* is the conversion done? */
00610 if ( fInP(stg->wBaseAddress + BRDTST) & BRDTST_EOC )
00611 return STG_FAILURE; /* no, return failure */
00612
00613 /* conversion is done, get counts. */
00614 /* *counts = fInPW(stg->wBaseAddress + ADC_1); */
00615 }
00616
00617 *counts = fInPW(stg->wBaseAddress + ADC_0 + (wAxis << 1));
00618
00619 if (*counts & 0x1000) /* is sign bit negative? */
00620 *counts |= 0xf000; /* sign extend */
00621 else
00622 *counts &= 0xfff; /* make sure high order bits are zero. */
00623
00624 return STG_SUCCESS;
00625
00626 };
|
|
|
Definition at line 1661 of file stg2.c. 01662 {
01663 unsigned short count;
01664 char *pByte = (char *)&count;
01665 fOutP(stg->wBaseAddress + TMRCMD, 0x80); /* timer 2, latch */
01666 *pByte++ = fInP(stg->wBaseAddress + TIMER_2); /* LSB */
01667 *pByte = fInP(stg->wBaseAddress + TIMER_2); /* MSB */
01668 return count;
01669 }
|
|
|
Definition at line 1030 of file stg2.c. 01031 {
01032 /* routine for Model 1 */
01033
01034 fInP(stg->wBaseAddress + ODDRST); /*lint !e534 reset index pulse latch for ODD axis */
01035 fInP(stg->wBaseAddress + BRDTST); /*lint !e534 reset index pulse latch for EVEN axis */
01036 }
|
|
||||||||||||
|
Definition at line 1038 of file stg2.c. 01039 {
01040 /* routine for Model 2 */
01041 fOutP(stg->wBaseAddress + IDL, byLatchBits);
01042 }
|
|
|
Definition at line 1527 of file stg2.c. 01528 {
01529 unsigned char byCntrl1 = fInP(stg->wBaseAddress + CNTRL1);
01530 byCntrl1 &= ~CNTRL1_WDTOUT; /*set bit low, to reset */
01531 /* don't reset other latches */
01532 byCntrl1 |= CNTRL1_INT_G2 | CNTRL1_INT_T2 | CNTRL1_INT_T0;
01533 fOutP(stg->wBaseAddress + CNTRL1, byCntrl1);
01534 }
|
|
||||||||||||||||
|
Definition at line 1050 of file stg2.c. 01051 {
01052 /* routine for Model 1 */
01053
01054 /* */
01055 /* initialize stuff to poll index pulse */
01056 /* */
01057 unsigned char byIntc;
01058
01059 stg->byIndexPollAxis = byAxis; /* save axis to check later */
01060 stg->byIndexPulsePolarity = byPol; /* save polarity as new default */
01061 byAxis &= 0x6; /* ignore low bit, we check 2 axes at a time */
01062 byAxis <<= 3; /* shift into position for IXS1, IXS0 */
01063 byIntc = fInP(stg->wBaseAddress + INTC); /* get a copy of INTC, we'll change */
01064 /* some bits in it, not all */
01065 byIntc &= ~(IXLVL | IXS1 | IXS0); /* zero bits for axis and polarity */
01066 byIntc |= byAxis; /* put axes address in INTC */
01067 if (byPol != 0) /* is index pulse active high? */
01068 byIntc |= IXLVL;
01069 fOutP(stg->wBaseAddress + INTC, byIntc);
01070 ResetIndexLatch(stg);
01071
01072 /* The latched index pulse should be low now. If it's not, either something's */
01073 /* wrong, or we happened to initialize it while the index pulse was active. */
01074 }
|
|
||||||||||||
|
Definition at line 1076 of file stg2.c. 01077 {
01078 /* routine for Model 2 */
01079
01080 fOutP(stg->wBaseAddress + SELDI, bySelectBits);
01081 }
|
|
||||||||||||
|
Definition at line 776 of file stg2.c. 00777 {
00778 if (stg->wNoBoardFlag == NO_BOARD)
00779 {
00780 return;
00781 }
00782
00783 if (lPeriodSelect != MAX_PERIOD)
00784 {
00785 fOutP(stg->wBaseAddress + TMRCMD, 0x56); /* timer 1, read/load LSB (MSB is 0) */
00786 /* mode 3 (square wave) */
00787 fOutP(stg->wBaseAddress + TIMER_1, 0xb4); /* 0xb4 = 180 -> 25 uSec period */
00788 }
00789 else
00790 {
00791 fOutP(stg->wBaseAddress + TMRCMD, 0x76); /* timer 1, read/load LSB then MSB */
00792 /* mode 3 (square wave) */
00793 fOutP(stg->wBaseAddress + TIMER_1, 0xff); /* LSB */
00794 fOutP(stg->wBaseAddress + TIMER_1, 0xff); /* MSB */
00795 }
00796
00797 switch (lPeriodSelect)
00798 {
00799 case _500_MICROSECONDS:
00800 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00801 /* MSB, mode 2 (real-time interrupt) */
00802 fOutP(stg->wBaseAddress + TIMER_0, 0x14); /* 0x14 = 20 = .5 mS */
00803 fOutP(stg->wBaseAddress + TIMER_0, 0x00);
00804 break;
00805 case _1_MILLISECOND:
00806 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00807 /* MSB, mode 2 (real-time interrupt) */
00808 fOutP(stg->wBaseAddress + TIMER_0, 0x28); /* 0x28 = 40 = 1 mS */
00809 fOutP(stg->wBaseAddress + TIMER_0, 0x00);
00810 break;
00811 case _2_MILLISECONDS:
00812 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00813 /* MSB, mode 2 (real-time interrupt) */
00814 fOutP(stg->wBaseAddress + TIMER_0, 0x50); /* 0x50 = 80 = 2 mS */
00815 fOutP(stg->wBaseAddress + TIMER_0, 0x00);
00816 break;
00817 case _3_MILLISECONDS:
00818 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00819 /* MSB, mode 2 (real-time interrupt) */
00820 fOutP(stg->wBaseAddress + TIMER_0, 0x78); /* 0x78 = 120 = 3 mS */
00821 fOutP(stg->wBaseAddress + TIMER_0, 0x00);
00822 break;
00823 case _4_MILLISECONDS:
00824 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00825 /* MSB, mode 2 (real-time interrupt) */
00826 fOutP(stg->wBaseAddress + TIMER_0, 0xA0); /* 0xA0 = 160 = 4 mS */
00827 fOutP(stg->wBaseAddress + TIMER_0, 0x00);
00828 break;
00829 case _5_MILLISECONDS:
00830 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00831 /* MSB, mode 2 (real-time interrupt) */
00832 fOutP(stg->wBaseAddress + TIMER_0, 0xC8); /* 0xC8 = 200 = 5 mS */
00833 fOutP(stg->wBaseAddress + TIMER_0, 0x00);
00834 break;
00835 case _10_MILLISECONDS:
00836 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00837 /* MSB, mode 2 (real-time interrupt) */
00838 fOutP(stg->wBaseAddress + TIMER_0, 0x90); /* 0x0190 = 400 = 10 mS */
00839 fOutP(stg->wBaseAddress + TIMER_0, 0x01);
00840 break;
00841 case _100_MILLISECONDS:
00842 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00843 /* MSB, mode 2 (real-time interrupt) */
00844 fOutP(stg->wBaseAddress + TIMER_0, 0xA0); /* 0x0FA0 = 4000 = 100 mS */
00845 fOutP(stg->wBaseAddress + TIMER_0, 0x0F);
00846 break;
00847 case _1_SECOND:
00848 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00849 /* MSB, mode 2 (real-time interrupt) */
00850 fOutP(stg->wBaseAddress + TIMER_0, 0x40); /* 0x9C40 = 40000 = 1 S */
00851 fOutP(stg->wBaseAddress + TIMER_0, 0x9c);
00852 break;
00853 case MAX_PERIOD:
00854 fOutP(stg->wBaseAddress + TMRCMD, 0x34); /* timer 0, read/load LSB followed by */
00855 /* MSB, mode 2 (real-time interrupt) */
00856 fOutP(stg->wBaseAddress + TIMER_0, 0xff); /* LSB */
00857 fOutP(stg->wBaseAddress + TIMER_0, 0xff); /* MSB */
00858 break;
00859 default:
00860 /* wrong input? then don't change it */
00861 break;
00862 }
00863 };
|
|
||||||||||||
|
Definition at line 244 of file stg2.c. 00245 {
00246 int t;
00247
00248 #if defined (LINUX)
00249 iopl(3); /* get access to I/O ports, must be root. */
00250 #endif
00251
00252 /* BUG FIX-- init globals */
00253 stg->wAxesInSys = 0;
00254 stg->wBaseAddress = 0;
00255 stg->wIrq = 0;
00256 stg->wModel = MODEL_NO_ID;
00257 stg->wNoBoardFlag = NO_BOARD;
00258 stg->wAxesInSys = 0;
00259 stg->wSaveDirs = 0;
00260 stg->byIndexPollAxis = 0;
00261 stg->byIndexPulsePolarity = 1;
00262 for (t = 0; t < MAX_AXIS; t++) {
00263 stg->lSimDac[t] = 0;
00264 stg->lSimEnc[t] = 0;
00265 stg->byEncHighByte[t] = 0;
00266 stg->byOldByte2[t] = 0;
00267 }
00268
00269 Initialize(stg, wRequestedIrq); /* figure out board address, init irq controller */
00270 EncoderInit(stg);
00271 SelectInterruptPeriod(stg, _1_MILLISECOND); /* initialize timer */
00272 stg->byIndexPulsePolarity = 1; /* default active level high */
00273 if (stg->wModel == MODEL2)
00274 fOutP(stg->wBaseAddress + CNTRL1, CNTRL1_NOT_SLAVE);
00275 };
|
|
|
Definition at line 282 of file stg2.c. 00283 {
00284 unsigned short nAxis;
00285
00286 StopInterrupts(stg);
00287
00288 /* set all the DAC outputs to 0. */
00289 for (nAxis = 0; nAxis < MAX_AXIS; nAxis++)
00290 RawDAC(stg, nAxis, 0);
00291
00292 /* set all the digital I/O bits to input */
00293 DioDirection(stg, 0);
00294 }
|
|
||||||||||||
|
Definition at line 1306 of file stg2.c. 01307 {
01308 unsigned char byHwDir; /* direction bits for hardware */
01309 unsigned char bySaveReg, bySaveIMR, bySaveCntrl1, bySaveCntrl0;
01310
01311 if (stg->wModel == MODEL1)
01312 {
01313 bySaveReg = fInP(stg->wBaseAddress + INTC); /* INTC needs to be saved, because */
01314 /* MIO_2 reinitializes the 8255 which */
01315 /* implements the INTC register. */
01316 byHwDir = 0x92; /* initialize port D input */
01317 if (nSwDir & STG_PORT_D) /* is port D output? */
01318 byHwDir &= ~D_DIR_BIT; /* if yes, set bit to 0, */
01319 bySaveIMR = fInP(stg->wBaseAddress + IMR); /* get the current interrupt mask */
01320 fOutP(stg->wBaseAddress + OCW1, 0xff); /* mask off all interrupts */
01321 fOutP(stg->wBaseAddress + MIO_2, byHwDir); /* set direction for port D */
01322 fOutP(stg->wBaseAddress + INTC, bySaveReg); /* restore interrupt control reg. */
01323 fOutP(stg->wBaseAddress + OCW1, bySaveIMR); /* restore interrupt mask */
01324 }
01325 else /* Model 2 */
01326 {
01327 bySaveCntrl0 = fInP(stg->wBaseAddress + CNTRL0); /* CNTRL0 needs to be saved, because */
01328 /* D_DIR reinitializes the 8255 which */
01329 /* implements the CNTRL0 register. */
01330 byHwDir = 0x8b; /* initialize CNTRL0 as output reg. */
01331 /* BRDTST to input. */
01332 /* sets port D, high and low, to input */
01333 if (nSwDir & STG_PORT_D_LO) /* low nibble */
01334 byHwDir &= ~D_LOW_DIR_BIT;
01335 if (nSwDir & STG_PORT_D_HI) /* high nibble */
01336 byHwDir &= ~D_HI_DIR_BIT;
01337
01338 bySaveCntrl1 = fInP(stg->wBaseAddress+CNTRL1);/* save for interrupt enables */
01339
01340 /* don't reset any latches; put in slave state; */
01341 /* disable interrupts, so the glitch in CTRL0 doesn't */
01342 /* cause an interrupt on wrong irq */
01343 fOutP(stg->wBaseAddress + CNTRL1, 0xf0);
01344
01345 fOutP(stg->wBaseAddress + D_DIR, byHwDir); /* set port D direction */
01346
01347 /* restore CNTRL0, because it was re-initialized, which */
01348 /* lost any previous contents. */
01349 fOutP(stg->wBaseAddress + CNTRL0, bySaveCntrl0);
01350
01351 /* re-enable interrupts, and restore slave state, don't */
01352 /* reset any latches. (1111xxxx) */
01353 fOutP(stg->wBaseAddress+CNTRL1, (bySaveCntrl1 & 0x0f) | 0xf0);
01354 }
01355 };
|
|
||||||||||||||||
|
Definition at line 1435 of file stg2.c. 01436 {
01437 unsigned short wAddress;
01438 char *ByteUnion = (char *)&lCounts; /* get pointer to lCounts, so you */
01439 /* can take it apart byte by byte */
01440
01441 wAddress = stg->wBaseAddress + CNT0_D;
01442 wAddress += (nAxis & 0x6) << 1; /* shift to multiply by 2 */
01443 /* pairs of data regs seperated by pairs */
01444 /* of control regs, skip over control. */
01445 wAddress += nAxis & 1;
01446 fOutP(wAddress, ByteUnion[0]);
01447 fOutP(wAddress, ByteUnion[1]);
01448 fOutP(wAddress, ByteUnion[2]);
01449
01450 /* transfer the preset register to the count register */
01451 fOutP(wAddress + 2, 0x09);
01452
01453 /* set things for the part that extends the 24 bit counter */
01454 /* to 32 bits. */
01455 stg->byEncHighByte[nAxis] = ByteUnion[3];
01456 stg->byOldByte2[nAxis] = ByteUnion[2];
01457 }
|
|
||||||||||||
|
Definition at line 301 of file stg2.c. 00302 {
00303 unsigned char byIntReg;
00304
00305 if (stg->wNoBoardFlag == NO_BOARD)
00306 return;
00307
00308 stg->wIrq = wRequestedIrq; /* assume it's OK for now, check later */
00309
00310 if (stg->wModel == MODEL1)
00311 byIntReg = 0x80; /* initial value for the high bits in the register */
00312 /* sets auto zero off */
00313 else /* MODEL2 */
00314 byIntReg = 0x88; /* cal high too, not calibrating ADC */
00315
00316 /* now put low bits into byIntReg to select irq */
00317
00318 switch (wRequestedIrq)
00319 {
00320 case 3: break; /* add zero */
00321
00322 case 5: byIntReg |= 4;
00323 break;
00324
00325 case 7: byIntReg |= 2;
00326 break;
00327
00328 case 9: byIntReg |= 6;
00329 break;
00330
00331 case 10: byIntReg |= 5;
00332 break;
00333
00334 case 11: byIntReg |= 7;
00335 break;
00336
00337 case 12: byIntReg |= 3;
00338 break;
00339
00340 case 15: byIntReg |= 1;
00341 break;
00342
00343 default: stg->wIrq = 5; /* ERROR, requested irq not valid, use 5 */
00344 byIntReg |= 4; /* There is no safe value, leaving zero */
00345 /* here would select IRQ 3 which is worse */
00346 /* than 5 because IRQ 3 is usually for COM 2 */
00347 break;
00348 }
00349
00350 if (stg->wModel == MODEL1)
00351 fOutP(stg->wBaseAddress + INTC, byIntReg); /* set irq */
00352 else /* MODEL2 */
00353 fOutP(stg->wBaseAddress + CNTRL0, byIntReg);
00354 }
|
|
||||||||||||
|
Definition at line 547 of file stg2.c. 00548 {
00549 short counts;
00550 short j;
00551
00552 if (stg->wNoBoardFlag == NO_BOARD)
00553 {
00554 return 0;
00555 }
00556
00557 if (wAxis > 7)
00558 return -1;
00559
00560 if (stg->wModel == MODEL1)
00561 {
00562 /* make sure conversion is done, assume polling delay is done. */
00563 /* EOC (End Of Conversion) is bit 0x08 in IIR (Interrupt Request */
00564 /* Register) of Interrupt Controller. Don't wait forever though */
00565 /* bail out eventually. */
00566
00567 for (j = 0; (!(CurrentIRR(stg) & 0x08)) && (j < 10000); j++);
00568
00569 counts = ( fInPW(stg->wBaseAddress + ADC_0 + (wAxis << 1)) );
00570 }
00571 else
00572 {
00573 /* is the conversion done? */
00574 for (j = 0; (fInP(stg->wBaseAddress + BRDTST) & BRDTST_EOC) && (j < 10000); j++);
00575
00576 /* conversion is done, get counts. */
00577 counts = fInPW(stg->wBaseAddress + ADC);
00578 }
00579
00580 if (counts & 0x1000) /* is sign bit negative? */
00581 counts |= 0xf000; /* sign extend */
00582 else
00583 counts &= 0xfff; /* make sure high order bits are zero. */
00584
00585 return counts;
00586 };
|
|
||||||||||||
|
Definition at line 495 of file stg2.c. 00496 {
00497 unsigned char Cntrl0;
00498
00499 if (stg->wNoBoardFlag == NO_BOARD)
00500 {
00501 return;
00502 }
00503
00504 if (wAxis > 7)
00505 return;
00506
00507 if (stg->wModel == MODEL1)
00508 {
00509 /* do a dummy read from the ADC, just to set the input multiplexer to */
00510 /* the right channel */
00511 fInPW(stg->wBaseAddress + ADC_0 + (wAxis << 1)); /*lint !e534 */
00512
00513 /* wait 4 uS for settling time on the multiplexer and ADC */
00514 /* you probably shouldn't really have a delay in */
00515 /* a driver. */
00516 Timer2Delay(stg, 28);
00517
00518 /* now start conversion. */
00519 fOutPW(stg->wBaseAddress + ADC_0 + (wAxis << 1), 0);
00520 }
00521 else /* Model 2 */
00522 {
00523 Cntrl0 = fInP(stg->wBaseAddress + CNTRL0) & 0x07; /* save irq */
00524
00525 Cntrl0 |= (wAxis << 4) | 0x88; /* shift bits to AD2, AD1, AD0 */
00526 /* set bit 0x80 high for autozero */
00527 /* set bit 0x08 high, not calibrating */
00528 fOutP(stg->wBaseAddress + CNTRL0, Cntrl0); /* select ADC channel */
00529
00530 /* don't have to do a dummy read for a model 2 */
00531
00532 /* wait 4 uS for settling time on the multiplexer and ADC */
00533 /* you probably shouldn't really have a delay in */
00534 /* a driver. */
00535 Timer2Delay(stg, 28);
00536
00537 /* now start conversion. */
00538 fOutPW(stg->wBaseAddress + ADC, 0);
00539 }
00540 };
|
|
|
Definition at line 1744 of file stg2.c. 01745 {
01746 if (stg->wNoBoardFlag == NO_BOARD)
01747 {
01748 return;
01749 }
01750 if (stg->wModel == MODEL1)
01751 fOutP(stg->wBaseAddress + OCW1, ~0x04); /* enable interrupt for timer 0 */
01752 else /* MODEL2 */
01753 /* we want to save the state of the slave mode, and set the */
01754 /* high nibble bits high, so you don't reset any latches. */
01755 /* 1111x001, where x means don't change */
01756 {
01757 fOutP(stg->wBaseAddress + CNTRL1, CNTRL1_IEN_T0 | CNTRL1_NOT_SLAVE);
01758 }
01759 };
|
|
||||||||||||
|
Definition at line 1646 of file stg2.c. 01647 {
01648 char *pByte = (char *)&count;
01649
01650 if (stg->wNoBoardFlag == NO_BOARD)
01651 {
01652 return;
01653 }
01654
01655 fOutP(stg->wBaseAddress + TMRCMD, 0xb4); /* timer 2, read/load LSB followed */
01656 /* by MSB, mode 2 (real time int). */
01657 fOutP(stg->wBaseAddress + TIMER_2, *pByte++); /* LSB (little endian) */
01658 fOutP(stg->wBaseAddress + TIMER_2, *pByte); /* MSB */
01659 }
|
|
||||||||||||
|
Definition at line 1631 of file stg2.c. 01632 {
01633 char *pByte = (char *)&count;
01634
01635 if (stg->wNoBoardFlag == NO_BOARD)
01636 {
01637 return;
01638 }
01639
01640 fOutP(stg->wBaseAddress + TMRCMD, 0xb0); /* timer 2, read/load LSB followed */
01641 /* by MSB, mode 0 (terminal count) */
01642 fOutP(stg->wBaseAddress + TIMER_2, *pByte++); /* LSB (little endian) */
01643 fOutP(stg->wBaseAddress + TIMER_2, *pByte); /* MSB */
01644 }
|
|
|
Definition at line 1766 of file stg2.c. 01767 {
01768 if (stg->wNoBoardFlag == NO_BOARD)
01769 {
01770 return;
01771 }
01772 if (stg->wModel == MODEL1)
01773 fOutP(stg->wBaseAddress + OCW1, 0xff); /* disable all interrupts */
01774 else /* MODEL2 */
01775 /* we want to save the state of the slave mode, and set the */
01776 /* high nibble bits high, so you don't reset any latches. */
01777 /* disable all interrupts, since only one can be enabled at */
01778 /* a time (currently). If more than one was enabled, it's */
01779 /* an error (currently). */
01780 /* 1111x000, where x means not changed. */
01781 fOutP(stg->wBaseAddress + CNTRL1,
01782 (fInP(stg->wBaseAddress + CNTRL1) & CNTRL1_NOT_SLAVE) | 0xf0);
01783 };
|
|
|
Definition at line 1599 of file stg2.c. 01600 {
01601 if (stg->wNoBoardFlag == NO_BOARD)
01602 {
01603 return;
01604 }
01605
01606 /* stop the timer by putting it into one shot mode, it will never get */
01607 /* a trigger */
01608
01609 /* bug bug this doesn't work */
01610
01611 fOutP(stg->wBaseAddress + TMRCMD, 0x0a); /* timer 0, mode 1 */
01612 }
|
|
||||||||||||
|
Definition at line 1619 of file stg2.c. 01620 {
01621 if (stg->wNoBoardFlag == NO_BOARD)
01622 {
01623 return;
01624 }
01625
01626 StartTimer2TerminalCount(stg, counts);
01627
01628 while (PollTimer2(stg));
01629 }
|
|
|
Definition at line 1725 of file stg2.c. 01726 {
01727 if (stg->wModel == MODEL1)
01728 fOutP(stg->wBaseAddress + OCW1, CurrentIRR(stg) & ~TP2);
01729 else /* Model 2 */
01730 {
01731 /* we want to save the state of the slave mode, and set the */
01732 /* high nibble bits high, so you don't reset any latches. */
01733 /* bit pattern: 1111x010 where x is don't change */
01734 fOutP(stg->wBaseAddress + CNTRL1,
01735 (fInP(stg->wBaseAddress + CNTRL1) & CNTRL1_NOT_SLAVE) | CNTRL1_IEN_T2);
01736 }
01737 }
|
|
|
Definition at line 39 of file stg2.c. 00039 : stg2.c,v 1.12 2001/10/31 20:21:47 wshackle Exp $";
00040
00041
00042 #if !defined(rtlinux) && !defined(rtai)
00043 #include <stdio.h>
00044 #endif
00045
00046 #include "stg2.h" /* these decls */
00047 #include "extintf.h" /* EXT_ENCODER_INDEX_MODEL */
00048
00049 /* base address-- override default at compile time in stg.h,
00050 or at module load time with STG_BASE_ADDRESS=value */
00051 unsigned short STG_BASE_ADDRESS = DEFAULT_STG_BASE_ADDRESS;
00052 int FIND_STG_BASE_ADDRESS=1;
00053
00054 #ifdef STG_8_AXES
00055 #define STG_MAX_AXIS 8
00056 #else
00057 #define STG_MAX_AXIS 4
00058 #endif
00059
00060 #if defined(rtlinux) || defined(rtai)
00061 #ifndef MODULE
00062 #define MODULE
00063 #endif
00064 #define DO_IT
00065 #endif
00066
00067 #ifdef LINUX
00068 #define DO_IT
00069 /*
00070 Compiling this for LINUX (not RTLINUX) means linking this into a Linux
00071 process, running non-real-time in user space. This is useful for debugging.
00072 If this is done, then the following stuff needs to be done to access the
00073 IO space.
00074 */
00075
00076 /*
00077 Because of a limitation in gcc (present at least in 2.7.2.1 and below), you
00078 _have to_ compile any source code that uses these routines with optimisation
00079 turned on (gcc -O1 or higher), or alternatively #define extern to be
00080 empty before #including <asm/io.h>.
00081
00082 Otherwise, you'll get errors at link time like:
00083
00084 stg.c:475: undefined reference to `__inbc'
00085 */
00086 #ifdef DEFINE_EXTERN_BEFORE_IO
00087 #define extern
00088 #endif
00089
00090
00091 /*
00092 Need to access ports in range 0x200-0x21F and 0x600-0x61F, for default
00093 STG base address. ioperm() only enables up to 0x3FF, so we need to use
00094 iopl() to grant full access to IO space.
00095 */
00096 #include <unistd.h> /* iopl() */
00097
00098 #endif /* LINUX */
00099
00100 #ifdef DO_IT
00101
00102 #if defined(__KERNEL__) && defined(linux)
00103 #include <linux/kernel.h>
00104 #endif
00105
00106 #if defined(linux) || defined(rtlinux) || defined(rtai)
00107 #include <sys/io.h> /* ioperm() */
00108 #endif
00109
00110 /* asm/io.h already included by sys/io.h for 2.2, 2.3, 2.4 kernels */
00111
00112 #ifndef LINUX_VERSION_CODE
00113 #include <linux/version.h>
00114 #endif
00115
00116 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,2,0)
00117 /* Linux or RT-Linux use io ports */
00118 #include <asm/io.h> /* outb, inb */
00119 #endif
00120
00121 #else
00122
00123 /* otherwise do nothing */
00124
00125 #include "rcs_prnt.hh"
00126
00127 static int iopl(int level)
00128 {
00129 return 0;
00130 }
|
|
|
Definition at line 132 of file stg2.c. 00133 {
00134 if (port >= STG_BASE_ADDRESS &&
00135 port <= STG_BASE_ADDRESS + 0x1f)
00136 {
00137 return 0;
00138 }
00139
00140 if (port >= STG_BASE_ADDRESS + 0x400 &&
00141 port <= STG_BASE_ADDRESS + 0x400 + 0x1f)
00142 {
00143 return 0;
00144 }
00145
00146 printf("inb: address out of bounds: %X\n", port);
00147 return 0;
00148 }
|
|
|
Definition at line 173 of file stg2.c. 00174 {
00175 if (port % 2)
00176 {
00177 printf("inw: alignment error: %X\n", port);
00178 return 0;
00179 }
00180
00181 if (port >= STG_BASE_ADDRESS &&
00182 port <= STG_BASE_ADDRESS + 0x1e)
00183 {
00184 return 0;
00185 }
00186
00187 if (port >= STG_BASE_ADDRESS + 0x400 &&
00188 port <= STG_BASE_ADDRESS + 0x400 + 0x1e)
00189 {
00190 return 0;
00191 }
00192
00193 printf("inw: address out of bounds: %X\n", port);
00194 return 0;
00195 }
|
|
||||||||||||
|
Definition at line 150 of file stg2.c. 00151 {
00152 /* allow writes to 0x80 for 1 msec delay */
00153 if (port == 0x80)
00154 {
00155 return;
00156 }
00157
00158 if (port >= STG_BASE_ADDRESS &&
00159 port <= STG_BASE_ADDRESS + 0x1f)
00160 {
00161 return;
00162 }
00163
00164 if (port >= STG_BASE_ADDRESS + 0x400 &&
00165 port <= STG_BASE_ADDRESS + 0x400 + 0x1f)
00166 {
00167 return;
00168 }
00169
00170 printf("outb: address out of bounds: %X\n", port);
00171 }
|
|
||||||||||||
|
Definition at line 197 of file stg2.c. 00198 {
00199 if (port % 2)
00200 {
00201 printf("outw: alignment error: %X\n", port);
00202 return;
00203 }
00204
00205 if (port >= STG_BASE_ADDRESS &&
00206 port <= STG_BASE_ADDRESS + 0x1e)
00207 {
00208 return;
00209 }
00210
00211 if (port >= STG_BASE_ADDRESS + 0x400 &&
00212 port <= STG_BASE_ADDRESS + 0x400 + 0x1e)
00213 {
00214 return;
00215 }
00216
00217 printf("outw: address out of bounds: %X\n", port);
00218 return;
00219 }
|
|
|
Definition at line 1840 of file stg2.c. 01841 {
01842 return STG_MAX_AXIS;
01843 }
|
|
||||||||||||
|
Definition at line 1868 of file stg2.c. Referenced by main(), and stgAioRead().
01869 {
01870 if (adc < 0 ||
01871 adc >= STG_MAX_AXIS) {
01872 return 0; /* don't care */
01873 }
01874
01875 *volts = (double) SpinReadADC(&theStg, (unsigned short) adc);
01876
01877 return 0;
01878 }
|
|
|
Definition at line 1845 of file stg2.c. Referenced by main(), and stgAioStart().
01846 {
01847 if (adc < 0 ||
01848 adc >= STG_MAX_AXIS) {
01849 return 0; /* don't care */
01850 }
01851
01852 StartADC(&theStg, (unsigned short) adc);
01853
01854 return 0;
01855 }
|
|
|
Definition at line 1859 of file stg2.c. 01860 {
01861 int t;
01862
01863 for (t = 0; t < STG_ADC_WAIT_USEC; t++) {
01864 _outp(0x80, 0); /* 0x80 is historical dummy, 1 usec write */
01865 }
01866 }
|
|
||||||||||||
|
Definition at line 2695 of file stg2.c. 02696 {
02697 if (index < 0 || index >= STG_MAX_AXIS) {
02698 *volts = 0.0;
02699 return 0;
02700 }
02701
02702 /* can't read outputs directly, so return stored value */
02703 *volts = checkedOutputs[index];
02704
02705 return 0;
02706 }
|
|
|
Definition at line 2654 of file stg2.c. 02655 {
02656 /* nothing need be done */
02657 return 0;
02658 }
|
|
|
Definition at line 2665 of file stg2.c. 02666 {
02667 return 8; /* make sure you have this option */
02668 }
|
|
|
Definition at line 2670 of file stg2.c. 02671 {
02672 return STG_MAX_AXIS;
02673 }
|
|
|
Definition at line 2660 of file stg2.c. 02661 {
02662 return 0;
02663 }
|
|
||||||||||||
|
Definition at line 2685 of file stg2.c. 02686 {
02687 return stgAdcRead(index, volts);
02688 }
|
|
|
Definition at line 2675 of file stg2.c. Referenced by extAioStart().
02676 {
02677 return stgAdcStart(index);
02678 }
|
|
|
Definition at line 2680 of file stg2.c. 02681 {
02682 stgAdcWait();
02683 }
|
|
||||||||||||
|
Definition at line 2690 of file stg2.c. 02691 {
02692 return stgDacWrite(index, volts);
02693 }
|
|
||||||||||||
|
|
|
||||||||||||
|
Definition at line 2276 of file stg2.c. 02277 {
02278 long bits;
02279 int retval = 0;
02280
02281 bits = RawDI(&theStg);
02282 *flag = 0;
02283
02284 switch (axis)
02285 {
02286 case 0:
02287 if (bits & FAULT_0)
02288 {
02289 *flag = 1;
02290 }
02291 break;
02292
02293 case 1:
02294 if (bits & FAULT_1)
02295 {
02296 *flag = 1;
02297 }
02298 break;
02299
02300 case 2:
02301 if (bits & FAULT_2)
02302 {
02303 *flag = 1;
02304 }
02305 break;
02306
02307 case 3:
02308 if (bits & FAULT_3)
02309 {
02310 *flag = 1;
02311 }
02312 break;
02313
02314 #ifdef STG_8_AXES
02315 case 4:
02316 if (bits & FAULT_4)
02317 {
02318 *flag = 1;
02319 }
02320 break;
02321
02322 case 5:
02323 if (bits & FAULT_5)
02324 {
02325 *flag = 1;
02326 }
02327 break;
02328
02329 #endif
02330
02331 default:
02332 retval = -1;
02333 break;
02334 }
02335
02336 return retval;
02337 }
|
|
|
Definition at line 1880 of file stg2.c. 01881 {
01882 return STG_MAX_AXIS;
01883 }
|
|
||||||||||||
|
Definition at line 1885 of file stg2.c. 01886 {
01887 long lCounts;
01888
01889 if (dac < 0 ||
01890 dac >= STG_MAX_AXIS)
01891 {
01892 return 0; /* don't care */
01893 }
01894
01895 checkedOutputs[dac] = volts;
01896
01897 // WPS -- Hack: This made little sense to be but this hack seems necessary.
01898 lCounts = (long) (( volts * 0x1FFF) / 20.0);
01899
01900 RawDAC(&theStg, dac, lCounts);
01901
01902 return 0;
01903 }
|
|
||||||||||||
|
Definition at line 1906 of file stg2.c. 01907 {
01908 int t;
01909 int smax;
01910
01911 /* clip smax to max supported-- if they want more, ignore */
01912 if (max > STG_MAX_AXIS) {
01913 smax = STG_MAX_AXIS;
01914 }
01915 else {
01916 smax = max;
01917 }
01918
01919 for (t = 0; t < smax; t++) {
01920 if (0 != stgDacWrite(t, volts[t])){
01921 return -1;
01922 }
01923 }
01924
01925 return 0;
01926 }
|
|
||||||||||||
|
Definition at line 2628 of file stg2.c. 02629 {
02630 if (index == 0)
02631 {
02632 *byte = _inp(STG_BASE_ADDRESS + DIO_C);
02633 return 0;
02634 }
02635
02636 *byte = 0;
02637 return -1;
02638 }
|
|
||||||||||||
|
Definition at line 2537 of file stg2.c. 02538 {
02539 if (index == 0)
02540 {
02541 *byte = _inp(STG_BASE_ADDRESS + DIO_A);
02542 return 0;
02543 }
02544
02545 if (index == 1)
02546 {
02547 *byte = _inp(STG_BASE_ADDRESS + DIO_B);
02548 return 0;
02549 }
02550
02551 if (index == 2)
02552 {
02553 *byte = _inp(STG_BASE_ADDRESS + DIO_D);
02554 return 0;
02555 }
02556
02557 *byte = 0;
02558 return -1;
02559 }
|
|
||||||||||||
|
Definition at line 2604 of file stg2.c. 02605 {
02606 if (index == 0)
02607 {
02608 _outp(STG_BASE_ADDRESS + DIO_C, byte);
02609 return 0;
02610 }
02611
02612 return -1;
02613 }
|
|
||||||||||||
|
Definition at line 2517 of file stg2.c. 02518 {
02519 unsigned char byte;
02520 unsigned char mask;
02521
02522 if (index < 0 || index >= 8)
02523 {
02524 *value = 0;
02525 return -1;
02526 }
02527
02528 byte = _inp(STG_BASE_ADDRESS + DIO_C);
02529 mask = 1 << index;
02530
02531 *value = (byte & mask ? 1 : 0);
02532
02533 return 0;
02534 }
|
|
|
Definition at line 2444 of file stg2.c. 02445 {
02446 /* set digital IO bits for A,B input, C output */
02447 DioDirection(&theStg, 0x0C);
02448
02449 return 0;
02450 }
|
|
|
Definition at line 2457 of file stg2.c. 02458 {
02459 return 24;
02460 }
|
|
|
Definition at line 2462 of file stg2.c. 02463 {
02464 return 24;
02465 }
|
|
|
Definition at line 2452 of file stg2.c. 02453 {
02454 return 0;
02455 }
|
|
||||||||||||
|
Definition at line 2467 of file stg2.c. 02468 {
02469 unsigned char byte;
02470 unsigned char mask;
02471
02472 mask = 1 << (index % 8);
02473
02474 /* try A */
02475 if (index >= 0 && index < 8)
02476 {
02477 byte = _inp(STG_BASE_ADDRESS + DIO_A);
02478 *value = (byte & mask ? 1 : 0);
02479 return 0;
02480 }
02481
02482 /* try B */
02483 if (index >= 8 && index < 16)
02484 {
02485 byte = _inp(STG_BASE_ADDRESS + DIO_B);
02486 *value = (byte & mask ? 1 : 0);
02487 return 0;
02488 }
02489
02490 /* try D */
02491 if (index >= 16 && index < 24)
02492 {
02493 byte = _inp(STG_BASE_ADDRESS + DIO_D);
02494 *value = (byte & mask ? 1 : 0);
02495 return 0;
02496 }
02497
02498 /* bad index */
02499 *value = 0;
02500 return -1;
02501 }
|
|
||||||||||||
|
Definition at line 2641 of file stg2.c. 02642 {
02643 *sh = 0;
02644 return -1;
02645 }
|
|
||||||||||||
|
Definition at line 2562 of file stg2.c. 02563 {
02564 unsigned char lo, hi;
02565
02566 if (index == 0)
02567 {
02568 lo = _inp(STG_BASE_ADDRESS + DIO_A);
02569 hi = _inp(STG_BASE_ADDRESS + DIO_B);
02570
02571 *sh = (hi << 8) + lo;
02572 return 0;
02573 }
02574
02575 if (index == 1)
02576 {
02577 lo = _inp(STG_BASE_ADDRESS + DIO_D);
02578
02579 *sh = lo;
02580 return 0;
02581 }
02582
02583 *sh = 0;
02584 return -1;
02585 }
|
|
||||||||||||
|
Definition at line 2616 of file stg2.c. 02617 {
02618 return -1;
02619 }
|
|
||||||||||||
|
Definition at line 2648 of file stg2.c. 02649 {
02650 *word = 0;
02651 return -1;
02652 }
|
|
||||||||||||
|
Definition at line 2588 of file stg2.c. 02589 {
02590 if (index != 0)
02591 {
02592 *word = 0;
02593 return -1;
02594 }
02595
02596 *word = _inp(STG_BASE_ADDRESS + DIO_D) << 16;
02597 *word += _inp(STG_BASE_ADDRESS + DIO_B) << 8;
02598 *word += _inp(STG_BASE_ADDRESS + DIO_A);
02599
02600 return 0;
02601 }
|
|
||||||||||||
|
Definition at line 2622 of file stg2.c. 02623 {
02624 return -1;
02625 }
|
|
||||||||||||
|
Definition at line 2504 of file stg2.c. 02505 {
02506 if (index < 0 || index >= 8)
02507 {
02508 return -1;
02509 }
02510
02511 RawDOPort(&theStg, index, (unsigned char) value, 2); /* 2 is port C */
02512
02513 return 0;
02514 }
|
|
|
Definition at line 1928 of file stg2.c. 01929 {
01930 return EXT_ENCODER_INDEX_MODEL_MANUAL;
01931 }
|
|
|
Definition at line 1943 of file stg2.c. 01944 {
01945 return STG_MAX_AXIS;
01946 }
|
|
||||||||||||
|
Definition at line 1948 of file stg2.c. 01949 {
01950 double allCounts[STG_MAX_AXIS];
01951
01952 if (encoder < 0 ||
01953 encoder >= STG_MAX_AXIS) {
01954 *counts = 0.0;
01955 return 0;
01956 }
01957
01958 stgEncoderReadAll(encoder + 1, allCounts);
01959
01960 *counts = allCounts[encoder];
01961
01962 return 0;
01963 }
|
|
||||||||||||
|
Definition at line 1965 of file stg2.c. 01966 {
01967 LONGBYTE lbEnc[MAX_AXIS];
01968 int t;
01969 int smax; /* how many we actually have */
01970
01971 /* clip smax to max supported-- if they want more, give
01972 them zeros */
01973 if (max > STG_MAX_AXIS) {
01974 smax = STG_MAX_AXIS;
01975 }
01976 else {
01977 smax = max;
01978 }
01979
01980 EncoderLatch(&theStg);
01981 EncReadAll(&theStg, lbEnc);
01982
01983 /* fill ours with the actual values */
01984 for (t = 0; t < smax; t++) {
01985 counts[t] = (double) lbEnc[t].Long;
01986 }
01987 /* and fill the rest with zeros */
01988 for (t = smax; t < max; t++) {
01989 counts[t] = 0.0;
01990 }
01991
01992 return 0;
01993 }
|
|
||||||||||||
|
Definition at line 2008 of file stg2.c. 02009 {
02010 *flag = IndexPulseLatch(&theStg);
02011
02012 return 0;
02013 }
|
|
||||||||||||
|
Definition at line 2016 of file stg2.c. 02017 {
02018 unsigned char byIRR, byAxisMask;
02019
02020 byIRR = CurrentIRR(&theStg);
02021 byAxisMask = (theStg.byIndexPollAxis & 1) ? IXODD : IXEVN;
02022
02023 if (byIRR & byAxisMask)
02024 {
02025 *flag = 1;
02026 }
02027 else
02028 {
02029 *flag = 0;
02030 }
02031
02032 return 0;
02033 }
|
|
|
Definition at line 1995 of file stg2.c. 01996 {
01997 if (encoder < 0 ||
01998 encoder >= STG_MAX_AXIS)
01999 {
02000 return 0;
02001 }
02002
02003 SelectIndexAxis(&theStg, encoder, 1);
02004
02005 return 0;
02006 }
|
|
|
Definition at line 1933 of file stg2.c. 01934 {
01935 if (model != EXT_ENCODER_INDEX_MODEL_MANUAL)
01936 {
01937 return -1;
01938 }
01939
01940 return 0;
01941 }
|
|
||||||||||||
|
Definition at line 2199 of file stg2.c. 02200 {
02201 long bits;
02202 int retval = 0;
02203
02204 bits = RawDI(&theStg);
02205 *flag = 0;
02206
02207 switch (axis)
02208 {
02209 case 0:
02210 if (bits & HOME_0)
02211 {
02212 *flag = 1;
02213 }
02214 break;
02215
02216 case 1:
02217 if (bits & HOME_1)
02218 {
02219 *flag = 1;
02220 }
02221 break;
02222
02223 case 2:
02224 if (bits & HOME_2)
02225 {
02226 *flag = 1;
02227 }
02228 break;
02229
02230 case 3:
02231 if (bits & HOME_3)
02232 {
02233 *flag = 1;
02234 }
02235 break;
02236
02237 #ifdef STG_8_AXES
02238 case 4:
02239 if (bits & HOME_4)
02240 {
02241 *flag = 1;
02242 }
02243 break;
02244
02245 case 5:
02246 if (bits & HOME_5)
02247 {
02248 *flag = 1;
02249 }
02250 break;
02251
02252 #endif
02253
02254 default:
02255 retval = -1;
02256 break;
02257 }
02258
02259 return retval;
02260 }
|
|
||||||||||||
|
Definition at line 2071 of file stg2.c. 02072 {
02073 long bits;
02074 int retval = 0;
02075
02076 bits = RawDI(&theStg);
02077 *flag = 0;
02078
02079 switch (axis)
02080 {
02081 case 0:
02082 if (bits & MAX_LIM_0)
02083 {
02084 *flag = 1;
02085 }
02086 break;
02087
02088 case 1:
02089 if (bits & MAX_LIM_1)
02090 {
02091 *flag = 1;
02092 }
02093 break;
02094
02095 case 2:
02096 if (bits & MAX_LIM_2)
02097 {
02098 *flag = 1;
02099 }
02100 break;
02101
02102 case 3:
02103 if (bits & MAX_LIM_3)
02104 {
02105 *flag = 1;
02106 }
02107 break;
02108
02109 #ifdef STG_8_AXES
02110 case 4:
02111 if (bits & MAX_LIM_4)
02112 {
02113 *flag = 1;
02114 }
02115 break;
02116
02117 case 5:
02118 if (bits & MAX_LIM_5)
02119 {
02120 *flag = 1;
02121 }
02122 break;
02123
02124 #endif
02125
02126 default:
02127 retval = -1;
02128 break;
02129 }
02130
02131 return retval;
02132 }
|
|
||||||||||||
|
Definition at line 2135 of file stg2.c. 02136 {
02137 long bits;
02138 int retval = 0;
02139
02140 bits = RawDI(&theStg);
02141 *flag = 0;
02142
02143 switch (axis)
02144 {
02145 case 0:
02146 if (bits & MIN_LIM_0)
02147 {
02148 *flag = 1;
02149 }
02150 break;
02151
02152 case 1:
02153 if (bits & MIN_LIM_1)
02154 {
02155 *flag = 1;
02156 }
02157 break;
02158
02159 case 2:
02160 if (bits & MIN_LIM_2)
02161 {
02162 *flag = 1;
02163 }
02164 break;
02165
02166 case 3:
02167 if (bits & MIN_LIM_3)
02168 {
02169 *flag = 1;
02170 }
02171 break;
02172
02173 #ifdef STG_8_AXES
02174 case 4:
02175 if (bits & MIN_LIM_4)
02176 {
02177 *flag = 1;
02178 }
02179 break;
02180
02181 case 5:
02182 if (bits & MIN_LIM_5)
02183 {
02184 *flag = 1;
02185 }
02186 break;
02187
02188 #endif
02189
02190 default:
02191 retval = -1;
02192 break;
02193 }
02194
02195 return retval;
02196 }
|
|
|
Definition at line 2708 of file stg2.c. 02709 {
02710 return theStg.wModel;
02711 }
|
|
|
Definition at line 1795 of file stg2.c. 01796 {
01797 int t;
01798
01799 /* call STG init, which is the "constructor" */
01800 ServoToGoConstructor(&theStg, 5);
01801 StopInterrupts(&theStg); /* we don't want interrupts */
01802
01803 /* output 0's to amps */
01804 for (t = 0; t < STG_MAX_AXIS; t++)
01805 {
01806 /* write 0 to DACs */
01807 stgDacWrite(t, 0.0);
01808 }
01809
01810 /* init digital IO directions */
01811 stgDioInit(0);
01812
01813 /* need to force a wait here-- calls to stgEncoderReadAll()
01814 immediately after this return garbage. Is there status to
01815 poll on for 'ready'? */
01816 for (t = 0; t < STG_INIT_WAIT; t++)
01817 {
01818 /* do a dummy 1 usec write */
01819 _outp(0x80, 0);
01820 }
01821
01822 return 0;
01823 }
|
|
|
Definition at line 1825 of file stg2.c. 01826 {
01827 int t;
01828
01829 for (t = 0; t < STG_MAX_AXIS; t++)
01830 {
01831 /* write 0's to DACs */
01832 stgDacWrite(t, 0.0);
01833 }
01834
01835 ServoToGoDestructor(&theStg);
01836
01837 return 0;
01838 }
|
|
|
|
|
|
|
|
|
|
|
|
|
1.2.11.1 written by Dimitri van Heesch,
© 1997-2001