# ๐ฆ Rust EtherNet/IP Driver
[](https://www.rust-lang.org)
[](https://github.com/sergiogallegos/rust-ethernet-ip/releases)
[](LICENSE)
[]()
[]()
[]()
[]()
[](https://crates.io/crates/rust-ethernet-ip)
[](https://docs.rs/rust-ethernet-ip)
[](https://crates.io/crates/rust-ethernet-ip)
[](https://github.com/sponsors/sergiogallegos)
A high-performance, production-ready EtherNet/IP communication library specifically designed for **Allen-Bradley CompactLogix and ControlLogix PLCs**. Built in pure Rust with focus on **PC applications**, offering exceptional performance, memory safety, and comprehensive industrial features.
**๐ฆ Available on [crates.io](https://crates.io/crates/rust-ethernet-ip)**
## ๐ฏ **Current Development Focus**
**We are currently focusing on polishing the .NET stack (C# wrappers and examples) to production quality.**
- ๐ฏ **Active Development**:
- C# wrapper library (`RustEtherNetIp.dll`)
- WinForms example application
- WPF example application
- ASP.NET example application
- Advanced features: TagGroup, Statistics, Batch Operations, STRING support, UDT arrays
- โธ๏ธ **On Hold**:
- Go wrapper and applications (will resume after .NET stack is complete)
- Python wrapper and applications (will resume after .NET stack is complete)
This focused approach ensures we deliver a robust, well-tested, production-ready .NET integration before expanding to other language ecosystems. The .NET stack serves as the reference implementation for future language bindings.
## ๐ฏ **Project Focus**
This library is specifically designed for:
- **Allen-Bradley CompactLogix** (L1x, L2x, L3x, L4x, L5x series)
- **Allen-Bradley ControlLogix** (L6x, L7x, L8x series)
- **PC Applications** (Windows, Linux, macOS)
- **Industrial Automation** software and SCADA systems
- **High-performance** data acquisition and control
### โ
**v0.6.0 New Features**
- **๐ง Generic UDT Format**: New `UdtData` struct with `symbol_id` and raw bytes
- Works with any UDT without requiring prior knowledge of member structure
- Supports reading and writing UDTs generically
- Enables parsing UDT members using UDT definitions when needed
- **๐ Array Element Access**: Full read/write support for array elements using intelligent workaround
- Controller-scoped arrays: `gArrayTest[0]`, `gArrayTest[1]`, etc.
- Program-scoped arrays: `Program:MainProgram.ArrayTest[0]`
- BOOL array support: Automatic DWORD bit extraction for BOOL arrays
- Automatic detection and workaround for array element access
- **โ๏ธ Array Element Writing**: Write individual array elements with automatic array modification
- Reads entire array, modifies element, writes back seamlessly
- Supports all data types (DINT, REAL, BOOL, etc.)
- Works with both controller-scoped and program-scoped arrays
- **โ
Library Health**: All 31 unit tests passing, production-ready core library
### โ
**v0.5.4 Features**
- **๐ UDT Definition Discovery**: Automatic UDT structure detection from PLC
- **๐ท๏ธ Enhanced Tag Discovery**: Full attribute support with permissions and scope
- **๐ฆ Packet Size Negotiation**: Dynamic optimization for firmware 20+
- **๐ฃ๏ธ Route Path Support**: Slot configuration and multi-hop routing
- **๐พ Cache Management**: Smart caching for UDT definitions and tag attributes
- **๐ง CIP Services**: Full implementation of Services 0x03 and 0x4C
- **๐ฏ Program Tag Support**: Fixed program-scoped tag access with correct CIP path format
- **๐ง Enhanced UDT Parsing**: Intelligent multi-member UDT parsing with byte alignment detection
- **โก Advanced Chunked Reading**: Multiple strategies for large UDTs with intelligent error recovery
- **๐ฏ .NET Stack Focus**: Comprehensive C# wrapper with WinForms, WPF, and ASP.NET examples
> **๐ Major Milestone Achieved!**
> v0.6.0 introduces a new generic UDT format (`UdtData`) that works with any UDT without requiring prior knowledge of member structure. The library core is production-ready with all 31 unit tests passing.
## โจ **Key Features**
### ๐ **UDT Discovery & Management (v0.5.4)**
- **Automatic UDT Structure Detection**: No more manual offset/size/type specifications
- **CIP Service 0x03**: Get Attribute List for comprehensive tag metadata
- **CIP Service 0x4C**: Read Tag Fragmented for large data structures
- **Smart Caching**: UDT definitions and tag attributes cached for performance
- **Template Management**: Full UDT template parsing and member discovery
- **Program-Scoped Discovery**: Find tags within specific program scopes
### ๐ฃ๏ธ **Route Path Support (v0.5.4, Enhanced in v0.6.0)**
- **Slot Configuration**: Support for slots 0-31 (โ
Fully implemented and tested)
- **Backplane Routing**: Direct communication with CPUs in different slots (โ
Fully implemented)
- **Network Routing**: Multi-hop routing through network addresses and ports (โ
Implemented)
- **CIP Path Building**: Automatic CIP route path byte generation (โ
Implemented)
- **ControlLogix Support**: Tested with ControlLogix systems with CPUs in different slots
- **Remote Rack Connections**: Basic support exists, needs additional testing
- **Dynamic Path Building**: Automatic CIP route path generation from slots, ports, and addresses
### ๐ฆ **Packet Size Optimization (v0.5.4)**
- **Dynamic Negotiation**: Automatically negotiates optimal packet size with PLC
- **Firmware 20+ Support**: Enhanced performance for modern PLCs
- **Adaptive Sizing**: Adjusts packet size based on PLC capabilities
- **Performance Boost**: 20-30% improvement for large data transfers
### ๐ง **Enhanced UDT Processing** โ
**NEW in v0.5.4**
- **Intelligent Multi-Member Parsing**: Automatically detects and parses multiple UDT members (DINT, DINT, REAL)
- **Byte Alignment Detection**: Smart alignment detection with reasonableness checks
- **Advanced Chunked Reading**: Multiple strategies for large UDTs with intelligent error recovery
- **Cross-Language Support**: All improvements work seamlessly across Rust, Go, and C# wrappers
- **Performance Optimized**: Sub-5ms response times for complex UDT operations
### ๐ง **Connection Robustness**
- **Automatic session management** with proper registration/unregistration
- **Connection health monitoring** with configurable timeouts
- **Network resilience** handling for industrial environments
- **Comprehensive error handling** with detailed CIP error mapping
### โ ๏ธ **Known Limitations**
The following operations are **not supported** due to PLC firmware restrictions. These limitations are inherent to the Allen-Bradley PLC firmware and cannot be bypassed at the library level.
#### STRING Tag Writing
**Cannot write directly to STRING tags** (e.g., `gTest_STRING`, `Program:TestProgram.gTest_STRING`).
**Root Cause:** PLC firmware limitation (CIP Error 0x2107). The PLC rejects direct write operations to STRING tags, regardless of the communication method used.
**What Works:**
- โ
Reading STRING tags: `gTest_STRING` (read successfully)
- โ
Reading STRING members in UDTs: `gTestUDT.Member5_String` (read successfully)
**What Doesn't Work:**
- โ Writing simple STRING tags: `gTest_STRING` (write fails - PLC limitation)
- โ Writing program-scoped STRING tags: `Program:TestProgram.gTest_STRING` (write fails - PLC limitation)
- โ Writing STRING members in UDTs directly: `gTestUDT.Member5_String` (write fails - must write entire UDT)
**Workaround for STRING Members in UDTs:**
If the STRING is part of a UDT structure, you can write it by reading the entire UDT, modifying the STRING member in memory, then writing the entire UDT back:
```rust
// Read entire UDT
let mut udt = client.read_tag("gTestUDT").await?;
// Modify STRING member in memory (if UDT structure is known)
// ... modify UDT structure ...
// Write entire UDT back
client.write_tag("gTestUDT", udt).await?;
```
**Note:** For standalone STRING tags (not part of a UDT), there is no workaround at the communication library level. Alternative approaches may include using PLC ladder logic or other PLC-side mechanisms to update STRING values.
#### UDT Array Element Member Writing
**Cannot write directly to members of UDT array elements** (e.g., `gTestUDT_Array[0].Member1_DINT`).
**Root Cause:** PLC firmware limitation (CIP Error 0x2107). The PLC does not support direct write operations to individual members within UDT array elements.
**What Works:**
- โ
Reading UDT array element members: `gTestUDT_Array[0].Member1_DINT` (read successfully)
- โ
Writing entire UDT array elements: `gTestUDT_Array[0]` (write full UDT structure)
- โ
Writing UDT members (non-array): `gTestUDT.Member1_DINT` (write individual members of non-array UDTs)
- โ
Writing simple array elements: `gArray[5]` (write elements of simple arrays like DINT[], REAL[], etc.)
**What Doesn't Work:**
- โ Writing UDT array element members: `gTestUDT_Array[0].Member1_DINT` (write fails - PLC limitation)
- โ Writing program-scoped UDT array element members: `Program:TestProgram.gTestUDT_Array[0].Member1_DINT` (write fails - PLC limitation)
**Workaround:**
Use a read-modify-write pattern:
```rust
// Read entire UDT array element
let mut element = client.read_tag("gTestUDT_Array[0]").await?;
// Modify member in memory (if UDT structure is known)
// ... modify UDT structure ...
// Write entire UDT array element back
client.write_tag("gTestUDT_Array[0]", element).await?;
```
#### Summary of Limitations
**Test Results (392 tags tested):**
- โ
**333/392 tags** (84.9%) successfully read and written
- โ **59/392 tags** failed due to PLC firmware limitations:
- 55 tags: UDT array element member writes (e.g., `gTestUDT_Array[0].Member1_DINT`)
- 2 tags: Simple STRING tag writes (e.g., `gTest_STRING`)
- 2 tags: STRING member writes in UDTs (e.g., `gTestUDT.Member5_String`)
**Important Notes:**
- These limitations are **PLC firmware restrictions**, not library bugs
- The library correctly implements the EtherNet/IP and CIP protocols
- All read operations work correctly for all tag types
- Workarounds are available for UDT array element members and STRING members in UDTs
- Standalone STRING tag writes have no workaround at the communication library level
**๐ For detailed technical information about these limitations, including official Rockwell documentation references and technical background, see [AB_String_UDT_Write_Limitations.md](docs/AB_String_UDT_Write_Limitations.md).**
### ๐ **Advanced Tag Addressing** โ
**COMPLETED**
- **Program-scoped tags**: `Program:MainProgram.Tag1` โ
**FIXED in v0.5.4**
- **Array element access**: `MyArray[5]`, `MyArray[1,2,3]` โ
**WORKING in v0.5.5**
- Automatic workaround: Reads entire array and extracts element
- Supports read and write operations
- Works with controller-scoped and program-scoped arrays
- Special handling for BOOL arrays (DWORD bit extraction)
- **Bit-level operations**: `MyDINT.15` (access individual bits)
- **UDT member access**: `MyUDT.Member1.SubMember`
- **String operations**: `MyString.LEN`, `MyString.DATA[5]`
- **Complex nested paths**: `Program:Production.Lines[2].Stations[5].Motor.Status.15`
### ๐ **Complete Data Type Support** โ
**COMPLETED**
All Allen-Bradley native data types with proper CIP encoding:
- **BOOL** - Boolean values (CIP type 0x00C1)
- **SINT** - 8-bit signed integer (-128 to 127, CIP type 0x00C2)
- **INT** - 16-bit signed integer (-32,768 to 32,767, CIP type 0x00C3)
- **DINT** - 32-bit signed integer (-2.1B to 2.1B, CIP type 0x00C4)
- **LINT** - 64-bit signed integer (CIP type 0x00C5)
- **USINT** - 8-bit unsigned integer (0 to 255, CIP type 0x00C6)
- **UINT** - 16-bit unsigned integer (0 to 65,535, CIP type 0x00C7)
- **UDINT** - 32-bit unsigned integer (0 to 4.3B, CIP type 0x00C8)
- **ULINT** - 64-bit unsigned integer (CIP type 0x00C9)
- **REAL** - 32-bit IEEE 754 float (CIP type 0x00CA)
- **LREAL** - 64-bit IEEE 754 double (CIP type 0x00CB)
- **STRING** - Variable-length strings (CIP type 0x00DA)
- **UDT** - User Defined Types with full nesting support (CIP type 0x00A0)
### ๐ **Language Bindings**
#### **C# Integration** ๐ฏ **CURRENT FOCUS - Active Development**
- **Complete C# wrapper** with all data types
- **22 FFI functions** for seamless integration
- **Type-safe API** with comprehensive error handling
- **Cross-platform support** (Windows, Linux, macOS)
- **Production-ready examples**: WinForms, WPF, ASP.NET
- **Advanced features**: TagGroup, Statistics, Batch Operations, STRING support
- **Status**: Actively being polished to production quality
#### **Go Integration** โธ๏ธ **ON HOLD**
- **CGO wrapper** with comprehensive API coverage
- **Type-safe Go bindings** for all PLC data types
- **Connection management** and health monitoring
- **Error handling** with Go-idiomatic patterns
- **Full-stack example** with Go backend + Next.js frontend ([see example](examples/gonextjs/README.md))
- **Status**: Development paused until .NET stack is complete
#### **Python Integration** โธ๏ธ **ON HOLD**
- **PyO3-based Python wrapper** with full API coverage
- **Type-safe Python bindings** for all PLC data types
- **Synchronous and asynchronous APIs** for flexible usage
- **Comprehensive error handling** with Python exceptions
- **Easy installation** via pip or maturin
- **Cross-platform support** (Windows, Linux, macOS)
- **Status**: Development paused until .NET stack is complete
### โ ๏ธ **Comprehensive Error Handling** โ
**COMPLETED**
- **Detailed CIP error mapping** with 40+ error codes
- **Network-level diagnostics** and troubleshooting
- **Granular error types** for precise error handling
- **Automatic error recovery** for transient issues
### ๐๏ธ **Build System** โ
**COMPLETED**
- **Automated build scripts** for Windows and Linux/macOS
- **Cross-platform compilation** with proper library generation
- **Comprehensive testing** with 30+ unit tests
- **CI/CD ready** with GitHub Actions examples
### โก **Real-Time Subscriptions** โ
**NEW in v0.4.0**
- **Real-time tag monitoring** with configurable update intervals (1ms - 10s)
- **Event-driven notifications** for tag value changes
- **Multi-tag subscriptions** supporting hundreds of concurrent monitors
- **Automatic reconnection** and error recovery
- **Memory-efficient engine** with minimal CPU overhead
### ๐ **High-Performance Batch Operations** โ
**NEW in v0.4.0**
- **Batch read operations** - read up to 100+ tags in a single request
- **Batch write operations** - write multiple tags atomically
- **Parallel processing** with concurrent execution
- **Transaction support** with rollback capabilities
- **2,000+ ops/sec throughput** with intelligent packet packing
## ๐ญ **HMI/SCADA Production Demo**
Experience a **professional-grade HMI dashboard** showcasing real-world industrial data tracking and monitoring capabilities. This demo demonstrates the library's potential for building production-ready SCADA systems and industrial dashboards.

### ๐ฏ **Demo Features**
- **๐ Real-time Production Monitoring** - Live production counts, targets, and progress tracking
- **๐ OEE Analysis** - Overall Equipment Effectiveness with availability, performance, and quality metrics
- **๐ก๏ธ Process Parameters** - Temperature, pressure, vibration monitoring with color-coded alerts
- **โ๏ธ Machine Status** - Real-time machine state, shift information, and operator tracking
- **๐ง Maintenance Management** - Scheduled maintenance tracking and history
- **๐ฑ Responsive Design** - Works seamlessly on desktop, tablet, and mobile devices
### ๐ **Perfect for Demonstrations**
This demo showcases:
- **High-frequency data collection** (1-second intervals)
- **Professional HMI aesthetics** with industrial-grade visualizations
- **Real-world metrics** that matter to production managers
- **Scalable architecture** for larger SCADA systems
- **Modern web technologies** for cross-platform deployment
### ๐ท๏ธ **Required PLC Tags**
The demo reads 13 industrial tags including machine status, production metrics, process parameters, and OEE data. See the [Go + Next.js example](examples/gonextjs/README.md) for complete tag specifications and setup instructions.
**Try it now:** Navigate to the "HMI Demo" tab in the [Go + Next.js fullstack example](examples/gonextjs/README.md)!
## ๐ **Performance Characteristics**
Optimized for PC applications with excellent performance:
> **๐ Latest Performance Improvements (v0.6.0)**
>
> Recent optimizations and improvements:
> - **Generic UDT Format**: New `UdtData` struct enables universal UDT handling
> - **Memory allocation improvements**: 20-30% reduction in allocation overhead for network operations
> - **Batch operations**: 3-10x faster than individual operations
> - **Code quality**: Enhanced with idiomatic Rust patterns and clippy optimizations
> - **Network efficiency**: Optimized packet building with pre-allocated buffers
> - **Library Health**: All 31 unit tests passing, production-ready core
| Single Tag Read | 3,000+ ops/sec | <1ms | ~800B |
| Single Tag Write | 1,500+ ops/sec | <2ms | ~800B |
| Batch Operations | 2,000+ ops/sec | 5-20ms | ~2KB |
| Real-time Subscriptions | 1,000+ tags/sec | 1-10ms | ~1KB |
| Tag Path Parsing | 10,000+ ops/sec | <0.1ms | ~1KB |
| Connection Setup | N/A | 50-200ms | ~4KB |
| Memory per Connection | N/A | N/A | ~4KB base |
## ๐ **Development Roadmap**
### ๐ฅ **Phase 1: Core Enhancements** โ
**COMPLETED - January 2026**
- [x] Basic tag read/write operations
- [x] Connection management and session handling
- [x] **Enhanced tag path parsing** (Program-scoped, arrays, bit access)
- [x] **Complete data type support** (All Allen-Bradley types)
- [x] **C# wrapper integration** (22 FFI functions)
- [x] **Comprehensive testing** (30+ unit tests)
- [x] **Build automation** (Cross-platform build scripts)
- [x] **Documentation** (Examples, API docs, guides)
### โก **Phase 2: Advanced Features** โ
**COMPLETED - January 2026**
- [x] **Batch operations** (multi-tag read/write) โ
**COMPLETED**
- [x] **Real-time subscriptions** (tag change notifications) โ
**COMPLETED**
- [x] **Performance optimizations** (20% faster operations + memory improvements) โ
**COMPLETED**
- [x] **Enhanced error handling & recovery** โ
**COMPLETED**
### ๐ฏ **Phase 3: Production Ready** โ
**COMPLETED - January 2026**
- [x] **Production monitoring** - Comprehensive metrics and health checks
- [x] **Configuration management** - Production-ready config system
- [x] **Error handling** - Detailed CIP error mapping and recovery
- [x] **Performance optimization** - Batch operations and connection pooling
- [x] **Generic UDT Format** - Universal UDT handling with `UdtData` struct (v0.6.0)
- [x] **Library Testing** - All 31 unit tests passing
- [x] **Code Quality** - Comprehensive examples and tests updated for new API
- [x] **Community features** - Discord server, GitHub discussions, sponsorship program
### ๐ **Phase 4: Industrial Routing Support** โ
**PARTIALLY IMPLEMENTED**
- [x] **Basic slot configuration** - Support for CPUs in slots 0-31 (โ
Implemented in v0.6.0)
- [x] **Simple backplane routing** - Direct backplane communication (โ
Implemented in v0.6.0)
- [x] **Route path building** - CIP route path construction (โ
Implemented in v0.6.0)
- [x] **Network routing** - Multi-hop network routing via addresses and ports (โ
Implemented in v0.6.0)
- [x] **Path validation** - Route path verification and CIP byte construction (โ
Implemented in v0.6.0)
- [ ] **Remote rack support** - Connect to remote racks via network (โ ๏ธ Basic support exists, needs testing)
- [ ] **Advanced routing** - Complex network topologies (โ ๏ธ Basic support exists, needs validation)
- [ ] **Route discovery** - Automatic path detection (โ Not implemented)
**Note:** ControlLogix systems with CPUs in different slots can be tested using the `RoutePath` API.
Use `EipClient::with_route_path()` or `set_route_path()` with `RoutePath::new().add_slot(slot_number)`
to connect to ControlLogix CPUs in slots 0-31.
## ๐ ๏ธ **Installation**
### ๐ฆ **Rust Library (Crates.io)**
The easiest way to get started is by adding the crate to your `Cargo.toml`:
```toml
[dependencies]
rust-ethernet-ip = "0.5.3"
tokio = { version = "1.0", features = ["full"] }
### Rust Library
Add to your `Cargo.toml`:
```toml
[dependencies]
rust-ethernet-ip = "0.6.0"
tokio = { version = "1.0", features = ["full"] }
```
### C# Wrapper
Install via NuGet:
```xml
<PackageReference Include="RustEtherNetIp" Version="0.6.0" />
```
Or via Package Manager Console:
```powershell
Install-Package RustEtherNetIp
```
### Python Wrapper
Install via pip:
```bash
pip install rust-ethernet-ip
```
Or build from source using maturin:
```bash
cd pywrapper
maturin develop
```
## ๐ **Quick Start**
### UDT Discovery (v0.5.4)
```rust
use rust_ethernet_ip::{EipClient, RoutePath};
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
// Connect to PLC
let mut client = EipClient::connect("192.168.0.1:44818").await?;
// Discover UDT structure automatically
let definition = client.get_udt_definition("Part_Data").await?;
println!("UDT: {}", definition.name);
for member in &definition.members {
println!(" {}: {} (offset: {}, size: {} bytes)",
member.name,
get_data_type_name(member.data_type),
member.offset,
member.size
);
}
// Read UDT data using discovered structure
let udt_data = client.read_udt_chunked("Part_Data").await?;
// Read individual members using discovered offsets
for member in &definition.members {
let value = client.read_udt_member_by_offset(
"Part_Data",
member.offset as usize,
member.size as usize,
member.data_type
).await?;
println!("{}: {:?}", member.name, value);
}
Ok(())
}
```
### Route Path Support (v0.5.4)
```rust
// Create route path for slot 2
let route = RoutePath::new()
.add_slot(0) // Backplane slot 0
.add_slot(2); // Target slot 2
// Connect with route path
let mut client = EipClient::with_route_path("192.168.0.1:44818", route).await?;
// Read tags through the route
let value = client.read_tag("TestTag").await?;
```
### Basic Usage
```rust
use rust_ethernet_ip::{EipClient, PlcValue};
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
// Connect to CompactLogix PLC
let mut client = EipClient::connect("192.168.1.100:44818").await?;
// Read different data types
let motor_running = client.read_tag("Program:Main.MotorRunning").await?;
let production_count = client.read_tag("Program:Main.ProductionCount").await?;
let temperature = client.read_tag("Program:Main.Temperature").await?;
// Write values
client.write_tag("Program:Main.SetPoint", PlcValue::Dint(1500)).await?;
client.write_tag("Program:Main.StartButton", PlcValue::Bool(true)).await?;
println!("Motor running: {:?}", motor_running);
println!("Production count: {:?}", production_count);
println!("Temperature: {:?}", temperature);
Ok(())
}
```
### C# Usage
```csharp
using RustEtherNetIp;
using var client = new EtherNetIpClient();
if (client.Connect("192.168.1.100:44818"))
{
// Read different data types
bool motorRunning = client.ReadBool("Program:Main.MotorRunning");
int productionCount = client.ReadDint("Program:Main.ProductionCount");
float temperature = client.ReadReal("Program:Main.Temperature");
// Write values
client.WriteDint("Program:Main.SetPoint", 1500);
client.WriteBool("Program:Main.StartButton", true);
Console.WriteLine($"Motor running: {motorRunning}");
Console.WriteLine($"Production count: {productionCount}");
Console.WriteLine($"Temperature: {temperature:F1}ยฐC");
}
```
### Python Usage
```python
from rust_ethernet_ip import PyEipClient
def main():
# Create a client and connect to the PLC
client = PyEipClient(addr="192.168.0.1")
if not client.connect():
print("Failed to connect to PLC")
return
try:
# Read a DINT value
value = client.read_dint("TestDINT")
print("Read TestDINT:", value)
# Write a new value
client.write_dint("TestDINT", 42)
print("Wrote 42 to TestDINT")
except Exception as e:
print("Error:", e)
if __name__ == "__main__":
main()
```
### Advanced Tag Addressing
```rust
// Program-scoped tags
let value = client.read_tag("Program:MainProgram.Tag1").await?;
// Array elements (v0.5.5 - automatic workaround)
let array_element = client.read_tag("Program:Main.MyArray[5]").await?;
// Writing array elements
client.write_tag("gArrayTest[0]", PlcValue::Dint(100)).await?;
// BOOL arrays work too
let bool_value = client.read_tag("gArrayBoolTest[5]").await?;
client.write_tag("gArrayBoolTest[5]", PlcValue::Bool(true)).await?;
let multi_dim = client.read_tag("Program:Main.Matrix[1,2,3]").await?;
// Bit access
let bit_value = client.read_tag("Program:Main.StatusWord.15").await?;
// UDT members
let udt_member = client.read_tag("Program:Main.MotorData.Speed").await?;
let nested_udt = client.read_tag("Program:Main.Recipe.Step1.Temperature").await?;
// String operations
let string_length = client.read_tag("Program:Main.ProductName.LEN").await?;
let string_char = client.read_tag("Program:Main.ProductName.DATA[0]").await?;
```
### Complete Data Type Examples
```rust
// All supported data types
let bool_val = client.read_tag("BoolTag").await?; // BOOL
let sint_val = client.read_tag("SintTag").await?; // SINT (-128 to 127)
let int_val = client.read_tag("IntTag").await?; // INT (-32,768 to 32,767)
let dint_val = client.read_tag("DintTag").await?; // DINT (-2.1B to 2.1B)
let lint_val = client.read_tag("LintTag").await?; // LINT (64-bit signed)
let usint_val = client.read_tag("UsintTag").await?; // USINT (0 to 255)
let uint_val = client.read_tag("UintTag").await?; // UINT (0 to 65,535)
let udint_val = client.read_tag("UdintTag").await?; // UDINT (0 to 4.3B)
let ulint_val = client.read_tag("UlintTag").await?; // ULINT (64-bit unsigned)
let real_val = client.read_tag("RealTag").await?; // REAL (32-bit float)
let lreal_val = client.read_tag("LrealTag").await?; // LREAL (64-bit double)
let string_val = client.read_tag("StringTag").await?; // STRING
let udt_val = client.read_tag("UdtTag").await?; // UDT
```
## โก **Batch Operations** โ
**COMPLETED**
**Dramatically improve performance** with batch operations that execute multiple read/write operations in a single network packet. Perfect for data acquisition, recipe management, and coordinated control scenarios.
### ๐ **Performance Benefits**
- **3-10x faster** than individual operations
- **Reduced network traffic** (1-5 packets instead of N packets for N operations)
- **Lower PLC CPU usage** due to fewer connection handling overheads
- **Better throughput** for data collection and control applications
### ๐ **Use Cases**
- **Data acquisition**: Reading multiple sensor values simultaneously
- **Recipe management**: Writing multiple setpoints at once
- **Status monitoring**: Reading multiple status flags efficiently
- **Coordinated control**: Atomic operations across multiple tags
### ๐ง **Basic Batch Reading**
```rust
use rust_ethernet_ip::{EipClient, BatchOperation, PlcValue};
// Read multiple tags in a single operation
let tags_to_read = vec![
"ProductionCount",
"Temperature_1",
"Temperature_2",
"Pressure_1",
"FlowRate",
];
let results = client.read_tags_batch(&tags_to_read).await?;
for (tag_name, result) in results {
match result {
Ok(value) => println!("๐ {}: {:?}", tag_name, value),
Err(error) => println!("โ {}: {}", tag_name, error),
}
}
```
### โ๏ธ **Basic Batch Writing**
```rust
// Write multiple tags in a single operation
let tags_to_write = vec![
("SetPoint_1", PlcValue::Real(75.5)),
("SetPoint_2", PlcValue::Real(80.0)),
("EnableFlag", PlcValue::Bool(true)),
("ProductionMode", PlcValue::Dint(2)),
("RecipeNumber", PlcValue::Dint(42)),
];
let results = client.write_tags_batch(&tags_to_write).await?;
for (tag_name, result) in results {
match result {
Ok(()) => println!("โ
{}: Write successful", tag_name),
Err(error) => println!("โ {}: {}", tag_name, error),
}
}
```
### ๐ **Mixed Operations (Reads + Writes)**
```rust
use rust_ethernet_ip::BatchOperation;
let operations = vec![
// Read current values
BatchOperation::Read { tag_name: "CurrentTemp".to_string() },
BatchOperation::Read { tag_name: "CurrentPressure".to_string() },
// Write new setpoints
BatchOperation::Write {
tag_name: "TempSetpoint".to_string(),
value: PlcValue::Real(78.5)
},
BatchOperation::Write {
tag_name: "PressureSetpoint".to_string(),
value: PlcValue::Real(15.2)
},
// Update control flags
BatchOperation::Write {
tag_name: "AutoModeEnabled".to_string(),
value: PlcValue::Bool(true)
},
];
let results = client.execute_batch(&operations).await?;
for result in results {
match result.operation {
BatchOperation::Read { tag_name } => {
match result.result {
Ok(Some(value)) => println!("๐ Read {}: {:?} ({}ฮผs)",
tag_name, value, result.execution_time_us),
Err(error) => println!("โ Read {}: {}", tag_name, error),
}
}
BatchOperation::Write { tag_name, .. } => {
match result.result {
Ok(_) => println!("โ
Write {}: Success ({}ฮผs)",
tag_name, result.execution_time_us),
Err(error) => println!("โ Write {}: {}", tag_name, error),
}
}
}
}
```
### โ๏ธ **Advanced Configuration**
```rust
use rust_ethernet_ip::BatchConfig;
// High-performance configuration
let high_perf_config = BatchConfig {
max_operations_per_packet: 50, // More operations per packet
max_packet_size: 4000, // Larger packets for modern PLCs
packet_timeout_ms: 1000, // Faster timeout
continue_on_error: true, // Don't stop on single failures
optimize_packet_packing: true, // Optimize packet efficiency
};
client.configure_batch_operations(high_perf_config);
// Conservative/reliable configuration
let conservative_config = BatchConfig {
max_operations_per_packet: 10, // Fewer operations per packet
max_packet_size: 504, // Smaller packets for compatibility
packet_timeout_ms: 5000, // Longer timeout
continue_on_error: false, // Stop on first error
optimize_packet_packing: false, // Preserve exact operation order
};
client.configure_batch_operations(conservative_config);
```
### ๐ **Performance Comparison Example**
```rust
use std::time::Instant;
let tags = vec!["Tag1", "Tag2", "Tag3", "Tag4", "Tag5"];
// Individual operations (traditional approach)
let individual_start = Instant::now();
for tag in &tags {
let _ = client.read_tag(tag).await?;
}
let individual_duration = individual_start.elapsed();
// Batch operations (optimized approach)
let batch_start = Instant::now();
let _ = client.read_tags_batch(&tags).await?;
let batch_duration = batch_start.elapsed();
let speedup = individual_duration.as_nanos() as f64 / batch_duration.as_nanos() as f64;
println!("๐ Performance improvement: {:.1}x faster with batch operations!", speedup);
```
### ๐จ **Error Handling**
```rust
// Batch operations provide detailed error information per operation
match client.execute_batch(&operations).await {
Ok(results) => {
let mut success_count = 0;
let mut error_count = 0;
for result in results {
match result.result {
Ok(_) => success_count += 1,
Err(_) => error_count += 1,
}
}
println!("๐ Results: {} successful, {} failed", success_count, error_count);
println!("๐ Success rate: {:.1}%",
(success_count as f32 / (success_count + error_count) as f32) * 100.0);
}
Err(e) => println!("โ Entire batch failed: {}", e),
}
```
### ๐ฏ **Best Practices**
- **Use batch operations for 3+ operations** to see significant performance benefits
- **Group similar operations** (reads together, writes together) for optimal packet packing
- **Adjust max_operations_per_packet** based on your PLC's capabilities (10-50 typical)
- **Use higher packet sizes** (up to 4000 bytes) for modern CompactLogix/ControlLogix PLCs
- **Enable continue_on_error** for data collection scenarios where partial results are acceptable
- **Disable optimize_packet_packing** if precise operation order is critical for your application
## ๐๏ธ **Building**
### Quick Build
```bash
# Windows
build.bat
# Linux/macOS
./build.sh
```
### Manual Build
```bash
# Build Rust library
cargo build --release --lib
# Copy to C# project (Windows)
copy target\release\rust_ethernet_ip.dll csharp\RustEtherNetIp\
# Build C# wrapper
cd csharp/RustEtherNetIp
dotnet build --configuration Release
```
See [BUILD.md](BUILD.md) for comprehensive build instructions.
## ๐งช **Testing**
Run the comprehensive test suite:
```bash
# Rust unit tests (30+ tests)
cargo test
# C# wrapper tests
cd csharp/RustEtherNetIp.Tests
dotnet test
# Run examples
cargo run --example advanced_tag_addressing
cargo run --example data_types_showcase
```
## ๐ฏ **Examples**
Explore comprehensive examples demonstrating all library capabilities across different platforms:
### **๐ TypeScript + React Dashboard** *(Recommended)*
Modern web-based PLC dashboard with real-time monitoring and advanced features.
```bash
# Start backend API
cd examples/AspNetExample
dotnet run
# Start frontend (new terminal)
cd examples/TypeScriptExample/frontend
npm install && npm run dev
```
**Features:**
- โ
**Modern UI/UX** with glassmorphism design and responsive layout
- โ
**Real-time monitoring** with live tag updates and performance metrics
- โ
**Complete data type support** for all 13 Allen-Bradley types
- โ
**Advanced tag addressing** with interactive examples
- โ
**Type-safe API** with comprehensive TypeScript interfaces
- โ
**Professional features** including benchmarking and activity logging
**Perfect for:** Web applications, dashboards, remote monitoring, modern industrial HMIs
### **๐ฅ๏ธ WPF Desktop Application**
Rich desktop application with MVVM architecture and modern UI.
```bash
cd examples/WpfExample
dotnet run
```
**Features:**
- โ
**MVVM architecture** with CommunityToolkit.Mvvm
- โ
**Real-time tag monitoring** with automatic refresh
- โ
**Advanced tag discovery** with type detection
- โ
**Performance benchmarking** with visual metrics
- โ
**Comprehensive logging** with timestamped activity
**Perfect for:** Desktop HMIs, engineering tools, maintenance applications
### **๐ช WinForms Application**
Traditional Windows Forms application with familiar UI patterns.
```bash
cd examples/WinFormsExample
dotnet run
```
**Features:**
- โ
**Classic Windows UI** with familiar controls
- โ
**Connection monitoring** with automatic reconnection
- โ
**Tag operations** with validation and error handling
- โ
**Performance testing** with real-time metrics
- โ
**Industrial styling** with professional appearance
**Perfect for:** Legacy system integration, simple HMIs, maintenance tools
### **๐ ASP.NET Core Web API**
RESTful API backend providing HTTP access to PLC functionality.
```bash
cd examples/AspNetExample
dotnet run
```
**Features:**
- โ
**RESTful endpoints** for all PLC operations
- โ
**Swagger documentation** with interactive API explorer
- โ
**Type-safe operations** with comprehensive validation
- โ
**Performance monitoring** with built-in benchmarking
- โ
**Production-ready** with proper error handling and logging
**Perfect for:** Web services, microservices, system integration, mobile backends
### **๐ฆ Rust Examples**
Native Rust examples demonstrating core library functionality.
```bash
# Advanced tag addressing showcase
cargo run --example advanced_tag_addressing
# Complete data types demonstration
cargo run --example data_types_showcase
# Batch operations performance demo
cargo run --example batch_operations_demo
```
**Features:**
- โ
**Advanced tag parsing** with complex path examples
- โ
**All data types** with encoding demonstrations
- โ
**Performance examples** with async/await patterns
- โ
**Error handling** with comprehensive error types
- โ
**Batch operations** with performance comparisons and configuration examples
**Perfect for:** Rust applications, embedded systems, high-performance scenarios
### **๐น Go + Next.js Fullstack Example** *(NEW in v0.4.0!)*
Modern fullstack demo with a Go backend (using the Rust Go wrapper) and a Next.js (TypeScript) frontend for real-time, batch, and performance operations.
```bash
# Start backend
cd examples/gonextjs/backend
go run .
# Start frontend (new terminal)
cd ../frontend
npm install && npm run dev
```
**Features:**
- โ
**Go backend** using the Rust EtherNet/IP Go wrapper (FFI)
- โ
**Next.js frontend** (TypeScript, Tailwind, App Router)
- โ
**Batch read/write** and individual tag operations
- โ
**Performance benchmarking** (ops/sec, latency)
- โ
**Real-time tag updates** via WebSocket
- โ
**Comprehensive PLC data type support**
- โ
**Modern, responsive UI**
- โ
**๐ญ Professional HMI/SCADA Demo** - Production-ready dashboard with OEE analysis, process monitoring, and industrial data visualization
**Perfect for:** Modern web dashboards, Go/TypeScript fullstack apps, real-time industrial monitoring, HMI/SCADA systems
### **โก Vue.js 3 + TypeScript Frontend** *(NEW in v0.4.0!)*
Modern Vue.js 3 frontend with TypeScript, Tailwind CSS, and Pinia state management, designed to integrate with ASP.NET Core backends.
```bash
# Start backend API
cd examples/AspNetExample
dotnet run
# Start Vue.js frontend (new terminal)
cd examples/VueExample
npm install && npm run dev
```
**Features:**
- โ
**Vue.js 3** with Composition API and TypeScript
- โ
**Tailwind CSS** for modern, responsive design
- โ
**Pinia state management** for application state
- โ
**Backend detection system** for automatic ASP.NET Core port discovery
- โ
**Component-based architecture** with reusable UI components
- โ
**Real-time connection monitoring** with PLC status display
- โ
**Tag operations interface** for read/write operations
- โ
**Professional dashboard** with metrics and activity logging
- โ
**Development tools** including BackendDetector for debugging
**Perfect for:** Modern web applications, Vue.js-based HMIs, industrial dashboards, ASP.NET Core integration
### **๐ Quick Start Guide**
1. **Choose your platform:**
- **Web/Modern UI** โ TypeScript + React Dashboard or Vue.js 3 + TypeScript
- **Desktop/Windows** โ WPF or WinForms Application
- **Web API/Services** โ ASP.NET Core Web API
- **Native/Performance** โ Rust Examples
2. **Start the backend** (for web examples):
```bash
cd examples/AspNetExample
dotnet run
```
3. **Run your chosen example** and connect to your PLC at `192.168.0.1:44818`
4. **Explore features:**
- Tag discovery with advanced addressing
- Real-time monitoring and benchmarking
- All 13 Allen-Bradley data types
- Professional error handling and logging
### **๐ Example Structure**
```
examples/
โโโ TypeScriptExample/ # React + TypeScript dashboard
โ โโโ frontend/ # Modern web UI
โ โโโ start-backend.bat # Backend startup script
โ โโโ start-frontend.bat # Frontend startup script
โโโ VueExample/ # Vue.js 3 + TypeScript frontend
โ โโโ src/ # Vue.js source code
โ โโโ start-frontend.bat # Frontend startup script
โ โโโ README.md # Comprehensive documentation
โโโ WpfExample/ # WPF desktop application
โโโ WinFormsExample/ # WinForms desktop application
โโโ AspNetExample/ # ASP.NET Core Web API
โโโ gonextjs/ # Go + Next.js fullstack example
โโโ rust-examples/ # Native Rust examples
โโโ advanced_tag_addressing.rs
โโโ data_types_showcase.rs
โโโ batch_operations_demo.rs
```
Each example includes comprehensive documentation, setup instructions, and demonstrates different aspects of the library's capabilities.
## ๐ **Documentation**
- **[API Documentation](https://docs.rs/rust-ethernet-ip)** - Complete API reference
- **[Examples](examples/)** - Practical usage examples
- **[Build Guide](BUILD.md)** - Comprehensive build instructions
- **[C# Wrapper Guide](csharp/RustEtherNetIp/README.md)** - C# integration documentation
- **[Changelog](CHANGELOG.md)** - Version history and changes
- **[Crates.io Page](https://crates.io/crates/rust-ethernet-ip)** - Official crate registry page
## ๐ **Sponsor This Project**
This project is developed for the industrial automation community. If you find this library valuable for your projects, please consider sponsoring its development!
### ๐ฏ **Why Sponsor?**
- **๐ Accelerate Development** - Help fund new features, performance improvements, and platform support
- **๐ Priority Bug Fixes** - Get faster resolution of issues affecting your production systems
- **๐ก Feature Requests** - Influence the roadmap with your specific industrial automation needs
- **๐ Enhanced Documentation** - Support creation of comprehensive guides and tutorials
- **๐ง Professional Support** - Access to direct developer support for complex implementations
### ๐ฐ **Sponsorship Tiers**
- **โ Coffee** - Show appreciation for the project
- **๐ Feature Sponsor** - Fund specific feature development
- **๐ญ Enterprise Sponsor** - Priority support and custom development
- **๐ Platinum Sponsor** - Direct collaboration and roadmap input
### ๐ **Sponsor Benefits**
- **Priority issue resolution** for production-critical bugs
- **Direct access** to development team for technical questions
- **Early access** to new features and beta releases
- **Custom feature development** for your specific use cases
- **Recognition** in project documentation and releases
**[Sponsor on GitHub โ](https://github.com/sponsors/sergiogallegos)**
### ๐ฌ **Feedback & Feature Requests**
We value your input! Help us improve the library by sharing:
#### ๐ **Bug Reports**
- **Production Issues** - Critical bugs affecting your systems
- **Performance Problems** - Slow operations or memory issues
- **Compatibility Issues** - Problems with specific PLC models or configurations
- **Error Handling** - Unexpected errors or unclear error messages
#### ๐ก **Feature Requests**
- **New Data Types** - Additional Allen-Bradley data type support
- **Platform Support** - New operating systems or architectures
- **Performance Features** - Batch operations, caching, or optimization requests
- **Integration Features** - New language bindings or framework integrations
- **Industrial Features** - SCADA-specific functionality, alarms, or trending
#### ๐ **Use Case Sharing**
- **Success Stories** - How you're using the library in production
- **Performance Metrics** - Real-world performance data from your applications
- **Integration Examples** - Custom implementations or workarounds
- **Best Practices** - Tips for other users in similar industries
**[Submit Feedback โ](https://github.com/sergiogallegos/rust-ethernet-ip/issues/new/choose)**
## ๐ค **Community & Support**
- **[Discord Server](https://discord.gg/uzaM3tua)** - Community discussions, support, and development updates
- **[GitHub Issues](https://github.com/sergiogallegos/rust-ethernet-ip/issues)** - Bug reports and feature requests
- **[GitHub Discussions](https://github.com/sergiogallegos/rust-ethernet-ip/discussions)** - General questions and ideas
- **[Crates.io](https://crates.io/crates/rust-ethernet-ip)** - Official Rust package registry
## ๐ **Inspiration**
This project draws inspiration from excellent libraries in the industrial automation space:
- **[pylogix](https://github.com/dmroeder/pylogix)** - Python library for Allen-Bradley PLCs
- **[pycomm3](https://github.com/ottowayi/pycomm3)** - Python library for Allen-Bradley PLCs
- **[gologix](https://github.com/danomagnum/gologix)** - Go library for Allen-Bradley PLCs
- **[libplctag](https://github.com/libplctag/libplctag)** - Cross-platform PLC communication library
## ๐ **Contributing**
We welcome contributions! Please see our [Contributing Guide](CONTRIBUTING.md) for details on:
- Code style and standards
- Testing requirements
- Pull request process
- Development setup
## โ ๏ธ **Disclaimer and Liability**
### **Use at Your Own Risk**
This library is provided "AS IS" without warranty of any kind. Users assume full responsibility for its use in their applications and systems.
### **No Warranties**
The developers and contributors make **NO WARRANTIES, EXPRESS OR IMPLIED**, including but not limited to:
- **Merchantability** or fitness for a particular purpose
- **Reliability** or availability of the software
- **Accuracy** of data transmission or processing
- **Safety** for use in critical or production systems
### **Industrial Safety Responsibility**
- **๐ญ Industrial Use:** Users are solely responsible for ensuring this library meets their industrial safety requirements
- **๐ Safety Systems:** This library should NOT be used for safety-critical applications without proper validation
- **โ๏ธ Production Systems:** Thoroughly test in non-production environments before deploying to production systems
- **๐ Compliance:** Users must ensure compliance with all applicable industrial standards and regulations
### **Limitation of Liability**
Under no circumstances shall the developers, contributors, or associated parties be liable for:
- **Equipment damage** or malfunction
- **Production downtime** or operational disruptions
- **Data loss** or corruption
- **Personal injury** or property damage
- **Financial losses** of any kind
- **Consequential or indirect damages**
### **User Responsibilities**
By using this library, you acknowledge and agree that:
- You have the technical expertise to properly implement and test the library
- You will perform adequate testing before production deployment
- You will implement appropriate safety measures and fail-safes
- You understand the risks associated with industrial automation systems
- You accept full responsibility for any consequences of using this library
### **Indemnification**
Users agree to indemnify and hold harmless the developers and contributors from any claims, damages, or liabilities arising from the use of this library.
---
**โ ๏ธ IMPORTANT: This disclaimer is an integral part of the license terms. Use of this library constitutes acceptance of these terms.**
## ๐ **License**
This project is licensed under the MIT License - see the [LICENSE](LICENSE) file for details.
---
**Built for the industrial automation community**
## ๐ฆ Examples
- **C# + React**: Modern web and desktop examples using the C# wrapper
- **Go + Next.js**: [Fullstack Go backend + Next.js frontend example](examples/gonextjs/README.md) (**NEW in v0.4.0!**)
- **Vue.js 3 + TypeScript**: [Modern Vue.js frontend with ASP.NET Core integration](examples/VueExample/README.md) (**NEW in v0.4.0!**)
- **TypeScript + ASP.NET**: Classic React + ASP.NET example
- ...and more in the `examples/` directory
## ๐๏ธ Build All
To build all wrappers, libraries, and examples (including Go + Next.js and Vue.js):
```bash
./build-all.bat
```
This script builds:
- Rust library (DLL/SO/DYLIB)
- C# wrapper and tests
- Go wrapper and tests
- All example backends and frontends (C#, Go, TypeScript, Next.js, Vue.js)
See [BUILD.md](BUILD.md) for details.
## ๐ Version
**Current Release:** v0.6.0 ([CHANGELOG.md](CHANGELOG.md))
## ๐ Changelog
### v0.6.0 (January 2026) - **CURRENT** ๐
- **๐ง Generic UDT Format**: New `UdtData` struct with `symbol_id` and raw bytes
- **โ
Library Health**: All 31 unit tests passing, production-ready core
- **๐ Array Element Access**: Full read/write support for array elements
- **โ๏ธ Array Element Writing**: Write individual array elements with automatic array modification
- **๐ C# Wrapper Enhancements**: Batch operations, TagGroup, Statistics, Data Quality & Timestamp
- **๐ง Connection Fixes**: Fixed RoutePath handling in WinForms, WPF, and ASP.NET applications
- **๐ Documentation**: Comprehensive documentation for STRING and UDT array write limitations
### v0.5.5 (December 2025)
- **๐ Array Element Access**: Full read/write support for array elements using intelligent workaround
- **โ๏ธ Array Element Writing**: Write individual array elements with automatic array modification
- **๐ง BOOL Array Support**: Automatic DWORD bit extraction for BOOL arrays
### v0.5.4 (October 2025)
- **๐ UDT Definition Discovery**: Automatic UDT structure detection from PLC
- **๐ท๏ธ Enhanced Tag Discovery**: Full attribute support with permissions and scope
- **๐ฆ Packet Size Negotiation**: Dynamic optimization for firmware 20+
- **๐ฃ๏ธ Route Path Support**: Slot configuration and multi-hop routing
- **๐พ Cache Management**: Smart caching for UDT definitions and tag attributes
- **๐ง CIP Services**: Full implementation of Services 0x03 and 0x4C
- **๐งช Comprehensive Testing**: 14 new unit tests for UDT discovery features
- **๐ Documentation**: Complete API documentation and examples
See [CHANGELOG.md](CHANGELOG.md) for a full list of changes.
## ๐ Release Notes
See [RELEASE_NOTES_v0.5.0.md](RELEASE_NOTES_v0.5.0.md) for detailed release notes and migration info.
## ๐ Quick Start: Go + Next.js Fullstack Example
- See [examples/gonextjs/README.md](examples/gonextjs/README.md) for step-by-step instructions.
- Features: Go backend (using Rust FFI), Next.js frontend, batch ops, real-time, performance, and more.