canio_kvaser.cc

00001 
00002 #include "canio_kvaser.h"
00003 
00004 
00005 CANIOKvaser::CANIOKvaser() : DualCANIO()
00006 {
00007   for (int i =0; i < DUALCAN_NR_CHANNELS; i++) 
00008   {
00009     channels[i] = -1;
00010   }
00011 }
00012 
00013 CANIOKvaser::~CANIOKvaser()
00014 {
00015 }
00016 
00017 /* Initializes the class by opening 2 can channels at the given
00018  * frequency, which should be one of the #defined BAUD_*K values
00019  *
00020  * returns: 0 on success, negative on error
00021  */
00022 int
00023 CANIOKvaser::Init(long channel_freq)
00024 {
00025   int ret;
00026 
00027   // Open up both CAN channels
00028   
00029   for (int i =0; i < DUALCAN_NR_CHANNELS; i++) 
00030   {
00031     if((channels[i] = 
00032         canOpenChannel(i, canWANT_EXCLUSIVE | canWANT_EXTENDED)) < 0) {
00033       return channels[i];
00034     }
00035     
00036     // set the channel params: 500Kbps ... CANLIB will set the other params
00037     // to defaults if we use BAUD_500K
00038     //    if ((ret = canSetBusParams(channels[i], channel_freq, 4, 3, 1, 1, 0)) < 0) {
00039     if ((ret = canSetBusParams(channels[i], channel_freq, 0, 0, 0, 0, 0)) < 0) 
00040       return ret;
00041     
00042     // set filter to only accept packets we are interested in...
00043     // that is, messages with IDs 0x400, 0x401, ..., 0x404
00044     if ((ret = canAccept(channels[i], 0x400, canFILTER_SET_MASK_STD)) < 0) {
00045       return ret;
00046     }
00047 
00048     if ((ret = canAccept(channels[i], 0x400, canFILTER_SET_CODE_STD)) < 0) {
00049       return ret;
00050     }
00051 
00052     // turn on the bus!
00053     if ((ret = canBusOn(channels[i])) < 0) 
00054       return ret;
00055   }
00056   
00057   return 0;
00058 }
00059   
00060 /* Closes the CAN channels
00061  *
00062  * returns: 0 on success, negative otherwise
00063  */
00064 int
00065 CANIOKvaser::Shutdown()
00066 {
00067   int ret;
00068   for(int i =0 ; i < DUALCAN_NR_CHANNELS; i++) 
00069   {
00070     if(channels[i] >= 0) 
00071     {
00072       if((ret = canClose(channels[i])) < 0) 
00073         return ret;
00074     }
00075   }
00076   return 0;
00077 }
00078   
00079 /* Writes the given packet out on both channels
00080  *
00081  * returns: 0 on success, negative error code otherwise
00082  */
00083 int
00084 CANIOKvaser::WritePacket(CanPacket &pkt)
00085 {
00086   int ret;
00087 
00088   //printf("CANIO: WRITE: pkt: %s\n", pkt.toString());
00089 
00090   for (int i=0; i < DUALCAN_NR_CHANNELS; i++) {
00091 
00092     if ((ret = canWriteWait(channels[i], pkt.id, pkt.msg, pkt.dlc, 
00093                         pkt.flags, 1000)) < 0) {
00094       printf("CANIO: write wait error %d\n", ret);
00095       return ret;
00096     }
00097 
00098     
00099     if ((ret = canWriteSync(channels[i], 10000)) < 0) {
00100       printf("CANIO: error %d on write sync\n", ret);
00101       switch (ret) {
00102       case canERR_TIMEOUT:
00103         printf("CANIO: TIMEOUT error\n");
00104         break;
00105       default:
00106         break;
00107       }
00108       return ret;
00109     }
00110     
00111   }
00112 
00113   return 0;
00114 }
00115 
00116 /* Reads a packet.  Looks like we can just read from one channel.
00117  * writes it into msg (must already be allocated), and returns id, dlc, and flags
00118  *
00119  * returns: # bytes in msg if a packet is read, 0 if no packet available, and
00120  * negative on error
00121  */
00122 int
00123 CANIOKvaser::ReadPacket(CanPacket *pkt, int channel)
00124 {
00125   int ret=0;
00126   long unsigned time;
00127 
00128   if((ret = canReadWait(channels[channel], &(pkt->id), &(pkt->msg), 
00129                      &(pkt->dlc), &(pkt->flags), &time, -1)) < 0) 
00130   {
00131     // either no messages or an error
00132     if(ret == canERR_NOMSG)
00133       return 0;
00134     else
00135       return ret;
00136   }
00137 
00138   return pkt->dlc;
00139 }
00140 
00141 

Last updated 12 September 2005 21:38:45