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

📄 mb_dev.c

📁 modbus的c语言版本应用于dos下
💻 C
📖 第 1 页 / 共 2 页
字号:
    memset(input_status,0,*byte_count);
    for(i=shift=byte_count_tmp=0;i<number_of_inputs;i++)
    {
      retval = mb_read_discrete_inputs_func(start_address + i,&input_tmp);
      if(retval == MB_NO_ERROR)
      {
        if(input_tmp)
        {
          input_status[byte_count_tmp]|= 1<<shift;
        }
        shift++;
        if(shift==8)
        {
          byte_count_tmp++;
          shift=0;
        }
      }
      else
      {
        break;
      }
    }
    //Enable interupts or release semaphore here, if they were used above the read loop

    #ifdef MB_DEV_DEBUG
    printf("\r\nRead discrete inputs: Return %d ",retval);
    if(retval==MB_NO_ERROR)
    {
       printf("\r\nInput_status: ");
       for(i=0;i<*byte_count;i++)
       {
          printf("%02X ",input_status[i]);
       }
    }
    #endif
    return retval;
}
/******************************************************************************
   Bit access: Called if modbus function code == 0x0F
   Handle a "write multiple coils" request (function code 0x0F)
   Input parameters:
   start_address    Address of the first coil
   number_of_coils  Quantity of coils to write
   byte_count       quantity of outputs / 8  (+1 if reminader!=0)
   outputs_value    the  provided storage outputs_value holds coil bit output values
                    in the order as described at the
                    "Modbus application protocol specification V1.1" from modbus.org

   Return 0: sucessful,  else errorcode (see modbus.h)
******************************************************************************/
#pragma argsused
int mb_write_multiple_coils(unsigned int start_address,
                            unsigned int number_of_coils,
                            unsigned char byte_count,
                            unsigned char * outputs_value)
{
    int i,coil_idx,shift;
    int retval;

    #ifdef MB_DEV_DEBUG
    printf("\r\nWrite multiple coils: start %d quantity %d",start_address, number_of_coils);
    printf("\r\nOutputs: ");
    for(i=0;i<number_of_coils;i++)
    {
      printf(" %04X",swap_int(outputs_value[i]));
    }
    #endif
    /*
      Write outputs_value bits to the device
      If the application requires no interruption during the following write coil loop,
      insert here semaphore protection or  disable interrupts
    */
    for(i=shift=coil_idx=0;i<number_of_coils;i++)
    {
      retval = mb_write_coil_func(start_address + i,(outputs_value[coil_idx]>>shift) & 0x01);
      if(retval == MB_NO_ERROR)
      {
        shift++;
        if(shift==8)
        {
          coil_idx++;
          shift=0;
        }
      }
      else
      {
        break;
      }
    }
    //Enable interupts or release semaphores here, if they were used above the write loop
    return retval;
}
/******************************************************************************
   16 Bit access: called if modbus function code == 0x03
   Handle a "read holding registers" request
   Input parameters:
   start_address   : address of first register
   number_of_regs  : Quantity of registers to read

   Return 0: sucessful ,  byte_count = number_of_regs * 2
                          the provided storage reg_value contains the read register values
          else errorcode (see modbus.h)
******************************************************************************/
int mb_read_holding_registers(unsigned int start_address,
                              unsigned int number_of_regs,
                              unsigned int * reg_value,
                              unsigned char * byte_count)
{
   int i;
   int retval;

   #ifdef MB_DEV_DEBUG
   printf("\r\nRead holding registers: start %d quantity %d",start_address, number_of_regs);
   #endif

   /*
      Read register values into the provided storage reg_value
      If the application requires no interruption during the following write coil loop,
      insert here semaphore protection or  disable interrupts
   */
   *byte_count=number_of_regs*2;
   for(i=0;i<number_of_regs;i++)
   {
      retval = mb_read_holding_register_func(start_address + i,&reg_value[i]);
      if(retval != MB_NO_ERROR)
      {
        break;
      }
      reg_value[i] = swap_int(reg_value[i]);
   }
   //Enable interupts or release semaphores here, if they were used above the write loop

   #ifdef MB_DEV_DEBUG
   printf("\r\nRead holding registers: retval %d",retval);
   if(retval==MB_NO_ERROR)
   {
     printf("\r\nRegister values: ");
     for(i=0;i<number_of_regs;i++)
     {
       printf(" %04X",reg_value[i]);
     }
   }
   #endif
   return retval;
}
/******************************************************************************
   16 Bit access: called if modbus function code == 0x04
   Handle a "read input registers" request
   Input parameters:
   start_address   : address of first register
   number_of_regs  : Quantity of input registers to read

   Return 0: sucessful ,  byte_count = number_of_regs * 2
                          the provided storage reg_value contains the read register values
          else errorcode (see modbus.h)

******************************************************************************/
int mb_read_input_registers(unsigned int start_address,
                            unsigned int number_of_regs,
                            unsigned int * reg_value,
                            unsigned char * byte_count)
{
   int i;
   int retval;

   #ifdef MB_DEV_DEBUG
   printf("\r\nRead input registers: start %d quantity %d",start_address, number_of_regs);
   #endif
   /*
      Read register values into the provided storage reg_value
      If the application requires no interruption during the following write coil loop,
      insert here semaphore protection or  disable interrupts
   */
   *byte_count=number_of_regs*2;
   for(i=0;i<number_of_regs;i++)
   {
      retval = mb_read_input_register_func(start_address + i,&reg_value[i]);
      if(retval != MB_NO_ERROR)
      {
        break;
      }
      reg_value[i] = swap_int(reg_value[i]);
   }
   //Enable interupts or release semaphores here, if they were used above the write loop

   #ifdef MB_DEV_DEBUG
   printf("\r\nRead input registers: retval %d",retval);
   if(retval==MB_NO_ERROR)
   {
     printf("\r\nRegister values: ");
     for(i=0;i<number_of_regs;i++)
     {
       printf(" %04X",reg_value[i]);
     }
   }
   #endif
   return retval;
}
/******************************************************************************
   Handle a "write multiple registers" request (function code 0x10)
   Input parameters:
   start_address   : address of first register
   number_of_regs  : Quantity of input registers to read
   reg_values      : Array which holds continuous the values to write

   Return 0: sucessful
   else errorcode (see modbus.h)
******************************************************************************/
int mb_write_multiple_registers(unsigned int start_address,
                                unsigned int number_of_regs,
                                unsigned int * reg_values
                               )
{
   int i;
   int retval;

   #ifdef MB_DEV_DEBUG
   printf("\r\nWrite multiple registers: start %d quantity %d",start_address, number_of_regs);
   printf("\r\nOutputs: ");
   for(i=0;i<number_of_regs;i++)
   {
      printf(" %04X", swap_int(reg_values[i]));
   }
   #endif
   /*
      Write register values from provided storage reg_values to the device
      If the application requires no interruption during the following write coil loop,
      insert here semaphore protection or  disable interrupts
   */
   for(i=0;i<number_of_regs;i++)
   {
      retval = mb_write_holding_register_func(start_address + i,swap_int(reg_values[i]));
      if(retval != MB_NO_ERROR)
      {
        break;
      }
    }
    //Enable interupts or release semaphores here, if they were used above the write loop
    return retval;
}

/******************************************************************************
   Handle a "write single register" request (function code 0x06)
   Input parameters:
   start_address   : address of first register
   number_of_regs  : Quantity of input registers to read
   reg_values      : Array which holds continuous the values to write

   Return 0: sucessful
   else errorcode (see modbus.h)
******************************************************************************/
int mb_write_single_register(unsigned int address, unsigned int value)
{
   #ifdef MB_DEV_DEBUG
   printf("\r\nWrite single register: address %d value %04X",address, swap_int(value));
   #endif
   return mb_write_holding_register_func(address,swap_int(value));
}
/******************************************************************************
 Handle a "read device identification" request (function code 0x2B)
 Currently supported Read Dev Id code: 01  (basic identification)
 Input parameters:
 mei_type   : MEI type always 0x0E(?)
 id code s  : Read device code id
 object_id  : ID of the first request object
 Output parameters:
 object_next: Contains after execution the id of thge nex object, if *more_follws==0xFF
 more_follwos:If value after excution==0xFF, there are more object available
 object_list: Storage contains after execution the listed objects, as specified at
              Modbus Application Spec 1.1
 object_list_length: Length of object_list

 Return 0: sucessful
 else errorcode (see modbus.h)
******************************************************************************/
int mb_read_device_ident(unsigned char mei_type,
                         unsigned char id_code,
                         unsigned char object_id,
                         unsigned char * object_next,
                         unsigned char * number_of_objects,
                         unsigned char * more_follows,
                         unsigned char * object_list,
                         unsigned char * object_list_length
                         )

{

  int i, j;
  unsigned char obj_length;

  #ifdef MB_DEV_DEBUG
  printf("\r\nRead device ident id_code: %d object_id %d",id_code, object_id);
  #endif

  //Check parameters
  if(mei_type!=0x0E)
  {
    return MB_SERVER_FAILURE;
  }

  if(id_code<1||id_code>0x02)
  {
    return MB_ILL_DATA_VAL;
  }

  if( object_id > MB_DEV_OBJ_MAX_ID - 1 ||
      ( id_code == 0x01 && object_id != 0x00 ) ||
      ( id_code == 0x02 && object_id != 0x03 ) )
  {
    return MB_ILL_DATA_ADDR;
  }


  *more_follows       =0;
  *object_list_length =0;  //size of MBAB + first data of response
  *object_next        =0;
  *number_of_objects  =0;
  //run through object array and fill provided list buffer
  if( id_code == 1 ) j = 0x03;
  else j = MB_DEV_OBJ_MAX_ID;

  for(i = object_id; i < j; i++)
  {
     obj_length = strlen(mb_object_id_table[i]);
     if(*object_list_length < MB_TCP_MAX_BUF - (obj_length+14))
     {
        object_list[(*object_list_length)++]= i;   //object id
        object_list[(*object_list_length)++]= obj_length;   //object lenght
        strcpy((char *)&object_list[*object_list_length],mb_object_id_table[i]);     //object value
        *object_list_length += obj_length;
     }
     else //no more space avail at frame
     {
       *more_follows=0xFF;
       *object_next = i+1;
       break;
     }
  }
  *number_of_objects  = i-object_id;

  #ifdef MB_DEV_DEBUG
  printf("\r\nRead device ident objects: %d length: %d",i, *object_list_length);
  #endif
  return MB_NO_ERROR;
}
//******************************************************************************
//end of file

⌨️ 快捷键说明

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