[1] | 1 | /********************************************************************
|
---|
| 2 | // created: 2011/02/21 - 10:46
|
---|
| 3 | // filename: PeakCanDriver.cpp
|
---|
| 4 | //
|
---|
| 5 | // author: Sergio Rodriguez
|
---|
| 6 | //
|
---|
| 7 | // version: $Id: PeakCanDriver.cpp srodrigu $
|
---|
| 8 | //
|
---|
| 9 | // purpose: Implementation of the PeakCanDriver class
|
---|
| 10 | //
|
---|
| 11 | *********************************************************************/
|
---|
| 12 |
|
---|
| 13 |
|
---|
| 14 | #include "PeakCanDriver.h"
|
---|
| 15 | #include <stdio.h>
|
---|
| 16 | #include <cstring>
|
---|
| 17 | #include <cstdlib>
|
---|
| 18 | #include <iostream>
|
---|
| 19 |
|
---|
| 20 | #define DEFAULT_NODE "/dev/pcanusb0"
|
---|
| 21 | #define WAIT_RECEIVING_FRAME_TIMEOUT 1000
|
---|
| 22 |
|
---|
| 23 | /**
|
---|
| 24 | * Constructor which enables to initialize the different attributes of the class with default values.
|
---|
| 25 | */
|
---|
| 26 | PeakCanDriver::PeakCanDriver (void)
|
---|
| 27 | {
|
---|
| 28 | printf("Notice : PEAK CAN Driver used\n");
|
---|
| 29 | //szDevNode_ = DEFAULT_NODE;
|
---|
| 30 | mode_ = ReadOnly;
|
---|
| 31 | }
|
---|
| 32 |
|
---|
| 33 | /**
|
---|
| 34 | * Constructor which enables to initialize the different attributes of the class with default values.
|
---|
| 35 | */
|
---|
| 36 | PeakCanDriver::PeakCanDriver (int channel)
|
---|
| 37 | {
|
---|
| 38 | printf("Notice : PEAK CAN Driver used\n");
|
---|
| 39 | //szDevNode_ = DEFAULT_NODE;
|
---|
| 40 | mode_ = ReadOnly;
|
---|
| 41 | }
|
---|
| 42 |
|
---|
| 43 | /**
|
---|
| 44 | * Constructor which enables to initialize the different attributes of the class with default values.
|
---|
| 45 | */
|
---|
| 46 | PeakCanDriver::PeakCanDriver (int channel, unsigned int bitRate)
|
---|
| 47 | {
|
---|
| 48 | printf("Notice : PEAK CAN Driver used\n");
|
---|
| 49 | //szDevNode_ = DEFAULT_NODE;
|
---|
| 50 | mode_ = ReadOnly;
|
---|
| 51 | }
|
---|
| 52 |
|
---|
| 53 | /**
|
---|
| 54 | * Constructor which enables to initialize the different attributes of the class with default values.
|
---|
| 55 | */
|
---|
| 56 | PeakCanDriver::PeakCanDriver(const char* port, const char* mode)
|
---|
| 57 | {
|
---|
| 58 | szDevNode_ =(char*) malloc(14*sizeof(char));
|
---|
| 59 | strcpy(szDevNode_,DEFAULT_NODE);
|
---|
| 60 |
|
---|
| 61 | printf("Notice : PEAK CAN Driver used\n");
|
---|
| 62 | //strcpy(szDevNode_, port);
|
---|
| 63 | printf("Driver to be connected at port: %s",szDevNode_);
|
---|
| 64 |
|
---|
| 65 | if (!strcmp(mode,"ReadOnly")){
|
---|
| 66 | mode_ = ReadOnly;
|
---|
| 67 | printf(" in ReadOnly mode\n");
|
---|
| 68 | }
|
---|
| 69 | else if (!strcmp(mode,"WriteOnly")){
|
---|
| 70 | mode_ = WriteOnly;
|
---|
| 71 | printf(" in WriteOnly mode\n");
|
---|
| 72 | }
|
---|
| 73 | else if (!strcmp(mode,"ReadWrite")){
|
---|
| 74 | mode_ = ReadWrite;
|
---|
| 75 | printf(" in ReadWrite dual mode\n");
|
---|
| 76 | }
|
---|
| 77 | else{
|
---|
| 78 | mode_= ReadOnly;
|
---|
| 79 | printf(" in ReadOnly mode since mode was not identified.\n");
|
---|
| 80 | }
|
---|
| 81 | }
|
---|
| 82 |
|
---|
| 83 | /**
|
---|
| 84 | * Destructor which clean up the different attributs of the class.
|
---|
| 85 | */
|
---|
| 86 | PeakCanDriver::~PeakCanDriver (void)
|
---|
| 87 | {
|
---|
| 88 |
|
---|
| 89 | }
|
---|
| 90 |
|
---|
| 91 | /**
|
---|
| 92 | * Member used to initialise the configuration of the CAN Card.
|
---|
| 93 | * @see cleanUpPort (void)
|
---|
| 94 | * @return a Pstatus variable which contain the error code of the function. On success, it return PSUCCESS. On failure, it return Pstatus error code.
|
---|
| 95 | */
|
---|
| 96 | short PeakCanDriver::initPort (void)
|
---|
| 97 | {
|
---|
| 98 |
|
---|
| 99 | switch(mode_)
|
---|
| 100 | {
|
---|
| 101 | case ReadOnly:
|
---|
| 102 | canDeviceHandle_ = LINUX_CAN_Open(szDevNode_, O_RDONLY);
|
---|
| 103 | break;
|
---|
| 104 | case WriteOnly:
|
---|
| 105 | canDeviceHandle_ = LINUX_CAN_Open(szDevNode_, O_WRONLY);
|
---|
| 106 | break;
|
---|
| 107 | case ReadWrite:
|
---|
| 108 | canDeviceHandle_ = LINUX_CAN_Open(szDevNode_, O_RDWR);
|
---|
| 109 | break;
|
---|
| 110 | default:
|
---|
| 111 | printf("Error on CAN port operation mode selection.\n");
|
---|
| 112 | break;
|
---|
| 113 | }
|
---|
| 114 |
|
---|
| 115 | return (!canDeviceHandle_)?1:PSUCCESS;
|
---|
| 116 | }
|
---|
| 117 |
|
---|
| 118 | /**
|
---|
| 119 | * Member used to clean up the configuration of the CAN Card.
|
---|
| 120 | * @see initPort (void)
|
---|
| 121 | * @return a Pstatus variable which contain the error code of the function. On success, it return PSUCCESS. On failure, it return Pstatus error code.
|
---|
| 122 | */
|
---|
| 123 | short PeakCanDriver::cleanUpPort (void)
|
---|
| 124 | {
|
---|
| 125 | if(canDeviceHandle_)
|
---|
| 126 | {
|
---|
| 127 | printf("Closing CAN Driver..");
|
---|
| 128 | CAN_Close(canDeviceHandle_);
|
---|
| 129 | return PSUCCESS;
|
---|
| 130 | }
|
---|
| 131 | printf("CAN Driver finished.\n");
|
---|
| 132 | return 1;
|
---|
| 133 | }
|
---|
| 134 |
|
---|
| 135 |
|
---|
| 136 | /**
|
---|
| 137 | * Member which permit to send a frame on the CAN bus and test if the frame is well acknowledged.
|
---|
| 138 | * @param flags a character which contain the flags of the sent frame.
|
---|
| 139 | * @param dlc a character which defined the number of characters of the sent frame.
|
---|
| 140 | * @param data a table of characters with the data of the sent frame.
|
---|
| 141 | * @see receiveFrame (unsigned char * flags, unsigned char * dlc, unsigned char ** data)
|
---|
| 142 | * @return a Pstatus variable which contain the error code of the function. On success, it return PSUCCESS. On failure, it return Pstatus error code.
|
---|
| 143 | */
|
---|
| 144 | short PeakCanDriver::sendFrame (struct CanFrame frame)
|
---|
| 145 | {
|
---|
[23] | 146 | TPCANMsg msg;
|
---|
| 147 | msg.MSGTYPE = 0; //normal message
|
---|
| 148 | //msg.MSGTYPE |= MSGTYPE_EXTENDED; //extended ?
|
---|
| 149 | msg.ID = frame.id;
|
---|
| 150 | msg.LEN = frame.dlc;
|
---|
| 151 | memcpy(msg.DATA, frame.data, frame.dlc);
|
---|
| 152 | if(CAN_Write(canDeviceHandle_, &msg)) {
|
---|
| 153 | perror("application: CAN_Write()");
|
---|
| 154 | return errno;
|
---|
| 155 | }
|
---|
[1] | 156 | return PSUCCESS;
|
---|
| 157 | }
|
---|
| 158 |
|
---|
| 159 |
|
---|
| 160 | /**
|
---|
| 161 | * Member which permit to receive of a frame on the CAN bus.
|
---|
| 162 | * @param flags a character pointer which contain the flags of the received frame.
|
---|
| 163 | * @param dlc a character pointer which defined the number of characters of the received frame.
|
---|
| 164 | * @param data a pointer of table of characters with the data of the received frame.
|
---|
| 165 | * @see sendFrame (unsigned char flags, unsigned char dlc, unsigned char * data)
|
---|
| 166 | * @return a Pstatus variable which contain the error code of the function. On success, it return PSUCCESS. On failure, it return Pstatus error code.
|
---|
| 167 | */
|
---|
| 168 | short PeakCanDriver::receiveFrame (struct CanFrame &frame)
|
---|
| 169 | {
|
---|
| 170 | TPCANRdMsg message;
|
---|
| 171 | __u32 status;
|
---|
| 172 |
|
---|
| 173 | //if ((errno = CAN_Read(canDeviceHandle_, &message)))
|
---|
| 174 | if ((errno = LINUX_CAN_Read_Timeout(canDeviceHandle_, &message, READ_TIMEOUT)))
|
---|
| 175 | {
|
---|
[23] | 176 | //Timeout:
|
---|
| 177 | //perror("application: CAN_Read()");
|
---|
[1] | 178 | return errno;
|
---|
| 179 | }
|
---|
| 180 | else
|
---|
| 181 | {
|
---|
| 182 | //print_message(&message.Msg);
|
---|
| 183 | // check if a CAN status is pending
|
---|
| 184 | if (message.Msg.MSGTYPE & MSGTYPE_STATUS)
|
---|
| 185 | {
|
---|
| 186 | status = CAN_Status(canDeviceHandle_);
|
---|
| 187 | if ((int)status < 0)
|
---|
| 188 | {
|
---|
| 189 | errno = nGetLastError();
|
---|
| 190 | perror("application: CAN_Status()");
|
---|
| 191 | return errno;
|
---|
| 192 | }
|
---|
| 193 | else
|
---|
| 194 | printf("application: pending CAN status 0x%04x read.\n", (__u16)status);
|
---|
| 195 | }
|
---|
| 196 | }
|
---|
| 197 |
|
---|
| 198 | /* Return the flags field, dlc field and data field of the sent frame */
|
---|
| 199 | //frame.flags = pEvent->tagData.msg.flags;
|
---|
| 200 | frame.dlc = message.Msg.LEN; //ok
|
---|
| 201 | frame.id = message.Msg.ID;
|
---|
| 202 |
|
---|
| 203 | if( ( frame.dlc > 8 ) || ( frame.dlc < 0 ))
|
---|
| 204 | frame.dlc = 8;
|
---|
| 205 | memcpy(frame.data,message.Msg.DATA, frame.dlc);
|
---|
| 206 |
|
---|
| 207 | return PSUCCESS;
|
---|
| 208 | }
|
---|
| 209 |
|
---|
| 210 |
|
---|
| 211 | /**
|
---|
| 212 | * Member which wait the reception of a frame on the CAN bus.
|
---|
| 213 | * @see sendFrame (unsigned char flags, unsigned char dlc, unsigned char * data)
|
---|
| 214 | * @see receiveFrame (unsigned char * flags, unsigned char * dlc, unsigned char ** data)
|
---|
| 215 | */
|
---|
| 216 | void PeakCanDriver::waitReceivingFrame(void)
|
---|
| 217 | {
|
---|
| 218 |
|
---|
| 219 | }
|
---|
| 220 | // print out the contents of a CAN message
|
---|
| 221 | void PeakCanDriver::print_message(TPCANMsg *m)
|
---|
| 222 | {
|
---|
| 223 | int i;
|
---|
| 224 |
|
---|
| 225 | // print RTR, 11 or 29, CAN-Id and datalength
|
---|
| 226 | printf("message: %c %c 0x%08x %1d ",
|
---|
| 227 | (m->MSGTYPE & MSGTYPE_RTR) ? 'r' : 'm',
|
---|
| 228 | (m->MSGTYPE & MSGTYPE_EXTENDED) ? 'e' : 's',
|
---|
| 229 | m->ID,
|
---|
| 230 | m->LEN);
|
---|
| 231 |
|
---|
| 232 | // don't print any telegram contents for remote frames
|
---|
| 233 | if (!(m->MSGTYPE & MSGTYPE_RTR))
|
---|
| 234 | for (i = 0; i < m->LEN; i++)
|
---|
| 235 | printf("0x%02x ", m->DATA[i]);
|
---|
| 236 |
|
---|
| 237 | printf("\n");
|
---|
| 238 | }
|
---|