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.

CC2652P: RTC causes issue after BLE stack upgrade

Part Number: CC2652P
Other Parts Discussed in Thread: BLE-STACK

Dear TI-Team,

We had the following setup:

  • BLE nodes running the CC2652P with an application based off simple_peripheral, BLE SimpleLink-SDK version 5.10
  • A so called "relay" consisting of the LAUNCHXL-CC1352P-4 dev-board running an application based off the simple_central, BLE SimpleLink-SDK version version 4.10
  • We implemented a time-sync mechanism which used the RTC channels 1 and 2 to time-stamp the 
    RFC_GPO3 signal which we routed through a pin. That signal indicates when the radio is transmitting.
     
    Now I attempted to update the relay firmware to SDK version 8.31. Unfortunately the time-sync mechanism doesn't work anymore. When I run it, the CPU seems kind of stuck: Not in the error-spin handler but it seems to constantly get interrupts. Whenever I halt it, it is mostly in the Hwi_asm_gcc.s file or in some other Hwi-related system files. Also, the timeout-Clock that we set doesn't get called even though the time has elapsed.
    As a test, I commented out all AONRTC-functions and now the timeout does get hit.
     
    This leads me to the suspicion, that the old SDK (4.10) only used RTC channel 0 and was okay with us using channels 1 and 2. The new SDK (8.31), however, seems to be disturbed by us using RTC channels 1 and 2.
     
    Can you please confirm that there is a change in how the SDK uses the RTC? Is there still a way to use parts of the RTC module for precise timestamping alongside the BLE-Stack? And if so, how should we implement precise timestamping, ideally without interrupts and code-execution-latency being involved?
     
    Kind regards,
    Raphael Fischer
  • Hi !

    Going from 4.10 to 8.31 is a significant migration, since you are applying 5 years of changes in one upgrade. Our user guides provides migration guides to help you with these upgrades, and they show what major changes have happened during all these years in the most common examples like simple_central. These would be a good starting point to upgrade your SDK, and I would recommend to follow the year-to-year migration guides one by one, so you can try to pinpoint which version of the SDK causes issues for you.

    To help you with your RTC issues directly, is there any way you could share the snippet of code that you are using to create and use the clocks ? If you are using the registers directly, you could instead try to directly use our clock API.

    Kind regards,
    Lea

  • Hi Lea!

    We are fully aware that we are doing a very large lift of the SDK, skipping many intermediate versions. I saw the very useful migration guides already and applied all relevant changes as best as I could. But trying out every intermediate SDK version would be too much effort for us.

    I reduced our issue to a minimal example, based off the simple_central example.The differences are:

    Syscfg:

    • BLE Default Tx Power Value = 20
    • BLE Radio Configuration > TX Power (dBm) = 20
    • BLE Max Number of PDUs = 6
    • BLE Max Size of PDU (bytes) = 255
    • BLE Bond Manager:
      • MITM Protection = disabled
      • IO Capabilities = No Display or Input Device
      • LRU Bond Replacement = True
    • BLE Advanced Settings > Extended Stack Settings = Guard Time
    • BLE Central Configuration:
      • Connection Interval Min = 7.5ms
      • Connection Interval Max = 4000ms
    • BLE Observer Configuration:
      • Duplicate Filter = Disabled
      • Maximum Number of Advertising reports = 0
    • GPIO: Added TIME_SYNC_INPUT_PIN:
      • Mode = Input
      • Pull = Pull Up
      • Interrupt Trigger = Falling Edge
      • PinMux > GPIO Pin = DIO27
    • Watchdog: Added CONFIG_WATCHDOG_0 with Period = 1000

    We configured the application such, that it automatically connects to our peripheral device. Via UART, we can send commands to the simple_central device and trigger the function timeSync_failureDemo() once peripheral and central have connected:

    #define TIME_SYNC_TIMEOUT_DURATION 5000  // in milliseconds
    #define OUTPUT_PIN IOID_22

    void timeSync_timeoutCb(void) {
      // I put a breakpoint here
      timeSyncFSM = SYNC_TIMEOUT;
    }

    void timeSync_failureDemo() {
      Util_startClock(&timeSyncTimeoutClock);

      // If you comment out the following lines until the end of the function,
      // timeSync_timeoutCb will be called after 5s. If you enable those lines, it
      // won't be called and upon halting the application, it always is in some Hwi
      // file
      AONEventRtcSet(AON_EVENT_RTCSEL_RTC_CH1_CAPT_EV_IOEV_RTC);
      AONRTCModeCh1Set(AON_RTC_MODE_CH1_CAPTURE);
      AONRTCEventClear(AON_RTC_CH1);


      // IOID_22 (output pin) and IOID_27 (input pin) are electrically connected
      IOCPortConfigureSet(OUTPUT_PIN, IOC_PORT_RFC_GPO3,
                          IOC_IOMODE_NORMAL | IOC_NO_IOPULL);
      IOCIOEvtSet(TIME_SYNC_INPUT_PIN, IOC_EVT_RTC_ENABLE);

      AONRTCChannelEnable(AON_RTC_CH1);
    }

    // Called in the main() function
    void timeSync_createTask() {
      Util_constructClock(&timeSyncTimeoutClock, (Clock_FuncPtr)timeSync_timeoutCb,
                          TIME_SYNC_TIMEOUT_DURATION, 0, false, 0);
    }

    (Sorry, the code insert functionality didn't work for me)

    Thank you very much for your help!

    Kind regards,
    Raphael Fischer

  • Hi !

    I don't exactly understand what you are doing or trying to do in the timeSync_failureDemo function. I wouldn't recommend to use the RTC directly using AON functions, if you could describe what it is you're trying to achieve exactly I could try to help you using the modern API to achieve this.

    Kind regards,
    Lea

  • Hi Lea,

    We are trying to very precisely capture the RTC time when the radio module starts transmitting. We are doing this via the RTC module to avoid the interrupt latency. We are measuring this via two GPIOs: We configured IOID_22 as an output that indicates when the radio is transmitting (IOC_PORT_RFC_GPO3 functionality). IOID_27 is connected to it and uses the RTC capture functionality to do the timestamping.

    Kind regards,

    Raphael Fischer

  • Hi !

    Thank you for your explainations, I now better understand what you're trying to do. I think you could use the ClockP API for this purpose. In particular, I think the ClockP_getSystemTicks64 function should be what you are looking for. Could you please try this function and see if it fits your need as you expect ?

    Kind regards,
    Lea

  • How should we use the ClockP_getSystemTicks64 function to measure the time of a GPIO pin change without any interrupt latency?

  • Hi !

    I would do something close to this, to adapt to your code :

    #define TIME_SYNC_TIMEOUT_DURATION 5000  // in milliseconds
    #define OUTPUT_PIN IOID_22
    
    void timeSync_timeoutCb(void) {
      // I put a breakpoint here
      timeSyncFSM = SYNC_TIMEOUT;
    }
    
    void timeSync_failureDemo() {
      Util_startClock(&timeSyncTimeoutClock);
    
      uint64_t timestamp = ClockP_getSystemTicks64();
    
    
      // IOID_22 (output pin) and IOID_27 (input pin) are electrically connected
      IOCPortConfigureSet(OUTPUT_PIN, IOC_PORT_RFC_GPO3,
                          IOC_IOMODE_NORMAL | IOC_NO_IOPULL);
      IOCIOEvtSet(TIME_SYNC_INPUT_PIN, IOC_EVT_RTC_ENABLE);
      
      // Do something with your timestamp and radio value here
      // log it, save it, send it through a pin, ...
    }
    
    // Called in the main() function
    void timeSync_createTask() {
      Util_constructClock(&timeSyncTimeoutClock, (Clock_FuncPtr)timeSync_timeoutCb,
                          TIME_SYNC_TIMEOUT_DURATION, 0, false, 0);
    }

    Kind regards,
    Lea

  • Okay, but this just gives the timestamp of the GPIO initialization and not of an actual pin change, doesn't it?

  • Hi,

    Ok I didn't see that you wanted no interrupt latency. I tried to reproduce your issue by copying your code and setup, but my timer is triggering correctly. However the RTC capture is not happening properly. I think that the best option would be to use interrupts, and suffer a little delay.

    Kind regards,
    Lea

  • In the past two weeks we implemented the whole thing with a high-prio GPIO interrupt which works fine. Now, while working on the peripheral application, I just found this article which describes exactly what we want:  CC1312R: How to use RTC channel 1 and 2 with TI-RTOS7? 

    On the peripheral application, it now works fine. Maybe we will rewrite the central application again to also make use of the RTC capture functionality.