def setTeam(wormid, team): if wormid in worms.keys() and worms[wormid].iID != -1: worms[wormid].Team = team io.setWormTeam(wormid, team) if cfg.TEAMCHANGE_LOGGING: io.messageLog( "TEAMCHANGE: Set worm " + str(wormid) + " " + worms[wormid].Name + " to team " + str(team), io.LOG_INFO) else: io.messageLog("Worm id %i invalid" % wormid, LOG_ADMIN)
def parseNewWorm(wormID, name): global worms name = name.replace("\t", " ").strip() # Do not allow tab in names, it will screw up our ranking tab-separated text-file database exists = False try: worm = worms[wormID] exists = True except KeyError: #Worm doesn't exist. worm = Worm() worm.Name = name worm.iID = wormID worm.Ping = [] worms[wormID] = worm if io.getGameType() == "Hide and Seek": minSeekers = 1 if len(worms.values()) >= 4: minSeekers = 2 if io.getNumberWormsInTeam(1) < minSeekers: io.setWormTeam(wormID, 1) # Seeker else: io.setWormTeam(wormID, 0) # Hider else: # Balance teams teams = [0,0,0,0] for w in worms.keys(): teams[worms[w].Team] += 1 minTeam = 0 minTeamCount = teams[0] for f in range(cfg.MAX_TEAMS): if minTeamCount > teams[f]: minTeamCount = teams[f] minTeam = f io.setWormTeam(wormID, minTeam) if cfg.RANKING_AUTHENTICATION: if not name in ranking.auth: ranking.auth[name] = getWormSkin(wormID) try: f = open(io.getFullFileName("pwn0meter_auth.txt"),"r") try: portalocker.lock(f, portalocker.LOCK_EX) except: pass f.write( name + "\t" + str(ranking.auth[name][0]) + " " + ranking.auth[name][1] + "\n" ) f.close() except IOError: msg("ERROR: Unable to open pwn0meter_auth.txt") else: if ranking.auth[name] != getWormSkin(wormID): io.kickWorm(wormID, "Player with name %s already registered" % name) wormIP = io.getWormIP(wormID).split(":")[0] # io.messageLog("Curtime " + str(time.time()) + " IP " + str(wormIP) + " Kicked worms: " + str(cmds.kickedUsers), io.LOG_INFO) if wormIP in cmds.kickedUsers and cmds.kickedUsers[ wormIP ] > time.time(): io.kickWorm( wormID, "You can join in " + str(int(cmds.kickedUsers[ wormIP ] - time.time())/60 + 1) + " minutes" ) return cmds.recheckVote()
def parseUserCommand(wormid, message): global kickedUsers try: # Do not check on msg size or anything, exception handling is further down if message in [ "y", "n", "start", "stop", "rank", "toprank", "ranktotal" ]: # Single-word usercommands for faster typing cmd = message else: if (not message.startswith(cfg.USER_PREFIX)): return False # normal chat cmd = message.split(" ")[0] cmd = cmd.replace(cfg.USER_PREFIX, "", 1).lower() #Remove the prefix if wormid >= 0: io.messageLog( "%i:%s issued %s" % (wormid, hnd.worms[wormid].Name, cmd.replace(cfg.USER_PREFIX, "", 1)), io.LOG_USRCMD) else: io.messageLog("ded admin issued %s" % cmd, io.LOG_USRCMD) # Unnecesary to split multiple times, this saves CPU. params = message.split(" ")[1:] if cmd == "help": userCommandHelp(wormid) if cfg.ALLOW_TEAM_CHANGE and cmd == "team": if not params: io.privateMsg(wormid, "You need to specify a team") raise Exception, "You need to specify a team" else: if params[0].lower() == "blue" or params[0].lower() == "b": io.setWormTeam(wormid, 0) elif params[0].lower() == "red" or params[0].lower() == "r": io.setWormTeam(wormid, 1) elif (params[0].lower() == "green" or params[0].lower() == "g") and cfg.MAX_TEAMS >= 3: io.setWormTeam(wormid, 2) elif (params[0].lower() == "yellow" or params[0].lower() == "y") and cfg.MAX_TEAMS >= 4: io.setWormTeam(wormid, 3) if cfg.RANKING: if cmd == "toprank": ranking.firstRank(wormid) if cmd == "rank": if wormid in hnd.worms: wormName = hnd.worms[wormid].Name if params: wormName = " ".join(params) ranking.myRank(wormName, wormid) if cmd == "ranktotal": io.privateMsg( wormid, "There are " + str(len(ranking.rank)) + " players in the ranking.") if cfg.VOTING: if cmd == "kick": kicked = int(params[0]) if not kicked in hnd.worms.keys(): raise Exception, "Invalid worm ID" addVote( "io.kickWorm(" + str(kicked) + ", 'You are kicked for " + str(cfg.VOTING_KICK_TIME) + " minutes')", wormid, "Kick %i: %s" % (kicked, hnd.worms[kicked].Name)) hnd.worms[kicked].Voted = -1 if cmd == "mute": if not kicked in hnd.worms.keys(): raise Exception, "Invalid worm ID" kicked = int(params[0]) addVote("io.muteWorm(" + str(kicked) + ")", wormid, "Mute %i: %s" % (kicked, hnd.worms[kicked].Name)) hnd.worms[kicked].Voted = -1 if cmd == "mod": # Users are proven to be stupid and can't tell the difference between mod and preset # so here we're first looking for a preset, and then looking for a mod with the same name if preset not found # (well, let's call that UI simplification) preset = -1 for p in range(len(hnd.availablePresets)): if hnd.availablePresets[p].lower().find( params[0].lower()) != -1: preset = p break if preset != -1: addVote( 'hnd.selectPreset( Preset = "%s" )' % hnd.availablePresets[preset], wormid, "Preset %s" % hnd.availablePresets[preset]) else: mod = "" for m in io.listMods(): if m.lower().find(" ".join(params[0:]).lower()) != -1: mod = m break if mod == "": io.privateMsg( wormid, "Invalid mod, available mods: " + ", ".join(hnd.availablePresets) + ", ".join(io.listMods())) else: addVote('hnd.selectPreset( Mod = "%s" )' % mod, wormid, "Mod %s" % mod) if cmd == "map": level = "" for l in io.listMaps(): if l.lower().find(" ".join(params[0:]).lower()) != -1: level = l break if level == "": io.privateMsg( wormid, "Invalid map, available maps: " + ", ".join(io.listMaps())) else: addVote('hnd.selectPreset( Level = "%s" )' % level, wormid, "Map %s" % level) if cmd == "lt": addVote('hnd.selectPreset( LT = %i )' % int(params[0]), wormid, "Loading time %i" % int(params[0])) if cmd == "start": addVote( 'hnd.lobbyWaitAfterGame = time.time(); hnd.lobbyWaitBeforeGame = time.time()', wormid, "Start game now") if cmd == "stop": addVote('io.gotoLobby()', wormid, "Go to lobby") if (cmd == "y" or cmd == "yes"): if hnd.worms[wormid].Voted != 1: hnd.worms[wormid].Voted = 1 recheckVote() if (cmd == "n" or cmd == "no"): if hnd.worms[wormid].Voted != -1: hnd.worms[wormid].Voted = -1 recheckVote() elif parseUserCommand_Preset and parseUserCommand_Preset( wormid, cmd, params): pass else: raise Exception, "Invalid user command" except: # All python classes derive from main "Exception", but confused me, this has the same effect. if wormid >= 0: io.privateMsg( wormid, "Invalid user command - type !help for list of commands") io.messageLog(formatExceptionInfo(), io.LOG_ERROR) #Helps to fix errors return False return True
def controlHandlerDefault(): global worms, gameState, lobbyChangePresetTimeout, lobbyWaitBeforeGame, lobbyWaitAfterGame global lobbyWaitGeneral, lobbyEnoughPlayers, oldGameState, scriptPaused, sentStartGame global presetCicler, modCicler, mapCicler, LT_Cicler global videoRecorder, videoRecorderSignalTime if scriptPaused: return curTime = time.time() cmds.recheckVote(False) if gameState == GAME_LOBBY: # Do not check ping in lobby - it's wrong if oldGameState != GAME_LOBBY: mapCicler.check() modCicler.check() LT_Cicler.check() presetCicler.check() lobbyEnoughPlayers = False # reset the state lobbyWaitGeneral = curTime + cfg.WAIT_BEFORE_SPAMMING_TOO_FEW_PLAYERS_MESSAGE lobbyWaitAfterGame = curTime if oldGameState == GAME_PLAYING: lobbyWaitAfterGame = curTime + cfg.WAIT_AFTER_GAME if videoRecorder: os.kill( videoRecorder.pid, signal.SIGINT ) # videoRecorder.send_signal(signal.SIGINT) # This is available only on Python 2.6 videoRecorderSignalTime = time.time() io.chatMsg("Waiting for video recorder to finish") canStart = True if videoRecorder and videoRecorder.returncode == None: canStart = False videoRecorder.poll() if time.time( ) - videoRecorderSignalTime > cfg.TIME_TO_KILL_VIDEORECORDER: io.chatMsg("Video recorder stalled, killing") os.kill(videoRecorder.pid, signal.SIGKILL) videoRecorder.poll() if videoRecorder.returncode != None: io.chatMsg("Video recorder encoding took " + str(int(time.time() - videoRecorderSignalTime)) + " secs") canStart = True videoRecorder = None if lobbyWaitAfterGame <= curTime: if not lobbyEnoughPlayers and lobbyWaitGeneral <= curTime: lobbyWaitGeneral = curTime + cfg.WAIT_BEFORE_SPAMMING_TOO_FEW_PLAYERS_MESSAGE io.chatMsg(cfg.TOO_FEW_PLAYERS_MESSAGE) if not lobbyEnoughPlayers and len( worms ) >= cfg.MIN_PLAYERS: # Enough players already - start game lobbyEnoughPlayers = True io.chatMsg(cfg.WAIT_BEFORE_GAME_MESSAGE) lobbyWaitBeforeGame = curTime + cfg.WAIT_BEFORE_GAME if lobbyEnoughPlayers and len( worms ) < cfg.MIN_PLAYERS: # Some players left when game not yet started lobbyEnoughPlayers = False io.chatMsg(cfg.TOO_FEW_PLAYERS_MESSAGE) if lobbyEnoughPlayers and not sentStartGame: if lobbyWaitBeforeGame <= curTime and canStart: # Start the game if io.getGameType() in ["Death Match", "Team Death Match"]: if len(worms ) >= cfg.MIN_PLAYERS_TEAMS: # Split in teams setvar("GameOptions.GameInfo.GameType", "Team Death Match") if not cfg.ALLOW_TEAM_CHANGE: counter = 0 for w in worms.values(): if w.iID != -1: io.setWormTeam(w.iID, counter % cfg.MAX_TEAMS) counter += 1 else: io.setvar("GameOptions.GameInfo.GameType", "Death Match") if io.startGame(): if cfg.ALLOW_TEAM_CHANGE and len( worms) >= cfg.MIN_PLAYERS_TEAMS: io.chatMsg(cfg.TEAM_CHANGE_MESSAGE) sentStartGame = True if cfg.RECORD_VIDEO: try: #io.messageLog("Running dedicated-video-record.sh, curdir " + os.path.abspath(os.path.curdir) ,io.LOG_INFO) videoRecorder = subprocess.Popen( [ "./dedicated-video-record.sh", "./dedicated-video-record.sh" ], stdin=open("/dev/null", "r"), stdout=open("../../../dedicatedVideo.log", "w"), stderr=subprocess.STDOUT, cwd="..") except: io.messageLog(formatExceptionInfo(), io.LOG_ERROR) else: io.chatMsg("Game could not be started") oldGameState == GAME_PLAYING # hack that it resets at next control handler call if gameState == GAME_WEAPONS: #checkMaxPing() # if we allow empty games, ignore this check if len(worms) < cfg.MIN_PLAYERS and not io.getVar( "GameOptions.GameInfo.AllowEmptyGames" ): # Some players left when game not yet started io.chatMsg("Too less players -> back to lobby") io.gotoLobby() sentStartGame = False if gameState == GAME_PLAYING: checkMaxPing()
def parseNewWorm(wormID, name): global worms name = name.replace("\t", " ").strip( ) # Do not allow tab in names, it will screw up our ranking tab-separated text-file database exists = False try: worm = worms[wormID] exists = True except KeyError: #Worm doesn't exist. worm = Worm() worm.Name = name worm.iID = wormID worm.Ping = [] worms[wormID] = worm if io.getGameType() == "Hide and Seek": minSeekers = 1 if len(worms.values()) >= 4: minSeekers = 2 if io.getNumberWormsInTeam(1) < minSeekers: io.setWormTeam(wormID, 1) # Seeker else: io.setWormTeam(wormID, 0) # Hider else: # Balance teams teams = [0, 0, 0, 0] for w in worms.keys(): teams[worms[w].Team] += 1 minTeam = 0 minTeamCount = teams[0] for f in range(cfg.MAX_TEAMS): if minTeamCount > teams[f]: minTeamCount = teams[f] minTeam = f io.setWormTeam(wormID, minTeam) if cfg.RANKING_AUTHENTICATION: if not name in ranking.auth: ranking.auth[name] = getWormSkin(wormID) try: f = open(io.getFullFileName("pwn0meter_auth.txt"), "r") try: portalocker.lock(f, portalocker.LOCK_EX) except: pass f.write(name + "\t" + str(ranking.auth[name][0]) + " " + ranking.auth[name][1] + "\n") f.close() except IOError: msg("ERROR: Unable to open pwn0meter_auth.txt") else: if ranking.auth[name] != getWormSkin(wormID): io.kickWorm(wormID, "Player with name %s already registered" % name) wormIP = io.getWormIP(wormID).split(":")[0] # io.messageLog("Curtime " + str(time.time()) + " IP " + str(wormIP) + " Kicked worms: " + str(cmds.kickedUsers), io.LOG_INFO) if wormIP in cmds.kickedUsers and cmds.kickedUsers[wormIP] > time.time(): io.kickWorm( wormID, "You can join in " + str(int(cmds.kickedUsers[wormIP] - time.time()) / 60 + 1) + " minutes") return cmds.recheckVote()
def parseUserCommand(wormid,message): global kickedUsers try: # Do not check on msg size or anything, exception handling is further down if message in [ "y", "n", "start", "stop", "rank", "toprank", "ranktotal" ]: # Single-word usercommands for faster typing cmd = message else: if (not message.startswith(cfg.USER_PREFIX)): return False # normal chat cmd = message.split(" ")[0] cmd = cmd.replace(cfg.USER_PREFIX,"",1).lower() #Remove the prefix if wormid >= 0: io.messageLog("%i:%s issued %s" % (wormid,hnd.worms[wormid].Name,cmd.replace(cfg.USER_PREFIX,"",1)),io.LOG_USRCMD) else: io.messageLog("ded admin issued %s" % cmd, io.LOG_USRCMD) # Unnecesary to split multiple times, this saves CPU. params = message.split(" ")[1:] if cmd == "help": userCommandHelp(wormid) if cfg.ALLOW_TEAM_CHANGE and cmd == "team": if not params: io.privateMsg(wormid, "You need to specify a team" ) raise Exception, "You need to specify a team" else: if params[0].lower() == "blue" or params[0].lower() == "b": io.setWormTeam(wormid, 0) elif params[0].lower() == "red" or params[0].lower() == "r": io.setWormTeam(wormid, 1) elif ( params[0].lower() == "green" or params[0].lower() == "g" ) and cfg.MAX_TEAMS >= 3: io.setWormTeam(wormid, 2) elif ( params[0].lower() == "yellow" or params[0].lower() == "y" ) and cfg.MAX_TEAMS >= 4: io.setWormTeam(wormid, 3) if cfg.RANKING: if cmd == "toprank": ranking.firstRank(wormid) if cmd == "rank": if wormid in hnd.worms: wormName = hnd.worms[wormid].Name if params: wormName = " ".join(params) ranking.myRank(wormName, wormid) if cmd == "ranktotal": io.privateMsg(wormid, "There are " + str(len(ranking.rank)) + " players in the ranking.") if cfg.VOTING: if cmd == "kick": kicked = int( params[0] ) if not kicked in hnd.worms.keys(): raise Exception, "Invalid worm ID" addVote( "io.kickWorm(" + str(kicked) + ", 'You are kicked for " + str(cfg.VOTING_KICK_TIME) + " minutes')", wormid, "Kick %i: %s" % ( kicked, hnd.worms[kicked].Name ) ) hnd.worms[kicked].Voted = -1 if cmd == "mute": if not kicked in hnd.worms.keys(): raise Exception, "Invalid worm ID" kicked = int( params[0] ) addVote( "io.muteWorm(" + str(kicked) +")", wormid, "Mute %i: %s" % ( kicked, hnd.worms[kicked].Name ) ) hnd.worms[kicked].Voted = -1 if cmd == "mod": # Users are proven to be stupid and can't tell the difference between mod and preset # so here we're first looking for a preset, and then looking for a mod with the same name if preset not found # (well, let's call that UI simplification) preset = -1 for p in range(len(hnd.availablePresets)): if hnd.availablePresets[p].lower().find(params[0].lower()) != -1: preset = p break if preset != -1: addVote( 'hnd.selectPreset( Preset = "%s" )' % hnd.availablePresets[preset], wormid, "Preset %s" % hnd.availablePresets[preset] ) else: mod = "" for m in io.listMods(): if m.lower().find(" ".join(params[0:]).lower()) != -1: mod = m break if mod == "": io.privateMsg(wormid,"Invalid mod, available mods: " + ", ".join(hnd.availablePresets) + ", ".join(io.listMods())) else: addVote( 'hnd.selectPreset( Mod = "%s" )' % mod, wormid, "Mod %s" % mod ) if cmd == "map": level = "" for l in io.listMaps(): if l.lower().find(" ".join(params[0:]).lower()) != -1: level = l break if level == "": io.privateMsg(wormid,"Invalid map, available maps: " + ", ".join(io.listMaps())) else: addVote( 'hnd.selectPreset( Level = "%s" )' % level, wormid, "Map %s" % level ) if cmd == "lt": addVote( 'hnd.selectPreset( LT = %i )' % int(params[0]), wormid, "Loading time %i" % int(params[0]) ) if cmd == "start": addVote( 'hnd.lobbyWaitAfterGame = time.time(); hnd.lobbyWaitBeforeGame = time.time()', wormid, "Start game now" ) if cmd == "stop": addVote( 'io.gotoLobby()', wormid, "Go to lobby" ) if ( cmd == "y" or cmd == "yes" ): if hnd.worms[wormid].Voted != 1: hnd.worms[wormid].Voted = 1 recheckVote() if ( cmd == "n" or cmd == "no" ): if hnd.worms[wormid].Voted != -1: hnd.worms[wormid].Voted = -1 recheckVote() elif parseUserCommand_Preset and parseUserCommand_Preset(wormid, cmd, params): pass else: raise Exception, "Invalid user command" except: # All python classes derive from main "Exception", but confused me, this has the same effect. if wormid >= 0: io.privateMsg(wormid, "Invalid user command - type !help for list of commands") io.messageLog(formatExceptionInfo(),io.LOG_ERROR) #Helps to fix errors return False return True
def controlHandlerDefault(): global worms, gameState, lobbyChangePresetTimeout, lobbyWaitBeforeGame, lobbyWaitAfterGame global lobbyWaitGeneral, lobbyEnoughPlayers, oldGameState, scriptPaused, sentStartGame global presetCicler, modCicler, mapCicler, LT_Cicler global videoRecorder, videoRecorderSignalTime if scriptPaused: return curTime = time.time() cmds.recheckVote(False) if gameState == GAME_LOBBY: # Do not check ping in lobby - it's wrong if oldGameState != GAME_LOBBY: mapCicler.check() modCicler.check() LT_Cicler.check() presetCicler.check() lobbyEnoughPlayers = False # reset the state lobbyWaitGeneral = curTime + cfg.WAIT_BEFORE_SPAMMING_TOO_FEW_PLAYERS_MESSAGE lobbyWaitAfterGame = curTime if oldGameState == GAME_PLAYING: lobbyWaitAfterGame = curTime + cfg.WAIT_AFTER_GAME if videoRecorder: os.kill(videoRecorder.pid, signal.SIGINT) # videoRecorder.send_signal(signal.SIGINT) # This is available only on Python 2.6 videoRecorderSignalTime = time.time() io.chatMsg("Waiting for video recorder to finish") canStart = True if videoRecorder and videoRecorder.returncode == None: canStart = False videoRecorder.poll() if time.time() - videoRecorderSignalTime > cfg.TIME_TO_KILL_VIDEORECORDER: io.chatMsg("Video recorder stalled, killing") os.kill(videoRecorder.pid, signal.SIGKILL) videoRecorder.poll() if videoRecorder.returncode != None: io.chatMsg("Video recorder encoding took " + str(int(time.time() - videoRecorderSignalTime)) + " secs") canStart = True videoRecorder = None if lobbyWaitAfterGame <= curTime: if not lobbyEnoughPlayers and lobbyWaitGeneral <= curTime: lobbyWaitGeneral = curTime + cfg.WAIT_BEFORE_SPAMMING_TOO_FEW_PLAYERS_MESSAGE io.chatMsg(cfg.TOO_FEW_PLAYERS_MESSAGE) if not lobbyEnoughPlayers and len(worms) >= cfg.MIN_PLAYERS: # Enough players already - start game lobbyEnoughPlayers = True io.chatMsg(cfg.WAIT_BEFORE_GAME_MESSAGE) lobbyWaitBeforeGame = curTime + cfg.WAIT_BEFORE_GAME if lobbyEnoughPlayers and len(worms) < cfg.MIN_PLAYERS: # Some players left when game not yet started lobbyEnoughPlayers = False io.chatMsg(cfg.TOO_FEW_PLAYERS_MESSAGE) if lobbyEnoughPlayers and not sentStartGame: if lobbyWaitBeforeGame <= curTime and canStart: # Start the game if io.getGameType() in ["Death Match","Team Death Match"]: if len(worms) >= cfg.MIN_PLAYERS_TEAMS: # Split in teams setvar("GameOptions.GameInfo.GameType", "Team Death Match") if not cfg.ALLOW_TEAM_CHANGE: counter = 0 for w in worms.values(): if w.iID != -1: io.setWormTeam( w.iID, counter % cfg.MAX_TEAMS ) counter += 1 else: io.setvar("GameOptions.GameInfo.GameType", "Death Match") if io.startGame(): if cfg.ALLOW_TEAM_CHANGE and len(worms) >= cfg.MIN_PLAYERS_TEAMS: io.chatMsg(cfg.TEAM_CHANGE_MESSAGE) sentStartGame = True if cfg.RECORD_VIDEO: try: #io.messageLog("Running dedicated-video-record.sh, curdir " + os.path.abspath(os.path.curdir) ,io.LOG_INFO) videoRecorder = subprocess.Popen( ["./dedicated-video-record.sh", "./dedicated-video-record.sh"], stdin=open("/dev/null","r"), stdout=open("../../../dedicatedVideo.log","w"), stderr=subprocess.STDOUT, cwd=".." ) except: io.messageLog(formatExceptionInfo(),io.LOG_ERROR) else: io.chatMsg("Game could not be started") oldGameState == GAME_PLAYING # hack that it resets at next control handler call if gameState == GAME_WEAPONS: #checkMaxPing() # if we allow empty games, ignore this check if len(worms) < cfg.MIN_PLAYERS and not io.getVar("GameOptions.GameInfo.AllowEmptyGames"): # Some players left when game not yet started io.chatMsg("Too less players -> back to lobby") io.gotoLobby() sentStartGame = False if gameState == GAME_PLAYING: checkMaxPing()