interfaces.py 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420
  1. import socket
  2. import struct
  3. import subprocess
  4. import numpy as np
  5. import serial
  6. import time as tm
  7. import msgpack
  8. probe = {
  9. '10mV': np.int8(0),
  10. '20mV': np.int8(1),
  11. '50mV': np.int8(2),
  12. '100mV': np.int8(3),
  13. '200mV': np.int8(4),
  14. '500mV': np.int8(5),
  15. '1V': np.int8(6),
  16. '2V': np.int8(7),
  17. '5V': np.int8(8),
  18. '10V': np.int8(9),
  19. '20V': np.int8(10),
  20. '50V': np.int8(11),
  21. '100V': np.int8(12),
  22. '200V': np.int8(13)
  23. }
  24. class adc_default:
  25. def __init__(self, port):
  26. self.port = port
  27. self.ndata = []
  28. self.channels_data = []
  29. self.measure_code = (0x00, 0)
  30. self.proto = {
  31. 'open': 0x01,
  32. 'set_rate': 0x07,
  33. 'set_points': 0x06,
  34. 'config_channels': 0x09,
  35. 'set_premeasure': 0x28,
  36. 'set_trignum': 0x19,
  37. 'start': 0x3B,
  38. 'stop': 0x03,
  39. }
  40. def connect(self, port=0):
  41. self.client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  42. self.client_socket.settimeout(10.0)
  43. resp = self.client_socket.connect(('127.0.0.1', self.port))
  44. return resp
  45. def send_command(self, cmd_code, *args):
  46. if not self.connected:
  47. print("Not connected. Use 'connect' first.")
  48. return None
  49. try:
  50. buf = bytearray()
  51. buf.extend(self.pk.pack(0xAA))
  52. buf.extend(self.pk.pack(cmd_code))
  53. for arg in args:
  54. buf.extend(self.pk.pack(arg))
  55. self.client_socket.sendall(buf)
  56. return self.receive_response()
  57. except Exception as e:
  58. print(f"Send failed: {e}")
  59. return None
  60. def receive_response(self):
  61. try:
  62. unpacker = msgpack.Unpacker()
  63. while True:
  64. chunk = self.client_socket.recv(8192)
  65. if not chunk:
  66. break
  67. unpacker.feed(chunk)
  68. objects = []
  69. for obj in unpacker:
  70. objects.append(obj)
  71. print(f"Code: {objects[1]}")
  72. return objects[1], objects[2:]
  73. except Exception as e:
  74. print(f"Receive failed: {e}")
  75. return None
  76. def resp_handler(self, resp, cmd):
  77. if(resp[0] != 0xAA):
  78. return (-1, 0)
  79. if(resp[1] == 0xFF):
  80. return (0xFF, resp[3])
  81. return (resp[1], 0)
  82. def open(self):
  83. resp = self.send_command(0x01)
  84. if resp:
  85. code, data = resp
  86. if code == 0xCC:
  87. return (0xCC, 0, 0)
  88. else:
  89. return (0xFF, code, data)
  90. def set_rate(self, rate):
  91. """Set sample rate. Usage: set_rate <rate>"""
  92. try:
  93. srate = int(rate)
  94. resp = self.send_command(0x07, srate)
  95. if resp:
  96. code, data = resp
  97. if code == 0xCC:
  98. return (0xCC, 0, 0)
  99. else:
  100. return (0xFF, code, data)
  101. except ValueError:
  102. return (0xFF, code, b"Invalid rate!")
  103. def set_points(self, points):
  104. """Set points vector. Usage: set_points <p1> <p2> ..."""
  105. try:
  106. resp = self.send_command(0x06, points)
  107. if resp:
  108. code, data = resp
  109. if code == 0xCC:
  110. return (0xCC, 0, 0)
  111. else:
  112. return (0xFF, code, data)
  113. except ValueError:
  114. return (0xFF, code, b"Invalid points!")
  115. def config_channels(self, nchannels, channel_ranges, trig_channel):
  116. """Configure channels. Usage: channel_configure <num_channels> <range1> <range2> ... <trig_channel>"""
  117. try:
  118. resp = self.send_command(0x09, nchannels, channel_ranges, trig_channel)
  119. if resp:
  120. code, data = resp
  121. if code == 0xCC:
  122. return (0xCC, 0, 0)
  123. else:
  124. return (0xFF, code, data)
  125. except ValueError:
  126. return (0xFF, code, b"Invalid channel data!")
  127. def trigger_configure(self, th_dir, thresh, auto_ms):
  128. """Configure trigger. Usage: trigger_configure <th_direction> <threshold> <auto_trigger_ms>"""
  129. try:
  130. resp = self.send_command(0x0A, th_dir, thresh, auto_ms) # Assuming 0x0A
  131. if resp:
  132. code, data = resp
  133. if code == 0xCC:
  134. return (0xCC, 0, 0)
  135. else:
  136. return (0xFF, code, data)
  137. except ValueError:
  138. return (0xFF, code, b"Invalid trigger data!")
  139. def set_premeasure(self, trig_premeasure):
  140. """Set premeasurement percentage. Usage: set_premeasurement <percentage>"""
  141. try:
  142. resp = self.send_command(0x0B, trig_premeasure) # Assuming 0x0B
  143. if resp:
  144. code, data = resp
  145. if code == 0xCC:
  146. return (0xCC, 0, 0)
  147. else:
  148. return (0xFF, code, data)
  149. except ValueError:
  150. return (0xFF, code, b"Invalid premeasurement!")
  151. def set_trignum(self, trig_num):
  152. pass # deprecated
  153. def start(self):
  154. """Start measurement."""
  155. resp = self.send_command(0x20)
  156. if resp:
  157. code, data = resp
  158. if code == 0xCC:
  159. return (0xCC, 0, 0)
  160. else:
  161. return (0xFF, code, data)
  162. def aqcuire_data(self):
  163. if not self.connected:
  164. print("Not connected.")
  165. return
  166. try:
  167. # Receive data packets
  168. unpacker = msgpack.Unpacker()
  169. data_collected = {}
  170. buf = bytearray()
  171. buf.extend(self.pk.pack(0xAA))
  172. buf.extend(self.pk.pack(0xBB))
  173. self.sock.sendall(buf)
  174. last_i = 0
  175. last_j = 0
  176. curr_data = []
  177. while True:
  178. resp_code, data = self.receive_response()
  179. print("Chunk recieved!")
  180. print(f'Resp: {resp_code} (need {0xCD} or {0xCE})')
  181. if resp_code == 0xCD:
  182. i, j, packet, size, packet_data = data[0], data[1], data[2], data[3], data[4]
  183. if last_j != j:
  184. print('Append channel')
  185. self.channels_data.append(curr_data)
  186. curr_data = []
  187. if last_i != i:
  188. print('Append signal')
  189. self.ndata.append(self.channels_data)
  190. self.channels_data = []
  191. last_i = i
  192. last_j = j
  193. curr_data.extend(packet_data)
  194. key = (i, j)
  195. print("Received packet params.")
  196. if key not in data_collected:
  197. data_collected[key] = []
  198. print("Key created!")
  199. data_collected[key].extend(packet_data) # Assuming packet is list of int16
  200. print("Appended!")
  201. buf = bytearray()
  202. buf.extend(self.pk.pack(0xAA))
  203. buf.extend(self.pk.pack(0x3D))
  204. self.sock.sendall(buf)
  205. elif resp_code == 0xCE:
  206. self.channels_data.append(curr_data)
  207. self.ndata.append(self.channels_data)
  208. curr_data = []
  209. self.channels_data = []
  210. # Assemble data
  211. buf = bytearray()
  212. buf.extend(self.pk.pack(0xAA))
  213. buf.extend(self.pk.pack(0x3E))
  214. self.sock.sendall(buf)
  215. print("Data received and acknowledged.")
  216. return
  217. else:
  218. print(f"Unexpected response: {resp_code}")
  219. return
  220. except Exception as e:
  221. print(f"Send points failed: {e}")
  222. def stop(self):
  223. resp = self.send_command(0x03)
  224. if resp:
  225. code, data = resp
  226. if code == 0xCC:
  227. return (0xCC, 0, 0)
  228. else:
  229. return (0xFF, code, data)
  230. def clear_ndata(self):
  231. self.ndata = []
  232. self.channels_data = []
  233. class sync_default:
  234. def __init__(self, port):
  235. if(port != -1):
  236. self.client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  237. self.proto = {
  238. 'upload': 0x01,
  239. 'trig_wait': 0x02
  240. }
  241. self.serial = None
  242. def connect(self, port):
  243. self.client_socket.settimeout(5.0)
  244. resp = self.client_socket.connect(('localhost', port))
  245. return resp
  246. def resp_handler(self, resp, cmd):
  247. if(resp[0] != 0xAA):
  248. return (-1, 0)
  249. if(resp[1] == 0xFF):
  250. return (0xFF, resp[3])
  251. return (resp[1], 0)
  252. def upload(self, programPath, filePath, port):
  253. try:
  254. process = subprocess.run([programPath, filePath, '-p', str(port), '--debug'])
  255. except subprocess.CalledProcessError as e:
  256. print(f"Ошибка команды {e.cmd}!")
  257. return process.returncode
  258. def serial_open(self, port):
  259. try:
  260. self.serial = serial.Serial('COM' + str(port), 9600, timeout=1)
  261. except serial.SerialException as e:
  262. print(e)
  263. return (0xFF, -1)
  264. return(0x00, 0)
  265. def trig_wait(self, port):
  266. try:
  267. self.serial.write(b'e')
  268. except serial.SerialException as e:
  269. print(e)
  270. return (0xFF, -1)
  271. return(0x00, 0)
  272. def serial_close(self):
  273. try:
  274. self.serial.close()
  275. except:
  276. return (0xFF, -1)
  277. return (0x00, 0)
  278. class sdr_default:
  279. def __init__(self, port):
  280. if(port != -1):
  281. self.client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  282. self.proto = {
  283. 'transf': 0x01
  284. }
  285. def connect(self, port):
  286. self.client_socket.settimeout(5.0)
  287. resp = self.client_socket.connect(('localhost', port))
  288. return resp
  289. def transf(self, programPath, filePath, freq, rate, ampl, gain):
  290. try:
  291. process = subprocess.run([programPath, '-t', filePath, '-f', str(freq), '-s', str(rate), '-a', str(ampl), '-x', str(gain)], check=True)
  292. except subprocess.CalledProcessError as e:
  293. print(f"Ошибка команды {e.cmd}!")
  294. return (0xFF, -1)
  295. return (0x00, process.returncode)
  296. class gra_default:
  297. def __init__(self, ip, port):
  298. if(port != -1):
  299. self.client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  300. self.client_socket.settimeout(5.0)
  301. self.client_socket.connect((ip, port))
  302. self.proto = {
  303. 'reset': 0x0001,
  304. 'ps_on': 0x0003,
  305. 'ps_off': 0x0004,
  306. 'state': 0x0005,
  307. 'upload': 0x0006,
  308. 'send_packet': 0x0007,
  309. 'confirm': 0x0008
  310. }
  311. def connect(self, port):
  312. self.client_socket.settimeout(5.0)
  313. resp = self.client_socket.connect(('localhost', port))
  314. return resp
  315. def reset(self):
  316. msg = struct.pack('<HH', 0xAAAA, self.proto['reset'])
  317. self.client_socket.send(msg)
  318. def ps_on(self):
  319. msg = struct.pack('<HH', 0xAAAA, self.proto['ps_on'])
  320. self.client_socket.send(msg)
  321. def ps_off(self):
  322. msg = struct.pack('<HH', 0xAAAA, self.proto['ps_off'])
  323. self.client_socket.send(msg)
  324. def ps_off(self):
  325. msg = struct.pack('<HH', 0xAAAA, self.proto['ps_off'])
  326. self.client_socket.send(msg)
  327. def state(self):
  328. msg = struct.pack('<HH', 0xAAAA, self.proto['state'])
  329. self.client_socket.send(msg)
  330. resp = self.client_socket.recv(4096)
  331. if(len(resp) == 6):
  332. magic, cmd, state = struct.unpack('<HHH', resp)
  333. return (cmd, state, 0, 0)
  334. elif(len(resp) > 6):
  335. magic, cmd, state, errbits, errpoint, current_setting_amp, current_amp, first_sensor, second_sensor = struct.unpack('<HHHIIiiii', resp)
  336. return (cmd, state, errbits, errpoint)
  337. def send_packet(self, nom, nodes_num, nodes_buf):
  338. i = 0
  339. time1, time2 = struct.unpack('<HH', nodes_buf[i][0].to_bytes(4, 'little'))
  340. nom = nom | 0x8000
  341. msg = struct.pack('<HHHHHHH', 0xAAAA, self.proto['send_packet'], nom, nodes_num, time1, time2, nodes_buf[i][1].to_bytes(2, 'little'))
  342. while(i < nodes_num):
  343. i += 1
  344. time1, time2 = struct.unpack('<HH', nodes_buf[i][0].to_bytes(4, 'little'))
  345. msg += struct.pack('<HHH', time1, time2, nodes_buf[i][1].to_bytes(2, 'little'))
  346. self.client_socket.send(msg)
  347. resp = self.client_socket.recv(4096)
  348. data_resp = struct.unpack('<HHH', resp)
  349. return data_resp[3]
  350. def upload(self, points, nodes):
  351. points1, points2 = struct.unpack('<HH', points.to_bytes(4, 'little'))
  352. nodes1, nodes2 = struct.unpack('<HH', nodes[points-1][0].to_bytes(4, 'little'))
  353. msg = struct.pack('<HHHHHH', 0xAAAA, self.proto['upload'], points1, points2, nodes1, nodes2)
  354. self.client_socket.send(msg)
  355. seg_num = 0
  356. total_packets = points // 200 + 1
  357. first_idx = 0
  358. while(seg_num < total_packets):
  359. if((points - first_idx) < 200):
  360. nodes_packet = points - first_idx
  361. else:
  362. nodes_packet = 200
  363. last_idx = first_idx + nodes_packet
  364. resp = self.send_packet(seg_num, nodes_packet, nodes[first_idx:last_idx])
  365. print(resp)
  366. first_idx = last_idx
  367. seg_num += 1
  368. msg = struct.pack('<HH', 0xAAAA, 0x0008)
  369. self.client_socket.send(msg)