chiark / gitweb /
@@@ tvec doc wip
[mLib] / utils / t / bits-testgen
1 #! /usr/bin/python
2 ### -*-python-*-
3 ###
4 ### Generate input script and expected output for bit manipulation,
5 ### particularly 64-bit arithmetic.
6
7 import sys as SYS
8 import random as R
9
10 if SYS.version_info >= (3,): xrange = range
11
12 NVEC = 64
13 WD = 64
14 LIMIT = 1 << WD
15 MASK = LIMIT - 1
16 FMT = "%%0%dx" % (WD/4)
17
18 def rol(x, n): return ((x << n) | (x >> (WD - n))) & MASK
19 def ror(x, n): return ((x >> n) | (x << (WD - n))) & MASK
20
21 class BaseVector (object):
22   def __init__(me):
23     me._all = []
24   def newseed(me, seed):
25     me._curr = []
26     me._all.append((seed, me._curr))
27   def _append(me, *args):
28     if len(args) != len(me._REGS):
29       raise TypeError("expected %d arguments" % len(me._REGS))
30     me._curr.append(args)
31   def write(me):
32     print("")
33     print("[%s]" % me._NAME)
34     for seed, vv in me._all:
35       print("")
36       print(";;; seed = 0x%08x" % seed)
37       for v in vv:
38         print("")
39         for r, x in zip(me._REGS, v): print("%s = %s" % (r, me._RFMT[r] % x))
40
41 class ShiftVector (BaseVector):
42   _REGS = ["x", "n", "z"]
43   _RFMT = { "x": FMT, "n": "%d", "z": FMT }
44   def add(me, r):
45     for i in xrange(NVEC):
46       x = r.randrange(LIMIT)
47       n = r.randrange(70)%WD
48       z = me._op(x, n)
49       me._append(x, n, z)
50     for i in xrange(4):
51       x = r.randrange(LIMIT)
52       z = me._op(x, WD/2)
53       me._append(x, WD/2, z)
54 class LSLVector (ShiftVector):
55   _NAME = "lsl64"
56   def _op(me, x, n): return (x << n)&MASK
57 class LSRVector (ShiftVector):
58   _NAME = "lsr64"
59   def _op(me, x, n): return (x >> n)&MASK
60 class ROLVector (ShiftVector):
61   _NAME = "rol64"
62   def _op(me, x, n): return rol(x, n)
63 class RORVector (ShiftVector):
64   _NAME = "ror64"
65   def _op(me, x, n): return ror(x, n)
66
67 class ArithVector (BaseVector):
68   _REGS = ["x", "y", "z"]
69   _RFMT = { "x": FMT, "y": FMT, "z": FMT }
70   def add(me, r):
71     for i in xrange(NVEC):
72       x = r.randrange(LIMIT)
73       y = r.randrange(LIMIT)
74       z = me._op(x, y)
75       me._append(x, y, z)
76 class AddVector (ArithVector):
77   _NAME = "add64"
78   def _op(me, x, y): return (x + y)&MASK
79 class SubVector (ArithVector):
80   _NAME = "sub64"
81   def _op(me, x, y): return (x - y)&MASK
82
83 VECS = [LSLVector(), LSRVector(), ROLVector(), RORVector(),
84         AddVector(), SubVector()]
85
86 for arg in SYS.argv[1:]:
87   if arg == "-": seed = R.SystemRandom().randrange(1 << 32)
88   else: seed = int(arg, 0)
89   r = R.Random(seed)
90   for v in VECS: v.newseed(seed); v.add(r)
91
92 print(";;; -*-conf-*- Test vectors for 64-bit arithmetic macros")
93 print(";;;   [generated]")
94
95 for v in VECS: v.write()