aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--shared/protocol.c14
-rw-r--r--shared/protocol.h3
-rw-r--r--shared/util.c7
-rw-r--r--shared/util.h2
-rw-r--r--stm32f091/esp8266.c27
-rw-r--r--stm32f091/protocol.c8
-rw-r--r--stm32f091/server.c54
-rw-r--r--stm32f091/server.h13
-rw-r--r--stm32f091/setup.c3
9 files changed, 88 insertions, 43 deletions
diff --git a/shared/protocol.c b/shared/protocol.c
index ca0edc4..fcc84a4 100644
--- a/shared/protocol.c
+++ b/shared/protocol.c
@@ -3,6 +3,7 @@
#include <string.h>
#include "protocol.h"
+#include "util.h"
#define WS_CMD_MAP(parsed_cmd, name, code) \
if (strlen(parsed_cmd->argv[0]) == strlen(name) && strncmp(parsed_cmd->argv[0], name, strlen(name)) == 0) return code;
@@ -99,10 +100,7 @@ ws_s_protocol_req_parser_state* ws_protocol_req_parser_alloc() {
void ws_protocol_req_cmd_init(ws_s_protocol_req_parser_state* state) {
state->target = malloc(sizeof(ws_s_protocol_parsed_req_cmd) + sizeof(char*) * state->arg_len);
for (unsigned int i = 0; i < state->arg_len; i++)
- state->target->argv[i] = malloc(sizeof(char) * (state->args_len[i] + 1)); // segfaults on 2nd run?
- // state->target->argv stays empty according to debugger
- // goes to HardFault_Handler on 2nd iteration
- // this might be the stm running out of heap memory though i'm not sure
+ state->target->argv[i] = malloc(sizeof(char) * (state->args_len[i] + 1));
state->target->argc = state->arg_len;
@@ -138,3 +136,11 @@ void ws_protocol_req_cmd_free(ws_s_protocol_parsed_req_cmd* cmd) {
free(cmd);
return;
}
+
+unsigned short ws_protocol_get_header_size(ws_s_protocol_res* response) {
+ unsigned short size = 2; // comma and trailing newline
+ if (response->success == WS_PROTOCOL_CMD_RETURN_OK) size += 2; // ok
+ if (response->success == WS_PROTOCOL_CMD_RETURN_ERROR) size += 5; // error
+ size += ws_log16(response->msg->bytes); // amount of characters for message size (hex)
+ return size;
+} \ No newline at end of file
diff --git a/shared/protocol.h b/shared/protocol.h
index fbe29d6..5bcb114 100644
--- a/shared/protocol.h
+++ b/shared/protocol.h
@@ -5,7 +5,7 @@
#include "bin.h"
-#define WS_PROTOCOL_CMD_MAX_ARGUMENTS (1)
+#define WS_PROTOCOL_CMD_MAX_ARGUMENTS (2)
#define WS_PROTOCOL_CMD_BUFFER_LEN (40)
#define WS_PROTOCOL_CMD_AMOUNT (1)
@@ -148,3 +148,4 @@ static ws_protocol_res_handler_t* g_ws_protocol_res_handlers[WS_PROTOCOL_CMD_AMO
[WS_PROTOCOL_CMD_LAST_RECORDS] = &ws_protocol_res_last_records,
};
+unsigned short ws_protocol_get_header_size(ws_s_protocol_res* response); \ No newline at end of file
diff --git a/shared/util.c b/shared/util.c
new file mode 100644
index 0000000..ea972b0
--- /dev/null
+++ b/shared/util.c
@@ -0,0 +1,7 @@
+#include "util.h"
+
+unsigned int ws_log16(unsigned int x) {
+ unsigned int l = 0;
+ while (x >>= 4) ++l; // bitshift right by 4 until x == 0
+ return l;
+} \ No newline at end of file
diff --git a/shared/util.h b/shared/util.h
index f39ff34..94a3dfe 100644
--- a/shared/util.h
+++ b/shared/util.h
@@ -2,3 +2,5 @@
#define WS_MIN(a, b) (((a) < (b)) ? (a) : (b))
#define WS_MAX(a, b) (((a) > (b)) ? (a) : (b))
+
+unsigned int ws_log16(unsigned int x);
diff --git a/stm32f091/esp8266.c b/stm32f091/esp8266.c
index d45954e..db134a0 100644
--- a/stm32f091/esp8266.c
+++ b/stm32f091/esp8266.c
@@ -80,30 +80,3 @@ void ws_esp8266_set_mac() {
void ws_esp8266_set_ip() {
ws_esp8266_send_seq("AT+CIPSTA=\"" WS_ESP8266_WLAN_IP "\"\r\n");
}
-
-// TODO: refactor code from here to EOF
-void ws_esp8266_ATsendCommand(uint8_t* data){
- char dataChar[20];
- uint8_t Tx_send[]="AT+CIPSEND=0,";
-
- itoa(strlen((char*)data),dataChar,10);
- strcat((char*)Tx_send,dataChar);
- strcat((char*)Tx_send,"\r\n");
- HAL_UART_Transmit(&huart1, Tx_send, strlen((char*)Tx_send),1000);
- HAL_Delay(2000);
- HAL_UART_Transmit(&huart1, data, strlen((char*)data),1000);
- HAL_Delay(1000);
- HAL_UART_Transmit(&huart2, data, strlen((char*)data),1000);
- HAL_Delay(5000);
-}
-void ws_esp8266_close(){
-
- uint8_t Tx_close[]="AT+CIPCLOSE=0\r\n";
-
-
- HAL_UART_Transmit(&huart1, Tx_close,strlen((char*)Tx_close), 100);
-
- HAL_Delay(3000);
-
-}
-
diff --git a/stm32f091/protocol.c b/stm32f091/protocol.c
index 589ee5d..3a8d78b 100644
--- a/stm32f091/protocol.c
+++ b/stm32f091/protocol.c
@@ -3,6 +3,8 @@
#include "../shared/protocol.h"
#include "backlog.h"
#include "util.h"
+#include "server.h"
+#include "esp8266.h"
void ws_protocol_res_last_records(ws_s_protocol_parsed_req_cmd* parsed_cmd, ws_s_protocol_res* response, bool send) {
static unsigned int record_amount = 0;
@@ -16,6 +18,7 @@ void ws_protocol_res_last_records(ws_s_protocol_parsed_req_cmd* parsed_cmd, ws_s
response->csh = true;
response->msg = ws_bin_s_alloc(0);
response->msg->bytes = strlen(response_header) + response_line_size * record_amount;
+ ws_server_req_respond_start(0, response->msg->bytes + ws_protocol_get_header_size(response));
} else {
ws_protocol_send_data(response_header, strlen(response_header));
char line[response_line_size + 1]; // +1 for null terminator -> sprintf
@@ -24,10 +27,11 @@ void ws_protocol_res_last_records(ws_s_protocol_parsed_req_cmd* parsed_cmd, ws_s
sprintf(line, "%04x,%02x,%02x,%02x\n", record->id, record->sens_temperature, record->sens_humidity, record->sens_atm_pressure);
ws_protocol_send_data(line, response_line_size);
}
+ ws_protocol_send_data("\r\n", 2); // test
}
}
void ws_protocol_send_data(const char* data, unsigned int length) {
- //TODO: implement on esp data channels
- HAL_UART_Transmit(&huart2, (uint8_t*) data, length, HAL_MAX_DELAY);
+ ws_server_buffer_send_append((uint8_t*) data, length);
+ // HAL_UART_Transmit(&huart1, (uint8_t*) data, length, HAL_MAX_DELAY);
}
diff --git a/stm32f091/server.c b/stm32f091/server.c
index 7e44774..d4f7e20 100644
--- a/stm32f091/server.c
+++ b/stm32f091/server.c
@@ -9,7 +9,7 @@
#include "setup.h"
#include "consts.h"
-static ws_s_server_parser g_ws_server_parser = {
+ws_s_server_parser g_ws_server_parser = {
.last_response = WS_SERVER_RC_NONE,
.mode = WS_SERVER_LM_IDLE,
@@ -20,7 +20,7 @@ static ws_s_server_parser g_ws_server_parser = {
};
static ws_s_protocol_req_parser_state* g_ws_protocol_parsers[WS_SERVER_MAX_CHANNELS] = {0};
-
+static unsigned int g_ws_esp8266_dma_tx_buffer_index = 0;
void ws_server_req_parse_byte(unsigned int channel, uint8_t byte, bool ignore) {
if (ignore) return;
@@ -80,6 +80,9 @@ void ws_server_req_incoming(uint8_t* data, size_t size) {
if (next_few_bytes_are("+IPD,")) {
i += 4; // skip I, P, D, and comma
g_ws_server_parser.mode = WS_SERVER_LM_IPD_LISTENING;
+ } else if (byte == '>') {
+ g_ws_server_parser.mode = WS_SERVER_LM_CIPSEND_LISTENING;
+ ws_server_buffer_send_finish();
}
break;
}
@@ -114,6 +117,7 @@ void ws_server_req_incoming(uint8_t* data, size_t size) {
g_ws_server_parser.channel_data_length = 0;
g_ws_server_parser.channel_listen_mode = WS_SERVER_CL_CHANNEL_ID;
ws_server_req_finish(g_ws_server_parser.current_channel, g_ws_server_parser.channel_data_ignore);
+ g_ws_server_parser.mode = WS_SERVER_LM_IDLE;
}
break;
}
@@ -121,6 +125,14 @@ void ws_server_req_incoming(uint8_t* data, size_t size) {
}
break;
}
+ case WS_SERVER_LM_CIPSEND_LISTENING: {
+ if (next_few_bytes_are("SEND OK")) {
+ i += 6;
+ // g_ws_server_parser.mode = WS_SERVER_LM_IDLE;
+ ws_server_req_respond_end(0);
+ }
+ break;
+ }
default: {}
}
}
@@ -132,9 +144,39 @@ void ws_server_send(uint8_t* data, size_t size) {
while (g_ws_server_parser.mode != WS_SERVER_LM_IDLE) {};
}
-void ws_server_req_respond(unsigned int channel, uint8_t* data, size_t size) {
- uint8_t Tx_send[]="AT+CIPSEND=0,LEN:";
- uint8_t Tx_close[]="AT+CIPCLOSE=0\r\n";
- return;
+void ws_server_buffer_send_append(uint8_t* data, size_t size) {
+ // TODO: buffer overrun protection
+ // while (!__HAL_DMA_GET_FLAG(&hdma_usart1_tx, DMA_FLAG_TC2)); // make sure buffer isn't used
+ strncpy((char*) &g_ws_esp8266_dma_tx_buffer[g_ws_esp8266_dma_tx_buffer_index], (char*) data, size); // append string
+ g_ws_esp8266_dma_tx_buffer_index += size; // shift head
+}
+
+void ws_server_buffer_send_finish() {
+#ifdef WS_DBG_PRINT_ESP_OVER_USART2
+ uint8_t green[] = { 0x1b, 0x5b, 0x33, 0x32, 0x6d };
+ HAL_UART_Transmit(&huart2, green, sizeof(green), 100);
+ HAL_UART_Transmit(&huart2, g_ws_esp8266_dma_tx_buffer, strlen((char*) g_ws_esp8266_dma_tx_buffer), 100);
+#endif
+
+ HAL_UART_Transmit_DMA(&huart1, g_ws_esp8266_dma_tx_buffer, strlen((char*) g_ws_esp8266_dma_tx_buffer));
+ __HAL_UART_ENABLE_IT(&huart1, UART_IT_TXE);
+ g_ws_esp8266_dma_tx_buffer_index = 0;
+ while (!__HAL_DMA_GET_FLAG(&hdma_usart1_tx, DMA_FLAG_TC2));
+}
+
+void ws_server_req_respond_start(unsigned int channel, size_t size) {
+ char* cmd = NULL;
+ size_t len = asiprintf(&cmd, "AT+CIPSEND=%d,%d\r\n", channel, size);
+ g_ws_server_parser.mode = WS_SERVER_LM_CMD_ECHO;
+ ws_esp8266_send((uint8_t*) cmd, len);
+ while (!__HAL_DMA_GET_FLAG(&hdma_usart1_tx, DMA_FLAG_TC2));
+}
+
+void ws_server_req_respond_end(unsigned int channel) {
+ char* cmd = NULL;
+ size_t len = asiprintf(&cmd, "AT+CIPCLOSE=%d\r\n", channel);
+ g_ws_server_parser.mode = WS_SERVER_LM_CMD_ECHO;
+ ws_esp8266_send((uint8_t*) cmd, len);
+ while (!__HAL_DMA_GET_FLAG(&hdma_usart1_tx, DMA_FLAG_TC2));
}
diff --git a/stm32f091/server.h b/stm32f091/server.h
index 44882e4..128b579 100644
--- a/stm32f091/server.h
+++ b/stm32f091/server.h
@@ -9,6 +9,7 @@ typedef enum {
WS_SERVER_LM_STATUS_CODE, /** @brief listen for busy, ERROR or OK */
WS_SERVER_LM_IDLE, /** @brief listen for incoming +IPD commands */
WS_SERVER_LM_IPD_LISTENING, /** @brief +IPD received, now reading data */
+ WS_SERVER_LM_CIPSEND_LISTENING, /** @brief AT+CIPSEND sent, now reading data */
} ws_e_server_listen_mode;
typedef enum {
@@ -34,6 +35,9 @@ typedef struct {
bool channel_data_ignore;
} ws_s_server_parser;
+/** @brief global server parser struct */
+extern ws_s_server_parser g_ws_server_parser;
+
/**
* @brief +IPD incoming request handler
*
@@ -46,8 +50,10 @@ typedef struct {
*/
void ws_server_req_incoming(uint8_t* data, size_t size);
-/** @brief send response to incoming request on specific channel */
-void ws_server_req_respond(unsigned int channel, uint8_t* data, size_t size);
+/** @brief send AT response header for incoming request on specific channel */
+void ws_server_req_respond_start(unsigned int channel, size_t size);
+/** @brief send AT tcp close on specific channel */
+void ws_server_req_respond_end(unsigned int channel);
/** @brief send data to esp, waiting until server returns to idle mode */
void ws_server_send(uint8_t* data, size_t size);
@@ -74,3 +80,6 @@ void ws_server_req_parse_byte(unsigned int channel, uint8_t byte, bool ignore);
* @param ignore ignore mode
*/
void ws_server_req_finish(unsigned int channel, bool ignore);
+
+void ws_server_buffer_send_append(uint8_t* data, size_t size);
+void ws_server_buffer_send_finish();
diff --git a/stm32f091/setup.c b/stm32f091/setup.c
index 5b6c6a4..1971809 100644
--- a/stm32f091/setup.c
+++ b/stm32f091/setup.c
@@ -8,6 +8,7 @@
#include "esp8266.h"
#include "setup.h"
#include "backlog.h"
+#include "server.h"
I2C_HandleTypeDef hi2c1 = {
.Instance = I2C1,
@@ -101,7 +102,7 @@ void ws_io_setup() {
ws_esp8266_set_ip();
#endif
ws_esp8266_ap_client_mode();
- ws_esp8266_connect();
+ do ws_esp8266_connect(); while (g_ws_server_parser.last_response == WS_SERVER_RC_ERR);
ws_esp8266_start_tcp_server();
}