Solar panel
Loading...
Searching...
No Matches
modbus.c
Go to the documentation of this file.
1
2
3#include "modbus.h"
4#include "crc.h"
5
6// Modbus functions
7#define READ_INPUT_REGISTERS 0x04
8#define READ_HOLDING_REGISTERS 0x03
9#define WRITE_SINGLE_REGISTER 0x06
10
11// Modbus data model
13uint16_t input_registers[2];
15
16
17// Modbus error codes
18#define ILLEGAL_FUNCTION 1
19#define ILLEGAL_DATA_ADDRESS 2
20#define ILLEGAL_DATA_VALUE 3
21#define SLAVE_DEVICE_FAILURE 4
22
27uint8_t rx_buf[256];
28uint8_t tx_buf[256];
29
30// Current position pointer for storing receive position
31uint8_t recPtr = 0;
32
33void modbus_timer(void) {
34 INTCONbits.TMR0IF = 0;
35 recPtr = 0;
38}
39extern uint16_t measure_voltage();
41 // TODO -> complete the modbus analyse and answer
42 uint16_t length = 0;
43 if(rx_buf[0] == modbusAddress){
44 tx_buf[0] = rx_buf[0]; // Adress
45 tx_buf[1] = rx_buf[1]; // Function
46 uint16_t adresseRegister = ((uint16_t)rx_buf[2] << 8) | rx_buf[3];
47
48 switch(rx_buf[1]){ // Check the function from rx buffer
50 length = ((uint16_t)rx_buf[4] << 8) | rx_buf[5];
51 tx_buf[2] = (uint8_t)(length*2); // Data length
52 for(uint16_t i = 0; i < length; i++){ // Data
53 tx_buf[i*2+4] = input_registers[adresseRegister+i];
54 tx_buf[i*2+3] = (input_registers[adresseRegister+i] >> 8);
55 }
56 length*=2;
57 length+=3;
58 break;
60 length = ((uint16_t)rx_buf[4] << 8) | rx_buf[5];
61 tx_buf[2] = (uint8_t)(length*2); // Data length
62 for(uint16_t i = 0; i < length; i++){ // Data
63 tx_buf[i*2+4] = holding_registers[adresseRegister+i];
64 tx_buf[i*2+3] = (holding_registers[adresseRegister+i] >> 8);
65 }
66 length*=2;
67 length+=3;
68 break;
70 holding_registers[adresseRegister] = ((uint16_t)rx_buf[4] << 8) | rx_buf[5];
71 for (int i = 2; i <= 5; i++) {
72 tx_buf[i] = rx_buf[i];
73 length = i+1;
74 }
75 break;
76 }
77
78 }
79
80 rx_buf[0] = 0;
81 modbus_send(length);
82
83}
84
86{
87 rx_buf[recPtr++] = RCREG1;
90}
91
92void modbus_send(uint8_t length)
93{
94
95 uint16_t crc = CRC16(tx_buf, length);
96
97 tx_buf[length] = crc;
98 tx_buf[length+1] = crc >> 8;
99
100 length += 2; // add 2 CRC bytes for total size
101
102 // For all the bytes to be transmitted
103 for (uint8_t i = 0; i < length; i++){
105 }
106}
107
108void modbus_init(uint8_t address)
109{
110 modbusAddress = address;
111 holding_registers[1] = address;
114}
uint16_t CRC16(const uint8_t *msg, uint16_t length)
Definition: crc.c:48
CRC calculation for Modbus.
void EUSART1_SetRxInterruptHandler(void(*interruptHandler)(void))
Definition: eusart1.c:234
void EUSART1_Write(uint8_t txData)
Definition: eusart1.c:162
uint16_t measure_voltage()
Definition: measure.c:37
uint16_t holding_registers[2]
Definition: modbus.c:14
uint8_t modbusAddress
Definition: modbus.c:12
uint8_t tx_buf[256]
Definition: modbus.c:28
void modbus_init(uint8_t address)
Definition: modbus.c:108
uint8_t modbus_analyse_and_answer(void)
Definition: modbus.c:40
#define READ_HOLDING_REGISTERS
Modbus function for read holding register = 03.
Definition: modbus.c:8
#define READ_INPUT_REGISTERS
Modbus function for read input register = 04.
Definition: modbus.c:7
uint8_t rx_buf[256]
Definition: modbus.c:27
uint8_t recPtr
Definition: modbus.c:31
void modbus_char_recvd(void)
Definition: modbus.c:85
void modbus_timer(void)
Definition: modbus.c:33
#define WRITE_SINGLE_REGISTER
Modbus function for write a single register = 06.
Definition: modbus.c:9
void modbus_send(uint8_t length)
Definition: modbus.c:92
uint16_t input_registers[2]
Definition: modbus.c:13
Modbus serial library.
void TMR0_SetInterruptHandler(void(*InterruptHandler)(void))
Definition: tmr0.c:156
void TMR0_StartTimer(void)
Definition: tmr0.c:97
void TMR0_Reload(void)
Definition: tmr0.c:129
void TMR0_StopTimer(void)
Definition: tmr0.c:103