EtherNet/IP™ Adapter3.09.00
 
Loading...
Searching...
No Matches
General Purpose Discrete I/O Device (Device Type: 0x07)

Scope

A General Purpose Discrete I/O Device according to Volume 1 Chapter 6 Device Profiles of the CIP NETWORKS LIBRARY interfaces to multiple discrete I/O device types that do not have network capabilities. Examples include sensors and actuators.

As such the General Purpose Discrete I/O Device supports a variety of objects described in Chapter 5A Object Library, Part A of the CIP NETWORKS LIBRARY.

Currently the example shipped with the SDK supports basic functionality of the following objects:

Discrete Input Point Object (Class Code: 0x08)

The Discrete Input Point (DIP) Object models discrete inputs in a product. Note that the term "input" is defined from the network's point of view. An input will produce data on the network.

The Discrete Input Point interface is to real input points such as a switch or screw terminal. The input is sampled and the data is stored in this object's Value attribute.

Discrete Output Point Object (Class Code: 0x09)

A Discrete Output Point (DOP) models discrete outputs in a product. Note that the term "output" is defined from the network's point of view. An output will consume data from the network.

The Discrete Output Point interface is to real output points such as a relay or LED. The output is read from this object's Values attribute and applied to the output terminal, such as a LED.

Discrete Output Group Object (Class Code: 0x1E)
The Discrete Output Group (DOG) Object binds a group of discrete output points in a module. All points bound to the group share all attributes contained in the group. If an attribute is shared across more than one Discrete Output Point (DOP), then it can be contained in a Discrete Output Group. A Discrete Output Point can also be bound to more than one Discrete Output Group.

The ODVA specifications model each individual input and output as separate instances of the Discrete Input Point and the Discrete Output Point Objects. The only required attribute is Attribute 3 Value of BOOL data type. BOOL types are encoded as octets, in compliance with the ODVA specifications. See C-5.2.1 BOOL Encoding in Volume 1.

The profile specific elements of this example are implemented in
device_profiles\discrete_io_device\discrete_io_device.c,
device_profiles\discrete_io_device\discrete_io_device_dip.c,
device_profiles\discrete_io_device\discrete_io_device_dop.c,
device_profiles\discrete_io_device\discrete_io_device_dog.c,
and device_profiles\discrete_io_device\discrete_io_device_asm.c.
The Discrete I/O Profile configuration is found under config\profile\discrete_io_device\cfg_profile_discrete_io_device.h

Create General Purpose Discrete I/O Device specific content

The initialization of the General Purpose Discrete I/O Device specific object model is peformed in DIO_DEVICE_init. It sequentially calls more specialized functions that cover the setup of the object structure of the Discrete Output Group Object (Class Code: 0x1E), Discrete Output Point Object (Class Code: 0x09), Discrete Input Point Object (Class Code: 0x08), and assemblies for cyclic I/O communication and configuration.

Initialization of the Discrete Output Group object

The Discrete Output Group object example code shipped with th EtherNet/IP stack currently implements Instance Attributes 6 to 10 only. In particular Instance Attributes 3 (number of DOP bound to the object) and 4 (list of all DOP bound to the object) can be easily added by the end user, because this information is already contained within each DOG object.

Initialization of the Discrete Output Point object

This object is described in Volume 1 of the CIP Network Library, section 5A-10. The behavior of the Discrete Output Point Object (DOP) is governed by the state machine in Figure 5A-10.3 and Table 5A-10.12 along side behavior description in other parts of section 5A-10.
The figure below shows the state diagram of DOP object:

DIO_DEVICE_DOP_init DIO_DEVICE_DOP_init (called as entry action in state Non-Existent) in file discrete_io_device_dop.c first creates the class object for Discrete Output Point. It then adds the Get_Attribute_Single as Class Service and adds Attribute 1, Revision to the Class Instance. According to Volume 1 Chapter 5A-10.3 Common Services, the Get_Attribute_Single service is required if any Class Attribute is implemented.

errCode = EI_API_CIP_createClass(pCipNode, CFG_PROFILE_DIO_DEVICE_DOP_CLASS_ID);
// Example how to evaluate error codes returned by API functions.
if (EI_API_CIP_eERR_OK != errCode)
{
OSAL_error (__func__, __LINE__, OSAL_STACK_INIT_ERROR, true, 0);
goto laError;
}
// set class instance
OSAL_MEMORY_memset(&service, 0, sizeof(service));
errCode = EI_API_CIP_addClassService(pCipNode, CFG_PROFILE_DIO_DEVICE_DOP_CLASS_ID, &service);
...
errCode = DIO_DEVICE_DOP_addClassAttribute(pCipNode, 1, &dopClassData_s.revision);
...
ETHIP_API uint32_t EI_API_CIP_addClassService(T *pCipNode_p, uint16_t classId_p, EI_API_CIP_SService_t *pService_p)
Add service/s to the class.
Definition EI_API_CIP_stub.c:292
ETHIP_API uint32_t EI_API_CIP_createClass(T *pCipNode_p, uint16_t classId_p)
Create a CIP class.
Definition EI_API_CIP_stub.c:215
@ EI_API_CIP_eSC_GETATTRSINGLE
Definition EI_API_def.h:109
@ EI_API_CIP_eERR_OK
Definition EI_API_CIP_define.h:26
Class attributes of the Discrete Output Point Object
Attribute ID Name Data Type Value
1 Revision UINT 1

After the class is set up, DOP instances can be added via DIO_DEVICE_DOP_addObject. For each DOP object, the user needs to supply the DIO_DEVICE_DOP_setOutputValue and also DIO_DEVICE_getConnectionEventInfo callbacks, as can be seen in the DIO_DEVICE_DOP_ObjectCfg_t structure. The table below shows the instance attributes created for each DOP object.
If the Object is configured to be part of a Discrete Output Group (by setting isBoundToGroup to 1), then the attributes 5 to 8 would be only gettable.
Those attributes are then configured by the corresponding Discrete Output Group and are not directly settable from remote side.

Instance Attributes of the Discrete Output Point
Attribute ID Name Data Type Value
3 Value BOOL 0
5 Fault Action BOOL default is set by user
6 Fault Value BOOL default is set by user
7 Idle Action BOOL default is set by user
8 Idle Value BOOL default is set by user
9 Run_Idle_Command BOOL 0
12 Object State USINT 0

In discrete_io_device.c the callback DIO_DEVICE_dopSetValue is used for all DOP objects. Each instance controls one LED.

static void DIO_DEVICE_dopSetValue (uint16_t instanceID, ei_api_cip_edt_bool value)
{
uint16_t instanceIndex = instanceID - 1;
if (0 != value)
{
DIO_DEVICE_dopLedStatus_s |= (1 << instanceIndex);
}
else
{
DIO_DEVICE_dopLedStatus_s &= ~(1 << instanceIndex);
}
DRV_LED_industrialSet(DIO_DEVICE_dopLedStatus_s);
}
static void DIO_DEVICE_dopSetValue(uint16_t instanceID, ei_api_cip_edt_bool value)
user function to set Discrete Output Point value
Definition discrete_io_device.c:308

Initialization of the Discrete Input Point object

This object is described in Volume 1 of the CIP Network Library, section 5A-9. The behavior of the Discrete Input Point object (DIP) is governed by the state machine in Figure 5A-9.1 and Table 5A-9.9.
The figure below shows the state diagram of DIP object:

DIO_DEVICE_DIP_init in discrete_io_device_dip.c first creates the class for Input Point Object. It adds the Get_Attribute_Single as Class Service and Attribute 1, Revision to the Class Instance. The value of the Revision Attribute is 2.

errCode = EI_API_CIP_createClass(pCipNode, CFG_PROFILE_DIO_DEVICE_DIP_CLASS_ID);
// Example how to evaluate error codes returned by API functions.
if (EI_API_CIP_eERR_OK != errCode)
{
OSAL_error (__func__, __LINE__, OSAL_STACK_INIT_ERROR, true, 0);
goto laError;
}
// set class instance
OSAL_MEMORY_memset(&service, 0, sizeof(service));
errCode = EI_API_CIP_addClassService(pCipNode, CFG_PROFILE_DIO_DEVICE_DIP_CLASS_ID, &service);
//...
errCode = DIO_DEVICE_DIP_addClassAttribute(pCipNode, 1, &dipClassData_s.revision);
//...
Class attributes of the Discrete Input Point Object
Attribute ID Name Data Type Value
1 Revision UINT 2

After the class is set up, DIP instances can be added via DIO_DEVICE_DIP_addObject. For each DIP object, the user needs to supply DIO_DEVICE_DIP_getInputValue and also DIO_DEVICE_getConnectionEventInfo callbacks, as can be seen in the DIO_DEVICE_DIP_ObjectCfg_t structure.
The callback DIO_DEVICE_DIP_getInputStatus is optional (it corresponds to Attribute 4 of DIP object). It is up to user to decide, if Attribute 4 has to be included in the Object or not.
The table below shows the instance attributes created for each DIP object.

Instance attributes of the Discrete Input Point
Attribute ID Name Data Type Value
3 Value BOOL
4(optional) Status BOOL

In discrete_io_device.c the callback DIO_DEVICE_dipGetValue is used for all DIP objects. Each instance simply reads status of one LED (mirroring DOP changes into DIP).

static void DIO_DEVICE_dipGetValue (uint16_t instanceID, uint8_t *pValue)
{
uint16_t instanceIndex = instanceID - 1;
//Mirror Output data into input
if(DIO_DEVICE_dopLedStatus_s & (1<<instanceIndex))
{
*pValue = 1;
}
else
{
*pValue = 0;
}
}
static void DIO_DEVICE_dipGetValue(uint16_t instanceID, uint8_t *pValue)
user function to read out Discrete Input Point value
Definition discrete_io_device.c:287

Create and Populate the device assemblies

As described in Volume 1 , Chapter 6-10 (General Purpose Discrete I/O Device [Profile]), there are a set of pre-defined assemblies for this device profile. These instances can be found in discrete_io_device_asm.h, DIO_DEVICE_ASM_instances_t.
Currently the function DIO_DEVICE_ASM_initInstance in discrete_io_device_asm.c supports only a subset of all the possible configurations.
when an instance is added via DIO_DEVICE_ASM_initInstance, the mapping between assemblies and Discrete I/O Device Profile objects (currently includes: DIP, DOP and DOG) are automatically done.
The provided example is using assembly instances DIO_DEVICE_ASM_4_Input_Point_No_Status (which automatically maps to DIP objects),
,DIO_DEVICE_ASM_4_Output_Point (which automatically maps to DOP objects) and DIO_DEVICE_ASM_Output_Configuration (which automatically maps to a pre-defined DOG object).
The DOG instance number to be used is defined in discrete_io_device_asm.h ( DIO_DOG_CONFIGUARTION_INSTANCE ) The used assemblies and consequently, the number of DOP and DIP objects are configurable in cfg_profile_discrete_io_device.h, as can be seen below:

#define CFG_PROFILE_DIO_DEVICE_ASSEMBLY_PRODUCING DIO_DEVICE_ASM_4_Input_Point_No_Status
#define CFG_PROFILE_DIO_DEVICE_ASSEMBLY_CONSUMING DIO_DEVICE_ASM_4_Output_Point
#define CFG_PROFILE_DIO_DEVICE_ASSEMBLY_CONFIGURATION DIO_DEVICE_ASM_Output_Configuration
#define CFG_PROFILE_DIO_DEVICE_DOP_NUM_OF_INST 4
#define CFG_PROFILE_DIO_DEVICE_DIP_NUM_OF_INST 4

In the EDS files this is reflected by the following Connection Manager section (example for the exclusive owner connection):

[Connection Manager]
Object_Name = "Connection Manager Object";
Object_Class_Code = 0x06;
Connection1 =
0x04010002, $ trigger & transport
$ 0-15 = supported transport classes (class 1)
$ 16 = cyclic (1 = supported)
$ 17 = change of state (0 = not supported)
$ 18 = on demand (0 = not supported)
$ 19-23 = reserved (must be zero)
$ 24-27 = exclusive owner
$ 28-30 = reserved (must be zero)
$ 31 = client 0 (don't care for classes 0 and 1)
0x44640405, $ point/multicast & priority & realtime format
$ 0 = O=>T fixed (1 = supported)
$ 1 = O=>T variable (0 = not supported)
$ 2 = T=>O fixed (1 = supported)
$ 3 = T=>O variable (0 = not supported)
$ 4-7 = reserved (must be zero)
$ 8-10 = O=>T header (4 byte run/idle)
$ 11 = reserved (must be zero)
$ 12-14 = T=>O header
$ 15 = reserved (must be zero)
$ 16-19 = O=>T point-to-point
$ 20-23 = T=>O multicast
$ 24-27 = O=>T scheduled
$ 28-31 = T=>O scheduled
,1,Assem2, $ O=>T RPI,Size,Format
,1,Assem1, $ T=>O RPI,Size,Format
,, $ config part 1 (dynamic assemblies)
1,Assem3, $ config part 2 (module configuration)
"Exclusive Owner", $ connection name
"", $ Help string
"20 04 24 28 2C 21 2C 03"; $ exclusive owner path

as can be seen in "exclusive owner path", 0x03 corresponds to DIO_DEVICE_ASM_4_Input_Point_No_Status, 0x21 (decimal 33) corresponds to DIO_DEVICE_ASM_4_Output_Point and 0x28 (decimal 40) corresponds to DIO_DEVICE_ASM_Output_Configuration.

Cyclic run function

The cyclic operation of the General Purpose Discrete I/O functionality is executed within the DIO_DEVICE_run function. Within this function, DIO_DEVICE_DIP_run and DIO_DEVICE_DOP_run are called, each of which runs the state machine of their respective objects.

void DIO_DEVICE_run(EI_API_CIP_NODE_T* pCipNode)
{
}
void DIO_DEVICE_DIP_run(void)
DIP processing funcion.
Definition discrete_io_device_dip.c:756
void DIO_DEVICE_DOP_run(void)
DOP processing funcion.
Definition discrete_io_device_dop.c:1166
static void DIO_DEVICE_run(EI_API_CIP_NODE_T *pCipNode)
Cyclically called run function.
Definition discrete_io_device.c:412