⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 profdrv.cpp

📁 自己编的用于工业触摸屏通讯的MODBUS RTU SLAVE 协议源代码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
    _coilnum = num;
}
//设置线圈值
int SetCoilVal(unsigned short addr, unsigned char data)
{
    if (0!=pcoilbuf)
    {
        if (addr <= _coilnum)
        {
            (pcoilbuf+addr)->wcoil = data;
            (pcoilbuf+addr)->flag = FLASH_ON;
            return NO_ERR;    
        }else
        {
            return ILLEGAL_DATA_ADDRESS;    
        }
    }else
    {
        return ILLEGAL_DATA_ADDRESS;    
    }		
}
//得到线圈值
int GetCoilVal(unsigned short addr, unsigned char *pdata)
{
    if (0!=pcoilbuf)
    {
        if (addr <= _coilnum)
        {
            *pdata = (pcoilbuf+addr)->rcoil;
            return NO_ERR;    
        }else
        {
            return ILLEGAL_DATA_ADDRESS;    
        }
    }else
    {
        return ILLEGAL_DATA_ADDRESS;    
    }		
}
//写单个线圈05号指令
int MDS_SetSingleCoil(unsigned short *paddr, unsigned short *pnum)
{
    int rvalue;
  	unsigned short data_addr;
  	unsigned char send_count;
  	unsigned int  send_len;
  	unsigned short temp_data = 0;
  	unsigned short crc_data;
	  unsigned char func_no;
	
	  func_no = getbuf[1];  	  	
  	U8ToU16(&getbuf[2], &data_addr);
    U8ToU16(&getbuf[4], &temp_data);
  	if (0==temp_data)
  	{
  	    rvalue = SetCoilVal(data_addr, 0);	
  	}else if(0xFF00==temp_data)
  	{
  	    rvalue = SetCoilVal(data_addr, 1);	
  	}else
  	{
  	    rvalue = ILLEGAL_DATA_VALUE;  	    
  	}
  	if (NO_ERR == rvalue)
    {
      	sendbuf[0] = _addr;
      	sendbuf[1] = func_no;
      	U16ToU8(data_addr, &sendbuf[2]);
      	U16ToU8(temp_data, &sendbuf[4]);
      	crc_data = CRC16(sendbuf,6);
      	U16ToU8(crc_data, &sendbuf[6]);
      	send_count = 8;
      	SendChars(_port, (unsigned int)send_count, sendbuf, &send_len);
      	rvalue = WRITE_BIT;
      	
      	*paddr = data_addr;
      	*pnum = 1;
   }else
   {
       MDS_ResponseErr((unsigned char) rvalue);		
   }
   return rvalue;  		
}
//写多个线圈15号指令
int MDS_SetCoils(unsigned short *paddr, unsigned short *pnum)
{ 
	  int rvalue = NO_ERR;
  	unsigned short data_addr;
  	unsigned short temp_addr;
  	unsigned short bit_count;
  	unsigned char byte_count;
  	unsigned char send_count;
  	unsigned int  send_len;
  	unsigned char temp_data = 0;
  	unsigned char bytecnt;
  	unsigned short bitcnt;
  	unsigned char i;
  	unsigned short crc_data; 
  	unsigned char func_no;
  	
  	func_no = getbuf[1];
  	U8ToU16(&getbuf[2], &data_addr); 	
  	temp_addr = data_addr;
  	U8ToU16(&getbuf[4], &bit_count);
  	byte_count = getbuf[6];
  	for (bytecnt=0;bytecnt<(byte_count-1);++bytecnt)
  	{
  	    temp_data = getbuf[7+bytecnt];
  	    for (i=0;i<8;++i)
  	    {	
      	    if (0==temp_data&(0x1<<i))
      	    {
      	        SetCoilVal(temp_addr, 0);	
      	    }else                             
      	    {
      	        SetCoilVal(temp_addr, 1);	
      	    }
      	    temp_addr++;
      	}
    }
    bitcnt = bit_count - (((unsigned char)(byte_count-1))<<3);
    temp_data = getbuf[7+byte_count-1];
    for (i=0;i<bitcnt;++i)
    {
        if (0==temp_data&(0x1<<i))
      	{
      	    rvalue = SetCoilVal(temp_addr, 0);	
      	}else                             
      	{
      	    rvalue = SetCoilVal(temp_addr, 1);	
      	}
      	temp_addr++;        	
    }
    if (NO_ERR==rvalue)
    {
      	sendbuf[0] = _addr;
      	sendbuf[1] = func_no;
      	U16ToU8(data_addr, &sendbuf[2]);
      	U16ToU8(bit_count, &sendbuf[4]);
      	crc_data = CRC16(sendbuf, 6);
      	U16ToU8(crc_data, &sendbuf[6]);
      	send_count = 8;
      	SendChars(_port, (unsigned int)send_count, sendbuf, &send_len);
      	rvalue = WRITE_BIT;
      	
      	*paddr = data_addr;
      	*pnum = bit_count;  		
    }else
    {
        MDS_ResponseErr((unsigned char) rvalue);	
    }	
    return rvalue;
}
//读多个线圈功能码01,02
int MDS_ReadCoils(unsigned short *paddr, unsigned short *pnum)
{
	  int rvalue = NO_ERR;
    unsigned short data_addr;
    unsigned short temp_addr;
    unsigned char temp_data;
    unsigned short bit_count;
    unsigned char byte_count;
    unsigned short send_count;
    unsigned int send_len;
    unsigned char bytecnt;
    char i;
    unsigned short crc_data;
    unsigned char func_no;
    
    func_no = getbuf[1];
    U8ToU16(&getbuf[2], &data_addr);
    temp_addr = data_addr;
    U8ToU16(&getbuf[4], &bit_count);
    byte_count = bit_count>>3;

    for (bytecnt=0;bytecnt<byte_count;++bytecnt)
    {
    	  sendbuf[bytecnt+3] = 0;
        for (i=0;i<8;++i)
        {
            rvalue = GetCoilVal(temp_addr, &temp_data);
            sendbuf[bytecnt+3] >>= 1;
            if (0!=temp_data)
            {
                sendbuf[bytecnt+3] |= 0x80;	
            }
            temp_addr++;
        }
    }
    if (0!=(bit_count&0x7))
    {
        byte_count++;	
        sendbuf[bytecnt+3] = 0;
        for (i=0;i<(bit_count&0x7);++i)
        {
            rvalue = GetCoilVal(temp_addr+i, &temp_data);
            if (0!=temp_data)
            {
                sendbuf[bytecnt+3] |= (0x1<<i);	
            }   	
        }
    }    
    if (NO_ERR==rvalue)
    {
        sendbuf[0] = _addr;
        sendbuf[1] = func_no;
        sendbuf[2] = byte_count;	
    	  send_count = byte_count+3;
      	crc_data = CRC16(sendbuf, send_count);
      	U16ToU8(crc_data, &sendbuf[send_count]);
      	send_count +=2;
      	SendChars(_port, (unsigned int)send_count, sendbuf, &send_len);
      	rvalue = READ_BIT;
      	
      	*paddr = data_addr;
      	*pnum = bit_count;	 
    }else     
    {
        MDS_ResponseErr((unsigned char) rvalue);		
    }
    return rvalue;
}

//返回错误指令
int MDS_ResponseErr(unsigned char err_code)
{
    unsigned short crc_data;
	  unsigned int send_len;
	  sendbuf[0] = getbuf[0];
	  sendbuf[1] = getbuf[1] + 0x80;
	  sendbuf[2] = err_code;
	  crc_data = CRC16(sendbuf, 3);
	  U16ToU8(crc_data, &sendbuf[3]);
	  SendChars(_port, 5, sendbuf, &send_len);
	  return err_code;
}
//检查指令
int MDS_CheckCommand(unsigned short *paddr, unsigned short *pnum)
{
	int rvalue = NO_ERR;
  	unsigned short crcData;
  	unsigned short tempData;
  	static unsigned char last_getcnt=0;
  	static long lastclock=0;
  	long nowclock;
  	nowclock = clock();
  	GetRec();
  	if (_getcnt!=last_getcnt)
  	{
  	    lastclock = nowclock;
  	}else
    {
  	    if (nowclock-lastclock>g_frame_delay)
  	    {
  	        _getcnt = 0;
  	        last_getcnt = 0;
  	        lastclock = nowclock;
  	    }
  	}
  	if(_getcnt > 5)
  	{
  		  rvalue = CMD_WAIT;
    		switch(getbuf[1])
    		{
      			case 1://读取线圈状态(读取点 16位以内)
      			case 2://读取线圈状态(读取点 16位以内)
      			case 3://读取保持寄存器(一个或多个)
      			case 4://读取寄存器(一个或多个)
      			case 5://强制单个线圈
      			case 6://设置单个寄存器
      			        if(_getcnt >= 8)
      					    {   //接收完成一组数据
      						      //应该关闭接收中断
      						      if(getbuf[0]==_addr)
      						      {
      							        crcData = CRC16(getbuf,6);
      							        if(crcData == getbuf[7]+(getbuf[6]<<8))
      							        {//校验正确
      								          switch(getbuf[1])
      								          {
                								    case 1:   //读取线圈状态(读取点)
                									          rvalue = MDS_ReadCoils(paddr, pnum);
                									          break;								
                								    case 2: //读取线圈状态(读取点)
                									          rvalue = MDS_ReadCoils(paddr, pnum);
                									          break;								
                								    case 3: //读取保持寄存器(一个或多个)
                								            rvalue = MDS_ReadRegisters(paddr, pnum);
                								            break;
                								    case 4: //读取保持寄存器(一个或多个)
                									          rvalue = MDS_ReadRegisters(paddr, pnum);
                									          break;
                								    case 5: //设置单个线圈
                											      rvalue = MDS_SetSingleCoil(paddr, pnum);
                									          break;								
                								    case 6: //设置单个寄存器
                									          rvalue = MDS_SetSingleRegister(paddr, pnum);
                									          break;
                									  default:break;								
      								          }// end switch(getbuf[1])
      							        }
      						      }						
      						      _getcnt = 0;
      						      last_getcnt = 0;
      					    }
      					    break;
      			case 15://设置多个线圈
      					    tempData = getbuf[6]; 
      					    tempData += 9;	//数据个数
          					if(_getcnt >= tempData)
          					{
          						  if(getbuf[0]==_addr)
          						  {
          							    crcData = CRC16(getbuf,tempData-2);
          							    if(crcData == (getbuf[tempData-2]<<8)+ getbuf[tempData-1])
          							    {
          								      rvalue = MDS_SetCoils(paddr, pnum);			
          							    }
          						  }	
          						  _getcnt = 0;
          						  last_getcnt = 0;
          					}
          					break;
      			case 16://设置多个寄存器
      					    tempData = (getbuf[4]<<8) + getbuf[5];
      					    tempData = tempData * 2;	//数据个数
      					    tempData += 9;
      					    if(_getcnt >= tempData)
      					    {
      						      if(getbuf[0]==_addr)
      						      {
      							        crcData = CRC16(getbuf,tempData-2);
      							        if(crcData == (getbuf[tempData-2]<<8)+ getbuf[tempData-1])
      							        {
      							            rvalue = MDS_SetRegisters(paddr, pnum);			
      							        }
      						      }	
      						      _getcnt = 0;
      						      last_getcnt = 0;
      					    }
      					    break;							
				default:    _getcnt = 0;
				            last_getcnt = 0;
							rvalue = MDS_ResponseErr(ILLEGAL_FUNCTION);
      					    break;			
    		}
  	}
  	return rvalue;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -