2014-02-23 07:05 AM
Dear all,
I'm having problems to understand what's happening. While searching for the cause of the error I started from the scratch - the code is stripped down to the bare minimum. I think any cross interference can be excluded. I use two different methods for sending CAN-messages. One to send raw CAN-messages directly and one to send CAN-messages according to ISO15765-2 (calling the other). The problem is: If I send a raw CAN-message before I'm calling the ISO15765-2 method to send another message, the same message (first one) will be transmitted over and over (/eventually) again (when I call the ISO15765-2 method) although even the debugger shows the right values inuint8_t CAN_Transmit(CAN_TypeDef* , CanTxMsg*) from stm32f10x_can.c. The code I use for sending a CAN-Message is:uint8_t NCAN_Send(CanTxMsg* pCanMsg)
{ // check if at least one of the three transmission mailboxes is ready \TODO timeout while(!(CAN1->TSR & CAN_TSR_TME0 || CAN1->TSR & CAN_TSR_TME1 || CAN1->TSR & CAN_TSR_TME2))
{} if( CAN_Transmit(CAN1, pCanMsg) != CAN_TxStatus_NoMailBox)
{ nMsgs++; NCanTxMsg outgoing; outgoing.CanMsg = *pCanMsg; outgoing.nCanMsg = nMsgs; // use outgoing for logging purposes... returnSUCCESS;
} returnERROR;
} The code I use for sending a CAN message according to ISO15765-2 isuint8_t NISO15765_TransmitExtendedStart(NProtocolDataUnit* pdu)
{CanTxMsg outgoing;
outgoing.IDE = CAN_Id_Standard; // set to standard 11-Bit identifieroutgoing.DLC = 8;
// datalength of single CAN-Messages is always 8outgoing.StdId = 0x600 | pdu->srcId;
// set source id, \test if 6| should be done here or in application layeroutgoing.Data[0] = pdu->destId;
// set the dest IDif
(pdu->length <= (NCAN_MAX_DATABYTES_PER_MSG - uiHeaderSizeSF))
// we only have 6 databytes left{
// set single Frame, high nibble (Bits 7-4) outgoing.Data[1] = ISO15765_PCITYPE_SF; // set datalen, low nibble (Bits 3-0) outgoing.Data[1] |= pdu->length; // copy the userdata inti;
for(i = 0; i < pdu->length; ++i)
{ outgoing.Data[2+i] = pdu->Data[i]; } // fill up with 0xFF for(i = pdu->length; i < (NCAN_MAX_DATABYTES_PER_MSG - uiHeaderSizeSF); ++i)
{ outgoing.Data[2+i] = 0xFF; } // send the message returnNCAN_Send(&outgoing);
} } So if I call onlyNProtocolDataUnit PDU;
PDU.destId = 0x12; PDU.srcId = 0xF1; PDU.length = 3; PDU.Data[0] = 0x09; PDU.Data[1] = 0x00; PDU.Data[2] = 0x00; uint8_t res = NISO15765_TransmitExtendedStart(&PDU); everything works just fine, I'll receive a6F1,8,12 03 09 00 00 FF FF FF
. BUTif I callCanTxMsg Mainoutput;
Mainoutput.DLC = 4; Mainoutput.Data[0] = 0x21; Mainoutput.Data[1] = 0x23; Mainoutput.Data[2] = 0x24; Mainoutput.Data[3] = 0x25; Mainoutput.IDE = CAN_Id_Standard; Mainoutput.RTR = 0; Mainoutput.StdId = 0x11; NCAN_Send(&Mainoutput); NProtocolDataUnit PDU; PDU.destId = 0x12; PDU.srcId = 0xF1; PDU.length = 3; PDU.Data[0] = 0x09; PDU.Data[1] = 0x00; PDU.Data[2] = 0x00; uint8_t res = NISO15765_TransmitExtendedStart(&PDU); res = NISO15765_TransmitExtendedStart(&PDU); res = NISO15765_TransmitExtendedStart(&PDU); res = NISO15765_TransmitExtendedStart(&PDU); res = NISO15765_TransmitExtendedStart(&PDU); res = NISO15765_TransmitExtendedStart(&PDU); res = NISO15765_TransmitExtendedStart(&PDU); I'll get11;4;21 23 24 25
6F1;8;12 03 09 00 00 FF FF FF 6F1;8;12 03 09 00 00 FF FF FF 6F1;4;21 23 24 25 6F1;8;12 03 09 00 00 FF FF FF 6F1;8;12 03 09 00 00 FF FF FF 6F1;4;21 23 24 25 6F1;8;12 03 09 00 00 FF FF FF So it seems to me, that the uC uses sometimes (?) the old value? And what makes it even more strange is: If I useuint8_t NCAN_Send(CanTxMsg* pCanMsg)
{ // check if at least one of the three transmission mailboxes is ready \TODO timeout while(!(CAN1->TSR & CAN_TSR_TME0 || CAN1->TSR & CAN_TSR_TME1 || CAN1->TSR & CAN_TSR_TME2))
{} if( CAN_Transmit(CAN1, pCanMsg) != CAN_TxStatus_NoMailBox)
{ returnSUCCESS;
} returnERROR;
} it works just fine. And if I'm usinguint8_t NCAN_Send(CanTxMsg* pCanMsg)
{ // check if at least one of the three transmission mailboxes is ready \TODO timeout while(!(CAN1->TSR & CAN_TSR_TME0 || CAN1->TSR & CAN_TSR_TME1 || CAN1->TSR & CAN_TSR_TME2))
{ intdoesNotMakeSense = 1;
} if( CAN_Transmit(CAN1, pCanMsg) != CAN_TxStatus_NoMailBox)
{ returnSUCCESS;
} returnERROR;
} It stops sending after the first (raw) CAN message - although the while loop is passed. Does anybody have any idea what the problem could be? I'm on CooCox CoIDE 1.7.6. and I'm compiling with GNU tools4.8 2013q4. Thank you so much in advance! #can #bug #coide2014-02-23 06:37 PM
I do not have an answer for your question, but I am curious what are you working on :)
ISO 15765-2 is OBDII over CAN is it? I am playing with something more or less from the same field. Too bad there are no Private Messages here :(2014-02-24 01:18 AM
OBD-II over CAN (mostly, except for multiframe stuff like a VIN request) works without ISO15765-2. The ISO is needed though if you want to communicate with the car using KWP2000 or UDS, cause then you need the ISO (which defines transport layer) in order to be able to transmit messages > 8 Byte.
2014-02-24 05:23 PM
Man, we need you on the rusEfi.com project!
http://rusefi.com/images/Frankenstein/20140224_state.jpg