This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Setting up multiple peripherals (CAN and ADC) at the same time through GPIO_E in TM4C1230E6PM

Hello all, I have a few questions on using multiple peripherals that have IO in the same port.  In this case, I am using PE3/AIN0 as an ADC input, and PE4/PE5 as CAN0RX/TX.  My problem is CAN is intially working well, but when I perform a measurement with the ADC, CAN will stop working.  The ADC code is in a separate function, and the ADC is configured and enabled well after the CAN is receiving messages.

1.  When you use CAN0 and ADC0 pins in GPIO_E, do you need to set up SysCtlPeripheralEnable, GPIOPinConfigure, and GPIOPinType for CAN0 and ADC0 at the same time?  Or can you set up GPIOPinTypeADC(GPIO_PORTE_BASE, GPIO_PIN_3) at a later time, immediately before SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0) is invoked, and well after CAN0 is fully enabled and working?

2.  Is there a GPIOPinConfigure definition for the ADC input pins, or is the ADC pin configure assumed when GPIOPinTypeADC(GPIO_PORTE_BASE, GPIO_PIN_3) is invoked?  I looked in pin_map.h, and couldn't find one (maybe I missed it though).

Thanks for all your help!

  • Find your post thoughtful & logical - nicely detailed - Bravo!

    And - despite my having been here from originating firm (LMI's) inception - I cannot respond w/absolute confidence.  I know that our firm has employed such, "mixed peripheral usage" - across a common Port - many times.  And your issue has (not yet) visited!  (whether by luck - or profound skill - unknown...)

    I can suggest a means for you to probe further - while awaiting Amit's (usually) insider info.  As you report success with each/every peripheral when operating alone - might you log each/every key Register in play - during that successful operation.  (and for  both peripherals)  Then - enable & configure the 2nd peripheral - and then review the Registers earlier configured - looking for "unwanted/illegal" modifications.

    Another thought - might the "order" in which you enable & configure peripherals impact results?  May be worthwhile.

    Experimentation may "save the day" when such discovery is not quickly/correctly forthcoming...

    Bon chance, mon ami.

    [edit] 14:38 CST... Noted that good as your post is - you employ the always precise, "will stop working!"  Cannot that mean - so many things - to so many?  Might it be that your ADC awaits completion (via a spinning loop) and thus CAN operation is "starved' at a critical moment?

    It's not possible to simultaneously enable peripherals - and ARM would never have grown so explosively - had there been so fundamental a flaw.  I'd wager (tall stack) that your set-up/config code is flawed - and causes your issue...

  • Hello cb1, thanks for the help and kind words.  I will try looking at the register issues as you suggest.  I'm a newbie on the programming side, and am still learning debugging, so it goes slow.


    My "will stop working" comment is indeed a bit vague.  What exactly happens is this: my code will configure and enable CAN so that input messages can be received and settings sent to the measurement (ADC) function.  The ADC function configures the ADC and performs a measurement when called by main (well after a CAN message is received).  When the measurement function is called, and the ADC is configured, and the measurement function is then exited, the CAN bus analyzer reports a bus fault.

    I found if I disabled the ADC measure function but still initialize the ADC, and exit the measurement function at that point, the CAN bus fault still happens.  If the ADC initialization and measure is disabled, no bus fault occurs.

    It seems to me that there is indeed a configuration error, and my questions are to that point.  I suspect I may not be initializing the pins and peripherals in the correct order.   I should have more time to experiment later today, but the manager of this program is arriving at our facility tomorrow, and I'd like to have something to show him.  Also I am very new with programming (have been a hardware guy for decades), so all this is new to me.

    Thanks again for the help!

  • I'm away from our office now - returning later tonight.  By early tomorrow morning - I should be able to get you sample code we wrote - which has run w/out flaw while enabling both CAN and ADC - from the same MCU port.

    Forum honcho Amit knows these MCUs inside/out.  (our group uses ARMs from 4 vendors - we require M3, M0 and M7 in addition to (only M4) as featured here - thus we're w/out Amit's inside knowledge...)

    Your posting your set-up & config code for both CAN & ADC here enables others to assist.  Be mindful that your MCU must run at (or above) 16MHz for the ADC to function properly.  This is set via SystemClock.

    Assume you're using CAN xcvrs @ both ends - w/terminating resistors @ each end.  (minus that - all bets are off...)

  • Thanks again for your reply.  I think I found out what is wrong; in much of the code examples SysCtlPeripheralEnable for the peripheral itself is entered prior to SysCtlPeripheralEnable for its GPIO port it is located in.  In my code I was setting up in this order:

    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIO_E)

    SysCtlPeripheralEnable(SYSCTL_PERIPH_CAN0)

    SysCtlADCSpeedSet(SYSCTL_ADCSPEED_1MSPS)

    SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0)

    When I changed to the following order:

    SysCtlADCSpeedSet(SYSCTL_ADCSPEED_1MSPS)

    SysCtlPeripheralEnable(SYSCTL_PERIPH_ADC0)

    SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIO_E)

    SysCtlPeripheralEnable(SYSCTL_PERIPH_CAN0)

    CAN stopped locking up and the code started executing.  Perhaps these devices are a little finicky on what order the peripherals are enabled and configured.  I still have other issues, but am back working now.  Thanks again for all the help!

  • What help - you found/solved 100% by yourself!  Good job.

    With the "move" away from proven (mucho robust) StellarisWare such issues arose.  (not good, that)  That, "SysCtlADCSpeedSet(SYSCTL_ADCSPEED_1MSPS)" is the (likely) villain here - and is order sensitive.  And - if memory serves - has been reported/resolved here...

    Don't believe the devices are "finicky" - I'd look instead @ the rebrand exercise.  (i.e. rebrandWare)