# HG changeset patch # User Ideenmodellierer # Date 1684871134 -7200 # Node ID 0b5f45448eb6f97b2def20f28ebcc78fcda7593d # Parent 74253a41cf80fc51d668c10a6fcf7361be88826e Added UART multiplexer support for DiveO2: The existing autodetect function now includes a UART multiplexer. The datastructures and protocol handling has been adapted to support several DiveO2 sensors connected to the UART. diff -r 74253a41cf80 -r 0b5f45448eb6 Small_CPU/Inc/externalInterface.h --- a/Small_CPU/Inc/externalInterface.h Mon May 22 09:15:09 2023 +0200 +++ b/Small_CPU/Inc/externalInterface.h Tue May 23 21:45:34 2023 +0200 @@ -46,7 +46,10 @@ DETECTION_START, DETECTION_ANALOG1, /* check ADC channels for connected sensors */ DETECTION_ANALOG2, - DETECTION_DIGO2, /* check UART channel for connected DigO2 sensor */ + DETECTION_UARTMUX, /* check if a uart multiplexer is present */ + DETECTION_DIGO2_0, /* check UART channel for connected DigO2 sensor */ + DETECTION_DIGO2_1, + DETECTION_DIGO2_2, #ifdef ENABLE_CO2_SUPPORT DETECTION_CO2, /* check UART channel for connected CO2 sensor */ #endif @@ -81,7 +84,7 @@ uint16_t externalInterface_GetCO2SignalStrength(void); void externalInterface_SetCO2State(uint16_t state); uint16_t externalInterface_GetCO2State(void); -uint8_t externalInterface_GetSensorData(uint8_t* pDataStruct); +uint8_t externalInterface_GetSensorData(uint8_t sensorId, uint8_t* pDataStruct); void externalInterface_SetSensorData(uint8_t dataId, uint8_t* pDataStruct); void externalInface_SetSensorMap(uint8_t* pMap); uint8_t* externalInterface_GetSensorMapPointer(uint8_t finalMap); diff -r 74253a41cf80 -r 0b5f45448eb6 Small_CPU/Inc/uart.h --- a/Small_CPU/Inc/uart.h Mon May 22 09:15:09 2023 +0200 +++ b/Small_CPU/Inc/uart.h Tue May 23 21:45:34 2023 +0200 @@ -92,6 +92,8 @@ void UART_HandleSentinelData(void); #endif void UART_HandleDigitalO2(void); +void UART_MapDigO2_Channel(uint8_t channel, uint8_t muxAddress); +void UART_SetDigO2_Channel(uint8_t channel); uint8_t UART_isDigO2Connected(); uint8_t UART_isCO2Connected(); uint8_t UART_isSentinelConnected(); diff -r 74253a41cf80 -r 0b5f45448eb6 Small_CPU/Src/externalInterface.c --- a/Small_CPU/Src/externalInterface.c Mon May 22 09:15:09 2023 +0200 +++ b/Small_CPU/Src/externalInterface.c Tue May 23 21:45:34 2023 +0200 @@ -67,8 +67,8 @@ static uint16_t externalCO2SignalStrength; static uint16_t externalCO2Status = 0; -static uint8_t sensorDataId = 0; -static SSensorDataDiveO2 sensorDataDiveO2; +static uint8_t lastSensorDataId = 0; +static SSensorDataDiveO2 sensorDataDiveO2[MAX_ADC_CHANNEL]; static externalInterfaceAutoDetect_t externalAutoDetect = DETECTION_OFF; static externalInterfaceSensorType SensorMap[EXT_INTERFACE_SENSOR_CNT] ={ SENSOR_OPTIC, SENSOR_OPTIC, SENSOR_OPTIC, SENSOR_NONE, SENSOR_NONE}; static externalInterfaceSensorType tmpSensorMap[EXT_INTERFACE_SENSOR_CNT]; @@ -331,7 +331,11 @@ case (EXT_INTERFACE_UART_CO2 >> 8): case (EXT_INTERFACE_UART_O2 >> 8): case (EXT_INTERFACE_UART_SENTINEL >> 8): - if((externalAutoDetect <= DETECTION_START) || ((protocol == EXT_INTERFACE_UART_O2 >> 8) && (externalAutoDetect == DETECTION_DIGO2)) + if((externalAutoDetect <= DETECTION_START) + || ((protocol == EXT_INTERFACE_UART_O2 >> 8) && (externalAutoDetect == DETECTION_DIGO2_0)) + || ((protocol == EXT_INTERFACE_UART_O2 >> 8) && (externalAutoDetect == DETECTION_DIGO2_1)) + || ((protocol == EXT_INTERFACE_UART_O2 >> 8) && (externalAutoDetect == DETECTION_DIGO2_2)) + || ((protocol == EXT_INTERFACE_UART_O2 >> 8) && (externalAutoDetect == DETECTION_UARTMUX)) #ifdef ENABLE_CO2_SUPPORT || ((protocol == EXT_INTERFACE_UART_CO2 >> 8) && (externalAutoDetect == DETECTION_CO2)) #endif @@ -340,7 +344,7 @@ #endif ) { - sensorDataId = 0; + lastSensorDataId = 0; externalUART_Protocol = protocol; MX_USART1_UART_DeInit(); if( protocol != 0) @@ -404,29 +408,34 @@ } -uint8_t externalInterface_GetSensorData(uint8_t* pDataStruct) +uint8_t externalInterface_GetSensorData(uint8_t sensorId, uint8_t* pDataStruct) { + uint8_t localId = sensorId; + if(localId == 0) + { + localId = lastSensorDataId; + } - if((pDataStruct != NULL) && sensorDataId != 0) + if((pDataStruct != NULL) && (localId > 0) && (localId <= MAX_ADC_CHANNEL)) { - memcpy(pDataStruct, &sensorDataDiveO2, sizeof(sensorDataDiveO2)); + memcpy(pDataStruct, &sensorDataDiveO2[localId-1], sizeof(SSensorDataDiveO2)); } - return sensorDataId; + return localId; } void externalInterface_SetSensorData(uint8_t dataId, uint8_t* pDataStruct) { if(pDataStruct != NULL) { - if(dataId != 0) + if((dataId != 0) && (dataId <= MAX_ADC_CHANNEL)) { - memcpy(&sensorDataDiveO2, pDataStruct, sizeof(sensorDataDiveO2)); + memcpy(&sensorDataDiveO2[dataId-1], pDataStruct, sizeof(SSensorDataDiveO2)); } else { memset(&sensorDataDiveO2,0,sizeof(sensorDataDiveO2)); } - sensorDataId = dataId; + lastSensorDataId = dataId; } } @@ -455,7 +464,9 @@ void externalInterface_AutodetectSensor() { - static uint8_t sensorIndex = 0; + static uint8_t tmpMuxMapping[MAX_ADC_CHANNEL]; + static uint8_t sensorIndex = 0; + static uint8_t uartMuxChannel = 0; uint8_t index = 0; if(externalAutoDetect != DETECTION_OFF) @@ -463,12 +474,18 @@ switch(externalAutoDetect) { case DETECTION_INIT: sensorIndex = 0; + uartMuxChannel = 0; tmpSensorMap[0] = SENSOR_OPTIC; tmpSensorMap[1] = SENSOR_OPTIC; tmpSensorMap[2] = SENSOR_OPTIC; tmpSensorMap[3] = SENSOR_NONE; tmpSensorMap[4] = SENSOR_NONE; + for(index = 0; index < MAX_ADC_CHANNEL; index++) + { + UART_MapDigO2_Channel(index,index); /* request all addresses */ + tmpMuxMapping[index] = 0xff; + } if(externalInterfacePresent) { externalInterface_SwitchPower33(0); @@ -504,10 +521,22 @@ tmpSensorMap[sensorIndex++] = SENSOR_NONE; } } - externalAutoDetect = DETECTION_DIGO2; + externalAutoDetect = DETECTION_UARTMUX; externalInterface_SwitchUART(EXT_INTERFACE_UART_O2 >> 8); + UART_SetDigO2_Channel(3); break; - case DETECTION_DIGO2: if(UART_isDigO2Connected()) + case DETECTION_UARTMUX: if(UART_isDigO2Connected()) + { + uartMuxChannel = 1; + } + externalAutoDetect = DETECTION_DIGO2_0; + externalInterface_SwitchUART(EXT_INTERFACE_UART_O2 >> 8); + UART_SetDigO2_Channel(0); + + break; + case DETECTION_DIGO2_0: + case DETECTION_DIGO2_1: + case DETECTION_DIGO2_2: if(UART_isDigO2Connected()) { for(index = 0; index < 3; index++) /* lookup a channel which may be used by digO2 */ { @@ -523,14 +552,28 @@ else { tmpSensorMap[index] = SENSOR_DIGO2; + tmpMuxMapping[index] = externalAutoDetect - DETECTION_DIGO2_0; } + UART_setTargetChannel(index); - UART_setTargetChannel(index); /* tmpSensorMap[sensorIndex++] = SENSOR_DIGO2; */ } + if(uartMuxChannel) + { + externalInterface_SwitchUART(EXT_INTERFACE_UART_O2 >> 8); + UART_SetDigO2_Channel(uartMuxChannel); + uartMuxChannel++; + } + else + { + externalAutoDetect = DETECTION_DIGO2_2; /* skip detection of other serial sensors */ + } externalAutoDetect++; #ifdef ENABLE_CO2_SUPPORT - externalInterface_SwitchUART(EXT_INTERFACE_UART_CO2 >> 8); + if(externalAutoDetect == DETECTION_CO2) + { + externalInterface_SwitchUART(EXT_INTERFACE_UART_CO2 >> 8); + } break; case DETECTION_CO2: if(UART_isCO2Connected()) { @@ -554,8 +597,11 @@ externalAutoDetect++; #endif #ifdef ENABLE_SENTINEL_MODE - externalInterface_SwitchUART(EXT_INTERFACE_UART_SENTINEL >> 8); - UART_StartDMA_Receiption(); + if(externalAutoDetect == DETECTION_SENTINEL) + { + externalInterface_SwitchUART(EXT_INTERFACE_UART_SENTINEL >> 8); + UART_StartDMA_Receiption(); + } break; case DETECTION_SENTINEL: @@ -571,29 +617,19 @@ externalAutoDetect++; #endif break; - case DETECTION_DONE: for(index = 0; index < EXT_INTERFACE_SENSOR_CNT; index++) + case DETECTION_DONE: if(uartMuxChannel) { - if(tmpSensorMap[index] != SENSOR_NONE) - { - break; - } + tmpSensorMap[EXT_INTERFACE_SENSOR_CNT-1] = SENSOR_MUX; } - - if(index != EXT_INTERFACE_SENSOR_CNT) /* return default sensor map if no sensor at all has been detected */ + for(index = 0; index < MAX_ADC_CHANNEL; index++) { - while(sensorIndex < EXT_INTERFACE_SENSOR_CNT) - { - tmpSensorMap[sensorIndex++] = SENSOR_NONE; - } + UART_MapDigO2_Channel(index,tmpMuxMapping[index]); } - else - { - tmpSensorMap[0] = SENSOR_OPTIC; - tmpSensorMap[1] = SENSOR_OPTIC; - tmpSensorMap[2] = SENSOR_OPTIC; - } + externalAutoDetect = DETECTION_OFF; + externalInterface_SwitchUART(0); + UART_SetDigO2_Channel(0); memcpy(SensorMap, tmpSensorMap, sizeof(tmpSensorMap)); - externalAutoDetect = DETECTION_OFF; + break; default: break; diff -r 74253a41cf80 -r 0b5f45448eb6 Small_CPU/Src/uart.c --- a/Small_CPU/Src/uart.c Mon May 22 09:15:09 2023 +0200 +++ b/Small_CPU/Src/uart.c Tue May 23 21:45:34 2023 +0200 @@ -28,6 +28,7 @@ #define CHUNK_SIZE (25u) /* the DMA will handle chunk size transfers */ #define CHUNKS_PER_BUFFER (5u) +#define COMMAND_TX_DELAY (30u) /* The time the sensor needs to recover from a invalid command request */ UART_HandleTypeDef huart1; DMA_HandleTypeDef hdma_usart1_rx; @@ -42,12 +43,14 @@ static uint8_t SentinelConnected = 0; /* Binary indicator if a sensor is connected or not */ static uint8_t ppO2TargetChannel = 0; /* The OSTC4 supports three slots for visualization of the ppo2. This one is reserved for the digital sensor */ -static SSensorDataDiveO2 sensorDataDiveO2; /* intermediate storage for additional sensor data */ +static SSensorDataDiveO2 tmpSensorDataDiveO2; /* intermediate storage for additional sensor data */ char tmpRxBuf[30]; uint8_t tmpRxIdx = 0; static uartO2Status_t Comstatus_O2 = UART_O2_INIT; +static uint8_t activeSensor = 0; +static uint8_t sensorMapping[MAX_ADC_CHANNEL]; /* The mapping is used to assign the visible sensor channel to the mux address (DiveO2) */ float LED_Level = 0.0; /* Normalized LED value which may be used as indication for the health status of the sensor */ float LED_ZeroOffset = 0.0; @@ -124,6 +127,27 @@ } +void DigitalO2_SelectSensor(uint8_t channel) +{ + uint8_t indexstr[4]; + uint8_t muxAddress = 0; + indexstr[0] = '~'; + indexstr[1] = '1'; + indexstr[2] = 0x0D; + indexstr[3] = 0x0A; + + if((channel < MAX_ADC_CHANNEL) && (sensorMapping[channel] != 0xff)) + { + muxAddress = sensorMapping[channel]; + } + else + { + muxAddress = MAX_ADC_CHANNEL; /* default to mux */ + } + indexstr[1] = '0' + muxAddress; + HAL_UART_Transmit(&huart1,indexstr,4,10); +} + void DigitalO2_SetupCmd(uint8_t O2State, uint8_t *cmdString, uint8_t *cmdLength) { switch (O2State) @@ -463,202 +487,277 @@ static uint8_t cmdLength = 0; static uint8_t cmdString[10]; static uint8_t cmdReadIndex = 0; + static uint32_t tickToTX = 0; + static uint32_t delayStartTick = 0; + uint8_t switchChannel = 0; + uint8_t index = 0; uint32_t tmpO2 = 0; uint32_t tmpData = 0; uint8_t localRX = rxReadIndex; uint32_t tick = HAL_GetTick(); - - if(Comstatus_O2 == UART_O2_INIT) - { - memset((char*)&rxBuffer[rxWriteIndex],(int)0,CHUNK_SIZE); - memset((char*) &sensorDataDiveO2, 0, sizeof(sensorDataDiveO2)); - externalInterface_SetSensorData(0,(uint8_t*)&sensorDataDiveO2); + uint8_t *pmap = externalInterface_GetSensorMapPointer(0); - lastAlive = 0; - curAlive = 0; - - Comstatus_O2 = UART_O2_CHECK; - DigitalO2_SetupCmd(Comstatus_O2,cmdString,&cmdLength); + /* The channel switch will cause the sensor to respond with an error message. */ + /* The sensor needs ~30ms to recover before he is ready to receive the next command => transmission delay needed */ + if((tickToTX) && (time_elapsed_ms(delayStartTick,tick) >= tickToTX )) + { HAL_UART_Transmit(&huart1,cmdString,cmdLength,10); + tickToTX = 0; + } + else + { + if(Comstatus_O2 == UART_O2_INIT) + { + memset((char*)&rxBuffer[rxWriteIndex],(int)0,CHUNK_SIZE); + memset((char*) &tmpSensorDataDiveO2, 0, sizeof(tmpSensorDataDiveO2)); + externalInterface_SetSensorData(0,(uint8_t*)&tmpSensorDataDiveO2); - rxState = O2RX_CONFIRM; - cmdReadIndex = 0; - lastO2ReqTick = tick; + lastAlive = 0; + curAlive = 0; - UART_StartDMA_Receiption(); - } - if(time_elapsed_ms(lastO2ReqTick,tick) > 1000) /* repeat request once per second */ - { - lastO2ReqTick = tick; - if(Comstatus_O2 == UART_O2_IDLE) /* cyclic request of o2 value */ - { - Comstatus_O2 = UART_O2_REQ_RAW; + Comstatus_O2 = UART_O2_CHECK; + DigitalO2_SetupCmd(Comstatus_O2,cmdString,&cmdLength); + DigitalO2_SelectSensor(activeSensor); + if(activeSensor < MAX_ADC_CHANNEL) + { + externalInterface_GetSensorData(activeSensor + 1, (uint8_t*)&tmpSensorDataDiveO2); + } + delayStartTick = tick; + tickToTX = COMMAND_TX_DELAY; + rxState = O2RX_CONFIRM; - } - DigitalO2_SetupCmd(Comstatus_O2,cmdString,&cmdLength); - - HAL_UART_Transmit(&huart1,cmdString,cmdLength,10); - } + cmdReadIndex = 0; + lastO2ReqTick = tick; - while((rxBuffer[localRX]!=0)) - { - - lastReceiveTick = tick; - switch(rxState) + UART_StartDMA_Receiption(); + } + if(time_elapsed_ms(lastO2ReqTick,tick) > 1000) /* repeat request once per second */ { - case O2RX_CONFIRM: if(rxBuffer[localRX] == '#') - { - cmdReadIndex = 0; - } - if(rxBuffer[localRX] == cmdString[cmdReadIndex]) - { - cmdReadIndex++; - if(cmdReadIndex == cmdLength - 1) - { - digO2Connected = 1; - tmpRxIdx = 0; - memset((char*) tmpRxBuf, 0, sizeof(tmpRxBuf)); - switch (Comstatus_O2) + lastO2ReqTick = tick; + index = activeSensor; + if(Comstatus_O2 == UART_O2_IDLE) /* cyclic request of o2 value */ + { + if(pmap[EXT_INTERFACE_SENSOR_CNT-1] == SENSOR_MUX) /* select next sensor if mux is connected */ + { + if(activeSensor < MAX_ADC_CHANNEL) + { + do + { + index++; + if(index == MAX_ADC_CHANNEL) + { + index = 0; + } + if(pmap[index] == SENSOR_DIGO2) + { + activeSensor = index; + switchChannel = 1; + break; + } + } while(index != activeSensor); + } + } + + Comstatus_O2 = UART_O2_REQ_RAW; + rxState = O2RX_CONFIRM; + } + if(switchChannel) + { + delayStartTick = tick; + DigitalO2_SelectSensor(activeSensor); + externalInterface_GetSensorData(activeSensor + 1, (uint8_t*)&tmpSensorDataDiveO2); + tickToTX = COMMAND_TX_DELAY; + if(tmpSensorDataDiveO2.sensorId == 0) + { + Comstatus_O2 = UART_O2_REQ_ID; + } + } + else + { + HAL_UART_Transmit(&huart1,cmdString,cmdLength,10); + } + DigitalO2_SetupCmd(Comstatus_O2,cmdString,&cmdLength); + } + + while((rxBuffer[localRX]!=0)) + { + lastReceiveTick = tick; + switch(rxState) + { + case O2RX_CONFIRM: if(rxBuffer[localRX] == '#') { - case UART_O2_CHECK: Comstatus_O2 = UART_O2_REQ_ID; - rxState = O2RX_CONFIRM; - DigitalO2_SetupCmd(Comstatus_O2,cmdString,&cmdLength); - HAL_UART_Transmit(&huart1,cmdString,cmdLength,10); - break; - case UART_O2_REQ_ID: rxState = O2RX_GETNR; - break; - case UART_O2_REQ_INFO: rxState = O2RX_GETTYPE; - break; - case UART_O2_REQ_RAW: - case UART_O2_REQ_O2: rxState = O2RX_GETO2; - break; - default: Comstatus_O2 = UART_O2_IDLE; - rxState = O2RX_IDLE; + cmdReadIndex = 0; + } + if(rxBuffer[localRX] == cmdString[cmdReadIndex]) + { + cmdReadIndex++; + if(cmdReadIndex == cmdLength - 1) + { + digO2Connected = 1; + tmpRxIdx = 0; + memset((char*) tmpRxBuf, 0, sizeof(tmpRxBuf)); + switch (Comstatus_O2) + { + case UART_O2_CHECK: Comstatus_O2 = UART_O2_IDLE; break; - } - } - } - break; - - case O2RX_GETSTATUS: - case O2RX_GETTEMP: - case O2RX_GETTYPE: - case O2RX_GETVERSION: - case O2RX_GETCHANNEL: - case O2RX_GETSUBSENSORS: - case O2RX_GETO2: - case O2RX_GETNR: - case O2RX_GETDPHI: - case O2RX_INTENSITY: - case O2RX_AMBIENTLIGHT: - case O2RX_PRESSURE: - case O2RX_HUMIDITY: - if(rxBuffer[localRX] != 0x0D) - { - if(rxBuffer[localRX] != ' ') - { - tmpRxBuf[tmpRxIdx++] = rxBuffer[localRX]; - } - else - { - if(tmpRxIdx != 0) - { - switch(rxState) - { - case O2RX_GETCHANNEL: StringToInt(tmpRxBuf,&tmpData); - rxState = O2RX_GETVERSION; + case UART_O2_REQ_ID: rxState = O2RX_GETNR; + break; + case UART_O2_REQ_INFO: rxState = O2RX_GETTYPE; + break; + case UART_O2_REQ_RAW: + case UART_O2_REQ_O2: rxState = O2RX_GETO2; + break; + default: Comstatus_O2 = UART_O2_IDLE; + rxState = O2RX_IDLE; break; - case O2RX_GETVERSION: StringToInt(tmpRxBuf,&tmpData); - rxState = O2RX_GETSUBSENSORS; - break; - case O2RX_GETTYPE: StringToInt(tmpRxBuf,&tmpData); - rxState = O2RX_GETCHANNEL; - break; - - case O2RX_GETO2: StringToInt(tmpRxBuf,&tmpO2); - setExternalInterfaceChannel(ppO2TargetChannel,(float)(tmpO2 / 10000.0)); - rxState = O2RX_GETTEMP; - break; - case O2RX_GETTEMP: StringToInt(tmpRxBuf,(uint32_t*)&sensorDataDiveO2.temperature); - rxState = O2RX_GETSTATUS; - break; - case O2RX_GETSTATUS: StringToInt(tmpRxBuf,&sensorDataDiveO2.status); /* raw data cycle */ - rxState = O2RX_GETDPHI; - break; - case O2RX_GETDPHI: /* ignored to save memory and most likly irrelevant for diver */ - rxState = O2RX_INTENSITY; - break; - case O2RX_INTENSITY: StringToInt(tmpRxBuf,(uint32_t*)&sensorDataDiveO2.intensity); /* raw data cycle */ - rxState = O2RX_AMBIENTLIGHT; - break; - case O2RX_AMBIENTLIGHT: StringToInt(tmpRxBuf,(uint32_t*)&sensorDataDiveO2.ambient); /* raw data cycle */ - rxState = O2RX_PRESSURE; - break; - case O2RX_PRESSURE: StringToInt(tmpRxBuf,(uint32_t*)&sensorDataDiveO2.pressure); /* raw data cycle */ - rxState = O2RX_HUMIDITY; - break; - default: - break; - } - memset((char*) tmpRxBuf, 0, tmpRxIdx); - tmpRxIdx = 0; } } } - else - { - switch (rxState) + break; + + case O2RX_GETSTATUS: + case O2RX_GETTEMP: + case O2RX_GETTYPE: + case O2RX_GETVERSION: + case O2RX_GETCHANNEL: + case O2RX_GETSUBSENSORS: + case O2RX_GETO2: + case O2RX_GETNR: + case O2RX_GETDPHI: + case O2RX_INTENSITY: + case O2RX_AMBIENTLIGHT: + case O2RX_PRESSURE: + case O2RX_HUMIDITY: + if(rxBuffer[localRX] != 0x0D) { - case O2RX_GETSTATUS: StringToInt(tmpRxBuf,&sensorDataDiveO2.status); - externalInterface_SetSensorData(1,(uint8_t*)&sensorDataDiveO2); - Comstatus_O2 = UART_O2_IDLE; - rxState = O2RX_IDLE; - break; - case O2RX_GETSUBSENSORS: StringToInt(tmpRxBuf,&tmpData); - Comstatus_O2 = UART_O2_IDLE; - rxState = O2RX_IDLE; + if(rxBuffer[localRX] != ' ') /* the following data entities are placed within the data stream => no need to store data at the end */ + { + tmpRxBuf[tmpRxIdx++] = rxBuffer[localRX]; + } + else + { + if(tmpRxIdx != 0) + { + switch(rxState) + { + case O2RX_GETCHANNEL: StringToInt(tmpRxBuf,&tmpData); + rxState = O2RX_GETVERSION; + break; + case O2RX_GETVERSION: StringToInt(tmpRxBuf,&tmpData); + rxState = O2RX_GETSUBSENSORS; + break; + case O2RX_GETTYPE: StringToInt(tmpRxBuf,&tmpData); + rxState = O2RX_GETCHANNEL; + break; + + case O2RX_GETO2: StringToInt(tmpRxBuf,&tmpO2); + setExternalInterfaceChannel(activeSensor,(float)(tmpO2 / 10000.0)); + rxState = O2RX_GETTEMP; + break; + case O2RX_GETTEMP: StringToInt(tmpRxBuf,(uint32_t*)&tmpSensorDataDiveO2.temperature); + rxState = O2RX_GETSTATUS; + break; + case O2RX_GETSTATUS: StringToInt(tmpRxBuf,&tmpSensorDataDiveO2.status); /* raw data cycle */ + rxState = O2RX_GETDPHI; + break; + case O2RX_GETDPHI: /* ignored to save memory and most likly irrelevant for diver */ + rxState = O2RX_INTENSITY; + break; + case O2RX_INTENSITY: StringToInt(tmpRxBuf,(uint32_t*)&tmpSensorDataDiveO2.intensity); /* raw data cycle */ + rxState = O2RX_AMBIENTLIGHT; + break; + case O2RX_AMBIENTLIGHT: StringToInt(tmpRxBuf,(uint32_t*)&tmpSensorDataDiveO2.ambient); /* raw data cycle */ + rxState = O2RX_PRESSURE; + break; + case O2RX_PRESSURE: StringToInt(tmpRxBuf,(uint32_t*)&tmpSensorDataDiveO2.pressure); /* raw data cycle */ + rxState = O2RX_HUMIDITY; + break; + default: + break; + } + memset((char*) tmpRxBuf, 0, tmpRxIdx); + tmpRxIdx = 0; + } + } + } + else + { /* the following data items are the last of a sensor respond => store temporal data */ + switch (rxState) + { + case O2RX_GETSTATUS: StringToInt(tmpRxBuf,&tmpSensorDataDiveO2.status); + externalInterface_SetSensorData(activeSensor+1,(uint8_t*)&tmpSensorDataDiveO2); + Comstatus_O2 = UART_O2_IDLE; + rxState = O2RX_IDLE; + break; + case O2RX_GETSUBSENSORS: StringToInt(tmpRxBuf,&tmpData); + Comstatus_O2 = UART_O2_IDLE; + rxState = O2RX_IDLE; + break; + case O2RX_HUMIDITY: StringToInt(tmpRxBuf,(uint32_t*)&tmpSensorDataDiveO2.humidity); /* raw data cycle */ + externalInterface_SetSensorData(activeSensor+1,(uint8_t*)&tmpSensorDataDiveO2); + Comstatus_O2 = UART_O2_IDLE; + rxState = O2RX_IDLE; + break; + case O2RX_GETNR: StringToUInt64((char*)tmpRxBuf,&tmpSensorDataDiveO2.sensorId); + externalInterface_SetSensorData(activeSensor+1,(uint8_t*)&tmpSensorDataDiveO2); + index = activeSensor; + + if(switchChannel == 0) + { + Comstatus_O2 = UART_O2_IDLE; + rxState = O2RX_IDLE; + } break; - case O2RX_HUMIDITY: StringToInt(tmpRxBuf,(uint32_t*)&sensorDataDiveO2.humidity); /* raw data cycle */ - externalInterface_SetSensorData(1,(uint8_t*)&sensorDataDiveO2); - Comstatus_O2 = UART_O2_IDLE; - rxState = O2RX_IDLE; - break; - case O2RX_GETNR: StringToUInt64((char*)tmpRxBuf,&sensorDataDiveO2.sensorId); - /* no break */ - default: Comstatus_O2 = UART_O2_IDLE; - rxState = O2RX_IDLE; - break; + default: Comstatus_O2 = UART_O2_IDLE; + rxState = O2RX_IDLE; + break; + } } - } + break; + default: rxState = O2RX_IDLE; break; - default: rxState = O2RX_IDLE; - break; + } + rxBuffer[localRX] = 0; + localRX++; + rxReadIndex++; + if(rxReadIndex >= CHUNK_SIZE * CHUNKS_PER_BUFFER) + { + localRX = 0; + rxReadIndex = 0; + } } - rxBuffer[localRX] = 0; - localRX++; - rxReadIndex++; - if(rxReadIndex >= CHUNK_SIZE * CHUNKS_PER_BUFFER) + + if((digO2Connected) && time_elapsed_ms(lastReceiveTick,HAL_GetTick()) > 4000) /* check for communication timeout */ { - localRX = 0; - rxReadIndex = 0; + digO2Connected = 0; + if(curAlive == lastAlive) + { + setExternalInterfaceChannel(ppO2TargetChannel,0.0); + } + lastAlive = curAlive; + } + if((dmaActive == 0) && (externalInterface_isEnabledPower33())) /* Should never happen in normal operation => restart in case of communication error */ + { + UART_StartDMA_Receiption(); } } +} - if((digO2Connected) && time_elapsed_ms(lastReceiveTick,HAL_GetTick()) > 4000) /* check for communication timeout */ +void UART_SetDigO2_Channel(uint8_t channel) +{ + if(channel <= MAX_ADC_CHANNEL) { - digO2Connected = 0; - if(curAlive == lastAlive) - { - setExternalInterfaceChannel(ppO2TargetChannel,0.0); - } - lastAlive = curAlive; + activeSensor = channel; } - if((dmaActive == 0) && (externalInterface_isEnabledPower33())) /* Should never happen in normal operation => restart in case of communication error */ +} +void UART_MapDigO2_Channel(uint8_t channel, uint8_t muxAddress) +{ + if((channel < MAX_ADC_CHANNEL) && (muxAddress < MAX_ADC_CHANNEL)) { - UART_StartDMA_Receiption(); + sensorMapping[channel] = muxAddress; } }