MANET achieve

The only says how to implement communication protocol with the C language, the underlying driver code specific SX1278 have a chance to say.

LoRaWAN a little trouble, you need to access the network, or self-built servers, are too expensive, might as well get hold of their own ad hoc network completely free, completely on my own customization.

First to thank my mentor before writing any teacher, no teacher supervision preference I may not like this, nor will these things.

This article may be some places not the right place, please correct me.

To save time and effort, I'll just modify existing agreements, and their design is too much trouble, I have finished the design becomes bald.

# 1. Design improving communication protocol

I use the company and in the industry using more of the Modbus protocol, ModBus by Modicon invented in 1979, is the world's first truly bus protocol for industrial field.

modbus简介
https://www.ni.com/zh-cn/innovations/white-papers/14/the-modbus-protocol-in-depth.html

Here Insert Picture Description
Modbus protocol data frame structure for the function code + slave address + data + checksum.

I want to use, then it needs to be improved, along with the data frame in a network address, such devices have two ID, device naming more standardized.

Improved data frames as follows:

Gateway:
Here Insert Picture Description
Slave:
Here Insert Picture Description

In fact, almost all parameters and the data is changed names.

# 2. DETAILED DESCRIPTION step

# 2.1 communication process
communication is nothing more than a gateway sends a command, the slave accepts data processing command and the process returns to the gateway receiving process data.

The gateway transmits a command function: sendMasterAsk(unsigned char slave_addr,unsigned char op_code,unsigned char pram);
gateway accepts data functions: receiveSlaveAck(unsigned char slave_addr,unsigned char op_code,unsigned char pram,DeviceBlock * pdevblock);
from the command gateway function processing machine:processMasterAsk(DeviceBlock * pdevblock);

# 2.2 Related Definitions section addresses
before writing the transmit and receive functions to get the preparation done, first written definition of each parameter, this can be written as an array of variables can be written macros can also be written, the personal preferences.

I wrote a macro definition, a good change up to the time change.

Gateway address, slave address, opcode, data is 8 bytes, unsigned char is just 8 bytes, so the relevant definitions are unsigned char; to space more luxurious, because I do not want to see one by one bit What is the meaning, too uncomfortable, especially in 1553, a bitter tears.

/*网络相关宏定义*/
#define NET_ADDR           0xB9    //网络地址
#define SLAVE1_ADDR        0x01    //子设备1地址
#define SLAVE2_ADDR        0x02    //子设备2地址
#define SLAVE3_ADDR        0x03    //子设备3地址

/*操作码相关宏定义*/
#define OP_R_SENSOR        0x01    //读传感器数据

/*参数相关宏定义*/
#define PRAM_R_TEMPERATURE 0x01    //只读取温度
#define PRAM_R_BPM         0x02    //只读取心跳
#define PRAM_R_HUMIDITY    0x03    //只读取湿度
#define PRAM_R_ALL         0x07    //读取所有传感器

设备块---主要是用起来方便
typedef struct 
{
    unsigned char Temperature;  //温度
    unsigned char BPM;     //BPM
    unsigned short int HUMIDITY;     //环境湿度
}DeviceBlock;

# 2.3 gateway transmitting section

Code section:

 sendMasterAsk(unsigned char slave_addr,unsigned char op_code,unsigned char pram)
{
    
    unsigned char sendbuffer[6] = {NET_ADDR,slave_addr,op_code,pram,0,0};  按照通信协议排列
    unsigned short int CRC16 = getModbusCRC16(sendbuffer,4);             

    sendbuffer[4] = CRC16>>8;                                             
    sendbuffer[5] = CRC16;                                               
    
    transmitPackets(sendbuffer,sizeof(sendbuffer));                     //发送
}

Set a network address array write the code, slave address, opcode parameters (that is, in this operation code to do things), and the remaining two is the CRC, the CRC can be implemented in hardware, the software can also be used, this does not matter. Finally API to send SX1278 on the line.

slave_addr是子机地址,调用时输入定义的地址
op_code是操作码,pram是操作码下相关操作

# 2.4 slave processing instruction section
code section:

processMasterAsk(DeviceBlock * pdevblock)
{
    unsigned char Askbuffer[6];  网关发给从机的数据
    unsigned char Ackbuffer[9] = {NET_ADDR,SLAVE1_ADDR}; 从机返回给网关的数据,按照通信协议排列
    unsigned char len;
    unsigned short int CRC16;
    unsigned char i;

    if(receivePackets(Askbuffer)==1)   表示收到数据
    {
        if(Askbuffer[0] != NET_ADDR)   检测网络地址对不对
        {
            return FRAME_NETADDR_ERR;  返回网络地址错误代码
        }

        if(Askbuffer[1] != SLAVE3_ADDR)  检测从机地址对不对
        {
            return FRAME_SLAVEADDR_ERR;  返回从机地址错误代码
        }

        len = getFrameLength(Askbuffer,sizeof(Askbuffer));  检测实际长度


		没问题后开始处理数据
      if(Askbuffer[2] == OP_R_SENSOR)   
        {
            Ackbuffer[2] = OP_R_SENSOR;

            for(i=0;i<8;++i) 8个字节每个位都来一遍,从第0位到第7{
                switch(Askbuffer[3] & (0x01<<i)) i从0位开始移位1每次移移位,移8次,对比呢个位是1,相同就走哪一步,具体定义见参数定义数字,然后将对应传感器数据写入设备块数据准备发送
                {
                    case PRAM_R_TEMPERATURE:Ackbuffer[3] = pdevblock->Temperature;break;

                    case PRAM_R_HUMIDITY   :Ackbuffer[4] = pdevblock->HUMIDITY;   break;

                    case PRAM_R_BPM        :
                    {
                                                Ackbuffer[5] = pdevblock->BPM;
                                            }                                     break;
                    default                :                                      break;
                }
            }

            CRC16 = getModbusCRC16(Ackbuffer,7);

            Ackbuffer[7] = CRC16>>8;

            Ackbuffer[8] = CRC16;

        }
}

# 2.4 gateway accepts part of the
code section:
most of them from the machine and the same part, facing it out

receiveSlaveAck(unsigned char slave_addr,unsigned char op_code,unsigned char pram,DeviceBlock * pdevblock)
{
    unsigned char receivebuffer[9];收到的从机数据
    unsigned char len;
    unsigned char i;

    if(receivePackets(receivebuffer)==1)
    {
        if(receivebuffer[0] != NET_ADDR) 
        {
            return FRAME_NETADDR_ERR;
        }

        if(receivebuffer[1] != slave_addr)
        {
            return FRAME_SLAVEADDR_ERR;
        }

        len = getFrameLength(receivebuffer,sizeof(receivebuffer));
   
      
     if(op_code==OP_R_SENSOR)    
        {
         
            for(i=0;i<8;++i)
            {

                switch(pram & (0x01<<i))
                {
                    case PRAM_R_TEMPERATURE:(pdevblock+slave_addr)->Temperature = receivebuffer[3];                break;  
                    读出从机传来的数据
                    case PRAM_R_HUMIDITY   :(pdevblock+slave_addr)->HUMIDITY = receivebuffer[4];                   break;
                    case PRAM_R_BPM        :(pdevblock+slave_addr)->BPM = receivebuffer[5];  break;
                    default                :                                                                       break;
                }                             
            }
        }
}

Released two original articles · won praise 1 · views 1324

Guess you like

Origin blog.csdn.net/qq_37870032/article/details/104683127