changeset 1033:5f66e44d69f0 Puls_Integration

Added functionality needed for subscription of standard Bluetooth pulse service notifications
author Ideenmodellierer
date Sat, 02 Aug 2025 22:42:51 +0200
parents 33b91584d827
children 195bfbdf961d
files Discovery/Inc/cv_heartbeat.h Discovery/Inc/ostc.h Discovery/Inc/tInfoLogger.h Discovery/Src/base.c Discovery/Src/cv_heartbeat.c Discovery/Src/tInfoLogger.c
diffstat 6 files changed, 232 insertions(+), 38 deletions(-) [+]
line wrap: on
line diff
--- a/Discovery/Inc/cv_heartbeat.h	Mon Jul 28 18:34:45 2025 +0200
+++ b/Discovery/Inc/cv_heartbeat.h	Sat Aug 02 22:42:51 2025 +0200
@@ -40,6 +40,8 @@
 	DEVICE_INDICATOR,
 	CONNECTION_INDICATOR,
 	SERVICE_INDICATOR,
+	CHARACTERISTIC_INDICATOR,
+	DESCRIPTOR_INDICATOR,
 	OK_INDICATOR,			/* module control */
 	ERROR_INDICATOR			/* module control */
 } indicatior_t;
@@ -54,7 +56,16 @@
 	BT_READ_SERV_HANDLE,
 	BT_READ_SERV_START,
 	BT_READ_SERV_END,
-	BT_READ_SERV_UUID
+	BT_READ_SERV_UUID,
+	BT_READ_CHAR_CONHANDLE,
+	BT_READ_CHAR_ATTRIBUTE,
+	BT_READ_CHAR_PROPERTY,
+	BT_READ_CHAR_VALUEHANDLE,
+	BT_READ_CHAR_UUID,
+	BT_READ_DESC_CONHANDLE,
+	BT_READ_DESC_CHARHANDLE,
+	BT_READ_DESC_DESCHANDLE,
+	BT_READ_DESC_UUID
 } readDataType_t;
 
 typedef enum
@@ -64,7 +75,11 @@
 	SENSOR_HB_CHECK_CONFIG,
 	SENSOR_HB_DISCOVER,
 	SENSOR_HB_CONNECT,
+	SENSOR_HB_DISCONNECT,
 	SENSOR_HB_SERVICES,
+	SENSOR_HB_CHARACTERISTIC,
+	SENSOR_HB_DESCRIPTOR,
+	SENSOR_HB_SUBSCRIBE,
 	SENSOR_HB_RESTART,
 	SENSOR_HB_DETECTION_INDICATOR,		/* searching for indicators to identify data items */
 	SENSOR_HB_DETECTION_RSSI,
@@ -92,10 +107,26 @@
 	uint8_t uuid[50];
 } btDeviceService_t;
 
+typedef struct
+{
+	uint8_t conHandle;
+	uint8_t attrHandle[10];
+	uint8_t properties[10];
+	uint8_t valueHandle[10];
+	uint8_t uuid[50];
+} btDeviceCharacteristic_t;
 
+typedef struct
+{
+	uint8_t conHandle;
+	uint8_t charHandle[10];
+	uint8_t descHandle[10];
+	uint8_t uuid[50];
+} btDeviceDescriptor_t;
 
 sensorHeartbeat_State_t cv_heartbeat_getState();
 void refresh_Heartbeat(void);
 void cv_heartbeat_Control(void);
+uint8_t cv_heartbeat_HandleData();
 
 #endif /* INC_CV_HEARTBEAT_H_ */
--- a/Discovery/Inc/ostc.h	Mon Jul 28 18:34:45 2025 +0200
+++ b/Discovery/Inc/ostc.h	Sat Aug 02 22:42:51 2025 +0200
@@ -60,7 +60,7 @@
 #define DISPLAY_VERSION_LCD						(0u)
 #define DISPLAY_VERSION_NEW						(1u)
 
-#define CHUNK_SIZE				(150u)		/* the DMA will handle chunk size transfers */
+#define CHUNK_SIZE				(160u)		/* the DMA will handle chunk size transfers */
 #define CHUNKS_PER_BUFFER		(3u)
 
 
--- a/Discovery/Inc/tInfoLogger.h	Mon Jul 28 18:34:45 2025 +0200
+++ b/Discovery/Inc/tInfoLogger.h	Sat Aug 02 22:42:51 2025 +0200
@@ -29,8 +29,8 @@
 #define TINFO_LOGGER_H
 
 #define LINE_HEADER_BYTES (3u)
-#define MAX_CHAR_PER_LINE (50u)
-#define MAX_LOGGER_LINES	(12u)
+#define MAX_CHAR_PER_LINE (60u)
+#define MAX_LOGGER_LINES  (13u)
 
 #define LOG_TX_LINE	(0u)
 #define LOG_RX_LINE (1u)
--- a/Discovery/Src/base.c	Mon Jul 28 18:34:45 2025 +0200
+++ b/Discovery/Src/base.c	Sat Aug 02 22:42:51 2025 +0200
@@ -237,6 +237,8 @@
 #include "t7.h"
 #include "t3.h"
 #include "tMenuEditSetpoint.h"
+#include "cv_heartbeat.h"
+#include "tInfoLogger.h"
 
 #ifdef DEMOMODE
 #include "demo.h"
@@ -527,6 +529,9 @@
         {
         	TriggerButtonAction();
         }
+
+        cv_heartbeat_HandleData();
+
         if(DoHousekeeping)
         {
            	DoHousekeeping = housekeepingFrame();
--- a/Discovery/Src/cv_heartbeat.c	Mon Jul 28 18:34:45 2025 +0200
+++ b/Discovery/Src/cv_heartbeat.c	Sat Aug 02 22:42:51 2025 +0200
@@ -41,19 +41,21 @@
 #define MAX_BT_DEVICE 10		/* max number of device which may be handled */
 static btDdeviceData_t btDeviceList[MAX_BT_DEVICE];
 static btDeviceService_t curDeviceService[10];
+static btDeviceCharacteristic_t curDevCharacteristic[10];
+static btDeviceDescriptor_t curDevDescriptor;
+
+
+static uint8_t curCharacteristicIndex = 0;
 static uint8_t curServiceIndex = 0;
 static uint8_t curBtIndex = 0;
 static uint8_t connHandle = ' ';
+static uint8_t evaluateDevIndex = 0xFF;
+static uint8_t evaluateSrvIndex = 0xFF;
+static uint8_t evaluateCharIndex = 0xFF;
+static uint8_t evaluateDescIndex = 0xFF;
 
 static indicatior_t checkIndicators(uint8_t* pdata)
 {
-#if 0
-	static uint8_t foundRSSI = 0;
-	static uint8_t foundNAME = 0;
-	static uint8_t foundMNF = 0;
-	static uint8_t foundUUID = 0;
-	static uint8_t foundOK = 0;
-#endif
 	indicatior_t ret = NO_INDICATOR;
 
 	if(strcmp((char*)pdata,"+UBTD:") == 0)
@@ -68,12 +70,22 @@
 	{
 		ret = SERVICE_INDICATOR;
 	}
+	else if(strcmp((char*)pdata,"+UBTGDCS:") == 0)
+	{
+		ret = CHARACTERISTIC_INDICATOR;
+	}
+	else if(strcmp((char*)pdata,"+UBTGDCD:") == 0)
+	{
+		ret = DESCRIPTOR_INDICATOR;
+	}
 
 	return ret;
 }
 
 static void handleOK()
 {
+	uint8_t index = 0;
+
 	switch(heartbeatState)
 	{
 		case SENSOR_HB_ENABLE_BLE:	heartbeatState = SENSOR_HB_CHECK_CONFIG;
@@ -82,10 +94,75 @@
 							break;
 		case SENSOR_HB_RESTART: 	heartbeatState = SENSOR_HB_OFFLINE;
 							break;
-		case SENSOR_HB_DISCOVER: heartbeatState = SENSOR_HB_CONNECT;
+		case SENSOR_HB_DISCOVER: 	if(curBtIndex > 0)
+									{
+										heartbeatState = SENSOR_HB_CONNECT;
+										evaluateDevIndex = 0;
+									}
+									else
+									{
+										heartbeatState = SENSOR_HB_OFFLINE;
+									}
+
+							break;
+		case SENSOR_HB_SERVICES: 	evaluateSrvIndex = 0xFF;
+									if(curServiceIndex != 0)
+									{
+										for(index = 0; index <= curServiceIndex; index++)
+										{
+											if(strcmp((char*)curDeviceService[index].uuid,"180D") == 0)
+											{
+												heartbeatState = SENSOR_HB_CHARACTERISTIC;
+												evaluateSrvIndex = index;
+												curCharacteristicIndex = 0;
+												break;
+											}
+										}
+									}
+									if(evaluateSrvIndex == 0xFF)		/* device does not provide heartbeat data => disconnect */
+									{
+										heartbeatState = SENSOR_HB_DISCONNECT;
+									}
 							break;
-		case SENSOR_HB_SERVICES: heartbeatState = SENSOR_HB_OFFLINE;
+		case SENSOR_HB_CHARACTERISTIC:	evaluateCharIndex = 0xFF;
+										if(curCharacteristicIndex != 0)
+										{
+											for(index = 0; index < curCharacteristicIndex; index++)
+											{
+												if(strcmp((char*)curDevCharacteristic[index].uuid,"2A37") == 0)
+												{
+													heartbeatState = SENSOR_HB_DESCRIPTOR;
+													evaluateCharIndex = index;
+													break;
+												}
+											}
+										}
+										if(evaluateCharIndex == 0xFF)		/* device does not provide heartbeat data => disconnect */
+										{
+											heartbeatState = SENSOR_HB_DISCONNECT;
+										}
 							break;
+		case SENSOR_HB_DESCRIPTOR:		if(strcmp((char*)curDevDescriptor.uuid,"2902") == 0)
+										{
+											heartbeatState = SENSOR_HB_SUBSCRIBE;
+										}
+										else
+										{
+											heartbeatState = SENSOR_HB_DISCONNECT;
+										}
+							break;
+		case SENSOR_HB_DISCONNECT:		evaluateDevIndex++;
+										connHandle= ' ';
+										if(evaluateDevIndex < curBtIndex)	/* more devices to be evaluated? */
+										{
+											heartbeatState = SENSOR_HB_CONNECT;
+										}
+										else
+										{
+											heartbeatState = SENSOR_HB_OFFLINE;
+										}
+							break;
+		case SENSOR_HB_CONNECT:			/* handled in data rx section */
 		default:
 							break;
 	}
@@ -93,10 +170,25 @@
 
 static void handleERROR()
 {
-
+	switch(heartbeatState)
+	{
+		case SENSOR_HB_DISCONNECT:			evaluateDevIndex++;
+											connHandle= ' ';
+											if(evaluateDevIndex < curBtIndex)	/* more devices to be evaluated? */
+											{
+												heartbeatState = SENSOR_HB_CONNECT;
+											}
+											else
+											{
+												heartbeatState = SENSOR_HB_OFFLINE;
+											}
+						break;
+		default:
+						break;
+	}
 }
 
-static uint8_t getDeviceList()
+uint8_t cv_heartbeat_HandleData()
 {
 	static uint8_t firstDevice = 1;
 	static uint8_t curLine[MAX_CHAR_PER_LINE];			/* holds complete line and is used for logging */
@@ -113,7 +205,7 @@
 
 	while((data != 0) && (complete == 0))
 	{
-		if(curLineIndex == MAX_CHAR_PER_LINE)		/* avoid overflow */
+		if(curLineIndex == MAX_CHAR_PER_LINE - 1)		/* avoid overflow */
 		{
 			InfoLogger_writeLine(curLine,curLineIndex,0);
 			memset(curLine,0,sizeof(curLine));
@@ -143,12 +235,23 @@
 												memcpy (btDeviceList[curBtIndex].name, parameter, writeIndex);
 											}
 								break;
-				case BT_READ_SERV_UUID: 	if(writeIndex < 50)
+				case BT_READ_SERV_UUID: 	if((writeIndex < 50) && (curServiceIndex < 10))
 											{
 												memcpy(curDeviceService[curServiceIndex].uuid, parameter, writeIndex);
 											}
 											curServiceIndex++;
 								break;
+				case BT_READ_CHAR_UUID: 	if(writeIndex < 50)
+											{
+												memcpy(curDevCharacteristic[curCharacteristicIndex].uuid, parameter, writeIndex);
+												curCharacteristicIndex++;
+											}
+								break;
+				case BT_READ_DESC_UUID: 	if(writeIndex < 50)
+											{
+												memcpy(curDevDescriptor.uuid, parameter, writeIndex);
+											}
+								break;
 				default:
 					break;
 			}
@@ -171,6 +274,13 @@
 						break;
 					case SERVICE_INDICATOR: 	readType = BT_READ_SERV_HANDLE;
 						break;
+					case CHARACTERISTIC_INDICATOR: readType = BT_READ_CHAR_CONHANDLE;
+								//					snprintf(text,40,"Found Char");
+							//						InfoLogger_writeLine((uint8_t*)text,strlen(text),0);
+						break;
+					case DESCRIPTOR_INDICATOR: 	readType = BT_READ_DESC_CONHANDLE;
+						break;
+
 					default:
 						break;
 				}
@@ -213,6 +323,7 @@
 						case BT_READ_CON_DETAILS:	connHandle = parameter[0];
 													heartbeatState = SENSOR_HB_SERVICES;
 													readType = BT_READ_NOTHING;
+													curServiceIndex = 0;
 										break;
 						case BT_READ_SERV_HANDLE:	curDeviceService[curServiceIndex].handle = parameter[0];
 													readType = BT_READ_SERV_START;
@@ -229,7 +340,42 @@
 													}
 													readType = BT_READ_SERV_UUID;
 										break;
-
+						case BT_READ_CHAR_CONHANDLE: curDevCharacteristic[curCharacteristicIndex].conHandle = parameter[0];
+													 readType = BT_READ_CHAR_ATTRIBUTE;
+										break;
+						case BT_READ_CHAR_ATTRIBUTE: if(writeIndex < 10)
+													{
+														memcpy(curDevCharacteristic[curCharacteristicIndex].attrHandle, parameter, writeIndex);
+													}
+													readType = BT_READ_CHAR_PROPERTY;
+										break;
+						case BT_READ_CHAR_PROPERTY: if(writeIndex < 10)
+													{
+														memcpy(curDevCharacteristic[curCharacteristicIndex].properties, parameter, writeIndex);
+													}
+													readType = BT_READ_CHAR_VALUEHANDLE;
+										break;
+						case BT_READ_CHAR_VALUEHANDLE: if(writeIndex < 10)
+													{
+														memcpy(curDevCharacteristic[curCharacteristicIndex].valueHandle, parameter, writeIndex);
+													}
+													readType = BT_READ_CHAR_UUID;
+										break;
+						case BT_READ_DESC_CONHANDLE: curDevDescriptor.conHandle = parameter[0];
+													 readType = BT_READ_DESC_CHARHANDLE;
+										break;
+						case BT_READ_DESC_CHARHANDLE: if(writeIndex < 10)
+													{
+														memcpy(curDevDescriptor.charHandle, parameter, writeIndex);
+													}
+													readType = BT_READ_DESC_DESCHANDLE;
+										break;
+						case BT_READ_DESC_DESCHANDLE: if(writeIndex < 10)
+													{
+														memcpy(curDevDescriptor.descHandle, parameter, writeIndex);
+													}
+													readType = BT_READ_DESC_UUID;
+										break;
 						default:					readType = BT_READ_NOTHING;
 							break;
 					}
@@ -299,15 +445,10 @@
 	static uint8_t action = 0;
 	static uint8_t retry = 0;
 	static uint8_t lastState = 0;
-	static uint8_t devicesIndex = 0;
-
-
 	char cmd[50];
 
 	cmd[0] = 0;
 
-	getDeviceList();
-
 	if(action == 3)
 	{
 		action = 0;
@@ -336,7 +477,7 @@
 			case SENSOR_HB_DISCOVER:	if(lastState != SENSOR_HB_DISCOVER)
 										{
 											snprintf(cmd, sizeof(cmd), "AT+UBTD=2,1\r\n" ); //+UBTLE=1 //"AT+UBTD=2,1,5000\r\n"
-											devicesIndex = 0;
+											curBtIndex = 0;
 										}
 
 										//snprintf(cmd, sizeof(cmd), "AT&W\r\n" ); //  AT+UBTD=2,1\r\n "AT+UBTD=2,1,5000\r\n"
@@ -347,22 +488,31 @@
 									//	snprintf(cmd, sizeof(cmd), "AT+CPWROFF\r\n" ); //  AT+UBTD=2,1\r\n "AT+UBTD=2,1,5000\r\n"
 				break;
 #endif
-			case SENSOR_HB_CONNECT:		if(curBtIndex != devicesIndex)
+			case SENSOR_HB_CONNECT:		if(evaluateDevIndex < curBtIndex)
 										{
-											snprintf(cmd, sizeof(cmd), "AT+UBTACLC=%s\r\n",btDeviceList[devicesIndex].address);
-											devicesIndex++;
+											snprintf(cmd, sizeof(cmd), "AT+UBTACLC=%s\r\n",btDeviceList[evaluateDevIndex].address);
+									//		evaluateDevIndex = devicesIndex;
+									//		devicesIndex++;
 										}
 				break;
+			case SENSOR_HB_DISCONNECT:		snprintf(cmd, sizeof(cmd), "AT+UBTACLD=%c\r\n",connHandle);
+				break;
 			case SENSOR_HB_SERVICES:	if((connHandle >= '0') && (connHandle <= '9') && (lastState != SENSOR_HB_SERVICES))
 										{
-											snprintf(cmd, sizeof(cmd), "AT+UBTGDP=0%c\r\n",connHandle);
-										}
-										else
-										{
-											heartbeatState = SENSOR_HB_OFFLINE;
+											snprintf(cmd, sizeof(cmd), "AT+UBTGDP=%c\r\n",connHandle);
+											memset(curDeviceService, 0, sizeof(curDeviceService));
 										}
 				break;
-
+			case SENSOR_HB_CHARACTERISTIC:	snprintf(cmd, sizeof(cmd), "AT+UBTGDCS=%c,%s,%s\r\n",connHandle,curDeviceService[evaluateSrvIndex].start
+																								,curDeviceService[evaluateSrvIndex].end);
+											memset(curDevCharacteristic, 0, sizeof(curDevCharacteristic));
+				break;
+			case SENSOR_HB_DESCRIPTOR: 		snprintf(cmd, sizeof(cmd), "AT+UBTGDCD=%c,%s,%s\r\n",connHandle,curDevCharacteristic[evaluateCharIndex].valueHandle
+																											,curDeviceService[evaluateSrvIndex].end);
+											//memset(curDevDescriptor, 0, sizeof(curDevCharacteristic));
+				break;
+			case SENSOR_HB_SUBSCRIBE: 		snprintf(cmd, sizeof(cmd), "AT+UBTGWC=%c,%s,1\r\n",connHandle,curDevDescriptor.descHandle);
+				break;
 			default:
 				break;
 		}
--- a/Discovery/Src/tInfoLogger.c	Mon Jul 28 18:34:45 2025 +0200
+++ b/Discovery/Src/tInfoLogger.c	Sat Aug 02 22:42:51 2025 +0200
@@ -58,13 +58,13 @@
 
 	if(lineLength <= MAX_CHAR_PER_LINE)
 	{
+		memset(&lines[lineWriteIndex][0],0, (MAX_CHAR_PER_LINE + LINE_HEADER_BYTES));
 		if(direction == LOG_TX_LINE)
 		{
 			lines[lineWriteIndex][LogIndex] = '\002';	/* align right */
 			LogIndex++;
 		}
 		memcpy(&lines[lineWriteIndex][LogIndex],pLine,lineLength);
-		lines[lineWriteIndex][LogIndex + lineLength] = 0;	/* make sure string is zero terminated */
 		lineWriteIndex++;
 		if(lineWriteIndex == MAX_LOGGER_LINES)
 		{
@@ -124,18 +124,26 @@
 		displayLine = lineWriteIndex;
 	}
 
+	if(lineReadIndex != lineWriteIndex)			/* needed for isUpdated function */
+	{
+		lineReadIndex++;
+		if(lineReadIndex == MAX_LOGGER_LINES)
+		{
+			lineReadIndex = 0;
+		}
+	}
 	while (index < displayLine)
 	{
 		color = CLUT_Font020;
 		if(lines[index][0] == '\002')
 		{
-			color = CLUT_Font021;
+			color = CLUT_NiceGreen;
 		}
-		if(lineReadIndex == lineWriteIndex)
+		if(lineReadIndex == index)
 		{
-			color = CLUT_Font022;
+			color = CLUT_NiceBlue;
 		}
-		tInfo_write_content_simple(  30, 770, 50 + (index * 30), &FontT24, (char*)lines[index], color);
+		tInfo_write_content_simple(  30, 770, 60 + (index * 30), &FontT24, (char*)lines[index], color);
 
 		if(lineReadIndex != lineWriteIndex)			/* needed for isUpdated function */
 		{