app.c 9.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349
  1. /**
  2. ******************************************************************************
  3. * Tranceiver Project
  4. ******************************************************************************
  5. * This project works as a 433MHz tranceiver between a Raspberry Pi and a
  6. * 433MHz tranceiver module. Target to run on a slower low power STM32L-CPU
  7. * System clock is 32MHz
  8. *
  9. * SysTick-counter is setup to handle the LED-flashing
  10. * The systick int is 1mS and it calles the LED-Handler
  11. *
  12. * TIM2 is set to sample the Rx-input in a 10uS period. TIM2_IRQHandler()
  13. * HW is set to 32 prescaler + 10 counter period
  14. *
  15. * TIM3 handles the micros() function by counting a 1mS variable.
  16. * HW is set to 32 prescaler + 1000 counter period
  17. *
  18. * The USART1 is used for comm to R-Pi. Also handled with interrupts.
  19. *
  20. * IO-Pins:
  21. * PA1 Output ENABLE
  22. * PA2 Output TX_ENABLE
  23. * PA3 Output TX_DATA
  24. * PB3 Input RX_DATA
  25. * PB6 Output LED_BLUE
  26. * PB7 Output LED_GREEN
  27. *
  28. ******************************************************************************
  29. */
  30. #include <stdio.h>
  31. #include "sw_fifo.h"
  32. #include "app.h"
  33. #include "main.h"
  34. #include "queue.h"
  35. #include "led_blink.h"
  36. #include "nexa.h"
  37. #include "temp1.h"
  38. #include "temp2.h"
  39. #include "transmit.h"
  40. #include "stm32l1xx_hal.h"
  41. #include "stm32l1xx_hal_gpio.h"
  42. volatile unsigned long width;
  43. boolean disableRx = true;
  44. void setup() {
  45. disableRx = true;
  46. digitalWrite(enablePin, LOW);
  47. digitalWrite(txEnablePin, LOW);
  48. digitalWrite(txPin, LOW);
  49. // ------------------ INIT THE TRANCEIVER -------------------------
  50. // From powerdown mode (pin 4-5-6 low),
  51. // 1. Drive high pin 6 (ENABLE)
  52. // 2. After 20us drive high pin 5 (RX/TX)200us, hold on 40us
  53. // 3. Drive down 20us pin 6 (ENABLE).
  54. digitalWrite(enablePin, HIGH); delayMicroseconds( 20 );
  55. digitalWrite(txEnablePin, HIGH); delayMicroseconds( 200 ); digitalWrite(txEnablePin, LOW);
  56. delayMicroseconds( 40 );
  57. digitalWrite(enablePin, LOW); delayMicroseconds( 20 ); digitalWrite(enablePin, HIGH);
  58. delayMicroseconds( 200 );
  59. // ------------------ INIT THE TRANCEIVER -------------------------
  60. rcvInitQueue();
  61. disableRx = false;
  62. }
  63. /*
  64. //button = (int)HAL_GPIO_ReadPin(GPIOA,GPIO_PIN_0);
  65. digitalWrite(enablePin, blue);
  66. //HAL_GPIO_WritePin(GPIOB,GPIO_PIN_6,(GPIO_PinState)blue); //blue);
  67. */
  68. // Debug
  69. __IO unsigned long long data[11] = {0,0,0,0,0,0,0,0,0,0,0};
  70. __IO int data_cnt=0;
  71. //********************************************************************
  72. // LOOP
  73. //
  74. // Test-code: <NT1B5C1D83>
  75. //********************************************************************
  76. #define SER_RX_MODE_WAIT 0
  77. #define SER_RX_MODE_RCV 1
  78. #define SER_RX_MODE_END 2
  79. void loop() {
  80. static int rxMode = SER_RX_MODE_WAIT;
  81. static int rxNum = 0;
  82. static unsigned char rxChars[20];
  83. static unsigned long last_rx_time = 0;
  84. static unsigned char txDataReady = 0;
  85. static unsigned long previous_x_data = 0;
  86. static unsigned long old_time=0;
  87. static unsigned long previous_temp1_x_data = 0;
  88. static unsigned long temp1_old_time=0;
  89. static char hex[100];
  90. static boolean firstRun = true;
  91. static unsigned int width;
  92. static unsigned long previous_now = 0; // Get the current time
  93. unsigned long now = millis(); // Get the current time
  94. // Check millis() for wrapping (after 49 days)
  95. if( previous_now > now ) {
  96. last_rx_time = 0; // Reset last rx time
  97. }
  98. // Display version information 5 sec after startup
  99. if( firstRun == true && now > 5000 ) {
  100. printf("\n\r433MHz STM32L Receiver module. Ver: 140111 08:02\n\r"); // **** VERSION ****
  101. firstRun = false;
  102. }
  103. if( rcvDeQueue(&width) ) {
  104. // ********** TEMP1 ***********
  105. if( nextPulseTemp1(width) ) {
  106. last_rx_time = now; // Set last rx time to now
  107. if( temp1_x_data != previous_temp1_x_data || now > (temp1_old_time+1000) ) {
  108. sprintf(hex,"<TR%08lX>",temp1_x_data);
  109. printf(hex);
  110. previous_temp1_x_data = temp1_x_data;
  111. blinkTheLED();
  112. }
  113. temp1_old_time = now;
  114. temp1ResetDecoder();
  115. }
  116. // ********** TEMP2 ***********
  117. if( nextPulseTemp2(width) ) {
  118. last_rx_time = now; // Set last rx time to now
  119. sprintf(hex,"<Tr%016llX>",temp2_x_data);
  120. printf(hex);
  121. blinkTheLED();
  122. temp2ResetDecoder();
  123. }
  124. // ***************** NEXA *********************
  125. if( nextPulseNexa(width) ) {
  126. last_rx_time = now; // Set last rx time to now
  127. if( x_data != previous_x_data || now > (old_time+1000) ) {
  128. sprintf(hex,"<NR%08lX>\n\r",x_data);
  129. printf(hex);
  130. previous_x_data = x_data;
  131. }
  132. old_time = now;
  133. resetDecoder();
  134. blinkTheLED();
  135. }
  136. }
  137. // Serial receive of the available buffer, only if we are not waiting to transmit something
  138. if( serialAvailable() > 0 && txDataReady == 0 ) {
  139. unsigned char c = serialRead();
  140. // Reset if we receive an '%'
  141. if( rxMode == SER_RX_MODE_WAIT && c == '%' ) {
  142. HAL_NVIC_SystemReset();
  143. }
  144. switch( rxMode ) {
  145. case SER_RX_MODE_WAIT:
  146. if( c == '<' ) {
  147. rxMode = SER_RX_MODE_RCV;
  148. rxNum = 0;
  149. }
  150. break;
  151. case SER_RX_MODE_RCV:
  152. if( (c >= '0' && c<= '9') || (c >= 'A' && c<= 'Z') ) {
  153. rxChars[rxNum++] = c;
  154. if( rxNum == 1 && rxChars[0] != 'N' ) {
  155. rxMode = SER_RX_MODE_WAIT;
  156. rxNum = 0;
  157. }
  158. else if( rxNum == 2 && rxChars[1] != 'T' ) {
  159. rxMode = SER_RX_MODE_WAIT;
  160. rxNum = 0;
  161. }
  162. else if( rxNum == 10 ) {
  163. rxMode = SER_RX_MODE_END;
  164. }
  165. }
  166. else {
  167. rxMode = SER_RX_MODE_WAIT;
  168. rxNum = 0;
  169. }
  170. break;
  171. case SER_RX_MODE_END:
  172. if( c == '>' ) {
  173. rxChars[rxNum] = '\0';
  174. txDataReady = 1; // Flag that we have something to transmit
  175. }
  176. rxMode = SER_RX_MODE_WAIT;
  177. rxNum = 0;
  178. break;
  179. }
  180. }
  181. if( txDataReady == 1 && (now > (last_rx_time+100)) ) { // Transmit if it has passed more than 50mS since last rx
  182. txDataReady = 0;
  183. blinkTheTxLED();
  184. sendNexaCodeStr(rxChars);
  185. }
  186. previous_now = now; // Store to check for wrapping of millis()
  187. }
  188. // ********************* ARCHIVE **********************
  189. /*
  190. void loop() {
  191. __IO int button;
  192. static unsigned int width;
  193. static unsigned long last_rx_time = 0;
  194. static unsigned long old_time=0;
  195. static unsigned long previous_x_data = 0;
  196. static unsigned char txDataReady = 0;
  197. static unsigned long txData = 0;
  198. static unsigned long previous_now = 0; // Get the current time
  199. unsigned long now = millis();
  200. // Check millis() for wrapping (after 49 days)
  201. if( previous_now > now ) {
  202. last_rx_time = 0; // Reset last rx time
  203. }
  204. // NEXA RX Loop
  205. if( rcvDeQueue(&width) ) {
  206. // ***************** TEMP1 *********************
  207. if( nextPulseTemp1(width) ) {
  208. static unsigned long long previous_temp1_x_data = 0;
  209. //if( previous_temp1_x_data != temp1_x_data ) {
  210. temp1_x_data = (temp1_x_data & 0x0FFF); // Just keep the temperature
  211. if( data_cnt<10 ) {
  212. data[data_cnt] = temp1_x_data;
  213. data_cnt++;
  214. }
  215. else {
  216. data_cnt=0;
  217. }
  218. blinkTheLED();
  219. //}
  220. previous_temp1_x_data = temp1_x_data;
  221. temp1ResetDecoder();
  222. }
  223. // ***************** NEXA *********************
  224. if( nextPulseNexa(width) ) {
  225. last_rx_time = now; // Set last rx time to now
  226. if( x_data != previous_x_data || now > (old_time+1000) ) {
  227. previous_x_data = x_data;
  228. // We have received a nexa code.
  229. }
  230. old_time = now;
  231. resetDecoder();
  232. blinkTheLED();
  233. }
  234. }
  235. if( txDataReady == 1 && (now > (last_rx_time+100)) ) { // Transmit if it has passed more than 50mS since last rx
  236. txDataReady = 0;
  237. sendNexaCode(txData);
  238. }
  239. previous_now = now; // Store to check for wrapping of millis()
  240. }
  241. */
  242. /*
  243. button = (int)HAL_GPIO_ReadPin(GPIOA,GPIO_PIN_0);
  244. if( button == 1 ) {
  245. sendNexaCode(708298896UL);
  246. }
  247. */
  248. /*
  249. volatile NEXA_QUEUE_DATA qd;
  250. qd.remote_id = (x_data & 0xFFFFFFC0) >>6;
  251. qd.group = (x_data & 0x00000020) >>5;
  252. qd.onOff = (x_data & 0x00000010) >>4;
  253. qd.channel = (x_data & 0x0000000C) >>2;
  254. qd.button = (x_data & 0x00000003);
  255. if( qd.remote_id == 11067170 && // This is the id of the white newer 8-button Nexa remote
  256. qd.group == 0 &&
  257. qd.channel == 0 &&
  258. qd.button == 0 ) {
  259. // We got the trigger code ! Yohoo
  260. // Now resend the same code (with one higher button value)
  261. qd.button++;
  262. //qd.remote_id -= 120;
  263. txData = ((qd.remote_id << 6) & 0xFFFFFFC0 );
  264. txData |= ((qd.group << 5) & 0x00000020 );
  265. txData |= ((qd.onOff << 4) & 0x00000010 );
  266. txData |= ((qd.channel << 2) & 0x0000000C );
  267. txData |= ((qd.button ) & 0x00000003 );
  268. txDataReady = 1; // Flag that we have something to transmit
  269. }
  270. */