Su Esp32 (e piu' in generale sui microcontrollori) la libreria Protobuf non puo' funzionare e quindi si deve usare nanopb (nano proto buffer) https://github.com/nanopb/nanopb
Il seguente progetto e' stato creato usando il plugin Esp-Idf di VSCode
Per utilizzarla si deve prima installare il compilare protoc e poi scaricare e compilare il pacchetto nanopb da GitHub ...questo servira' come plugin per protoc
Si procede quindi con il seguente comando che genera i file sensor.pb.c e sensor.pb.h dove sono inserite le classi per la lettura scrittura del file sensor.proto. questi due file sono da inserire nella main del progetto mentre i file pb_common.c pb_common.h pb_decode.c pb_decode.h pc_encode.c e pb_encode.h si inseriscono nel folder nanopb all'interno del folder main
protoc --plugin=protoc-gen-nanopb=/home/luca/nanopb/generator/protoc-gen-nanopb --nanopb_out=./ --proto_path=/home/luca/nanopb/generator/proto sensor.proto
sensor.proto
syntax = "proto3";
message SensorData {
int32 id = 1;
float temperature = 2;
float humidity = 3;
}
Si modifica quindi il file CMakeLists.txt per puntare i nuovi file
idf_component_register(
SRCS
"main.c"
"sensor.pb.c"
"nanopb/pb_encode.c"
"nanopb/pb_decode.c"
"nanopb/pb_common.c"
INCLUDE_DIRS
"."
"nanopb"
)
e si puo' compilare questo semplice programma di esempio sull'utilizzo di nanopb
#include <stdio.h>
#include "sensor.pb.h"
#include "pb_encode.h"
#include "pb_decode.h"
#include "driver/uart.h"
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
void app_main(void)
{
const uart_config_t uart_config = {
.baud_rate = 115200,
.data_bits = UART_DATA_8_BITS,
.parity = UART_PARITY_DISABLE,
.stop_bits = UART_STOP_BITS_1,
.flow_ctrl = UART_HW_FLOWCTRL_DISABLE
};
uart_driver_install(UART_NUM_0, 1024, 0, 0, NULL, 0);
uart_param_config(UART_NUM_0, &uart_config);
const char *msg = "Hello from UART0 via USB!\n";
uart_write_bytes(UART_NUM_0, msg, strlen(msg));
vTaskDelay(pdMS_TO_TICKS(3000));
printf("USB CDC active\n");
vTaskDelay(pdMS_TO_TICKS(500)); // Delay to let USB CDC connect
uint8_t buffer[128];
pb_ostream_t stream = pb_ostream_from_buffer(buffer, sizeof(buffer));
SensorData da = SensorData_init_zero;
da.id = 42;
da.temperature = 23.5;
da.humidity = 55.2;
if (pb_encode(&stream, SensorData_fields, &da)) {
size_t message_length = stream.bytes_written;
// Send buffer over serial, BLE, etc.
} else {
//Serial.println("Encoding failed!");
}
size_t message_length = stream.bytes_written;
SensorData da_r = SensorData_init_zero;
//int received_length = 0;
pb_istream_t str = pb_istream_from_buffer(buffer, message_length);
while(1){
if (pb_decode(&str, SensorData_fields, &da_r)) {
char str_out[32];
snprintf(str_out, sizeof(str_out), "%.2f\n", da_r.humidity);
uart_write_bytes(UART_NUM_0, str_out, strlen(str_out));
printf("Temp: %.2f, Humidity: %.2f\n",da_r.temperature, da_r.humidity);
} else {
uart_write_bytes(UART_NUM_0, "Decoding error\n", strlen("Decoding error\n"));
printf("Error decoding\n");
}
vTaskDelay(pdMS_TO_TICKS(1000));}
}
Nessun commento:
Posta un commento