libreria modbus
TRANSCRIPT
1
//Definiciones referentes al modo de Modbus
#include<avr/io.h>
#include<avr/interrupt.h>
#include<util/delay.h>
//------------------- Definiciones -----------------------------------------
#define TRUE 1
#define FALSE 0
#define BITS_UCHAR 8U
#define MB_ASCII_ENABLED ( 1 )
#define MB_RTU_ENABLED ( 1 )
#define MB_TCP_ENABLED ( 0 )
#define MB_ASCII_TIMEOUT_SEC ( 1 )
#ifndef MB_ASCII_TIMEOUT_WAIT_BEFORE_SEND_MS
#define MB_ASCII_TIMEOUT_WAIT_BEFORE_SEND_MS ( 0 )
#endif
#define MB_FUNC_HANDLERS_MAX ( 16 )
#define MB_FUNC_OTHER_REP_SLAVEID_BUF ( 32 )
#define MB_FUNC_OTHER_REP_SLAVEID_ENABLED ( 1 )
//Definiciones referentes a la trama
/*
* <------------------------ MODBUS SERIAL LINE PDU (1) ------------------->
* <----------- MODBUS PDU (1') ---------------->
* +-----------+---------------+----------------------------+-------------+
* | Address | Function Code | Data | CRC/LRC |
* +-----------+---------------+----------------------------+-------------+
* | | | |
* (2) (3/2') (3') (4)
*
* (1) ... MB_SER_PDU_SIZE_MAX = 256
* (2) ... MB_SER_PDU_ADDR_OFF = 0
* (3) ... MB_SER_PDU_PDU_OFF = 1
2
* (4) ... MB_SER_PDU_SIZE_CRC = 2
*
* (1') ... MB_PDU_SIZE_MAX = 253
* (2') ... MB_PDU_FUNC_OFF = 0
* (3') ... MB_PDU_DATA_OFF = 1
* </code>
*/
#define MB_PDU_SIZE_MAX 253 /*!< Maximum size of a PDU. */
#define MB_PDU_SIZE_MIN 1 /*!< Function Code */
#define MB_PDU_FUNC_OFF 0 /*!< Offset of function code in PDU. */
#define MB_PDU_DATA_OFF 1 /*!< Offset for response data in PDU. */
/* ------------- Definiciones Puertos --------------------------------------------------------------*/
define INLINE inline
#define PR_BEGIN_EXTERN_C extern "C" {
#define PR_END_EXTERN_C }
#define ENTER_CRITICAL_SECTION( ) cli()
#define EXIT_CRITICAL_SECTION( ) sei()
#define assert( x )
/* ----------------------- Definiciones Locación Bobinas -------------------------------------*/
#define REG_COILS_START 1000
#define REG_COILS_SIZE 30
/* ----------------------- Definiciones Locación Entradas discretas -------------------------------------*/
#define REG_DISCRETE_START 2000
#define REG_DISCRETE_SIZE 50
/* ----------------------- Definiciones Locación Holding Registers --------------------------------------*/
#define REG_HOLDREG_START 4000
#define REG_HOLDREG_NREGS 20
/* ----------------------- Definiciones Locación Registros de Entradas -------------------------------------*/
#define REG_INPUT_START 5000
#define REG_INPUT_NREGS 10
/* ----------------------- Prototipos 0-------------------------------------*/
3
typedef char BOOL; //Variable TRUE o FALSE
typedef unsigned char UCHAR;
typedef char CHAR;
typedef unsigned short USHORT;
typedef short SHORT;
typedef unsigned long ULONG;
typedef long LONG;
volatile UCHAR ucHoldRegBuf[REG_HOLDREG_NREGS];
typedef enum
{
MB_RTU, // Modo de transmisión RTU.
MB_ASCII, // Modo de transmisión ASCII.(No implementado)
MB_TCP // Modo TCP.(No implementado)
} eMBMode;
typedef enum
{
MB_REG_READ, // Lee valores de registros.
MB_REG_WRITE // Escribe valores de registros.
} eMBRegisterMode;
typedef enum
{
MB_ENOERR, // Sin error.
MB_ENOREG, // Dirección de registro inválida.
MB_EINVAL, // Argumento inválido.
MB_EPORTERR, // Error en capa de puerto serie.
MB_ENORES, // Recursos insuficientes.
MB_EIO, // Error de E/S.
MB_EILLSTATE, // Pila de protocolo en estado inválido.
MB_ETIMEDOUT // Expiró el timeout.
4
} eMBErrorCode;
typedef void ( *pvMBFrameStart ) ( void );
typedef void ( *pvMBFrameStop ) ( void );
typedef eMBErrorCode( *peMBFrameReceive ) ( UCHAR * pucRcvAddress, UCHAR ** pucFrame, USHORT * pusLength );
typedef eMBErrorCode( *peMBFrameSend ) ( UCHAR slaveAddress, const UCHAR * pucFrame, USHORT usLength );
typedef void( *pvMBFrameClose ) ( void );
/* ----------------------- Definiciones de tipo ---------------------------------*/
typedef enum
{
STATE_RX_INIT, // Receptor está en su estado inicial.
STATE_RX_IDLE, // Receptor está en estado idle.
STATE_RX_RCV, // Trama siendo recibida.
STATE_RX_ERROR // Trama inválida.
} eMBRcvState;
typedef enum
{
STATE_TX_IDLE, // Transmisor en estado idle.
STATE_TX_XMIT // Transmisor en estado de transferencia.
} eMBSndState;
/* ----------------------- Definiciones de Eventos ---------------------------------*/
typedef enum
{
EV_READY, // Preámbulo finalizado
EV_FRAME_RECEIVED, // Trama recibida.
EV_EXECUTE, // Función en ejecución.
EV_FRAME_SENT // Trama enviada.
} eMBEventType;
5
typedef enum
{
MB_PAR_NONE, // Sin paridad.
MB_PAR_ODD, // Paridad impar.
MB_PAR_EVEN // Paridad par.
} eMBParity;
/* ----------------------- Definiciones de Funciones del Protocolo --------------------------*/
#define MB_ADDRESS_BROADCAST ( 0 ) // Dirección de difución Modbus.
#define MB_ADDRESS_MIN ( 1 ) // Dirección más pequeña posible de esclavo.
#define MB_ADDRESS_MAX ( 247 ) // Dirección más alta posible de esclavo.
#define MB_FUNC_NONE ( 0 ) //No implementada.
#define MB_FUNC_READ_COILS ( 1 )
#define MB_FUNC_READ_DISCRETE_INPUTS ( 2 )
#define MB_FUNC_READ_HOLDING_REGISTER ( 3 )
#define MB_FUNC_READ_INPUT_REGISTER ( 4 )
#define MB_FUNC_WRITE_SINGLE_COIL ( 5 )
#define MB_FUNC_WRITE_REGISTER ( 6 )
#define MB_FUNC_WRITE_MULTIPLE_COILS ( 15 )
#define MB_FUNC_WRITE_MULTIPLE_REGISTERS ( 16 )
#define MB_FUNC_READWRITE_MULTIPLE_REGISTERS ( 23 ) //No implementada.
#define MB_FUNC_DIAG_READ_EXCEPTION ( 7 ) //No implementada.
#define MB_FUNC_DIAG_DIAGNOSTIC ( 8 ) //No implementada.
#define MB_FUNC_DIAG_GET_COM_EVENT_CNT ( 11 ) //No implementada.
#define MB_FUNC_DIAG_GET_COM_EVENT_LOG ( 12 ) //No implementada.
#define MB_FUNC_OTHER_REPORT_SLAVEID ( 17 ) //No implementada.
#define MB_FUNC_ERROR ( 128 ) //No implementada.
/* ----------------------- Definiciones de Excepciones ---------------------------------*/
typedef enum
{
MB_EX_NONE = 0x00,
6
MB_EX_ILLEGAL_FUNCTION = 0x01,
MB_EX_ILLEGAL_DATA_ADDRESS = 0x02,
MB_EX_ILLEGAL_DATA_VALUE = 0x03,
MB_EX_SLAVE_DEVICE_FAILURE = 0x04,
MB_EX_ACKNOWLEDGE = 0x05,
MB_EX_SLAVE_BUSY = 0x06,
MB_EX_MEMORY_PARITY_ERROR = 0x08,
MB_EX_GATEWAY_PATH_FAILED = 0x0A,
MB_EX_GATEWAY_TGT_FAILED = 0x0B
} eMBException;
typedef eMBException( *pxMBFunctionHandler ) ( UCHAR * pucFrame, USHORT * pusLength );
typedef struct
{
UCHAR ucFunctionCode;
pxMBFunctionHandler pxHandler;
} xMBFunctionHandler;
/* -------------------Prototipo de Funciones ------------------------------*/
/* Inicia el protocolo Modbus RTU o ASCII.
* El protocolo permanece deshabilitado hasta que no se llame a eMBEnable( ).
* eMode: ASCII ó RTU.
* ucSlaveAddress: Dirección del esclavo. Solo las tramas enviadas a este esclavo procesa.
* ucPort: El puerto usado, por ejemplo, 1 para COM1 en Windows. Este valor es dependiente
* de la plataforma y algunos puertos eligen ignorarla. (No implementado).
* ulBaudRate: velocidad en baudios. Por ejemplo 19200.
* eParity: Paridad usada en transmisión serial.
*
* Si no ocurre error la función retorna eMBErrorCode::MB_ENOERR.
*/
eMBErrorCode eMBInic( eMBMode eMode, UCHAR ucSlaveAddress, UCHAR ucPort, ULONG ulBaudRate, eMBParity eParity );
// Esta función deshabilita el protocolo Modbus y libera todo recurso de hardware usado.
eMBErrorCode eMBClose( void );
7
eMBErrorCode eMBEnable( void );
// eMBErrorCode::MB_ENOERR. Si no estaba en estado habilitado retorna
// eMBErrorCode::MB_EILLSTATE.
eMBErrorCode eMBDisable( void );
eMBErrorCode eMBPoll( void );
eMBErrorCode eMBSetSlaveID( UCHAR ucSlaveID, BOOL xIsRunning, UCHAR const *pucAdditional, USHORT usAdditionalLen );
//-------------- Funciones de implementación ----------------------------
eMBErrorCode eMBRegisterCB( UCHAR ucFunctionCode, pxMBFunctionHandler pxHandler );
eMBErrorCode eMBRegInputCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNRegs );
eMBErrorCode eMBRegHoldingCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNRegs, eMBRegisterMode eMode );
eMBErrorCode eMBRegCoilsCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNCoils, eMBRegisterMode eMode );
eMBErrorCode eMBRegDiscreteCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNDiscrete );
/* ---------------------- Funciones Modbus ---------------------------------------*/
eMBException eMBFuncReportSlaveID( UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncReadInputRegister( UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncReadHoldingRegister( UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncWriteHoldingRegister( volatile UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncWriteMultipleHoldingRegister( UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncReadCoils( UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncWriteCoil( UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncWriteMultipleCoils( UCHAR * pucFrame, USHORT * usLen );
eMBException eMBFuncReadDiscreteInputs( UCHAR * pucFrame, USHORT * usLen );
/* ----------------------- Funciones de soporte -----------------------------*/
BOOL xMBPortEventInic( void );
BOOL xMBPortEventPost( eMBEventType eEvent );
BOOL xMBPortEventGet( eMBEventType * eEvent );
/* ----------------------- Funciones del puerto serie ----------------------------*/
BOOL xMBPortSerialInic( UCHAR ucPort, ULONG ulBaudRate, UCHAR ucDataBits, eMBParity eParity );
void vMBPortClose( void );
void xMBPortSerialClose( void );
void vMBPortSerialEnable( BOOL xRxEnable, BOOL xTxEnable );
8
BOOL xMBPortSerialGetByte( CHAR * pucByte );
BOOL xMBPortSerialPutByte( CHAR ucByte );
/* ----------------------- Funciones de Temporizado ---------------------------------*/
BOOL xMBPortTimersInic( USHORT usTimeOut50us );
void xMBPortTimersClose( void );
void vMBPortTimersEnable( void );
void vMBPortTimersDisable( void );
void vMBPortTimersDelay( USHORT usTimeOutMS );
/* ----------------------- Llamadas genéricas a protocolo ---------------------*/
extern BOOL( *pxMBFrameCBByteReceived ) ( void );
extern BOOL( *pxMBFrameCBTransmitterEmpty ) ( void );
extern BOOL( *pxMBPortCBTimerExpired ) ( void );
/*- Funciones útiles para trabajar con bits en las funciones referentes a coils ---*/
void xMBUtilSetBits( UCHAR * ucByteBuf, USHORT usBitOffset, UCHAR ucNBits, UCHAR ucValues );
UCHAR xMBUtilGetBits( UCHAR * ucByteBuf, USHORT usBitOffset, UCHAR ucNBits );
/* ---- Funciones de transmisión protocolo Modbus RTU ----------------------------------*/
eMBErrorCode eMBRTUInic( UCHAR slaveAddress, UCHAR ucPort, ULONG ulBaudRate, eMBParity eParity );
void eMBRTUStart( void );
void eMBRTUStop( void );
eMBErrorCode eMBRTUReceive( UCHAR * pucRcvAddress, UCHAR ** pucFrame, USHORT * pusLength );
eMBErrorCode eMBRTUSend( UCHAR slaveAddress, const UCHAR * pucFrame, USHORT usLength );
BOOL xMBRTUReceiveFSM( void );
BOOL xMBRTUTransmitFSM( void );
BOOL xMBRTUTimerT15Expired( void );
BOOL xMBRTUTimerT35Expired( void );
eMBErrorCode eMBRegDiscreteCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNDiscrete );
eMBErrorCode eMBRegCoilsCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNCoils, eMBRegisterMode eMode );
eMBErrorCode eMBRegHoldingCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNRegs, eMBRegisterMode eMode );
eMBErrorCode eMBRegInputCB( UCHAR * pucRegBuffer, USHORT usAddress, USHORT usNRegs );
9
UCHAR temporario;
static volatile eMBRcvState eRcvState;
static volatile eMBSndState eSndState;
static volatile FrameError;
static volatile ParityError;
static volatile OverRunError;