example PoSy receiver
Stefan Schuermans

Stefan Schuermans commited on 2014-04-23 17:22:44
Showing 1 changed files, with 111 additions and 0 deletions.

... ...
@@ -0,0 +1,111 @@
1
+#! /usr/bin/env python
2
+
3
+# Stage Director receiver
4
+# Copyright 2014 Stefan Schuermans <stefan@schuermans.info>
5
+# Copyleft: GNU public license - http://www.gnu.org/copyleft/gpl.html
6
+
7
+import datetime
8
+import fcntl
9
+import os
10
+import select
11
+import socket
12
+import struct
13
+import sys
14
+import time
15
+
16
+scriptdir = os.path.dirname(os.path.abspath(__file__))
17
+
18
+class Receiver:
19
+
20
+  def __init__(self):
21
+    """construct a Stage Director Receiver object"""
22
+    # set constants
23
+    self.select_timeout = 0.1 # timeout (s) for select syscall
24
+    # create member variables
25
+    self.sock = None
26
+    # startup
27
+    self.sockSetup()
28
+
29
+  def __del__(self):
30
+    """deconstruct object"""
31
+    self.sockClose()
32
+
33
+  def posyParse(self, data):
34
+    """parse received PoSy packet"""
35
+    if len(data) < 76 or data[0:4] != "PoSy":
36
+      return False
37
+    flags, name, pos_ms = struct.unpack("!I64sI", data[4:76])
38
+    name_end = name.find("\0")
39
+    if name_end >= 0:
40
+      name = name[:name_end]
41
+    if flags & 1:
42
+      pause = True
43
+    else:
44
+      pause = False
45
+    # store info from PoSy packet
46
+    print("name=%s pos=%.3fs puase=%s" % (name, pos_ms * 1e-3, pause))
47
+
48
+  def run(self):
49
+    """run application"""
50
+    try:
51
+      while True:
52
+        self.waitForInput()
53
+    except KeyboardInterrupt:
54
+      pass
55
+
56
+  def sockRecv(self):
57
+    """receive data from socket"""
58
+    if self.sock is None:
59
+      return
60
+    # receive message
61
+    data = self.sock.recv(4096)
62
+    print("data from socket: %d bytes" % len(data))
63
+    # parse (ignore message on error)
64
+    self.posyParse(data)
65
+
66
+  def sockClose(self):
67
+    """close UDP socket"""
68
+    if self.sock is not None:
69
+      self.sock.close()
70
+      self.sock = None
71
+
72
+  def sockSetup(self):
73
+    """create a new UDP socket and bind it"""
74
+    self.sockClose()
75
+    try:
76
+      self.sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
77
+      self.sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
78
+      self.sock.bind(("0.0.0.0", 5740))
79
+    except:
80
+      self.sockClose()
81
+
82
+  def waitForInput(self):
83
+    """wait for input from UDP socket"""
84
+    # poll for data
85
+    inputs = []
86
+    outputs = []
87
+    errors = []
88
+    wait_txt = ""
89
+    if self.sock is not None:
90
+      inputs.append(self.sock)
91
+      wait_txt += " socket"
92
+    print("waiting for input:" + wait_txt)
93
+    rds, wrs, exs = select.select(inputs, outputs, errors, self.select_timeout)
94
+    # obtain available data
95
+    for rd in rds:
96
+      if self.sock is not None and rd is self.sock:
97
+        print("input from socket")
98
+        self.sockRecv()
99
+
100
+# main function
101
+def main(argv):
102
+  # run application
103
+  app = Receiver()
104
+  app.run()
105
+  # done
106
+  return 0
107
+
108
+# main application entry point
109
+if __name__ == "__main__":
110
+  sys.exit(main(sys.argv))
111
+
0 112