From 474cd9c321dff396dc40c181c63e1cb9ad4c2ad9 Mon Sep 17 00:00:00 2001
From: Martin Teichmann <martin.teichmann@xfel.eu>
Date: Mon, 28 Dec 2020 16:10:40 +0000
Subject: [PATCH] use readable opcodes in tests, kindof

---
 ebpf.py      | 21 ++++++---------------
 ebpf_test.py | 24 +++++++++++++++++++++++-
 2 files changed, 29 insertions(+), 16 deletions(-)

diff --git a/ebpf.py b/ebpf.py
index e7ddfd6..7b48072 100644
--- a/ebpf.py
+++ b/ebpf.py
@@ -41,8 +41,8 @@ class Opcode(Enum):
     REG = 8
     LONG = 3
 
-    H = 8
     W = 0
+    H = 8
     B = 0x10
     DW = 0x18
 
@@ -60,13 +60,7 @@ class Opcode(Enum):
         return OpcodeFlags({self}) + value
 
     def __repr__(self):
-        return self.name
-
-    def __eq__(self, value):
-        return self is value or self.value == value
-
-    def __hash__(self):
-        return super().__hash__()
+        return 'O.' + self.name
 
 class OpcodeFlags:
     def __init__(self, opcodes):
@@ -83,13 +77,10 @@ class OpcodeFlags:
             return OpcodeFlags(self.opcodes | value.opcodes)
 
     def __repr__(self):
-        return "|".join(op.name for op in self.opcodes)
+        return "+".join(repr(op) for op in self.opcodes)
 
     def __eq__(self, value):
-        if isinstance(value, int):
-            return self.value == value
-        else:
-            self.opcodes == value.opcodes
+        return self.value == value.value
 
 
 class AssembleError(Exception):
@@ -468,7 +459,7 @@ class PseudoFd(Expression):
         else:
             free = False
         self.ebpf.append(Opcode.DW, dst, 1, 0, self.fd)
-        self.ebpf.append(0, 0, 0, 0, 0)
+        self.ebpf.append(Opcode.W, 0, 0, 0, 0)
         return dst, long, signed, free
 
 
@@ -492,7 +483,7 @@ class RegisterDesc:
                                 self.no, 0, 0, value)
             else:
                 instance.append(Opcode.DW, self.no, 0, 0, value & 0xffffffff)
-                instance.append(0, 0, 0, 0, value >> 32)
+                instance.append(Opcode.W, 0, 0, 0, value >> 32)
         elif isinstance(value, Expression):
             value.calculate(self.no, self.long, self.signed, True)
         elif isinstance(value, Instruction):
diff --git a/ebpf_test.py b/ebpf_test.py
index 243f9b5..aaf0346 100644
--- a/ebpf_test.py
+++ b/ebpf_test.py
@@ -1,9 +1,31 @@
 from unittest import TestCase, main
 
-from .ebpf import AssembleError, EBPF, Instruction
+from . import ebpf
+from .ebpf import AssembleError, EBPF, Opcode, OpcodeFlags, Opcode as O
 from .bpf import ProgType
 
 
+opcodes = list((v.value, v) for v in Opcode)
+opcodes.sort(reverse=True)
+
+
+def Instruction(opcode, dst, src, off, imm):
+    if isinstance(opcode, OpcodeFlags):
+        return ebpf.Instruction(opcode, dst, src, off, imm)
+    bigger = [(k, v) for k, v in opcodes if opcode >= k]
+    for bk, bv in bigger:
+        parts = {bv}
+        lo = opcode - bk
+        for k, v in opcodes[:-1]:
+            if lo >= k:
+                lo -= k
+                parts.add(v)
+        if lo == 0:
+            break
+    else:
+        raise RuntimeError
+    return ebpf.Instruction(OpcodeFlags(parts), dst, src, off, imm)
+
 class Tests(TestCase):
     def test_assemble(self):
         e = EBPF()
-- 
GitLab