Skip to main content

Connect to CIP Devices over EtherNet/IP

The ETHERNETIP route connects Coreflux to CIP-compatible devices using EtherNet/IP explicit messaging (TCP port 44818). Define an ETHERNETIP_CONFIG block, add TAGs with CIP addresses, and publish each data point to its own MQTT topic — with optional scaling, bit extraction, joined attribute reads, and bidirectional writes.
Like reading labeled drawers in a filing cabinet. Each CIP address (Class.Instance.Attribute.Index) points to a specific property on the device. The route opens the drawer, reads the value, and places it on an MQTT topic — on a schedule or when you send a command.

When to use this

Use the EtherNet/IP route when you need explicit messaging to CIP objects on Allen-Bradley PLCs, remote I/O modules, VFDs, or other ODVA-compatible devices. Addresses use the numeric CIP path format ClassID.InstanceID.AttributeID.AttributeIndex.
For symbolic tag names (for example Program:MainProgram.Temperature), use the dedicated Allen-Bradley route instead. The EtherNet/IP route reads and writes via CIP class/instance/attribute paths.

Key capabilities

  • Explicit messaging — direct read/write to CIP attributes over TCP (port 44818)
  • TAG-based polling — per-point MQTT topics with configurable intervals
  • Bit extractionBIT_ADDRESS to read a single bit from an integer word
  • Joined attribute reads — combine bytes from two CIP attributes (legacy asset parity)
  • ARRAY and STRUCT decoding — packed assembly buffers published as JSON arrays or objects
  • Bidirectional writesWRITABLE scalar tags with DESTINATION_TOPIC
  • Engineering unitsSCALING / OFFSET / DEADBAND per tag

Quick Start

Read an analog input point every 500 ms and publish to MQTT:

Connection Configuration

ETHERNETIP_CONFIG Parameters

The config block may be declared as ADD ETHERNETIP_CONFIG or ADD EIP_CONFIG — both are equivalent.

Connection Example

Implicit I/O Mode (Forward Open)

Not implemented in release 2.2. The route parser accepts IO_MODE "IMPLICIT" and related assembly/RPI settings for forward compatibility, but the broker does not establish Forward Open / cyclic UDP connections yet. Use explicit CIP assembly attributes (4.x.y.z paths) for I/O adapter devices until implicit mode ships.
Planned parameters (validated when present, not yet wired to the adapter):

CIP Addressing

EtherNet/IP uses CIP (Common Industrial Protocol) addressing. The adapter issues CIP Get_Attribute_Single / Set_Attribute_Single against numeric paths. Required format: ClassID.InstanceID.AttributeID.AttributeIndex — four numeric segments, dot-separated.

Common CIP Classes

EtherNet/IP Communication Types


Data Types

Allen-Bradley Type Mapping


TAG Configuration

Every polled data point is an ADD TAG inside an ADD MAPPING block. Tags without their own SOURCE_TOPIC inherit {mapping SOURCE_TOPIC}/{tagName} when the mapping sets a base topic.

Complete TAG Example

TAG Parameters

ADDRESS
string
required
CIP path: ClassID.InstanceID.AttributeID.AttributeIndex
DATA_TYPE
string
required
CIP data type (see table above).
LENGTH
integer
Bytes to read from the primary CIP attribute starting at AttributeIndex (the fourth segment of ADDRESS). Default: 1. For STRING tags, this is the maximum string size. For numeric tags in join mode, LENGTH + JOIN_LENGTH must equal the byte width of DATA_TYPE (for example 1 + 1 = 2 for INT16).
BIT_ADDRESS
integer
Extract a single bit (0-based) from the underlying integer word. Alias: BIT. Use with integer types (UINT16, INT32, etc.) or with BOOL when the device returns a packed word. For BOOL + BIT_ADDRESS, read width auto-widens: bits 0–7 read 1 byte, 8–15 read 2 bytes, 16–31 read 4 bytes, 32–63 read 8 bytes.
ENABLE_JOIN_ATTRIBUTE
string
When "true", perform a second CIP Get_Attribute_Single against the join target and concatenate those bytes onto the primary read before parsing, scaling, or bit extraction. Default: false.
JOIN_CLASS_ID
integer
CIP Class ID of the joined attribute. Required when ENABLE_JOIN_ATTRIBUTE is true (must be > 0).
JOIN_INSTANCE_ID
integer
CIP Instance ID of the joined attribute. Required when join is enabled (must be >= 0; instance 0 is valid on some devices).
JOIN_ATTRIBUTE_ID
integer
CIP Attribute ID of the joined attribute. Required when join is enabled (must be > 0).
JOIN_INDEX
integer
Byte offset within the joined CIP response where the slice starts. Default: 0.
JOIN_LENGTH
integer
Bytes to take from the joined attribute starting at JOIN_INDEX. Required when join is enabled (must be > 0). Not related to SCALING_FACTOR.
SCALING
decimal
Multiply the parsed numeric value after byte parsing. Alias: SCALING_FACTOR. Default: 1.0. Unrelated to byte layout — does not replace JOIN_LENGTH.
OFFSET
decimal
Add after scaling. Default: 0.0.
DEADBAND
decimal
Suppress MQTT publish when the change is below this threshold. Default: 0.0.
DECIMAL_PLACES
integer
Decimal places for FLOAT32 / FLOAT64 MQTT payloads. Default: 2.
SOURCE_TOPIC
string
MQTT topic where polled values are published.
PUBLISH_MODE
string
VALUE_ONLY (default — publish just the value) or JSON (value, quality, and timestamp). Aliases: VALUE, SIMPLE for value-only; FULL, METADATA for JSON.
WRITABLE
boolean
When true, subscribe to DESTINATION_TOPIC and write incoming MQTT values to the device.
DESTINATION_TOPIC
string
MQTT topic to receive write commands. Required when WRITABLE is true.

Publish Modes

VALUE_ONLY (default) — publishes just the scaled scalar value:
JSON — publishes a metadata wrapper when explicitly set:

ARRAY and STRUCT Tags

CIP assembly buffers often contain packed arrays or structured records. Use DATA_TYPE "ARRAY" or DATA_TYPE "STRUCT" to decode them into JSON on MQTT.

ARRAY

MQTT payload: JSON array, e.g. [10, 20, 30, 40, 50].

STRUCT

Field spec format: name:byte_offset:type:size (comma-separated). Types follow the same aliases as scalar DATA_TYPE. MQTT payload: JSON object, e.g. {"temp":25.5,"pressure":101.325,"status":1}.
ARRAY and STRUCT tags are read-focused in release 2.2. Writable scalar tags use normal CIP encoding; complex-type writes from JSON arrays/objects are not yet supported.

Joined Attribute Reads

Some legacy CIP devices split a logical value across two attributes (for example a status word plus an extension attribute). When ENABLE_JOIN_ATTRIBUTE is "true", the broker performs two Get_Attribute_Single reads per cycle, concatenates the byte buffers (primary first, joined second), then parses, scales, and applies BIT_ADDRESS. If the join read fails, a warning is logged and the primary buffer is parsed alone — the polling loop continues.
For numeric DATA_TYPE values in join mode, LENGTH + JOIN_LENGTH must equal the type byte width (2 for 16-bit, 4 for 32-bit, 8 for 64-bit). BOOL tags with BIT_ADDRESS are exempt (Kaeser-style alarm bit pattern).
SCALING / SCALING_FACTOR multiplies the parsed value — it does not replace JOIN_LENGTH. Using scaling to compensate for a missing join length produces silently wrong values.

Migrating from a Legacy EtherNet/IP Asset

If you are converting an EtherNet/IP Asset (Coreflux HUB Configure / Tags panel) into a Route, map each asset field to the LoT parameter below.

Examples

Read identity object attributes on a slow interval:

CIP Object Reference


Best Practices

Match the interval to how fast the value changes: 100 ms for safety-critical data, 1 s for process variables, 10 s or more for slow-changing status.
Use DEADBAND on noisy analog values to reduce MQTT traffic. Set 0.0 on digital status tags so every change publishes.
Increase CONNECTION_TIMEOUT and READ_WRITE_TIMEOUT on congested or remote networks. Raise RETRY_ATTEMPTS when connections are intermittent.
Always set JOIN_LENGTH explicitly when ENABLE_JOIN_ATTRIBUTE is "true". Verify LENGTH + JOIN_LENGTH matches the numeric type width before deploying to production.
Use numeric CIP paths on this route. For Rockwell tag-name access (Program:MainProgram.Counter), use the Allen-Bradley route.

Troubleshooting

  • Verify IP with ping
  • Confirm port 44818 (TCP) is open through firewalls
  • Ensure the device is powered and allows external connections
  • Increase CONNECTION_TIMEOUT and RETRY_ATTEMPTS
  • Confirm four-segment format: ClassID.InstanceID.AttributeID.AttributeIndex
  • Check the device manual for valid class/instance/attribute numbers
  • Instance numbering varies by device (often starts at 1, not 0)
  • Verify DATA_TYPE matches the device attribute
  • Check DEADBAND is not suppressing small changes
  • For join tags, confirm JOIN_LENGTH and LENGTH byte layout
  • For bit tags, confirm BIT_ADDRESS is within the read width
  • JOIN_CLASS_ID and JOIN_ATTRIBUTE_ID must be > 0
  • JOIN_INSTANCE_ID must be present and >= 0
  • JOIN_LENGTH must be > 0
  • For numeric types, LENGTH + JOIN_LENGTH must equal the type byte width (unless BOOL + BIT_ADDRESS)

Next Steps

Allen-Bradley Route

Symbolic tag-name access for ControlLogix, CompactLogix, and MicroLogix PLCs.

Industrial Routes Overview

Compare OT routes and choose the right protocol for your devices.
Last modified on July 7, 2026