adjusted, but too few SPIs

This commit is contained in:
2021-01-09 23:32:01 +01:00
parent 6671348d22
commit e9914f5bb1
37 changed files with 10253 additions and 744 deletions

View File

@ -5,38 +5,16 @@
#include <spi.h>
#include <assert.h>
#define CONFIG_MAGIC 0xdead000a
#define DEVICE_MAGIC 0xaffe0000
#define CONFIG_MAGIC 0xdead0001
typedef struct __attribute__((__packed__)) s_configBlock {
uint32_t configMagic;
char deviceName[16];
uint8_t macAddress[6];
int32_t frontendThreshold;
char brokerName[64];
char watchdogTopic[64];
char startupTopic[64];
char statusTopic[64];
char mbusDataTopic[64];
char syslogServerName[64];
uint8_t numOfDeviceBlocks;
uint8_t filler[1];
uint8_t filler[6];
} t_configBlock;
#define MAX_MBUS_DEVICES 16
#define MBUSDEVICE_NAMELENGTH 16
#define MBUSDEVICE_NUM_OF_CONSIDEREDFIELDS 4
typedef struct __attribute__((__packed__)) s_deviceBlock {
uint32_t deviceMagic;
char deviceName[MBUSDEVICE_NAMELENGTH];
uint8_t address;
int8_t consideredField[MBUSDEVICE_NUM_OF_CONSIDEREDFIELDS];
int32_t period;
uint8_t filler[3];
} t_deviceBlock;
void configInit();
t_configBlock* getConfig();

View File

@ -27,13 +27,11 @@ typedef struct __attribute__((__packed__)) s_deviceStats {
static_assert((sizeof(t_deviceStats) <= EEPROM_WRITE_BLOCK_SIZE), "t_deviceStats has illegal size, must be less than or equal 32");
static_assert((sizeof(t_configBlock) % 32 == 0), "t_configBlock has illegal size, must be dividable by 32");
static_assert((sizeof(t_deviceBlock) % 32 == 0), "t_deviceBlock has illegal size, must be dividable by 32");
#define EEPROM_BASE_ADDR 0
#define EEPROM_DEVICE_STATS_ADDR 32
#define EEPROM_CONFIG_BLOCK_ADDR 64
#define EEPROM_DEVICE_BLOCK_BASE_ADDR (EEPROM_CONFIG_BLOCK_ADDR + sizeof(t_configBlock))
@ -44,7 +42,5 @@ void eepromSpiTxCpltCallback(SPI_HandleTypeDef *hspi);
t_deviceStats* getGlobalDeviceStats();
void eepromReadConfigBlock(t_configBlock *destConfigBlock);
void eepromWriteConfigBlock(t_configBlock *srcConfigBlock);
void eepromReadDeviceBlock(uint8_t blockNum, t_deviceBlock *destDeviceBlock);
void eepromWriteDeviceBlock(uint8_t blockNum, t_deviceBlock *srcDeviceBlock);
#endif /* EEPROM_H_ */

View File

@ -1,13 +0,0 @@
#ifndef _FRONTEND_H_
#define _FRONTEND_H_
#include <stdint.h>
#include <adc.h>
void frontendInit();
void frontendAdcCallback(ADC_HandleTypeDef* hadc);
void frontendEnable();
void frontendDisable();
#endif // _FRONTEND_H_

View File

@ -29,7 +29,7 @@ void logFree();
// return value can be ignored, it is only used in test
int logMsg(const char *format, ...);
int coloredMsg(const t_logColor color, bool syslogToo, const char *format, ...);
int coloredMsg(const t_logColor color, const char *format, ...);
#ifdef LOGGER_OUTPUT_BY_INTERRUPT
void debugTxCpltCallback(UART_HandleTypeDef *huart);

View File

@ -2,74 +2,19 @@
#include <logger.h>
#include <string.h>
#include <mbusComm.h>
#include <loopCtrl.h>
// clear statistics
static bool clearCmd(uint8_t argc, char **args) {
t_mbusCommStats zeroedStats = { .mbusRequestCnt = 0, .mbusErrorCnt = 0, .uartOctetCnt = 0, .uartOverrunCnt = 0, .uartFramingErrCnt = 0, .uartParityErrCnt = 0, .uartNoiseErrCnt = 0 };
mbusCommSetStats(zeroedStats);
coloredMsg(LOG_YELLOW, true, "ch cc global statistics cleared");
coloredMsg(LOG_YELLOW, "ch cc global statistics cleared");
return true;
}
static bool mbusCommEnableCmd(uint8_t argc, char **args) {
bool retCode = true;
if (argc == 2) {
if (0 == strcmp("false", args[1])) {
mbusCommEnable(false);
coloredMsg(LOG_YELLOW, true, "ch mcec Meterbus communication disabled");
} else if (0 == strcmp("true", args[1])) {
mbusCommEnable(true);
coloredMsg(LOG_YELLOW, true, "ch mcec Meterbus communication enabled");
} else {
retCode = false;
}
} else {
retCode = false;
}
return retCode;
}
static bool loopEnableCmd(uint8_t argc, char **args) {
bool retCode = true;
if (argc == 2) {
if (0 == strcmp("false", args[1])) {
loopDisable();
coloredMsg(LOG_YELLOW, true, "ch lec loop disabled");
} else if (0 == strcmp("true", args[1])) {
loopEnable();
coloredMsg(LOG_YELLOW, true, "ch lec loop enabled");
} else {
retCode = false;
}
} else {
retCode = false;
}
return retCode;
}
const cmd_t ADMIN_COMMANDS[] = {
{ .name = "clear", .cmdFunc = clearCmd,
.help = \
"clear ................................ Clears the global Meterbus\n\r" \
" statistics\n\r"
},
{ .name = "mbusCommEnable", .cmdFunc = mbusCommEnableCmd,
.help = \
"mbusCommEnable true|false ............ Enables or disables the Meterbus\n\r" \
" communication\n\r"
},
{ .name = "loopEnable", .cmdFunc = loopEnableCmd,
.help = \
"loopEnable true|false ................ Enables or disables the loop.\n\r" \
" Disable Meterbus communication\n\r" \
" first if you want to disable the\n\r" \
" for a longer time, otherwise the\n\r" \
" request will enable it again\n\r"
"clear ................................ Clears the global statistics\n\r"
},
{ .name = "END_OF_CMDS", .help = "",.cmdFunc = NULL }
};

View File

@ -91,7 +91,7 @@ static int8_t cmdExecuteCommand(uint8_t *cmdLine, bool resetSpecialModes) {
commands = getConfigCommands();
}
coloredMsg(LOG_YELLOW, true, "ch cec cmdLine is %s", cmdLine);;
coloredMsg(LOG_YELLOW, "ch cec cmdLine is %s", cmdLine);;
#define MAX_NUM_OF_ARGS 8
char *args[MAX_NUM_OF_TASKS];
@ -107,7 +107,7 @@ static int8_t cmdExecuteCommand(uint8_t *cmdLine, bool resetSpecialModes) {
char *cmd = args[0];
int8_t retCode = 0;
coloredMsg(LOG_YELLOW, true, "ch cec cmd is %s, number of arguments %d", cmd, argc);
coloredMsg(LOG_YELLOW, "ch cec cmd is %s, number of arguments %d", cmd, argc);
if (0 == strcmp(cmd, "quit")) {
messageToSend = (uint8_t*)GOODBYE_MSG;
@ -128,16 +128,16 @@ static int8_t cmdExecuteCommand(uint8_t *cmdLine, bool resetSpecialModes) {
}
messageToSend = NULL;
} else if (0 == strcmp(cmd, "enable")) {
coloredMsg(LOG_YELLOW, true, "ch cec enable admin mode");
coloredMsg(LOG_YELLOW, "ch cec enable admin mode");
adminMode = true;
retCode = 1;
} else if (0 == strcmp(cmd, "disable")) {
coloredMsg(LOG_YELLOW, true, "ch cec disable admin mode");
coloredMsg(LOG_YELLOW, "ch cec disable admin mode");
adminMode = false;
configMode = false;
retCode = 3;
} else if (0 == strcmp(cmd, "config")) {
coloredMsg(LOG_YELLOW, true, "ch cec enable config mode");
coloredMsg(LOG_YELLOW, "ch cec enable config mode");
configMode = true;
retCode = 2;
} else {
@ -157,7 +157,7 @@ static int8_t cmdExecuteCommand(uint8_t *cmdLine, bool resetSpecialModes) {
}
if (messageToSend) {
coloredMsg(LOG_YELLOW, true, "ch cec command finally returns %s", messageToSend);
coloredMsg(LOG_YELLOW, "ch cec command finally returns %s", messageToSend);
send(CMD_SOCK, messageToSend, strlen((char*)messageToSend));
}
@ -192,13 +192,13 @@ static void cmdHandlerEngine(void *handle) {
if (isNetworkAvailable()) {
switch (state) {
case CH_INIT:
coloredMsg(LOG_YELLOW, false, "ch che initializing socket");
coloredMsg(LOG_YELLOW, "ch che initializing socket");
res = socket(CMD_SOCK, Sn_MR_TCP, cmdPort, SF_IO_NONBLOCK);
coloredMsg(LOG_YELLOW, false, "ch che socket returns %d", res);
coloredMsg(LOG_YELLOW, "ch che socket returns %d", res);
if (res == CMD_SOCK) {
coloredMsg(LOG_YELLOW, false, "ch che socket is initialized");
coloredMsg(LOG_YELLOW, "ch che socket is initialized");
state = CH_LISTEN;
} else {
state = CH_ERROR;
@ -206,13 +206,13 @@ static void cmdHandlerEngine(void *handle) {
break;
case CH_LISTEN:
coloredMsg(LOG_YELLOW, false, "ch che listening");
coloredMsg(LOG_YELLOW, "ch che listening");
res = listen(CMD_SOCK);
coloredMsg(LOG_YELLOW, false, "ch che listen returns %d", res);
coloredMsg(LOG_YELLOW, "ch che listen returns %d", res);
if (res == SOCK_OK) {
coloredMsg(LOG_YELLOW, false, "ch che ok, waiting for established");
coloredMsg(LOG_YELLOW, "ch che ok, waiting for established");
state = CH_WAITING;
} else {
state = CH_ERROR;
@ -222,25 +222,25 @@ static void cmdHandlerEngine(void *handle) {
case CH_WAITING:
sockState = getSn_SR(CMD_SOCK);
if (sockState != SOCK_LISTEN) {
coloredMsg(LOG_YELLOW, false, "ch che socket state is 0x%02x", sockState);
coloredMsg(LOG_YELLOW, "ch che socket state is 0x%02x", sockState);
state = CH_DISCONNECT;
}
if (sockState == SOCK_ESTABLISHED) {
coloredMsg(LOG_YELLOW, true, "ch che connection is established");
coloredMsg(LOG_YELLOW, "ch che connection is established");
state = CH_BANNER;
}
break;
case CH_BANNER:
coloredMsg(LOG_YELLOW, false, "ch che send banner");
coloredMsg(LOG_YELLOW, "ch che send banner");
sockState = getSn_SR(CMD_SOCK);
if (sockState != SOCK_ESTABLISHED) {
coloredMsg(LOG_YELLOW, true, "ch che sockState is 0x%02x when trying to send banner", sockState);
coloredMsg(LOG_YELLOW, "ch che sockState is 0x%02x when trying to send banner", sockState);
state = CH_DISCONNECT;
} else {
resultSend = send(CMD_SOCK, (uint8_t*)banner, strlen(banner));
coloredMsg(LOG_YELLOW, false, "ch che sent banner, send returns 0x%02x", resultSend);
coloredMsg(LOG_YELLOW, "ch che sent banner, send returns 0x%02x", resultSend);
prompt = defaultPrompt;
resetSpecialModes = true;
state = CH_PROMPT;
@ -248,14 +248,14 @@ static void cmdHandlerEngine(void *handle) {
break;
case CH_PROMPT:
coloredMsg(LOG_YELLOW, false, "ch che send prompt");
coloredMsg(LOG_YELLOW, "ch che send prompt");
sockState = getSn_SR(CMD_SOCK);
if (sockState != SOCK_ESTABLISHED) {
coloredMsg(LOG_YELLOW, true, "ch che sockState is 0x%02x when trying to send promt", sockState);
coloredMsg(LOG_YELLOW, "ch che sockState is 0x%02x when trying to send promt", sockState);
state = CH_DISCONNECT;
} else {
sendFormatString("%s %s", getConfig()->deviceName, prompt);
coloredMsg(LOG_YELLOW, false, "ch che sent prompt %s %s", getConfig()->deviceName, prompt);
coloredMsg(LOG_YELLOW, "ch che sent prompt %s %s", getConfig()->deviceName, prompt);
state = CH_RECEIVE;
}
break;
@ -263,7 +263,7 @@ static void cmdHandlerEngine(void *handle) {
case CH_RECEIVE:
sockState = getSn_SR(CMD_SOCK);
if (sockState != SOCK_ESTABLISHED) {
coloredMsg(LOG_YELLOW, true, "ch che sockState is 0x%02x when trying to receive something", sockState);
coloredMsg(LOG_YELLOW, "ch che sockState is 0x%02x when trying to receive something", sockState);
state = CH_DISCONNECT;
} else {
receivedOctets = getSn_RX_RSR(CMD_SOCK);
@ -271,7 +271,7 @@ static void cmdHandlerEngine(void *handle) {
if (receivedOctets > 0) {
memset(receiveBuffer, 0, sizeof(receiveBuffer));
resultRecv = recv(CMD_SOCK, receiveBuffer, sizeof(receiveBuffer));
coloredMsg(LOG_YELLOW, false, "ch che recv returns 0x%02x", resultRecv);
coloredMsg(LOG_YELLOW, "ch che recv returns 0x%02x", resultRecv);
if (resultRecv > 0) {
if ((receiveBuffer[strlen((char*)receiveBuffer) - 1] == 0x0a) ||
(receiveBuffer[strlen((char*)receiveBuffer) - 1] == 0x0d)) {
@ -281,7 +281,7 @@ static void cmdHandlerEngine(void *handle) {
(receiveBuffer[strlen((char*)receiveBuffer) - 1] == 0x0d)) {
receiveBuffer[strlen((char*)receiveBuffer) - 1] = 0;
}
coloredMsg(LOG_YELLOW, false, "ch che received: %s", receiveBuffer);
coloredMsg(LOG_YELLOW, "ch che received: %s", receiveBuffer);
int8_t resCEC = cmdExecuteCommand(receiveBuffer, resetSpecialModes);
resetSpecialModes = false;
switch (resCEC) {
@ -310,29 +310,29 @@ static void cmdHandlerEngine(void *handle) {
break;
case CH_DISCONNECT:
coloredMsg(LOG_YELLOW, true, "ch che close our end");
coloredMsg(LOG_YELLOW, "ch che close our end");
resultDisconnect = disconnect(CMD_SOCK);
coloredMsg(LOG_YELLOW, true, "ch che disconnect returns 0x%02x", resultDisconnect);
coloredMsg(LOG_YELLOW, "ch che disconnect returns 0x%02x", resultDisconnect);
state = CH_DISCONNECT_WAIT;
break;
case CH_DISCONNECT_WAIT:
//coloredMsg(LOG_YELLOW, false, "ch che waiting after disconnect");
//coloredMsg(LOG_YELLOW, "ch che waiting after disconnect");
sockState = getSn_SR(CMD_SOCK);
//coloredMsg(LOG_YELLOW, false, "ch che sockState is 0x%02x", sockState);
//coloredMsg(LOG_YELLOW, "ch che sockState is 0x%02x", sockState);
if (sockState == SOCK_CLOSED) {
coloredMsg(LOG_YELLOW, true, "ch che socket is closed now");
coloredMsg(LOG_YELLOW, "ch che socket is closed now");
state = CH_INIT;
}
break;
case CH_ERROR:
coloredMsg(LOG_YELLOW, true, "ch che error state, will stop here");
coloredMsg(LOG_YELLOW, "ch che error state, will stop here");
schDel(cmdHandlerEngine, NULL);
state = CH_INIT;
schAdd(cmdHandlerEngine, NULL, 5000, 100);
coloredMsg(LOG_YELLOW, true, "ch che restart command handler engine in 5s");
coloredMsg(LOG_YELLOW, "ch che restart command handler engine in 5s");
break;
}
}

View File

@ -4,91 +4,13 @@
#include <config.h>
#include <eeprom.h>
#include <logger.h>
#include <mbusComm.h>
#define NUM_OF_DEFAULT_DEVICES 8
t_deviceBlock defaultDeviceBlock[] = {
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Total",
.address = 80,
.consideredField = { 0, 17, -1, -1 },
.period = 10,
.filler = { 0, 0, 0 }
},
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Computer",
.address = 85,
.consideredField = { 0, 4, 2, 3 },
.period = 10,
.filler = { 0, 0, 0 }
},
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Dryer",
.address = 81,
.consideredField = { 0, 4, 2, 3 },
.period = 10,
.filler = { 0, 0, 0 }
},
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Laundry",
.address = 82,
.consideredField = { 0, 4, 2, 3 },
.period = 10,
.filler = { 0, 0, 0 }
},
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Dishwasher",
.address = 83,
.consideredField = { 0, 4, 2, 3 },
.period = 10,
.filler = { 0, 0, 0 }
},
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Light",
.address = 84,
.consideredField = { 0, 4, 2, 3 },
.period = 10,
.filler = { 0, 0, 0 }
},
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Freezer",
.address = 86,
.consideredField = { 0, 4, 2, 3 },
.period = 10,
.filler = { 0, 0, 0 }
},
{
.deviceMagic = DEVICE_MAGIC,
.deviceName = "Fridge",
.address = 87,
.consideredField = { 0, 4, 2, 3 },
.period = 10,
.filler = { 0, 0, 0 }
}
};
t_configBlock defaultConfigBlock = {
.configMagic = CONFIG_MAGIC,
.deviceName = "MBGW3",
.macAddress = { 0x00, 0xA0, 0x57, 0x05, 0x3E, 0x0D },
.frontendThreshold = 240,
.brokerName = "mqttbroker",
.watchdogTopic = "IoT/Watchdog",
.startupTopic = "IoT/MBGW3/Startup",
.statusTopic = "IoT/MBGW3/Status",
.mbusDataTopic = "IoT/MBGW3/Measurement",
.syslogServerName = "syslogserver",
.numOfDeviceBlocks = NUM_OF_DEFAULT_DEVICES,
.filler = { 0 }
};
@ -113,11 +35,6 @@ void configInit() {
eepromWriteConfigBlock(&defaultConfigBlock);
coloredMsg(LOG_BLUE, false, "cfg ci Default configuration block written to eeprom");
for (uint8_t i = 0; i < NUM_OF_DEFAULT_DEVICES; i++) {
eepromWriteDeviceBlock(i, &defaultDeviceBlock[i]);
}
coloredMsg(LOG_BLUE, false, "cfg ci Default device blocks written to eeprom");
coloredMsg(LOG_BLUE, false, "cfg ci Reading configuration block from eeprom again");
eepromReadConfigBlock(&mainConfigBlock);
}
@ -129,36 +46,5 @@ void configInit() {
mainConfigBlock.macAddress[3],
mainConfigBlock.macAddress[4],
mainConfigBlock.macAddress[5]);
coloredMsg(LOG_BLUE, false, "cfg ci frontend threshold: %ld", mainConfigBlock.frontendThreshold);
coloredMsg(LOG_BLUE, false, "cfg ci broker: %s", mainConfigBlock.brokerName);
coloredMsg(LOG_BLUE, false, "cfg ci watchdogTopic: %s", mainConfigBlock.watchdogTopic);
coloredMsg(LOG_BLUE, false, "cfg ci startupTopic: %s", mainConfigBlock.startupTopic);
coloredMsg(LOG_BLUE, false, "cfg ci statusTopic: %s", mainConfigBlock.statusTopic);
coloredMsg(LOG_BLUE, false, "cfg ci mbusDataTopic: %s", mainConfigBlock.mbusDataTopic);
coloredMsg(LOG_BLUE, false, "cfg ci syslog server: %s", mainConfigBlock.syslogServerName);
coloredMsg(LOG_BLUE, false, "cfg ci device block cnt: %d", mainConfigBlock.numOfDeviceBlocks);
for (uint8_t i = 0; i < mainConfigBlock.numOfDeviceBlocks; i++) {
t_deviceBlock tmpDeviceBlock;
eepromReadDeviceBlock(i, &tmpDeviceBlock);
if (tmpDeviceBlock.deviceMagic == DEVICE_MAGIC) {
coloredMsg(LOG_BLUE, false, "cfg ci device %d: ", i);
coloredMsg(LOG_BLUE, false, " Name: %s, Address: %d, Period: %d",
tmpDeviceBlock.deviceName, tmpDeviceBlock.address, tmpDeviceBlock.period);
coloredMsg(LOG_BLUE, false, " Considered Fields: %d %d %d %d",
tmpDeviceBlock.consideredField[0],
tmpDeviceBlock.consideredField[1],
tmpDeviceBlock.consideredField[2],
tmpDeviceBlock.consideredField[3]);
if (tmpDeviceBlock.period == 0) {
coloredMsg(LOG_BLUE, false, " device is marked as inactive");
} else if (tmpDeviceBlock.period == -1) {
coloredMsg(LOG_BLUE, false, " device is marked as deleted");
} else {
mbusCommAddDevice(&tmpDeviceBlock);
}
} else {
coloredMsg(LOG_BLUE, false, "magic of device %d does not match, ignored", i);
}
}
}

View File

@ -24,39 +24,10 @@ static bool showConfigCmd(uint8_t argc, char **args) {
configBlock.macAddress[3],
configBlock.macAddress[4],
configBlock.macAddress[5]);
sendFormatString("frontend threshold: %ld\n\r", configBlock.frontendThreshold);
sendFormatString("broker: %s\n\r", configBlock.brokerName);
sendFormatString("watchdogTopic: %s\n\r", configBlock.watchdogTopic);
sendFormatString("startupTopic: %s\n\r", configBlock.startupTopic);
sendFormatString("statusTopic: %s\n\r", configBlock.statusTopic);
sendFormatString("mbusDataTopic: %s\n\r", configBlock.mbusDataTopic);
sendFormatString("syslog server: %s\n\r", configBlock.syslogServerName);
sendFormatString("device block cnt: %d\n\r", configBlock.numOfDeviceBlocks);
for (uint8_t i = 0; i < configBlock.numOfDeviceBlocks; i++) {
t_deviceBlock tmpDeviceBlock;
eepromReadDeviceBlock(i, &tmpDeviceBlock);
if (tmpDeviceBlock.deviceMagic == DEVICE_MAGIC) {
sendFormatString("device %d: \n\r", i);
sendFormatString(" Name: %s, Address: %d, Period: %d\n\r",
tmpDeviceBlock.deviceName, tmpDeviceBlock.address, tmpDeviceBlock.period);
sendFormatString(" Considered Fields: %d %d %d %d\n\r",
tmpDeviceBlock.consideredField[0],
tmpDeviceBlock.consideredField[1],
tmpDeviceBlock.consideredField[2],
tmpDeviceBlock.consideredField[3]);
if (tmpDeviceBlock.deviceMagic != DEVICE_MAGIC) {
sendString(" DEVICE MAGIC DOES NOT MATCH\n\r");
}
}
}
return retCode;
}
static bool setStringParameterCmd(uint8_t argc, char **args, size_t offset, size_t length) {
bool retCode = true;
@ -77,6 +48,7 @@ static bool setStringParameterCmd(uint8_t argc, char **args, size_t offset, size
return retCode;
}
/*
static bool setInt32ParameterCmd(uint8_t argc, char **args, size_t offset, int32_t minV, int32_t maxV) {
bool retCode = true;
@ -100,7 +72,7 @@ static bool setInt32ParameterCmd(uint8_t argc, char **args, size_t offset, int32
return retCode;
}
*/
static bool setDeviceNameCmd(uint8_t argc, char **args) {
return setStringParameterCmd(argc, args,
@ -108,211 +80,7 @@ static bool setDeviceNameCmd(uint8_t argc, char **args) {
sizeof(((t_configBlock*)0)->deviceName));
}
static bool setBrokerNameCmd(uint8_t argc, char **args) {
return setStringParameterCmd(argc, args,
offsetof(t_configBlock, brokerName),
sizeof(((t_configBlock*)0)->brokerName));
}
static bool setSyslogServerCmd(uint8_t argc, char **args) {
return setStringParameterCmd(argc, args,
offsetof(t_configBlock, syslogServerName),
sizeof(((t_configBlock*)0)->syslogServerName));
}
static bool setWatchdogTopicCmd(uint8_t argc, char **args) {
return setStringParameterCmd(argc, args,
offsetof(t_configBlock, watchdogTopic),
sizeof(((t_configBlock*)0)->watchdogTopic));
}
static bool setStartupTopicCmd(uint8_t argc, char **args) {
return setStringParameterCmd(argc, args,
offsetof(t_configBlock, startupTopic),
sizeof(((t_configBlock*)0)->startupTopic));
}
static bool setStatusTopicCmd(uint8_t argc, char **args) {
return setStringParameterCmd(argc, args,
offsetof(t_configBlock, statusTopic),
sizeof(((t_configBlock*)0)->statusTopic));
}
static bool setMbusDataTopicCmd(uint8_t argc, char **args) {
return setStringParameterCmd(argc, args,
offsetof(t_configBlock, mbusDataTopic),
sizeof(((t_configBlock*)0)->mbusDataTopic));
}
static bool setFrontendThresholdCmd(uint8_t argc, char **args) {
return setInt32ParameterCmd(argc, args,
offsetof(t_configBlock, frontendThreshold),
0, 1023);
}
static bool makeDevice(uint8_t argOffset, uint8_t argc, char **args, t_deviceBlock *deviceBlock) {
if (strcmp(args[1], "help") == 0) {
sendString("deviceName address period field1 field2 field3 field4\n\r");
sendString("deviceName: max. length = 16\n\r");
sendString("address: between 1 and 254\n\r");
sendString("period: in seconds, between 0 (disabled) and 86400 (1 day)\n\r");
sendString("fields: between -1 (not considered) and 254\n\r");
return false;
}
if ((argc - argOffset) != 8) {
sendString("wrong number of arguments\n\r");
return false;
}
char *deviceName = args[1 + argOffset];
if (strcmp(deviceName, "*") != 0) {
if (strlen(deviceName) >= sizeof(deviceBlock->deviceName)) {
sendString("devicename too long\n\r");
return false;
}
strcpy(deviceBlock->deviceName, deviceName);
}
char *rawAddressStr = args[2 + argOffset];
if (strcmp(rawAddressStr, "*") != 0) {
long int rawAddress = strtol(rawAddressStr, NULL, 10);
if (rawAddress < 1 || rawAddress > 254) {
sendString("illegal address\n\r");
return false;
}
deviceBlock->address = (uint8_t)rawAddress;
}
char *rawPeriodStr = args[3 + argOffset];
if (strcmp(rawPeriodStr, "*") != 0) {
long int rawPeriod = strtol(rawPeriodStr, NULL, 10);
if (rawPeriod < 0 || rawPeriod > 86400) {
sendString("illegal period\n\r");
return false;
}
deviceBlock->period = (int32_t) rawPeriod;
}
for (uint8_t i = 0; i < MBUSDEVICE_NUM_OF_CONSIDEREDFIELDS; i++) {
char *rawFieldNumStr = args[4 + i + argOffset];
if (strcmp(rawFieldNumStr, "*") != 0) {
long int rawFieldNum = strtol(rawFieldNumStr, NULL, 10);
if (rawFieldNum < -1 || rawFieldNum > 127) {
sendString("illegal considered field index\n\r");
return false;
}
deviceBlock->consideredField[i] = (int8_t) rawFieldNum;
}
}
return true;
}
static bool addDeviceCmd(uint8_t argc, char **args) {
t_deviceBlock deviceBlock = { .deviceName = "", .address = 0, .period = 0, .consideredField = { -1, -1, -1, -1}};
bool retCode = makeDevice(0, argc, args, &deviceBlock);
if (retCode) {
sendString("New device would be:\n\r");
sendFormatString(" Name: %s, Address: %d, Period: %d\n\r",
deviceBlock.deviceName, deviceBlock.address, deviceBlock.period);
for (uint8_t i = 0; i < MBUSDEVICE_NUM_OF_CONSIDEREDFIELDS; i++) {
sendFormatString(" Considered field: %d\n\r", deviceBlock.consideredField[i]);
}
}
deviceBlock.deviceMagic = DEVICE_MAGIC;
uint8_t index = getConfig()->numOfDeviceBlocks;
for (uint8_t i = 0; i < getConfig()->numOfDeviceBlocks; i++) {
t_deviceBlock tmpDeviceBlock;
eepromReadDeviceBlock(i, &tmpDeviceBlock);
if (tmpDeviceBlock.period == -1) {
index = i;
break;
}
}
eepromWriteDeviceBlock(index, &deviceBlock);
if (index == getConfig()->numOfDeviceBlocks) {
t_configBlock configBlock;
eepromReadConfigBlock(&configBlock);
configBlock.numOfDeviceBlocks += 1;
eepromWriteConfigBlock(&configBlock);
}
return retCode;
}
static bool deleteDeviceCmd(uint8_t argc, char **args) {
long int rawIndex = strtol(args[1], NULL, 10);
if (rawIndex < 0 || rawIndex > getConfig()->numOfDeviceBlocks) {
sendFormatString("illegal index, must be greater 0 and less %d\n\r", getConfig()->numOfDeviceBlocks);
return false;
}
uint8_t index = (uint8_t) rawIndex;
t_deviceBlock deviceBlock;
eepromReadDeviceBlock(index, &deviceBlock);
deviceBlock.period = -1;
eepromWriteDeviceBlock(index, &deviceBlock);
return true;
}
static bool changeDeviceCmd(uint8_t argc, char **args) {
if (strcmp(args[1], "help") == 0) {
sendString("First argument: index of device in list\n\r");
sendFormatString("Between 0 and %d\n\r", getConfig()->numOfDeviceBlocks);
sendString("For further arguments use a * to keep the value\n\r");
return makeDevice(0, argc, args, NULL);
}
long int rawIndex = strtol(args[1], NULL, 10);
if (rawIndex < 0 || rawIndex > getConfig()->numOfDeviceBlocks) {
sendFormatString("illegal index, must be greater 0 and less %d\n\r", getConfig()->numOfDeviceBlocks);
return false;
}
uint8_t index = (uint8_t) rawIndex;
t_deviceBlock deviceBlock;
eepromReadDeviceBlock(index, &deviceBlock);
bool retCode = makeDevice(1, argc, args, &deviceBlock);
if (retCode) {
sendString("Changed device will be:\n\r");
sendFormatString(" Index: %d\n\r", index);
sendFormatString(" Name: %s, Address: %d, Period: %d\n\r",
deviceBlock.deviceName, deviceBlock.address, deviceBlock.period);
for (uint8_t i = 0; i < MBUSDEVICE_NUM_OF_CONSIDEREDFIELDS; i++) {
sendFormatString(" Considered field: %d\n\r", deviceBlock.consideredField[i]);
}
if (deviceBlock.period == 0) {
sendString(" Device is marked as inactive\n\r");
}
eepromWriteDeviceBlock(index, &deviceBlock);
}
return retCode;
}
static bool listDevicesCmd(uint8_t argc, char **args) {
for (uint8_t i = 0; i < getConfig()->numOfDeviceBlocks; i++) {
t_deviceBlock deviceBlock;
eepromReadDeviceBlock(i, &deviceBlock);
sendFormatString("Index: %d\n\r", i);
sendFormatString(" Name: %s, Address: %d, Period: %d\n\r",
deviceBlock.deviceName, deviceBlock.address, deviceBlock.period);
for (uint8_t i = 0; i < MBUSDEVICE_NUM_OF_CONSIDEREDFIELDS; i++) {
sendFormatString(" Considered field: %d\n\r", deviceBlock.consideredField[i]);
}
if (deviceBlock.period == 0) {
sendString(" Device is marked as inactive\n\r");
} else if (deviceBlock.period == -1) {
sendString(" Device is marked as deleted\n\r");
}
}
return true;
}
const static cmd_t SET_COMMANDS[] = {
@ -320,34 +88,6 @@ const static cmd_t SET_COMMANDS[] = {
.help = \
"devicename ........................... Name of this device\n\r"
},
{ .name = "brokername", .cmdFunc = setBrokerNameCmd,
.help = \
"brokername ........................... Hostname of the MQTT broker\n\r"
},
{ .name = "syslogserver", .cmdFunc = setSyslogServerCmd,
.help = \
"syslogserver ......................... Hostname of the Syslog server\n\r"
},
{ .name = "watchdogtopic", .cmdFunc = setWatchdogTopicCmd,
.help = \
"watchdogtopic ........................ Watchdog Topic\n\r"
},
{ .name = "startuptopic", .cmdFunc = setStartupTopicCmd,
.help = \
"startuptopic ......................... Startup Topic\n\r"
},
{ .name = "statustopic", .cmdFunc = setStatusTopicCmd,
.help = \
"statustopic .......................... Status Topic\n\r"
},
{ .name = "mbusdatatopic", .cmdFunc = setMbusDataTopicCmd,
.help = \
"mbusdatatopic ........................ MBus Data Topic\n\r"
},
{ .name = "frontendthreshold", .cmdFunc = setFrontendThresholdCmd,
.help = \
"frontendthreshold .................... Frontend Threshold (default: 240)\n\r"
},
{ .name = "END_OF_CMDS", .help = "",.cmdFunc = NULL }
};
@ -415,23 +155,6 @@ const cmd_t CONFIG_COMMANDS[] = {
" Argument help gives a list of \n\r" \
" parameters\n\r"
},
{ .name = "addDevice", .cmdFunc = addDeviceCmd,
.help = \
"addDevice ............................ Add a new device to the end of the list\n\r"
},
{ .name = "changeDevice", .cmdFunc = changeDeviceCmd,
.help = \
"changeDevice ......................... Change a new device by index\n\r"
},
{ .name = "listDevices", .cmdFunc = listDevicesCmd,
.help = \
"listDevices .......................... List the configured devices\n\r"
},
{ .name = "deleteDevice", .cmdFunc = deleteDeviceCmd,
.help = \
"deleteDevice ......................... Delete a device\n\r" \
" Argument: index\n\r"
},
{ .name = "restart", .cmdFunc = restartCmd,
.help = \
"restart .............................. Restart the system,\n\r" \

View File

@ -3,7 +3,6 @@
#include <eeprom.h>
#include <string.h>
#include <logger.h>
#include <mbusComm.h>
#include <PontCoopScheduler.h>
#include <utils.h>
@ -35,6 +34,8 @@ typedef union {
static t_eepromHeaderBlock eepromHeader;
static const uint16_t CONFIG_BLOCK_ADDR = EEPROM_CONFIG_BLOCK_ADDR;
typedef union {
t_deviceStats s;
@ -44,10 +45,6 @@ typedef union {
static const uint16_t DEVICE_STATS_ADDR = EEPROM_DEVICE_STATS_ADDR;
static t_deviceStatsBlock deviceStats;
static const uint16_t CONFIG_BLOCK_ADDR = EEPROM_CONFIG_BLOCK_ADDR;
static const uint16_t DEVICE_BLOCK_ADDR = EEPROM_DEVICE_BLOCK_BASE_ADDR;
typedef union {
@ -117,10 +114,8 @@ void eepromSpiTxCpltCallback(SPI_HandleTypeDef *hspi) {
static void eepromHourlyUpdateDeviceStats(void *handle) {
deviceStats.s.totalRunningHours += 1;
t_mbusCommStats *stats = mbusCommGetStats();
deviceStats.s.totalRequests += stats->mbusRequestCnt;
deviceStats.s.totalFailures += stats->mbusErrorCnt;
deviceStats.s.totalRequests += 0;
deviceStats.s.totalFailures += 0;
logMsg("eeHUDS, about to write updated device stats");
logMsg("eeHUDS, total powercycles so far: %d", deviceStats.s.totalPowercycles);
@ -146,26 +141,6 @@ void eepromWriteConfigBlock(t_configBlock *srcConfigBlock) {
}
}
void eepromReadDeviceBlock(uint8_t blockNum, t_deviceBlock *destDeviceBlock) {
static_assert((sizeof(*destDeviceBlock) % EEPROM_WRITE_BLOCK_SIZE == 0), "device block has illegal size, must be dividable by 32");
for (uint8_t i = 0; i < (sizeof(*destDeviceBlock) / EEPROM_WRITE_BLOCK_SIZE); i++) {
eepromRead(DEVICE_BLOCK_ADDR + (blockNum * sizeof(*destDeviceBlock)) + (i * EEPROM_WRITE_BLOCK_SIZE),
((uint8_t*)destDeviceBlock) + (i * EEPROM_WRITE_BLOCK_SIZE),
EEPROM_WRITE_BLOCK_SIZE);
}
}
void eepromWriteDeviceBlock(uint8_t blockNum, t_deviceBlock *srcDeviceBlock) {
for (uint8_t i = 0; i < (sizeof(*srcDeviceBlock) / EEPROM_WRITE_BLOCK_SIZE); i++) {
eepromWrite(DEVICE_BLOCK_ADDR + (blockNum * sizeof(*srcDeviceBlock)) + (i * EEPROM_WRITE_BLOCK_SIZE),
((uint8_t*)srcDeviceBlock) + (i * EEPROM_WRITE_BLOCK_SIZE),
EEPROM_WRITE_BLOCK_SIZE);
eepromActiveDelay(EEPROM_AFTER_WRITE_DELAY);
}
}
void eepromInit() {
__EEPROM_CS(HIGH);

View File

@ -1,59 +0,0 @@
#include <stdbool.h>
#include <main.h>
#include <adc.h>
#include <frontend.h>
#include <logger.h>
#include <show.h>
#include <config.h>
static t_configBlock *config;
static volatile int32_t frontendAdcThreshold = 0;
static volatile bool frontendEnabled = false;
void frontendInit() {
config = getConfig();
frontendAdcThreshold = config->frontendThreshold;
HAL_ADCEx_Calibration_Start(&frontendAdc);
logMsg("frontendInit, calibration done");
HAL_ADC_Start_IT(&frontendAdc);
logMsg("frontendInit, adc started");
}
void frontendEnable() {
frontendEnabled = true;
}
void frontendDisable() {
frontendEnabled = false;
}
void frontendAdcCallback(ADC_HandleTypeDef* hadc) {
static int32_t holdValue = 0;
if (frontendEnabled) {
int32_t currentValue = (int32_t) HAL_ADC_GetValue(hadc);
if (holdValue == 0) {
holdValue = currentValue;
}
if (currentValue - holdValue > frontendAdcThreshold) {
HAL_GPIO_WritePin(Frontend_Out_GPIO_Port, Frontend_Out_Pin, GPIO_PIN_RESET);
} else {
HAL_GPIO_WritePin(Frontend_Out_GPIO_Port, Frontend_Out_Pin, GPIO_PIN_SET);
}
} else {
if (holdValue != 0) {
holdValue = 0;
HAL_GPIO_WritePin(Frontend_Out_GPIO_Port, Frontend_Out_Pin, GPIO_PIN_SET);
}
}
}

View File

@ -4,8 +4,6 @@
#include <PontCoopScheduler.h>
#include <logger.h>
#include <ringbuffer.h>
#include <wizHelper.h>
#include <socket.h>
#include <config.h>
#include <stdint.h>
@ -29,9 +27,6 @@
static t_configBlock *config;
extern const uint8_t SYSLOG_SOCK;
uint8_t syslogAddr[4];
uint8_t singleOctetTXBuffer;
static ringbuffer_t logBuffer;
@ -70,41 +65,8 @@ int logExec() {
}
#endif //LOGGER_OUTPUT_BY_INTERRUPT
void syslog(char *msg) {
static uint8_t state = 0;
int8_t res8 = 0;
int32_t res32 = 0;
if (isNetworkAvailable()) {
switch (state) {
case 0:
res8 = socket(SYSLOG_SOCK, Sn_MR_UDP, 514, SF_IO_NONBLOCK);
if (res8 != SYSLOG_SOCK) {
break;
}
state = 1;
// no break
case 1:
if (! wizDnsQuery(config->syslogServerName, syslogAddr)) {
disconnect(SYSLOG_SOCK);
state = 0;
break;
}
state = 2;
// no break
case 2:
res32 = sendto(SYSLOG_SOCK, (uint8_t*)msg, strlen(msg), syslogAddr, 514);
if (res32 != strlen(msg)) {
disconnect(SYSLOG_SOCK);
state = 0;
}
break;
}
}
}
static int innerLogMsg(const char *pre, const char *post, bool syslogToo, const char *format, va_list vl) {
const static char SYSLOG_HEADER[] = "<133>1 ";
static int innerLogMsg(const char *pre, const char *post, const char *format, va_list vl) {
#define MAX_PREFIX_SIZE 20
int res = -1;
char msgBuffer[MSGBUFFER_SIZE+MAX_PREFIX_SIZE];
@ -112,9 +74,8 @@ static int innerLogMsg(const char *pre, const char *post, bool syslogToo, const
memset(msgBuffer, 0, MSGBUFFER_SIZE+MAX_PREFIX_SIZE);
uint16_t syslogHeaderSize = strlen(SYSLOG_HEADER);
uint16_t preSize = (pre) ? strlen(pre) : 0;
uint16_t prefixSize = (syslogHeaderSize > preSize) ? syslogHeaderSize : preSize;
uint16_t prefixSize = preSize;
if (prefixSize > MAX_PREFIX_SIZE) {
return -1;
}
@ -122,11 +83,6 @@ static int innerLogMsg(const char *pre, const char *post, bool syslogToo, const
int vcnt = vsnprintf(bufferStart, MSGBUFFER_SIZE, format, vl);
if (vcnt < MSGBUFFER_SIZE) {
if (syslogToo) {
memcpy(bufferStart - syslogHeaderSize, SYSLOG_HEADER, syslogHeaderSize);
syslog(bufferStart - syslogHeaderSize);
}
if (pre) {
memcpy(bufferStart - preSize, pre, preSize);
}
@ -154,12 +110,12 @@ static int innerLogMsg(const char *pre, const char *post, bool syslogToo, const
int logMsg(const char *format, ...) {
va_list vl;
va_start(vl, format);
int res = innerLogMsg(NULL, "\r\n", false, format, vl);
int res = innerLogMsg(NULL, "\r\n", format, vl);
va_end(vl);
return res;
}
int coloredMsg(const t_logColor color, bool syslogToo, const char *format, ...) {
int coloredMsg(const t_logColor color, const char *format, ...) {
const static char POST[] = "\x1b[0m\r\n";
const static char HIGH[] = "\x1b[1m";
const static char RED[] = "\x1b[31;1m";
@ -189,7 +145,7 @@ int coloredMsg(const t_logColor color, bool syslogToo, const char *format, ...)
}
va_list vl;
va_start(vl, format);
int res = innerLogMsg(pre, POST, syslogToo, format, vl);
int res = innerLogMsg(pre, POST, format, vl);
va_end(vl);
return res;
}

View File

@ -5,19 +5,14 @@
#include <main.h>
#include <usart.h>
#include <adc.h>
#include <spi.h>
#include <PontCoopScheduler.h>
#include <show.h>
#include <loopCtrl.h>
#include <mbusComm.h>
#include <logger.h>
#include <frontend.h>
#include <eeprom.h>
#include <wizHelper.h>
#include <mqttComm.h>
#include <cmdHandler.h>
#include <oled.h>
#include <config.h>
@ -53,16 +48,9 @@ void my_setup_2() {
wizInit();
oledPrint(OLED_SCREEN0, "network init");
mqttCommInit();
oledPrint(OLED_SCREEN0, "mqtt init");
cmdHandlerInit();
oledPrint(OLED_SCREEN0, "cmdhandler init");
frontendInit();
oledPrint(OLED_SCREEN0, "frontend init");
mbusCommInit();
oledPrint(OLED_SCREEN0, "Meterbus init");
oledPrint(OLED_SCREEN0, "App running");
}
@ -74,26 +62,12 @@ void my_loop() {
#ifndef LOGGER_OUTPUT_BY_INTERRUPT
logExec();
#endif //LOGGER_OUTPUT_BY_INTERRUPT
mbusCommExec();
}
void SYSTICK_Callback() {
schUpdate();
}
void HAL_GPIO_EXTI_Callback(uint16_t pin) {
if (pin == Loop_Status_Pin) {
loopStatusCallback();
}
}
void HAL_ADC_ConvCpltCallback(ADC_HandleTypeDef* hadc) {
if (hadc == &frontendAdc) {
frontendAdcCallback(hadc);
}
}
void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart) {
#ifdef LOGGER_OUTPUT_BY_INTERRUPT
if (huart == &debugUart) {

View File

@ -1,7 +1,6 @@
#include <cmdHelper.h>
#include <logger.h>
#include <mbusComm.h>
#include <eeprom.h>
@ -25,19 +24,6 @@ static bool globalStatsCmd(uint8_t argc, char **args) {
deviceStats->totalRequests, deviceStats->totalFailures
);
t_mbusCommStats *mbusStats = mbusCommGetStats();
sendFormatString(\
"Global Meterbus/UART statistics\n\r" \
" Meterbus Requests: %ld\n\r" \
" Meterbus Errors: %ld\n\r" \
" UART Octets: %ld\n\r" \
" UART Overruns: %ld\n\r" \
" UART Framing Errs: %ld\n\r" \
" UART Parity Errs: %ld\n\r" \
" UART Noise Errs: %ld\n\r",
mbusStats->mbusRequestCnt, mbusStats->mbusErrorCnt,
mbusStats->uartOctetCnt, mbusStats->uartOverrunCnt, mbusStats->uartFramingErrCnt, mbusStats->uartParityErrCnt, mbusStats->uartNoiseErrCnt
);
return true;
}

View File

@ -5,7 +5,7 @@
#include <stdint.h>
#include <stdlib.h>
#include <stm32f103xe.h>
#include <stm32f103xb.h>
typedef struct {