Advertisement
Guest User

Untitled

a guest
Feb 21st, 2018
63
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 9.31 KB | None | 0 0
  1. /*
  2.  * onewire.c
  3.  *
  4.  *  Created on: 13.02.2012
  5.  *      Author: di
  6.  */
  7.  
  8. #include "onewire.h"
  9.  
  10. #ifdef OW_USART1
  11.  
  12. #undef OW_USART2
  13. #undef OW_USART3
  14. #undef OW_USART4
  15.  
  16. #define OW_USART        USART1
  17. #define OW_DMA_CH_RX    DMA1_Channel5
  18. #define OW_DMA_CH_TX    DMA1_Channel4
  19. #define OW_DMA_FLAG     DMA1_FLAG_TC5
  20.  
  21. #endif
  22.  
  23.  
  24. #ifdef OW_USART2
  25.  
  26. #undef OW_USART1
  27. #undef OW_USART3
  28. #undef OW_USART4
  29.  
  30. #define OW_USART        USART2
  31. #define OW_DMA_CH_RX    DMA1_Channel6
  32. #define OW_DMA_CH_TX    DMA1_Channel7
  33. #define OW_DMA_FLAG     DMA1_FLAG_TC6
  34.  
  35. #endif
  36.  
  37.  
  38. // Буфер для приема/передачи по 1-wire
  39. uint8_t ow_buf[8];
  40.  
  41. #define OW_0    0x00
  42. #define OW_1    0xff
  43. #define OW_R_1  0xff
  44.  
  45. //-----------------------------------------------------------------------------
  46. // функция преобразует один байт в восемь, для передачи через USART
  47. // ow_byte - байт, который надо преобразовать
  48. // ow_bits - ссылка на буфер, размером не менее 8 байт
  49. //-----------------------------------------------------------------------------
  50. void OW_toBits(uint8_t ow_byte, uint8_t *ow_bits) {
  51.     uint8_t i;
  52.     for (i = 0; i < 8; i++) {
  53.         if (ow_byte & 0x01) {
  54.             *ow_bits = OW_1;
  55.         } else {
  56.             *ow_bits = OW_0;
  57.         }
  58.         ow_bits++;
  59.         ow_byte = ow_byte >> 1;
  60.     }
  61. }
  62.  
  63. //-----------------------------------------------------------------------------
  64. // обратное преобразование - из того, что получено через USART опять собирается байт
  65. // ow_bits - ссылка на буфер, размером не менее 8 байт
  66. //-----------------------------------------------------------------------------
  67. uint8_t OW_toByte(uint8_t *ow_bits) {
  68.     uint8_t ow_byte, i;
  69.     ow_byte = 0;
  70.     for (i = 0; i < 8; i++) {
  71.         ow_byte = ow_byte >> 1;
  72.         if (*ow_bits == OW_R_1) {
  73.             ow_byte |= 0x80;
  74.         }
  75.         ow_bits++;
  76.     }
  77.  
  78.     return ow_byte;
  79. }
  80.  
  81. //-----------------------------------------------------------------------------
  82. // инициализирует USART и DMA
  83. //-----------------------------------------------------------------------------
  84. uint8_t OW_Init() {
  85.     GPIO_InitTypeDef GPIO_InitStruct;
  86.     USART_InitTypeDef USART_InitStructure;
  87.  
  88.     if (OW_USART == USART1) {
  89.         RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_AFIO,
  90.                 ENABLE);
  91.  
  92.         // USART TX
  93.         GPIO_InitStruct.GPIO_Pin = GPIO_Pin_9;
  94.         GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;
  95.         GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
  96.  
  97.         GPIO_Init(GPIOA, &GPIO_InitStruct);
  98.  
  99.         // USART RX
  100.         GPIO_InitStruct.GPIO_Pin = GPIO_Pin_10;
  101.         GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN_FLOATING;
  102.         GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
  103.  
  104.         GPIO_Init(GPIOA, &GPIO_InitStruct);
  105.  
  106.         RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);
  107.  
  108.         RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);
  109.     }
  110.  
  111.     if (OW_USART == USART2) {
  112.         RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_AFIO,
  113.                 ENABLE);
  114.  
  115.         GPIO_InitStruct.GPIO_Pin = GPIO_Pin_2;
  116.         GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AF_PP;
  117.         GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
  118.  
  119.         GPIO_Init(GPIOA, &GPIO_InitStruct);
  120.  
  121.         GPIO_InitStruct.GPIO_Pin = GPIO_Pin_3;
  122.         GPIO_InitStruct.GPIO_Mode = GPIO_Mode_IN_FLOATING;
  123.         GPIO_InitStruct.GPIO_Speed = GPIO_Speed_50MHz;
  124.  
  125.         GPIO_Init(GPIOA, &GPIO_InitStruct);
  126.  
  127.         RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2, ENABLE);
  128.  
  129.         RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);
  130.     }
  131.  
  132.     USART_InitStructure.USART_BaudRate = 115200;
  133.     USART_InitStructure.USART_WordLength = USART_WordLength_8b;
  134.     USART_InitStructure.USART_StopBits = USART_StopBits_1;
  135.     USART_InitStructure.USART_Parity = USART_Parity_No;
  136.     USART_InitStructure.USART_HardwareFlowControl =
  137.             USART_HardwareFlowControl_None;
  138.     USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
  139.  
  140.     USART_Init(OW_USART, &USART_InitStructure);
  141.     USART_Cmd(OW_USART, ENABLE);
  142.     return OW_OK;
  143. }
  144.  
  145. //-----------------------------------------------------------------------------
  146. // осуществляет сброс и проверку на наличие устройств на шине
  147. //-----------------------------------------------------------------------------
  148. uint8_t OW_Reset() {
  149.     uint8_t ow_presence;
  150.     USART_InitTypeDef USART_InitStructure;
  151.  
  152.     USART_InitStructure.USART_BaudRate = 9600;
  153.     USART_InitStructure.USART_WordLength = USART_WordLength_8b;
  154.     USART_InitStructure.USART_StopBits = USART_StopBits_1;
  155.     USART_InitStructure.USART_Parity = USART_Parity_No;
  156.     USART_InitStructure.USART_HardwareFlowControl =
  157.             USART_HardwareFlowControl_None;
  158.     USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
  159.     USART_Init(OW_USART, &USART_InitStructure);
  160.  
  161.     // отправляем 0xf0 на скорости 9600
  162.     USART_ClearFlag(OW_USART, USART_FLAG_TC);
  163.     USART_SendData(OW_USART, 0xf0);
  164.     while (USART_GetFlagStatus(OW_USART, USART_FLAG_TC) == RESET) {
  165. #ifdef OW_GIVE_TICK_RTOS
  166.         taskYIELD();
  167. #endif
  168.     }
  169.  
  170.     ow_presence = USART_ReceiveData(OW_USART);
  171.  
  172.     USART_InitStructure.USART_BaudRate = 115200;
  173.     USART_InitStructure.USART_WordLength = USART_WordLength_8b;
  174.     USART_InitStructure.USART_StopBits = USART_StopBits_1;
  175.     USART_InitStructure.USART_Parity = USART_Parity_No;
  176.     USART_InitStructure.USART_HardwareFlowControl =
  177.             USART_HardwareFlowControl_None;
  178.     USART_InitStructure.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;
  179.     USART_Init(OW_USART, &USART_InitStructure);
  180.  
  181.     if (ow_presence != 0xf0) {
  182.         return OW_OK;
  183.     }
  184.  
  185.     return OW_NO_DEVICE;
  186. }
  187.  
  188.  
  189. //-----------------------------------------------------------------------------
  190. // процедура общения с шиной 1-wire
  191. // sendReset - посылать RESET в начале общения.
  192. //      OW_SEND_RESET или OW_NO_RESET
  193. // command - массив байт, отсылаемых в шину. Если нужно чтение - отправляем OW_READ_SLOTH
  194. // cLen - длина буфера команд, столько байт отошлется в шину
  195. // data - если требуется чтение, то ссылка на буфер для чтения
  196. // dLen - длина буфера для чтения. Прочитается не более этой длины
  197. // readStart - с какого символа передачи начинать чтение (нумеруются с 0)
  198. //      можно указать OW_NO_READ, тогда можно не задавать data и dLen
  199. //-----------------------------------------------------------------------------
  200. uint8_t OW_Send(uint8_t sendReset, uint8_t *command, uint8_t cLen,
  201.         uint8_t *data, uint8_t dLen, uint8_t readStart) {
  202.  
  203.             DMA_InitTypeDef DMA_InitStructure;
  204.  
  205.     // если требуется сброс - сбрасываем и проверяем на наличие устройств
  206.     if (sendReset == OW_SEND_RESET) {
  207.         if (OW_Reset() == OW_NO_DEVICE) {
  208.             return OW_NO_DEVICE;
  209.         }
  210.     }
  211.  
  212.     while (cLen > 0) {
  213.  
  214.         OW_toBits(*command, ow_buf);
  215.         command++;
  216.         cLen--;
  217.  
  218.  
  219.         // DMA на чтение
  220.         DMA_DeInit(OW_DMA_CH_RX);
  221.         DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t) &(USART2->DR);
  222.         DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t) ow_buf;
  223.         DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;
  224.         DMA_InitStructure.DMA_BufferSize = 8;
  225.         DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
  226.         DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
  227.         DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;
  228.         DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;
  229.         DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;
  230.         DMA_InitStructure.DMA_Priority = DMA_Priority_Low;
  231.         DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;
  232.         DMA_Init(OW_DMA_CH_RX, &DMA_InitStructure);
  233.  
  234.         // DMA на запись
  235.         DMA_DeInit(OW_DMA_CH_TX);
  236.         DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t) &(USART2->DR);
  237.         DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t) ow_buf;
  238.         DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralDST;
  239.         DMA_InitStructure.DMA_BufferSize = 8;
  240.         DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
  241.         DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
  242.         DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;
  243.         DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;
  244.         DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;
  245.         DMA_InitStructure.DMA_Priority = DMA_Priority_Low;
  246.         DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;
  247.         DMA_Init(OW_DMA_CH_TX, &DMA_InitStructure);
  248.  
  249.         // старт цикла отправки
  250.         USART_ClearFlag(OW_USART, USART_FLAG_RXNE | USART_FLAG_TC | USART_FLAG_TXE);
  251.         USART_DMACmd(OW_USART, USART_DMAReq_Tx | USART_DMAReq_Rx, ENABLE);
  252.         DMA_Cmd(OW_DMA_CH_RX, ENABLE);
  253.         DMA_Cmd(OW_DMA_CH_TX, ENABLE);
  254.  
  255.         // Ждем, пока не примем 8 байт
  256.         while (DMA_GetFlagStatus(OW_DMA_FLAG) == RESET){
  257. #ifdef OW_GIVE_TICK_RTOS
  258.             taskYIELD();
  259. #endif
  260.         }
  261.  
  262.         // отключаем DMA
  263.         DMA_Cmd(OW_DMA_CH_TX, DISABLE);
  264.         DMA_Cmd(OW_DMA_CH_RX, DISABLE);
  265.         USART_DMACmd(OW_USART, USART_DMAReq_Tx | USART_DMAReq_Rx, DISABLE);
  266.  
  267.         // если прочитанные данные кому-то нужны - выкинем их в буфер
  268.         if (readStart == 0 && dLen > 0) {
  269.             *data = OW_toByte(ow_buf);
  270.             data++;
  271.             dLen--;
  272.         } else {
  273.             if (readStart != OW_NO_READ) {
  274.                 readStart--;
  275.             }
  276.         }
  277.     }
  278.  
  279.     return OW_OK;
  280. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement