Skip to main content
raivo
Associate
December 29, 2012
Question

1-Wire library for STM32 in C

  • December 29, 2012
  • 10 replies
  • 18334 views
Posted on December 29, 2012 at 08:38

Could not find a ready solution for using 1-wire protocol with STM32 in C (working wiwth IAR), so I decided to rework the C++ library that came with arduino.

So, if anyone needs it - here it is a fully working solution (compiled wit IAR, tested on STM32F103VET6 processor running at 72 Mhz - Delay functions need to be modified for other frequencies). I have not yet add comments to functions in code, but it should not be hard to understand, as it is 1:1 ported from arduino library. Sample code:

OWire OneWire;
unsigned char DeviceAddress[8];
int nCount = 0;
OWInit(&OneWire, GPIOB, GPIO_Pin_14); 
while(OWSearch(&OneWire, DeviceAddress))
{
printf(''Device %d: %02X %02X %02X %02X %02X %02X %02X %02X \n\r'',
nCount+1,
DeviceAddress[7],DeviceAddress[6],
DeviceAddress[5],DeviceAddress[4],
DeviceAddress[3],DeviceAddress[2],
DeviceAddress[1],DeviceAddress[0]);
nCount++;
}
printf(''DeviceCount: %d'',nCount);

Output: 0690X00000602n4QAA.jpg May be someone finds the Delay library useful too. Working on DallasTemp library now - will post here when finished.. Any comments, suggestions are welcome... #1wire #delay #1-wire
    This topic has been closed for replies.

    10 replies

    Andrew Neil
    Super User
    January 3, 2013
    Posted on January 03, 2013 at 16:00

    ''rework the C++ library that came with arduino''

    I guess it's a result of this that the code contains variable declarations intermixed with executable statements - which is allowed in C++, but not in so-called ''ANSI'' C.

    Therefore compiling this code will require C++/C99, or some option to ''allow C++ extensions'' - or a bit of reorganisation to move all the delcarations before the code...

    http://stackoverflow.com/questions/2896177/mixed-declarations-and-codes

    If no-one else beats me to it, I'll post an update sometime...

    A complex system that works is invariably found to have evolved from a simple system that worked.A complex system designed from scratch never works and cannot be patched up to make it work.
    Andrew Neil
    Super User
    December 31, 2013
    Posted on December 31, 2012 at 15:17

    Why is there no lightbulb icon to ''like'' this contribution??

    A complex system that works is invariably found to have evolved from a simple system that worked.A complex system designed from scratch never works and cannot be patched up to make it work.
    September 6, 2016
    Posted on September 06, 2016 at 17:09

    Hello, 

     

    Hello, I am using STM32F0 microcontroller and currently implementing DS18S20 using one wire protocol. I am searching for delay and one wire library but not able to find, I have made my own delay library using Systick timer but it is not making precise delay in microseconds?  Help in this regard would be highly appreciated.

    slimen
    Visitor II
    September 6, 2016
    Posted on September 06, 2016 at 17:42

    Hi,

    Maybe this

    http://stm32f4-discovery.net/2015/07/hal-library-05-onewire-for-stm32fxxx/

    is helpful for you.

    Regards

    Tesla DeLorean
    Guru
    September 6, 2016
    Posted on September 06, 2016 at 18:27

    For micro-second delays on the CM0 I'd recommend using a TIM configured in a free-running mode, and pacing bus transitions with spin-loops against that.

    The micro-controller isn't going to be able to interrupt at 1 MHz, so those types of software counters used by SysTick, etc, are not viable.

    On STM32 M3/M4 designs there is also the DWT_CYCCNT often providing nano-second level resolutions.

    Tips, Buy me a coffee, or three.. PayPal Venmo (See Profile) Up vote any posts that you find helpful, it shows what's working..
    mahdi zamani
    Associate III
    January 28, 2017
    Posted on January 28, 2017 at 07:40

    can connect two micro stm32f103xxxx whit this protocol ?

    have a sample fore this ?

    thanks

    Tesla DeLorean
    Guru
    January 28, 2017
    Posted on January 28, 2017 at 13:07

    Not sure this is an efficient way. Wouldn't it be far easier to use a USART and let the peripheral hardware do all the work rather than doing it a bit at a time managing the timing? 

    Tips, Buy me a coffee, or three.. PayPal Venmo (See Profile) Up vote any posts that you find helpful, it shows what's working..
    mahdi zamani
    Associate III
    February 3, 2017
    Posted on February 03, 2017 at 11:29

    my usart pin used ...

    Bogdan Golab
    Lead
    February 3, 2017
    Posted on February 03, 2017 at 13:41

    Two suggestions:

    1. Use I2c to 1-wire adapter: DS2482

    https://www.maximintegrated.com/en/products/interface/controllers-expanders/DS2482-100.html

     

    This way you can i2c library for easy handling of 1-wire

    2. My favorite solution: connect the 1-wire device to the uart as per maxim app note:

    https://www.maximintegrated.com/en/app-notes/index.mvp/id/214

     

    This way you can access the 1-wire device the same as you use the uart.

    Here is the project in Russion:

    http://we.easyelectronics.ru/STM32/stm32-1-wire-dma.html

     

    I made a few project using UART for the purpose of handling 1-wire thermometer e.g. DS18B20

    Bogdan

    Bogdan Golab
    Lead
    February 3, 2017
    Posted on February 03, 2017 at 14:26

    Sorry for the 2nd solution - I have not noticed that you have all UARTs occupied.

    gjepali
    Associate II
    February 20, 2018
    Posted on February 20, 2018 at 09:30

    Hi, thanks for your OneWire library and sorry for my bad english. It's working, but not on F0. I tried it on F0 with 48 MHz, but input and output initialization takes too long (almost 20 us - F0 has only Thumb instruction list). So I tried to optimize the code slightly. I have found that there is no need to reconfigure pin to input or output. If the pin is set as output, it can be read at the same time. So when initializing OneWire_Init(..) I set the pin once as open-drain output and then set only its logic zero or high (high impedance) and then read its real state. And it works well. The delay is almost zero. You need only these functions:

    void ONEWIRE_OUTPUT(OneWire_t *gp)

    {

       GPIO_InitTypeDef gpinit;

       gpinit.GPIO_Mode = GPIO_OType_OD;

       gpinit.GPIO_PuPd = GPIO_PuPd_NOPULL;

       gpinit.GPIO_Speed = GPIO_Speed_Level_2;

       gpinit.GPIO_Pin = gp->GPIO_Pin;

       GPIO_Init(gp->GPIOx,&gpinit);

    }

    void ONEWIRE_LOW(OneWire_t *gp)

    {

       gp->GPIOx->BSRR = gp->GPIO_Pin<<16;

    }

    void ONEWIRE_HIGH(OneWire_t *gp)

    {

       gp->GPIOx->BSRR = gp->GPIO_Pin;

    }

    uint8_t ONEWIRE_READ(OneWire_t *gp)

    {

       return GPIO_ReadInputDataBit(gp->GPIOx, gp->GPIO_Pin);

    }

    Further adjustment for F0 (original delay library is not working with Thumb instruction list):

    #define ONEWIRE_DELAY(us) do {\

    asm volatile ( 'MOV R0,%[loops]\n\t'\

    '1: \n\t'\

    'SUB R0, #1\n\t'\

    'CMP R0, #0\n\t'\

    'BNE 1b \n\t' : : [loops] 'r' (8*us) : 'memory'\

    );\

    } while(0)

    You need to adjust the constant '8' depending on the processor frequency. This Delay loop takes 6 ticks (48 MHz / 6 = 8). The delay function is not dependent on code optimization. So the function is written in the assembler and it's also as macro, so there are no jumps depended on optimization and compiler.

    Stoian Ivanov
    Associate
    April 3, 2018
    Posted on April 04, 2018 at 01:56

    I'm working on stm32f0 lib for interrupt driven 1-wire library supporting multiple buses on different pins. It seems possible with only PLL-doubled internal 8MHz.  The sending seem working with decent speeds and almost no busy-waiting. The interface allows series of 'driver' implemented reset_presence-write-read with callback for result. I anyone is interested PM me I hope to have it done in few days (working late at night, robbing myself of sleep)