def base_player(self):
return self
+
+
def __init__(self):
threading.Thread.__init__(self)
self.result = None
+ self.exception = None
def run(self):
- self.result = open(name, mode)
+ try:
+ self.result = open(name, mode)
+ except Exception, e:
+ self.exception = e
+ self.result = None
w = Worker()
while time.time() - start < timeout:
if w.is_alive() == False:
w.join()
+ if w.exception != None:
+ raise w.exception
return w.result
time.sleep(0.1)
if w.is_alive():
#sys.stderr.write("FIFO_TIMEOUT!\n")
- if mode == "r":
- f = open(name, "w")
- else:
- f = open(name, "r")
+ # Recursive to deal with possible race condition
+ try:
+ if mode == "r":
+ f = open_fifo(name, "w", 1)
+ else:
+ f = open_fifo(name, "r", 1)
+ except:
+ pass
#sys.stderr.write("Opened other end!\n")
while w.is_alive():
raise Exception("FIFO_TIMEOUT")
else:
w.join()
+ if w.exception != None:
+ raise w.exception
return w.result
Player.__init__(self, name, colour)
os.mkfifo(self.name+".in")
os.mkfifo(self.name+".out")
-
-
-
-
-
+
+
+ try:
+ self.fifo_out = open_fifo(self.name+".out","w", FifoPlayer.timeout)
+ except:
+ raise Exception("FIFO_TIMEOUT")
+ else:
+ self.fifo_out.write("START "+colour+"\n")
+ self.fifo_out.close()
+
+
def update(self, result):
sys.stderr.write("update fifo called\n")
try:
try:
self.fifo_out = open_fifo(self.name+".out", "w", FifoPlayer.timeout)
except:
- os.remove(self.name+".in")
- os.remove(self.name+".out")
- #raise Exception("FIFO_TIMEOUT")
-
+ pass
else:
self.fifo_out.write(result + "\n")
self.fifo_out.close()
+
+ try:
os.remove(self.name+".in")
os.remove(self.name+".out")
+ except OSError:
+ pass
# Player that runs from another process
class ExternalAgent(Player):
def __init__(self, name, colour):
Player.__init__(self, name, colour)
+ #raise Exception("waht")
self.p = subprocess.Popen(name,bufsize=0,stdin=subprocess.PIPE, stdout=subprocess.PIPE, shell=True,universal_newlines=True)
self.send_message(colour)
def __init__(self, name, colour):
Player.__init__(self, name, colour)
+
# Select your preferred account
def select(self):
if isinstance(graphics, GraphicsThread):
sys.stdout.write("SELECTION?\n")
try:
p = map(int, sys.stdin.readline().strip("\r\n ").split(" "))
+ return p
except:
sys.stderr.write("ILLEGAL GIBBERISH\n")
continue
+
# It's your move captain
def get_move(self):
if isinstance(graphics, GraphicsThread):
sys.stdout.write("MOVE?\n")
try:
p = map(int, sys.stdin.readline().strip("\r\n ").split(" "))
+ return p
except:
sys.stderr.write("ILLEGAL GIBBERISH\n")
continue
self.board = Board(style = "agent")
-
+ def argForm(self):
+ return "@internal:"+self.name
def update(self, result):
if self.src in ready:
s = self.src.recv(1)
else:
- raise Exception("UNRESPONSIVE")
+ raise Exception("NET_UNRESPONSIVE")
+
+ debug("Network get_response s = " + str(s))
while s[len(s)-1] != '\n':
# Timeout on each character in the message
if self.src in ready:
s += self.src.recv(1)
else:
- raise Exception("UNRESPONSIVE")
+ raise Exception("NET_UNRESPONSIVE")
return s.strip(" \r\n")
if self.src in ready:
self.src.send(s + "\n")
else:
- raise Exception("UNRESPONSIVE")
+ raise Exception("NET_UNRESPONSIVE")
self.cond = threading.Condition() # conditional for some reason, I forgot
self.final_result = ""
self.server = server
+ self.retry_illegal = False
-
-
-
+
# Run the game (run in new thread with start(), run in current thread with run())
def run(self):
break
except Exception,e:
#if False:
- result = e.message
- #sys.stderr.write(result + "\n")
-
- self.stop()
+
- with self.lock:
- self.final_result = self.state["turn"].colour + " " + e.message
- break
+ result = e.message
+ if self.retry_illegal:
+ self.state["turn"].update(result);
+ else:
+ sys.stderr.write("qchess.py exception: "+result + "\n")
+ self.stop()
+ with self.lock:
+ self.final_result = self.state["turn"].colour + " " + e.message
+ break
def client(addr, player="@human"):
-
+ debug("Client " + player + " starts")
s = socket.socket()
s.connect((addr, 4562))
[colour,port] = s.recv(1024).strip(" \r\n").split(" ")
- #debug("Colour: " + colour + ", port: " + port)
+ debug("Colour: " + colour + ", port: " + port)
s.shutdown(socket.SHUT_RDWR)
s.close()
else:
p = subprocess.Popen(["python", "qchess.py", "@network:"+addr+":"+port, player])
p.wait()
- return 0# --- server.py --- #
+ return 0
+# --- server.py --- #
#!/usr/bin/python -u
# Do you know what the -u does? It unbuffers stdin and stdout
[game, graphics] = [None, None]
def make_player(name, colour):
+ debug(name)
if name[0] == '@':
if name[1:] == "human":
return HumanPlayer(name, colour)
global sleep_timeout
+ retry_illegal = False
server_addr = None
max_moves = None
i += 1
arg = argv[i]
if arg[0] != '-':
- p = make_player(arg, colour)
- if not isinstance(p, Player):
- sys.stderr.write(sys.argv[0] + " : Fatal error creating " + colour + " player\n")
- return 100
- players.append(p)
- if colour == "white":
- colour = "black"
- elif colour == "black":
- pass
- else:
- sys.stderr.write(sys.argv[0] + " : Too many players (max 2)\n")
+ players.append(arg)
continue
# Option parsing goes here
sleep_timeout = -1
else:
sleep_timeout = float(arg[2:].split("=")[1])
-
+ elif (arg[1] == '-' and arg[2:] == "retry-illegal"):
+ retry_illegal = not retry_illegal
elif (arg[1] == '-' and arg[2:] == "help"):
# Help
os.system("less data/help.txt") # The best help function
sys.stderr.write("Only a single player may be provided when --server is used\n")
return 1
if len(players) == 1:
- return client(server_addr, players[0].name)
+ return client(server_addr, players[0])
else:
return client(server_addr)
-
+ for i in xrange(len(players)):
+ p = make_player(players[i], colour)
+ if not isinstance(p, Player):
+ sys.stderr.write(sys.argv[0] + " : Fatal error creating " + colour + " player\n")
+ return 100
+ players[i] = p
+ if colour == "white":
+ colour = "black"
+ elif colour == "black":
+ pass
+ else:
+ sys.stderr.write(sys.argv[0] + " : Too many players (max 2)\n")
+
# Create the board
# Construct a GameThread! Make it global! Damn the consequences!
board = Board(style)
board.max_moves = max_moves
game = GameThread(board, players)
+ game.retry_illegal = retry_illegal
# --- main.py --- #
-# EOF - created from make on Sun May 19 00:54:03 WST 2013
+# EOF - created from make on Monday 24 June 23:55:46 WST 2013