From f9c3c16579722ea8cbba8a5d6a6bc848458f5c80 Mon Sep 17 00:00:00 2001
From: Martin Teichmann <martin.teichmann@xfel.eu>
Date: Thu, 16 Feb 2023 16:44:50 +0100
Subject: [PATCH] set pdo size to its actual value

we used to initialize the sync manager to what was
in the eeprom, which is big enough normally, but not always.

Now we read out the pdo assignment first, and set the sync
manager size accordingly.
---
 ebpfcat/ebpfcat.py  |  6 ++++--
 ebpfcat/ethercat.py | 20 ++++++++++++++++----
 2 files changed, 20 insertions(+), 6 deletions(-)

diff --git a/ebpfcat/ebpfcat.py b/ebpfcat/ebpfcat.py
index dbcdbed..e6e2b0f 100644
--- a/ebpfcat/ebpfcat.py
+++ b/ebpfcat/ebpfcat.py
@@ -223,8 +223,10 @@ class EBPFTerminal(Terminal):
                 f"Incompatible Terminal: {self.vendorId}:{self.productCode}")
         await self.to_operational(2)
         self.pdos = {}
-        if self.has_mailbox():
-            await self.parse_pdos()
+        outbits, inbits = await self.parse_pdos()
+        self.pdo_out_sz = int((outbits + 7) // 8)
+        self.pdo_in_sz = int((inbits + 7) // 8)
+        await self.write_pdo_sm()
 
     def allocate(self, packet, readonly):
         """allocate space in packet for the pdos of this terminal
diff --git a/ebpfcat/ethercat.py b/ebpfcat/ethercat.py
index a316104..d0deba9 100644
--- a/ebpfcat/ethercat.py
+++ b/ebpfcat/ethercat.py
@@ -450,6 +450,16 @@ class Terminal:
             elif mode == 6:
                 self.mbx_out_off = offset
                 self.mbx_out_sz = size
+            else:
+                print("wrong mode")
+
+    async def write_pdo_sm(self):
+        await self.write(0x816, "B", 0)
+        await self.write(0x812, "H", self.pdo_out_sz)
+        await self.write(0x816, "B", self.pdo_out_sz > 0)
+        await self.write(0x81E, "B", 0)
+        await self.write(0x81A, "H", self.pdo_in_sz)
+        await self.write(0x81E, "B", self.pdo_in_sz > 0)
 
     async def parse_pdos(self):
         async def parse_eeprom(s):
@@ -490,16 +500,18 @@ class Terminal:
                         (sm, bitpos // 8,
                          {8: "B", 16: "H", 32: "I", 64: "Q"}[bits])
                 bitpos += bits
+            return bitpos
 
         self.pdos = {}
         if self.has_mailbox():
-            await parse(parse_sdo(0x1c12, 2))
-            await parse(parse_sdo(0x1c13, 3))
+            return (await parse(parse_sdo(0x1c12, 2)),
+                    await parse(parse_sdo(0x1c13, 3)))
         else:
-            if 50 in self.eeprom:
+            return (
                 await parse(parse_eeprom(self.eeprom[50]))
-            if 51 in self.eeprom:
+                if 50 in self.eeprom else 0,
                 await parse(parse_eeprom(self.eeprom[51]))
+                if 51 in self.eeprom else 0)
 
     async def parse_pdo(self, index, sm):
         assignment = await self.sdo_read(index)
-- 
GitLab