TD1204 – getting start with accelerometers

The Telecom Design TD 1204, used on Sigfox network have a builtin 3 axis accelerometer and a lack of documentation as usual… By the way, here is the result of my searches to make it work.

Basically, the provided libraries makes it easy to use, in the setup part you have to initialize the accelerometers and in the main loop you have to run a TD_ACCELERO_Process(); method to monitor the IRQ and call your callback function to read the data.

It means that the accelerometers is not automatically waking up the device but managed during the 32KHz wakeup look.

The next part is detailing how to use it.

Accelerometer used

The accelerometer used in the TD1204 is a ST Microelectronic LIS3DH 3axes accelerometer.

TD1204 accelerometer setup

To use the accelerometer, just call init in the setup function, then in init or anywhere else you can start the measure :

void TD_USER_Setup(void)
{    
    // accelerometer initialization
    TD_ACCELERO_Init();

    // start to sample the data
    TD_ACCELERO_MonitorData(true,   // Monitoring enabled
            true,                   // Low-power mode enable
            TD_ACCELERO_10HZ,       // Sampling rate 10 Hz
            TD_ACCELERO_ALL_AXIS,   // Axis mask: all axis
            TD_ACCELERO_2G,         // Scale 2 g
            1,                      // High-pass filter enable
            TD_ACCELERO_STREAM,     // FIFO stream mode
            5,                      // Look like a call after 5 values so half a second
            AcceleroCallback);      // User defined callback function
}

The TD_ACCELERO_MonitorData will start a listener on the accelerometer. Here are the parameters

  1. Enable / disable monitoring -To stop monitor we call this function a second time and change for false this will power down accelerometer
  2. Low power mode – It seams that the resolution is lower in this mode and you can access up 5KHz sampling rate when normal mode is limited to 1.25KHz
  3. Sampling rate – How many data to capture / second for 1HZ to 5KHz, take a look to td_accelero.h to get all the possible values.
  4. Define what axis you want to monitor
  5. Is the scale, it can be configure to measure +/- 2g to +/- 16g
  6. High pass filter : this seems to be here to correct a Z axis bug a value > 0 enable it and to look to be  a software filter, this value is used as a parameter… the value to use is unclear, the datasheet not more…
  7. FiFo mode : there is multiple FIFO mode see explanation under this list
  8. Watermark : this is the number of value we are waiting to get in the fifo before calling the user defined callback function… by-the-way, according to the test I have done, do not count on it to get a precise result…
  9. This is the function to call once the data have been received in the FIFO

Fifo management

When the accelerometer capture data, it stores it in a FIFO memory, there are different mode:

  • TD_ACCELERO_BYPASS : FIFO is not used and only 1 value is stored in FIFO[0] the next value will overwrite the previous one.
  • TD_ACCELERO_FIFO : The values are stored in the FIFO until this one is becoming full. At that point the next values are lost
  • TD_ACCELERO_STREAM : The values ares stored in the FIFO until this one is becoming full. At that point, all the values of the fifo are shift. The oldest value is lost and the new one is queued at the end.
  • TD_ACCELERO_STREAMFIFO : this mode is a STREAM mode but when a triggered event arrives, the mode automatically change for FIFO mode (that way the event data are not lost)

The chip can store 32 measures in the FIFO, each measure is a signed 10bit value on all of the 3 axis. It seems that the data are transformed a little bit as the result is more between +/-10000 than limited to 1024…

Callback function

The callback function is called by the TD_ACCELERO_Process() function you must call as much as possible and basically add in the main loop:

void TD_USER_Loop(void)
{
     TD_ACCELERO_Process();
}

This function check the interrupt and call the callback function

static void AcceleroCallback(TD_ACCELERO_Data_t data[32], uint8_t count, bool overrun)
{
    int i;

    tfp_printf("mesures : %d\r\n",count);
    for (i = 0; i < count; i++) {
        tfp_printf("accelero data : %d \t %d \t %d\r\n", data[i].x, data[i].y, data[i].z);
    }

    if (overrun) {
        tfp_printf("overrun\r\n");
    }

}

The function receives a table with count values from the accelerometer ; is should be equal to the watermark but eventually as the interrupt is scanned by the TD_USER_Loop you can get some extra values before being called.

The overrun boolean indicates if you missed some values (as much as I understood).

For each of the values you will get a X,Y,Z axis value ; it should be a signed 10bits value.

 Create an activity sensor with this

 

/* ----------------------------------------------------
 * get the max absolute value on any axis
 * got around 75 when no activity
 * got around 200 when walking
 * got around 2000 when running
 * ----------------------------------------------------
 */
static void AcceleroCallback(TD_ACCELERO_Data_t data[32], uint8_t count, bool overrun)
{
    int i;
    int maxAbs = 0;
    int absX,absY,absZ;

    for (i = 0; i < count; i++) {
        absX = ( data[i].x > 0 ) ? data[i].x : -data[i].x;
        absY = ( data[i].y > 0 ) ? data[i].y : -data[i].y;
        absZ = ( data[i].z > 0 ) ? data[i].z : -data[i].z;
        maxAbs = ( maxAbs > (absX + absY + absZ))?maxAbs:(absX + absY + absZ);
    }
    tfp_printf("Activity : %d\r\n",maxAbs);
}

void TD_USER_Setup(void)
{
    TD_ACCELERO_Init();
    TD_ACCELERO_MonitorData(true,    // Monitoring enabled
            true,                    // Low-power mode enable
            TD_ACCELERO_10HZ,        // Sampling rate 10 Hz
            TD_ACCELERO_ALL_AXIS,    // Axis mask: all axis
            TD_ACCELERO_4G,          // Scale 4g
            1,                       // High-pass filter enable
            TD_ACCELERO_STREAM,      // FIFO stream mode => keep the last if some are lost
            0,                       // no watermark
            AcceleroCallback);
}
/***************************************************************************//**
 * @brief
 *   User loop function.
 ******************************************************************************/
void TD_USER_Loop(void)
{   
   TD_ACCELERO_Process();
}

 

 

 

8 thoughts on “TD1204 – getting start with accelerometers

  1. Hi Paul,

    First of all, I have spend the last 2 days reading all your posts about Sigfox. I have really appreciated all of it, thank you!

    I am now considering turning the TD1204 into an activity tracker. The code you propose above is a perfect example for me. The issue is that I have no clue how much it use the battery. On datasheet, TD write that a “movement detection” monitoring at 1hz use 0,004 mAh/h.
    What is a “movement detection” ? Is it a MonitorData or a EventData function!
    This consumption seems very low comparing to Idle state (0,0025 mAh/h).
    In my case, I would like to store some value, do you thing it is an extra cost of battery?

    Another question is how do you enter in Idle state?

    Thank you again for this blog!

    • Hello,
      The TDxxxx are in idle state most of the time you have nothing to do to be in idle time (compared to arduino that consume always) I have written a post explaining how the loop() works, you should take a look. To make it simple, loop is started by an interrupt (programmed or external event) and proceed the interrupt. At end of the loop the device is going idle until next interrupt (so in fact it is loop really a loop.
      Concerning your first question, the accelerometer get acc data in background and raise an interrupt when it have data to deliver of its buffer full of data, depends on your setting. So during acc capture your device can be idle and only the accelerometer will works. That is why the energy consumption is low.

      • Hello,

        The issue for me is all about the acc data monitoring. What I understood about the acc is when working in monitoring (vs. event mode), it send data all the time to the device (let’s say with a frequency at 50hz considering a FIFO of 30 value, every 0,66s). In that case, the idle mode is almost never active, is that true?

        Thank you for your help

        Jean

      • idle mode is active between end of interrupt and next 0.66s period ; it depends on your code but it should be a large part of the time.
        idle
        — 0.66s interrupt
        your code duration
        idle time = 0.66 – your code duration

  2. Hello paul,

    i am using TD1204, but i didnot found any information concerning where is the accelerometer exactly in TD1204, and am not using arduino ,so i can use your code for example, can you tell me how can i flash the program in TD1204 ? if you suggest me it will be very useful for my project

    • You can flash over serial port using ftdi cable or swd interface with a jtag cable. Take a look to my other sigfox post where you will finf more details

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.