fork download
  1. import struct
  2.  
  3. class Register:
  4. class Wrapper:
  5. def __init__ (self, buffer, format_str):
  6. self.buffer = buffer
  7. self.st = struct.Struct(format_str)
  8.  
  9. def __setitem__ (self, slot, value):
  10. f = list(self.st.unpack(self.buffer))
  11. f[slot] = value
  12. self.st.pack_into(self.buffer, 0, *f)
  13.  
  14. def __getitem__ (self, slot):
  15. return self.st.unpack(self.buffer)[slot]
  16.  
  17. def __string__ (self):
  18. return str(self.st.unpack(self.buffer))
  19.  
  20. def __repr__ (self):
  21. return repr(self.st.unpack(self.buffer))
  22.  
  23. def __init__ (self):
  24. self.byte = bytearray(16)
  25. self.float32 = Register.Wrapper(self.byte, "<ffff")
  26. self.float64 = Register.Wrapper(self.byte, "<dd")
  27. self.signed8 = Register.Wrapper(self.byte, "<bbbbbbbbbbbbbbbb")
  28. self.signed16 = Register.Wrapper(self.byte, "<hhhhhhhh")
  29. self.signed32 = Register.Wrapper(self.byte, "<iiii")
  30. self.signed64 = Register.Wrapper(self.byte, "<qq")
  31. self.unsigned8 = Register.Wrapper(self.byte, "<BBBBBBBBBBBBBBBB")
  32. self.unsigned16 = Register.Wrapper(self.byte, "<HHHHHHHH")
  33. self.unsigned32 = Register.Wrapper(self.byte, "<IIII")
  34. self.unsigned64 = Register.Wrapper(self.byte, "<QQ")
  35.  
  36. class Memory:
  37. class Wrapper:
  38. def __init__ (self, buffer, format_str):
  39. self.buffer = buffer
  40. self.st = struct.Struct(format_str)
  41.  
  42. def __setitem__ (self, address, value):
  43. self.st.pack_into(self.buffer, address, value)
  44.  
  45. def __getitem__ (self, address):
  46. return self.st.unpack_from(self.buffer, address)[0]
  47.  
  48. def __init__ (self, size):
  49. self.size = size
  50. self.byte = bytearray(size)
  51. self.float32 = Memory.Wrapper(self.byte, "<f")
  52. self.float64 = Memory.Wrapper(self.byte, "<d")
  53. self.signed8 = Memory.Wrapper(self.byte, "<b")
  54. self.signed16 = Memory.Wrapper(self.byte, "<h")
  55. self.signed32 = Memory.Wrapper(self.byte, "<i")
  56. self.signed64 = Memory.Wrapper(self.byte, "<q")
  57. self.unsigned8 = Memory.Wrapper(self.byte, "<B")
  58. self.unsigned16 = Memory.Wrapper(self.byte, "<H")
  59. self.unsigned32 = Memory.Wrapper(self.byte, "<I")
  60. self.unsigned64 = Memory.Wrapper(self.byte, "<Q")
  61.  
  62. def __len__ (self):
  63. return len(self.byte)
  64.  
  65. if __name__ == "__main__":
  66. # 1000 bytes memory
  67. memory = Memory(1000)
  68.  
  69. # 16x 128 bits SSE registers
  70. xmm = []
  71. for i in range(16):
  72. xmm.append(Register())
  73.  
  74. #test register aliasing
  75. xmm[0].unsigned32[:] = (4, 5, 6, 7) # fill the whole register (4 x 32 bits)
  76. temp = xmm[0].float64[:] # copy as float64 (2 x 64 bits)
  77. xmm[0].float64[:] = temp # write back
  78. print("xmm[0]:", xmm[0].unsigned32) # (4, 5, 6, 7)
  79.  
  80. # memory aliasing
  81. memory.unsigned32[100] = 0x882233FF
  82. for i in range(103, 99, -1): #Little endian !
  83. print(hex(memory.byte[i]), end=" ")
  84. else:
  85. print()
  86.  
  87. # register to register
  88. xmm[1].unsigned32[:] = xmm[0].unsigned32[:]
  89. xmm[1].float64[0] = xmm[0].float32[3]
  90.  
  91. # mem to register
  92. xmm[0].unsigned32[0] = memory.unsigned32[100]
  93. print(hex(xmm[0].unsigned32[0])) # 0x882233FF
Success #stdin #stdout 0.1s 10088KB
stdin
Standard input is empty
stdout
xmm[0]: (4, 5, 6, 7)
0x88 0x22 0x33 0xff 
0x882233ff