www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Lm3s9b96 CAN controller initialisierung


Important announcement: there is an English version of this forum on EmbDev.net. Posts you create there will be displayed on Mikrocontroller.net and EmbDev.net.
Autor: Timmi (Gast)
Datum:

Diesen Beitrag bewerten:
lesenswert
nicht lesenswert
Hallo,
bin grad dabei mich mit dem LM3s9b96 vom Stellaris auseinander zu 
setzen. Bin dabei über das Stellaris Board, wobei auf dem 2 CAN 
controller drauf sind, mit dem canalyzer anzuschließen. Hab zwar in c 
schon die initialisierung komplett durchgenommen, jedoch kommt da nichts 
gescheites dabei raus, die CAN0H und CAN0L Pins geben am Oszi nichts 
gescheites bei raus. Ich kann ja mal meinen code hier reinstellen, 
vielleicht erkennt ja jemand den Fehler, vielleicht vergesse ich nur 
etwas. Ich möchte über dem CAN 0 Daten zum Canalyzer senden, dort 
sollten normalerweise die ID und Daten zu sehen sein, jedoch gibt er mir 
nur ein ERROR Frame zurück. Immerhin sagt er dass auf dem Can 1 Daten 
empfangen oder gesendet werden.

Kann mir da einer weiterhelfen?

int
main(void)
{

      // Set the clocking to run directly from the PLL.
      //
    SysCtlClockSet(SYSCTL_SYSDIV_4 | SYSCTL_USE_PLL | SYSCTL_OSC_MAIN | SYSCTL_XTAL_16MHZ);


      //
      // Configure CAN 0 Pins.
      //
      SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOB);


      // Configure the GPIO pin muxing to select CAN0 functions for these pins.
      // This step selects which alternate function is available for these pins.
      // This is necessary if your part supports GPIO pin function muxing.
      // Consult the data sheet to see which functions are allocated per pin.
      // TODO: change this to select the port/pin you are using
      //
      GPIOPinConfigure(GPIO_PB4_CAN0RX);
      GPIOPinConfigure(GPIO_PB5_CAN0TX);

//      GPIOPinConfigure(GPIO_PF0_CAN1RX);
//      GPIOPinConfigure(GPIO_PF1_CAN1TX);

      GPIOPinTypeCAN(GPIO_PORTB_BASE, GPIO_PIN_4 | GPIO_PIN_5);


      //
      // Enable the CAN controller.
      //
      SysCtlPeripheralEnable(SYSCTL_PERIPH_CAN0);

      //
      // Reset the state of all the message object and the state of the CAN
      // module to a known state.
      //
      CANInit(CAN0_BASE);

      //
      // Set up the bit rate for the CAN bus.  This function sets up the CAN
      // bus timing for a nominal configuration.  You can achieve more control
      // over the CAN bus timing by using the function CANBitTimingSet() instead
      // of this one, if needed.
      // In this example, the CAN bus is set to 500 kHz.  In the function below,
      // the call to SysCtlClockGet() is used to determine the clock rate that
      // is used for clocking the CAN peripheral.  This can be replaced with a
      // fixed value if you know the value of the system clock, saving the extra
      // function call.  For some parts, the CAN peripheral is clocked by a fixed
      // 8 MHz regardless of the system clock in which case the call to
      // SysCtlClockGet() should be replaced with 8000000.  Consult the data
      // sheet for more information about CAN peripheral clocking.
      //
      CANBitRateSet(CAN0_BASE, SysCtlClockGet(), 500000);
                //


      //
      // Enable interrupts from CAN controller.
      //
      CANIntEnable(CAN0_BASE, CAN_INT_MASTER | CAN_INT_ERROR);// | CAN_INT_STATUS

      //
      // Enable the CAN interrupt on the processor (NVIC).
      //
      //IntEnable(INT_CAN0);

      // Enable the CAN for operation.
      //
      CANEnable(CAN0_BASE);

      // Initialize message object 1 to be able to send CAN message 1.  This
      // message object is not shared so it only needs to be initialized one
      // time, and can be used for repeatedly sending the same message ID.

      g_sCANMsgObject1.ulMsgID = 0x100;
      g_sCANMsgObject1.ulMsgIDMask = 0;
      g_sCANMsgObject1.ulFlags = MSG_OBJ_TX_INT_ENABLE;
      g_sCANMsgObject1.ulMsgLen = sizeof(g_ucMsg1);
      g_sCANMsgObject1.pucMsgData = g_ucMsg1;

      // Initialize message object 2 to be able to send CAN message 2.  This
      // message object is not shared so it only needs to be initialized one
      // time, and can be used for repeatedly sending the same message ID.
      //
      g_sCANMsgObject2.ulMsgID = 0x200;
      g_sCANMsgObject2.ulMsgIDMask = 0;
      g_sCANMsgObject2.ulFlags = MSG_OBJ_TX_INT_ENABLE;
      g_sCANMsgObject2.ulMsgLen = sizeof(g_ucMsg2);
      g_sCANMsgObject2.pucMsgData = g_ucMsg2;

      for(;;)
          {
              //
              // Send message 1 using CAN controller message object 1.  This is
              // the only message sent using this message object.  The
              // CANMessageSet() function will cause the message to be sent right
              // away.
              //
              //PrintCANMessageInfo(&g_sCANMsgObject1, 1);
              CANMessageSet(CAN0_BASE, 1, &g_sCANMsgObject1, MSG_OBJ_TYPE_TX);

              //
              // Send message 2 using CAN controller message object 2.  This is
              // the only message sent using this message object.  The
              // CANMessageSet() function will cause the message to be sent right
              // away.
              //
             // PrintCANMessageInfo(&g_sCANMsgObject2, 2);
              CANMessageSet(CAN0_BASE, 2, &g_sCANMsgObject2, MSG_OBJ_TYPE_TX);

              //
              // Load message object 3 with message 3.  This is needs to be done each
              // time because message object 3 is being shared for two different
              // messages.
              //
              g_sCANMsgObject3.ulMsgID = 0x300;
              g_sCANMsgObject3.ulMsgIDMask = 0;
              g_sCANMsgObject3.ulFlags = MSG_OBJ_TX_INT_ENABLE;
              g_sCANMsgObject3.ulMsgLen = sizeof(g_ucMsg3);
              g_sCANMsgObject3.pucMsgData = g_ucMsg3;

              //
              // Clear the flag that indicates that message 3 has been sent.  This
              // flag will be set in the interrupt handler when a message has been
              // sent using message object 3.
              //
              g_bMsgObj3Sent = 0;

              //
              // Now send message 3 using CAN controller message object 3.  This is
              // the first message sent using this message object.  The
              // CANMessageSet() function will cause the message to be sent right
              // away.
              //
              PrintCANMessageInfo(&g_sCANMsgObject3, 3);
              CANMessageSet(CAN0_BASE, 3, &g_sCANMsgObject3, MSG_OBJ_TYPE_TX);

              //
              // Wait for the indication from the interrupt handler that message
              // object 3 is done, because we are re-using it for another message.
              //
//              while(!g_bMsgObj3Sent)
//              {
//              }

              //
              // Load message object 3 with message 4.  This is needed because
              // message object 3 is being shared for two different messages.
              //
              g_sCANMsgObject3.ulMsgID = 0x300;
              g_sCANMsgObject3.ulMsgIDMask = 0;
              g_sCANMsgObject3.ulFlags = MSG_OBJ_TX_INT_ENABLE;
              g_sCANMsgObject3.ulMsgLen = sizeof(g_ucMsg4);
              g_sCANMsgObject3.pucMsgData = g_ucMsg4;

              //
              // Now send message 4 using CAN controller message object 3.  This is
              // the second message sent using this message object.  The
              // CANMessageSet() function will cause the message to be sent right
              // away.
              //
              //PrintCANMessageInfo(&g_sCANMsgObject3, 3);
              CANMessageSet(CAN0_BASE, 3, &g_sCANMsgObject3, MSG_OBJ_TYPE_TX);

              //
              // Wait 1 second before continuing
              //
              SimpleDelay();

              //
              // Check the error flag to see if errors occurred
              //
              if(g_bErrFlag)
              {
                  UARTprintf(" error - cable connected?\n");
              }
              else
              {
                  //
                  // If no errors then print the count of message sent
                  //
                  UARTprintf(" total count = %u\n",
                             g_ulMsg1Count + g_ulMsg2Count + g_ulMsg3Count);
              }

              //
              // Change the value in the message data for each of the messages.
              //
              (*(unsigned long *)g_ucMsg1)++;
              (*(unsigned long *)g_ucMsg2)++;
              (*(unsigned long *)g_ucMsg3)++;
              (*(unsigned long *)&g_ucMsg4[0])++;
              (*(unsigned long *)&g_ucMsg4[4])--;
          }

          //
          // Return no errors
          //
          return(0);
}


Autor: Timmi (Gast)
Datum:

Diesen Beitrag bewerten:
lesenswert
nicht lesenswert
keiner der mir hierbei helfen kann?

Autor: Timmi (Gast)
Datum:

Diesen Beitrag bewerten:
lesenswert
nicht lesenswert
Ich sehe nun zwar eine CAN Frame jedoch entspricht sie nicht der 
normalen Frame, da ich nnur 16 bits sehe, normalerweise sollte ich mehr 
bits sehen, zumal 11 bits vom identifier sind und mehrere bits der Daten 
dayu kommen noch start und stop bits etc. kann mir einer vielleicht hier 
helfen und und weis das das Problem sein koennte.

Autor: Hannes (Gast)
Datum:

Diesen Beitrag bewerten:
lesenswert
nicht lesenswert
HAllo, ich habe mir ma deinen Code angeschaut weil ich gerad den CAN bus 
bei einem lm3s5749 inbetrieb nehmen will.

Wo sind denn deine INitialiserungen der entsprechenden Register???
kannst du bitte das gesamte projekt mal posten ....da ich nciht weiß was 
sich hinter deien Fuktionen verbirgt..


Mit freundlcihen Grüßen

Autor: Hannes (Gast)
Datum:

Diesen Beitrag bewerten:
lesenswert
nicht lesenswert
hatte vergessen meien email anzugeben

;-)

Autor: Markus R. (maggus)
Datum:

Diesen Beitrag bewerten:
lesenswert
nicht lesenswert
Hannes schrieb:
> Wo sind denn deine INitialiserungen der entsprechenden Register???

Die werden durch die Funktionen (z.B. CANBitRateSet(...)) gesetzt. Die 
Funktionen sind in den StellarisWare Bibliotheken enthalten, zu denen es 
auch ein Manual (Stellaris Peripheral Driver Library User's Guide) gibt.

Die Funktion CANBitRateSet gibt die tatsächlich eingestellte Bitrate als 
unsigned long zurück, schau mal ob das richtig eingestellt wird (bei 
manchen Taktraten sind nicht alle Bitraten möglich).

Probier mal zum Testen dieses Msg-Object:
unsigned char buffer[10];
tCANMsgObject sMsgObjectTx;

sMsgObjectTx.ulMsgID = 0x100;
sMsgObjectTx.ulMsgIDMask = 0;
sMsgObjectTx.ulFlags = 0;
sMsgObjectTx.ulMsgLen = 8;
sMsgObjectTx.pucMsgData = buffer;

Versenden mit
CANMessageSet(CAN0_BASE, 1, &sMsgObjectTx, MSG_OBJ_TYPE_TX);

Bei CAN ist es ausgesprochen wichtig, dass auch ein Emfänger (mit 
gleicher Bitrate) am Bus hängt, der die Nachrichten durch das ACK-Bit 
bestätigt. Außerdem muss der Bus mit 120 Ohm abeschlossen sein und es 
müssen RX UND TX des Transceivers mit dem Mikrocontroller verbunden sein 
(der CAN-Protokollcontroller muss "sich selbst hören können").

Wenn du keine Interrupts verwendest, CANIntEnable(...) auskommentieren.
Mit CANRetrySet(CAN0_BASE, true); kannst du die automatische 
Retransmission ein bzw. ausschalten.

// Edit: Ich seh grad, der Beitrag war schon älter. Vllt. hilfts ja 
trotzdem irgendwann mal jemandem...

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel




Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder GIF-Format hochladen.
Siehe Bildformate
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken erkennst du die Nutzungsbedingungen an.

webmaster@mikrocontroller.netImpressumNutzungsbedingungenWerbung auf Mikrocontroller.net