123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424 |
- #include <stdio.h>
- #include <stdlib.h>
- #include <string.h>
- #include <stdint.h>
- #include <stdbool.h>
- #include <limits.h>
- #include <gfambrtumst.h>
- #include "mbmstapp.h"
- #include "inc/hw_memmap.h"
- #include "inc/hw_gpio.h"
- #include "inc/hw_uart.h"
- #include "inc/hw_ints.h"
- #include "driverlib/gpio.h"
- #include "driverlib/uart.h"
- #include "driverlib/sysctl.h"
- #include "driverlib/pin_map.h"
- #if HW_PLATFORM == HW_PLATFORM_OLS1V
- #include "ols1v.h"
- #elif HW_PLATFORM == HW_PLATFORM_EAV1V
- #include "eav1v.h"
- #else
- #error Unknown hardware platform!
- #endif // HW_PLATFORM
- /////////////////////////////////////////////////////////////////////////////
- #define _REQ_DELAY 10
- #define _METRONIK_SENSOR_SLAVE_ID 0x40
- #define _NEDAP_SLAVE_ID_1 1
- #define _NEDAP_SLAVE_ID_2 2
- #define TID_METRONIC_ILM_READ_UV 0x0101
- #define TID_METRONIC_ILM_READ_TEMP 0x0102
- #define TID_METRONIC_ILM_READ_SERIAL 0x0103
- #define TID_METRONIC_ILM_READ_RANGE 0x0104
- #define TID_NEDAP_CLEAR_CTRS_AND_DIAGNOSTIC_REG 0x0201
- #define TID_NEDAP_REPORT_SLAVE_ID 0x0202
- #define TID_NEDAP_PRESET_SINGLE_REGISTER_7 0x0203
- #define TID_NEDAP_WRITE_MULTIPLE_REGISTERS_7_2 0x0204
- #define TID_NEDAP_RETURN_BUS_EXCEPTION_ERROR_COUNT 0x0205
- #define TID_NEDAP_READ_REGISTERS_0_50 0x0206
- /////////////////////////////////////////////////////////////////////////////
- static HMBRTUMST g_hMbMst = NULL;
- static uint64_t g_nSendTick = 0;
- static bool g_bCTS = false;
- static uint16_t g_nRegs[MODBUS_MAX_READ_REGISTERS] = {0};
- /////////////////////////////////////////////////////////////////////////////
- static void _OnMasterStateChanged(GFA_MODBUS_RTU_MST_STATES newState, GFA_MODBUS_RTU_MST_STATES oldState)
- {
- switch(newState)
- {
- case MB_RTU_MST_Idle:
- // OlsClearLeds(OLS_LED_MASK);
- break;
- case MB_RTU_MST_TxStart:
- // OlsSetLeds(OLS_LED_GREEN_RIGHT);
- break;
- case MB_RTU_MST_TxDone:
- // OlsClearLeds(OLS_LED_GREEN_RIGHT);
- break;
- case MB_RTU_MST_RxSlvID:
- // OlsSetLeds(OLS_LED_GREEN_LEFT);
- break;
- case MB_RTU_MST_RxError:
- // OlsClearSetLeds(OLS_LED_MASK, OLS_LED_RED_TOP);
- break;
- case MB_RTU_MST_ReportError:
- // OlsClearSetLeds(OLS_LED_MASK, OLS_LED_RED_BOTTOM);
- break;
- }
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _RetriggerRequestTimer(void)
- {
- g_nSendTick = GfaSystickGetCount() + _REQ_DELAY;
- }
- /////////////////////////////////////////////////////////////////////////////
- static bool _RequestTimerElapsed(void)
- {
- return g_nSendTick < GfaSystickGetCount();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _ReportError(uint16_t errcode)
- {
- // Report error. See gfambrtumst.h for error codes
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _FinishRequest(void)
- {
- _RetriggerRequestTimer();
- g_bCTS = true;
- }
- /////////////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////////////
- static void _OnReadRegistersComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, const uint16_t *pRegs, size_t nRegCount)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- if(nTID == TID_NEDAP_READ_REGISTERS_0_50)
- {
- // ...
- }
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnWriteRegistersComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, uint16_t nRegStart, uint16_t nRegsWritten)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnPresetRegisterComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnDiagnosisComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, uint16_t nSubFunc, uint16_t nData)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- switch(nSubFunc)
- {
- case MB_SUBFUNC_CLEAR_CTRS_AND_DIAGNOSTIC_REG:
- // Success! Do whatever needs to be done ...
- break;
- case MB_SUBFUNC_RETURN_BUS_EXCEPTION_ERROR_COUNT:
- // Success! Do whatever needs to be done ...
- break;
- }
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnReportSlaveIDComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, const void *pData, size_t nCbData)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnReadUVComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, uint16_t nVal)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnReadTempComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, uint8_t nVal)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnReadRangeComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, uint16_t nVal)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _OnReadSerialComplete(uint32_t nTID, uint8_t nSlvID, uint16_t err, const uint8_t *pVal, size_t nCbVal)
- {
- if(err)
- {
- _ReportError(err);
- }
- else
- {
- // Success! Do whatever needs to be done ...
- }
- _FinishRequest();
- }
- /////////////////////////////////////////////////////////////////////////////
- static bool _DoMetronik(uint8_t nSlaveID)
- {
- static uint32_t nState = 0;
- bool bRet = false;
- switch(nState++ % 4)
- {
- case 0:
- bRet = GfaModbusRTUMstILMReadUV(g_hMbMst, TID_METRONIC_ILM_READ_UV, nSlaveID, _OnReadUVComplete);
- break;
- case 1:
- bRet = GfaModbusRTUMstILMReadTemp(g_hMbMst, TID_METRONIC_ILM_READ_TEMP, nSlaveID, _OnReadTempComplete);
- break;
- case 2:
- bRet = GfaModbusRTUMstILMReadSerial(g_hMbMst, TID_METRONIC_ILM_READ_SERIAL, nSlaveID, _OnReadSerialComplete);
- break;
- case 3:
- bRet = GfaModbusRTUMstILMReadRange(g_hMbMst, TID_METRONIC_ILM_READ_RANGE, nSlaveID, _OnReadRangeComplete);
- break;
- }
- return bRet;
- }
- /////////////////////////////////////////////////////////////////////////////
- static bool _DoNedap(uint8_t nSlaveID, uint32_t *pnState)
- {
- bool bRet = false;
- switch((*pnState)++)
- {
- case 0:
- bRet = GfaModbusRTUMstDiagnosis(g_hMbMst, TID_NEDAP_CLEAR_CTRS_AND_DIAGNOSTIC_REG, nSlaveID, MB_SUBFUNC_CLEAR_CTRS_AND_DIAGNOSTIC_REG, 0, _OnDiagnosisComplete);
- break;
- case 1:
- bRet = GfaModbusRTUMstReportSlaveID(g_hMbMst, TID_NEDAP_REPORT_SLAVE_ID, nSlaveID, 4, _OnReportSlaveIDComplete);
- break;
- case 10:
- bRet = GfaModbusRTUMstPresetSingleRegister(g_hMbMst, TID_NEDAP_PRESET_SINGLE_REGISTER_7, nSlaveID, 7, 0x801E, _OnPresetRegisterComplete);
- break;
- case 50:
- g_nRegs[0] = 0x801E;
- g_nRegs[1] = 0x0015;
- bRet = GfaModbusRTUMstWriteMultipleRegisters(g_hMbMst, TID_NEDAP_WRITE_MULTIPLE_REGISTERS_7_2, nSlaveID, 7, 2, g_nRegs, _OnWriteRegistersComplete);
- break;
- case 100:
- bRet = GfaModbusRTUMstDiagnosis(g_hMbMst, TID_NEDAP_RETURN_BUS_EXCEPTION_ERROR_COUNT, nSlaveID, MB_SUBFUNC_RETURN_BUS_EXCEPTION_ERROR_COUNT, 0, _OnDiagnosisComplete);
- *pnState = 1;
- break;
- default:
- bRet = GfaModbusRTUMstReadHoldingRegisters(g_hMbMst, TID_NEDAP_READ_REGISTERS_0_50, nSlaveID, 0, 50, _OnReadRegistersComplete);
- break;
- }
- return bRet;
- }
- /////////////////////////////////////////////////////////////////////////////
- static void _InitUARTConfig(LPGFA_UART_CONFIG puc)
- {
- memset(puc, 0, sizeof(LPGFA_UART_CONFIG));
- puc->P_UART_BASE = UART_BASE;
- puc->P_UART_BASE_SYSCTL = UART_BASE_SYSCTL;
- puc->P_UART_PORT = UART_PORT;
- puc->P_UART_PORT_SYSCTL = UART_PORT_SYSCTL;
- puc->P_UART_RX_PIN = UART_RX_PIN;
- puc->P_UART_RX_PIN_MUX = UART_RX_PIN_MUX;
- puc->P_UART_TX_PIN = UART_TX_PIN;
- puc->P_UART_TX_PIN_MUX = UART_TX_PIN_MUX;
- puc->P_UART_INT = UART_INT;
- puc->P_UART_INT_PRIORITY = MODBUS_RTU_UART_INT_PRIORITY;
- puc->P_EN_485_PORT_SYSCTL = EN_485_PORT_SYSCTL;
- puc->P_EN_485_PORT = EN_485_PORT;
- puc->P_EN_485_PIN = EN_485_PIN;
- puc->nBaud = MODBUS_RTU_BAUDRATE;
- puc->nDatabits = MODBUS_RTU_DATABITS;
- puc->nStopbits = MODBUS_RTU_STOPBITS;
- puc->parity = MODBUS_RTU_PARITY;
- puc->nFifoIndexRx = 0;
- puc->nFifoIndexTx = 1;
- }
- /////////////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////////////
- /////////////////////////////////////////////////////////////////////////////
- bool GfaInitModbusMasterApp(void)
- {
- GFA_UART_CONFIG uartParams;
- g_hMbMst = NULL;
- _InitUARTConfig(&uartParams);
- if(GfaMbUartInit(&uartParams))
- {
- GFA_MODBUS_RTU_MASTER_PARAMETERS mstParams;
- memset(&mstParams, 0, sizeof(mstParams));
- mstParams.hFifoRX = GfaMbUartGetRxFifo();
- mstParams.hFifoTX = GfaMbUartGetTxFifo();
- mstParams.nRxTimeoutUs = MODBUS_RTU_MASTER_RX_TIMEOUT_US;
- GfaMbUartGetProtocolTimeouts(&mstParams.mpt);
- mstParams.appItf.pfnStateChanged = _OnMasterStateChanged;
- if(!(g_hMbMst = GfaModbusRTUMstCreate(&mstParams)))
- GfaMbUartRelease();
- else
- g_bCTS = true;
- }
- return !!g_hMbMst;
- }
- /////////////////////////////////////////////////////////////////////////////
- void GfaDoModbusMasterApp(void)
- {
- static uint32_t nLoop = 0, nStateN1 = 0, nStateN2 = 0;
- bool bRet = false;
- if(g_bCTS && _RequestTimerElapsed())
- {
- g_bCTS = false;
- switch(nLoop++ % 3)
- {
- case 0:
- bRet = _DoMetronik(_METRONIK_SENSOR_SLAVE_ID);
- break;
- case 1:
- bRet = _DoNedap(_NEDAP_SLAVE_ID_1, &nStateN1);
- break;
- case 2:
- bRet = _DoNedap(_NEDAP_SLAVE_ID_2, &nStateN2);
- break;
- }
- if(!bRet)
- {
- _ReportError(GFA_MB_MST_ERROR_UNEXPECTED);
- _FinishRequest();
- }
- }
- GfaModbusRTUMstStateMachine(g_hMbMst);
- }
- /////////////////////////////////////////////////////////////////////////////
|