From cd732b6de31331627a680146d077cbc45e305ee3 Mon Sep 17 00:00:00 2001 From: Patrick Dahlke Date: Fri, 22 May 2026 10:22:54 +0200 Subject: [PATCH 1/2] fix(examples): use correct EtherCAT configured station address in ethercat-real-bus MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit `EthercrabBusDriver::with_subdevice_inputs` matches on `sd.configured_address()`, which `ethercrab`'s `init_single_group` auto-assigns starting at `0x1000` — not on the 0-based topology index. The example was pinned to `SUBDEV: u16 = 1`, which matched no SubDevice on a real EK1100 + EL1008 rig, so the reader silently yielded zero envelopes. Bump the const to `0x1001` and update the module docs, the routing comment, and the README's "Topology assumption" section to describe configured station addresses so the next person doesn't trip on the same gap. Verified live on a Raspberry Pi 5 against an EK1100 + EL1008 + EL2004 — envelopes now flow at the expected ~1/cycle (10 ms tick), and toggling inputs produces `bits=…` lines as the README predicts. --- examples/ethercat-real-bus/README.md | 12 +++++++---- examples/ethercat-real-bus/src/main.rs | 30 +++++++++++++++----------- 2 files changed, 25 insertions(+), 17 deletions(-) diff --git a/examples/ethercat-real-bus/README.md b/examples/ethercat-real-bus/README.md index fa44c00..81ed056 100644 --- a/examples/ethercat-real-bus/README.md +++ b/examples/ethercat-real-bus/README.md @@ -21,10 +21,14 @@ does NOT run it (no NIC, no EK1100 in CI). NIC to the EK1100's **IN (X1)** port. The OUT (X2) port is for daisy-chaining additional couplers; leave it empty. -> **Topology assumption.** The example pins the EL1008 to SubDevice -> address `1` (the EK1100 is index `0` with no PDI). If you have -> additional terminals between the EK1100 and EL1008, edit the -> `SUBDEV` constant in `src/main.rs`. +> **Topology assumption.** The example pins the EL1008 to the EtherCAT +> configured station address `0x1001`. `ethercrab` auto-assigns these +> starting at `0x1000` in bus-scan order, so EK1100 = `0x1000`, +> EL1008 = `0x1001`, EL2004 = `0x1002`, etc. The driver matches on +> the configured station address (not a 0-based topology index), so +> this needs to be the real EtherCAT address. If you have additional +> terminals between the EK1100 and EL1008, edit the `SUBDEV` constant +> in `src/main.rs` accordingly. ## Host setup diff --git a/examples/ethercat-real-bus/src/main.rs b/examples/ethercat-real-bus/src/main.rs index 4574978..3af0b73 100644 --- a/examples/ethercat-real-bus/src/main.rs +++ b/examples/ethercat-real-bus/src/main.rs @@ -2,11 +2,12 @@ //! EK1100 + EL1008 over a real Linux NIC. See README.md for hardware //! setup and run instructions. //! -//! Topology assumption: EK1100 is SubDevice 0 (no PDI; it's a bus -//! coupler) and the EL1008 is SubDevice 1 with an 8-bit Tx PDO at -//! bit offset 0. If your topology has additional terminals between -//! the EK1100 and EL1008, edit `SUBDEV` to the EL1008's actual -//! auto-incremented address. +//! Topology assumption: `ethercrab` assigns configured station +//! addresses starting at `0x1000` — EK1100 = `0x1000` (no PDI; it's +//! a bus coupler), EL1008 = `0x1001` with an 8-bit Tx PDO at bit +//! offset 0. If your topology has additional terminals between the +//! EK1100 and EL1008, edit `SUBDEV` to the EL1008's actual +//! configured station address. use core::time::Duration; use std::sync::{Arc, Mutex}; @@ -24,11 +25,14 @@ use taktora_executor::{ControlFlow, ExecuteResult, Executor, ExecutorError, item /// Channel capacity (iceoryx2 service buffer slots). const N: usize = 256; -/// EL1008's auto-incremented EtherCAT SubDevice address. With a bare -/// EK1100 + EL1008 the EL1008 lands at index 1 (the EK1100 is index 0 -/// with no PDI). Adjust if you have additional terminals between -/// them. -const SUBDEV: u16 = 1; +/// EL1008's EtherCAT configured station address. `ethercrab`'s +/// `init_single_group` assigns auto-incrementing addresses starting +/// at `0x1000` (EK1100 = 0x1000, EL1008 = 0x1001, EL2004 = 0x1002, +/// etc.). The driver matches on `sd.configured_address()`, not the +/// topology index, so this needs to be the actual EtherCAT station +/// address — not `1`. Adjust if you have additional terminals +/// between the EK1100 and EL1008. +const SUBDEV: u16 = 0x1001; /// 8 digital input bits, one PDI byte. const ROUTING_BITS: u16 = 8; @@ -139,9 +143,9 @@ fn main() -> Result<(), Box> { let state = Arc::new(EthercatState::new(opts.clone())); let mut connector = EthercatConnector::new(state, driver, RawByteCodec)?; - // 4. Routing — EL1008 inputs at SubDevice 1, bit offset 0, 8 bits. - // PdoDirection::Tx means the SubDevice writes (Tx) and the - // master reads. + // 4. Routing — EL1008 inputs at configured station address + // `0x1001`, bit offset 0, 8 bits. PdoDirection::Tx means the + // SubDevice writes (Tx) and the master reads. let routing = EthercatRouting::new(SUBDEV, PdoDirection::Tx, 0, ROUTING_BITS); let desc = ChannelDescriptor::::new("ethercat.el1008.inputs", routing)?; From 295d9dcc3fc09624eba0a7d0421c7a9855bc63ee Mon Sep 17 00:00:00 2001 From: Patrick Dahlke Date: Fri, 22 May 2026 10:53:06 +0200 Subject: [PATCH 2/2] docs(examples): replace speculative ethercat-real-bus output with real capture MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The "What you should see" block was written from doc-reading, with illustrative timestamps and bit patterns that didn't reflect what the binary actually emits. Replace it with a trimmed transcript of a real Pi 5 session: bring-up, the iceoryx2 default-config warning, the first all-zeros sample, the Connecting → Up → Degraded health flow, and a walking-bit pattern from probing each EL1008 input in turn (verifies all 8 channels end-to-end). Also explain when readers should expect Up → Degraded — it's tied to having an extra output terminal (the captured rig had an EL2004) not being written to, which is asymmetric-PDO behaviour the connector intentionally flags. With the bare topology this README documents, the transition does not appear. --- examples/ethercat-real-bus/README.md | 47 ++++++++++++++++++++++------ 1 file changed, 38 insertions(+), 9 deletions(-) diff --git a/examples/ethercat-real-bus/README.md b/examples/ethercat-real-bus/README.md index 81ed056..4e84ee6 100644 --- a/examples/ethercat-real-bus/README.md +++ b/examples/ethercat-real-bus/README.md @@ -76,20 +76,49 @@ Or cap the run length for a quick smoke test (each tick is the ## What you should see +Bring-up, then (if any inputs are wired) one change-event per +transition on the EL1008's 24 V inputs. The excerpt below is from a +Pi 5 walking a 24 V probe across the eight input channels in order — +captured on the documented topology plus an extra EL2004 between the +EL1008 and the end cap: + ``` +0 [W] "Config::global_config()" + | No config file was loaded, a config with default values will be used. ethercat connector health at startup: Connecting +t=+ 531ms bits=0b00000000 decimal=0 ethercat connector health: Connecting -> Up -t=+ 12ms bits=0b00000000 decimal=0 -t=+ 1842ms bits=0b00000001 decimal=1 -t=+ 2103ms bits=0b00000011 decimal=3 -... +ethercat connector health: Up -> Degraded +t=+ 23510ms bits=0b00000001 decimal=1 +t=+ 23650ms bits=0b00000000 decimal=0 +t=+ 25360ms bits=0b00000010 decimal=2 +t=+ 25780ms bits=0b00000000 decimal=0 +t=+ 27170ms bits=0b00000100 decimal=4 +t=+ 27460ms bits=0b00000000 decimal=0 +t=+ 28580ms bits=0b00001000 decimal=8 +t=+ 28840ms bits=0b00000000 decimal=0 +t=+ 30190ms bits=0b00010000 decimal=16 +t=+ 30410ms bits=0b00000000 decimal=0 +t=+ 31370ms bits=0b00100000 decimal=32 +t=+ 31610ms bits=0b00000000 decimal=0 +t=+ 33730ms bits=0b01000000 decimal=64 +t=+ 33960ms bits=0b00000000 decimal=0 +t=+ 34730ms bits=0b10000000 decimal=128 +t=+ 34881ms bits=0b00000000 decimal=0 ``` -Bring-up usually completes within 1–2 seconds on a Pi 4. If you see -only `Connecting -> Up` and then no further output, that's expected -with no inputs wired — the EL1008 just reports all zeros. The bus is -alive; press a button on any 24V input channel to watch the byte -change. +Bring-up usually completes within 1–2 seconds on a Pi 4 or 5. With +no inputs wired the EL1008 just reports all zeros — bring-up still +runs to completion, the initial `bits=0b00000000` line prints, and +nothing further appears until you touch 24 V to one of the input +channels. + +The `Up -> Degraded` line above is rig-specific: adding an output +terminal such as the EL2004 without writing to it makes the working +counter come back lower than ethercrab expects, which trips the +connector's asymmetric-PDO degradation flag. Reads from the EL1008 +keep flowing. With the bare EK1100 + EL1008 topology this README +documents you stay at `Up` and never see the `Degraded` transition. ## Troubleshooting