/// <summary> /// Template method for common code needed in UpdateServerInfo, UpdatePlayers and UpdateRules /// </summary> private bool ExecuteUpdate(UpdateRequest request, ServerRow row, Server server, Func <Action <int>, bool> updater) { if (request.IsCancelled) { return(false); } try { row.Status = "updating " + row.Retries; request.SetDataModified(); bool ok = updater(retry => { if (request.IsCancelled) { throw new OperationCanceledException(); } if (row.Retries == 0) { Interlocked.Increment(ref request.TasksWithRetries); } row.Status = "updating " + (++row.Retries + 1); request.SetDataModified(); }); if (ok) { return(true); } Interlocked.Increment(ref request.TasksWithTimeout); } catch { } return(false); }
/// <summary> /// Start the game if necessary and then connect to the given game server. /// </summary> public virtual bool Connect(ServerRow server, string password, bool spectate) { this.ActivateGameWindow(this.FindGameWindow()); var proc = Process.Start("steam://connect/" + server.EndPoint + (string.IsNullOrEmpty(password) ? "" : "/" + password)); return(proc != null); }
public override bool Connect(ServerRow server, string password, bool spectate) { // servers with skill restrictions neither allow connections with "steam://connect" nor with an "open ip:port" console command if ((string) this.GetServerCellValue(server, "_skillclass") != "1-12") { var res = XtraMessageBox.Show("This server has a skill restriction.\nOnly the in-game browser can connect to such servers.\nLaunch TOXIKK anyway?", "Toxikk Server", MessageBoxButtons.YesNo, MessageBoxIcon.Exclamation); if (res == DialogResult.No) return false; if (FindToxikkWindow() == IntPtr.Zero) StartToxikk(); return true; } if (consoleKey == Keys.None) { using (var dlg = new KeyBindForm("Please press your Toxikk console key...")) { if (dlg.ShowDialog(Application.OpenForms[0]) == DialogResult.Cancel) return false; consoleKey = dlg.Key; Properties.Settings.Default.ToxikkConsoleKey = (int) consoleKey; Properties.Settings.Default.Save(); } } ThreadPool.QueueUserWorkItem(context => ConnectInBackground(server, password, spectate), null); return true; }
private bool UpdateServerInfo(UpdateRequest request, ServerRow row, Server server) { bool ok = ExecuteUpdate(request, row, server, retryCallback => { var si = request.CallGetInfo || row.ServerInfo == null ? server.GetInfo(retryCallback) : row.ServerInfo; if (si == null) { return(false); } row.ServerInfo = si; var gameId = si.Extra.GameId; if (gameId == 0) { gameId = si.Id; } if (gameId == 0) { gameId = (int)request.AppId; } var extension = this.gameExtensions.Get((Game)gameId); row.SetGameExtension(extension); row.QueryPlayers = extension.SupportsPlayersQuery(row); row.QueryRules = extension.SupportsRulesQuery(row); return(true); }); //if (!ok) // row.ServerInfo = null; return(ok); }
private void UpdatePlayers(UpdateRequest request, ServerRow row, Server server) { if (!row.QueryPlayers) { return; } bool ok = ExecuteUpdate(request, row, server, retryCallback => { var sw = (row.ServerInfo?.Ping ?? -1) == 0 ? new Stopwatch() : null; var players = server.GetPlayers(retryCallback, sw); if (players == null) { return(false); } if (sw != null) { row.ServerInfo.Ping = sw.ElapsedMilliseconds; } row.Players = new List <Player>(players); return(true); }); if (!ok) { row.Players = null; row.QueryPlayers = false; } }
public override object GetServerCellValue(ServerRow row, string fieldName) { switch (fieldName) { case "_goalscore": { var gt = row.GetRule("g_gametype"); if (gt == "1" || gt == "2") // DUEL, RACE return null; if (gt == "4" || gt == "9" || gt == "12") // CA, FT, RR return row.GetRule("roundlimit"); if (gt == "5" || gt == "6") // CTF, 1FLAG return row.GetRule("capturelimit"); if (gt == "8" || gt == "10" || gt == "11") // HAR, DOM, A&D return row.GetRule("scorelimit"); return row.GetRule("fraglimit"); // 0=FFA, 3=TDM } case "_gametype": { var gt = row.GetRule("g_gametype"); string instaPrefix = row.GetRule("g_instagib") == "1" ? "i" : ""; int num; string name; if (int.TryParse(gt, out num) && gameTypeName.TryGetValue(num, out name)) return instaPrefix + name; return instaPrefix + gt; } case "g_instagib": return row.GetRule(fieldName) == "1"; } return base.GetServerCellValue(row, fieldName); }
private void LoadQlstatsPlayerList(ServerRow row, Action callback = null) { this.qlstatsPlayerlists[row] = null; using (var client = new XWebClient(2000)) { client.Encoding = Encoding.UTF8; client.DownloadStringCompleted += (sender, args) => { try { using (var strm = new MemoryStream(Encoding.UTF8.GetBytes(args.Result))) { var playerList = (QlstatsPlayerList)playerListJsonParser.ReadObject(strm); this.qlstatsPlayerlists[row] = playerList; if (playerList.serverinfo != null) { this.skillInfo[row.EndPoint.ToString()] = playerList.serverinfo; } callback?.Invoke(); } } catch { } }; client.DownloadStringAsync(new Uri("http://api.qlstats.net/api/server/" + row.EndPoint + "/players")); } }
// shared update code #region UpdateServerAndDetails() private void UpdateServerAndDetails(UpdateRequest request, ServerRow row, bool fireRefreshSingleServerComplete) { string status = ""; try { if (request.IsCancelled) { return; } using (Server server = ServerQuery.GetServerInstance(EngineType.Source, row.EndPoint, false, request.Timeout, request.Timeout)) { row.Retries = 0; server.SendFirstPacketTwice = this.sendFirstUdpPacketTwice; server.Retries = 3; status = "timeout"; if (this.UpdateServerInfo(request, row, server)) { row.GameExtension = gameExtensions.Get((Game)(row.ServerInfo.Extra?.GameId ?? row.ServerInfo.Id)); this.UpdatePlayers(request, row, server); this.UpdateRules(request, row, server); status = "ok"; } row.RequestTimestamp = request.Timestamp; } if (request.IsCancelled) // status might have changed { return; } if (row.Retries > 0) { status += " (" + row.Retries + ")"; } } catch { // this happens when you hibernate windows and the program resumes before the network connection has be reestablished status = "network error"; } finally { row.Status = status; row.Update(); request.SetDataModified(); if (fireRefreshSingleServerComplete && !request.IsCancelled) { this.RefreshSingleServerComplete?.Invoke(this, new ServerEventArgs(row)); } if (!request.PendingTasks.IsSet) { request.PendingTasks.Signal(); } } }
// ZeroMQ rcon stuff #if ZMQ #region Rcon() public override void Rcon(ServerRow row, int port, string password, string command) { using (var ctx = ZContext.Create()) { ZSocket client, monitor; var endpoint = new IPEndPoint(row.EndPoint.Address, port); this.CreateClientAndMonitorSockets(ctx, endpoint, password, out client, out monitor); using (client) using (monitor) { while (true) { ZMessage msg = new ZMessage(); ZError err; var poll = ZPollItem.CreateReceiver(); var ev = client.Poll(poll, ZPoll.In | ZPoll.Out | ZPoll.Err, ref msg, out err, TimeSpan.FromMilliseconds(500)); if (err == ZError.ETERM) { break; } var evMonitor = CheckMonitor(monitor); if (evMonitor != null) { if (evMonitor.Item1 == ZMonitorEvents.Connected) { client.Send(new ZFrame("register")); client.Send(new ZFrame(command)); return; } if (evMonitor.Item1 == ZMonitorEvents.Closed || evMonitor.Item1 == ZMonitorEvents.Disconnected) { return; } } if (!ev) { continue; } while (true) { client.ReceiveMessage(ref msg, ZSocketFlags.DontWait, out err); if (err != ZError.None) { if (err != ZError.EAGAIN) { Console.WriteLine(err); } break; } Console.WriteLine(msg); } } } } }
public override int GetSpectatorCount(ServerRow row) { var info = this.skillInfo.GetValueOrDefault(row.EndPoint.ToString(), null); if (info != null) { return(info.sc); } return(0); }
public override bool SupportsPlayersQuery(ServerRow server) { // in case the matchmaking servers weren't filtered out on the server side, we also have a client-side check here if (server?.ServerInfo?.Extra.Keywords != null && server.ServerInfo.Extra.Keywords.Contains("valve_ds")) { return(false); } return(true); }
public override int?GetMaxPlayers(ServerRow row) { var val = row.GetRule("NumPublicConnections"); if (val != null) { return(int.Parse(val)); } return(base.GetMaxPlayers(row)); }
public override int?GetBotCount(ServerRow row) { var info = this.skillInfo.GetValueOrDefault(row.EndPoint.ToString(), null); if (info != null) { return(info.bc); } return(base.GetRealPlayerCount(row)); }
public override bool Connect(ServerRow server, string password, bool spectate) { if (useKeystrokesToConnect) { // don't use the ThreadPool b/c it might be full with waiting server update requests new Thread(ctx => { ConnectInBackground(server, password, spectate); }).Start(); return(true); } return(base.Connect(server, password, spectate)); }
public override int?GetRealPlayerCount(ServerRow row) { if (row.Rules == null) { return(base.GetRealPlayerCount(row)); } var strSteamIds = (row.GetRule("p1073741829") ?? "") + "," + (row.GetRule("p1073741830") ?? "") + "," + (row.GetRule("p1073741831") ?? ""); return(strSteamIds == "" ? 0 : strSteamIds.Split(',', ';').Count(id => id != "")); }
public override string GetPrettyNameForRule(ServerRow row, string ruleName) { switch (ruleName) { case MinCombatants: return("min. Combatants"); case ScoreLimit: return("Score Limit"); case TimeLimit: return("Time Limit"); case Mutators: return("Mutators"); case GameVersion: return("GameVersion"); case OldOfficialNewRanked: return("Ranked (pre-1.1.8: Official)"); case NewOfficial: return("Official (since 1.1.8)"); case ModdingLevel: return("Modding level"); case ToxikkSkillInfo.MinSkillClass: return("Min SC"); case ToxikkSkillInfo.MaxSkillClass: return("Max SC"); case "p1073741825": return("Map"); case "p1073741826": return("Gametype Class"); case "p1073741827": return("Server Description"); case "p1073741829": return("Player IDs #1"); case "p1073741830": return("Player IDs #2"); case "p1073741831": return("Player IDs #3"); case "p1073741832": return("Player names #1"); case "p1073741833": return("Player names #2"); case "p1073741834": return("Player names #3"); case "p1073741837": return("Player SCs"); case "p1073741838": return("Player ranks"); case "s0": return("Bot difficulty"); case "p268435706": return("Max. players"); case "p1073741840": return("Map list"); } return(null); }
public override int?GetPrivateClients(ServerRow row) { var cli = row.GetRule("sv_privateclients"); int val; if (!string.IsNullOrEmpty(cli) && int.TryParse(cli, out val)) { return(val); } return(0); }
public override void CustomizePlayerContextMenu(ServerRow server, Player player, List<PlayerContextMenuItem> menu) { this.UpdatePlayerInfos(server); ToxikkPlayerInfo info; if (!this.playerInfos.TryGetValue(player.Name, out info)) return; menu.Insert(0, new PlayerContextMenuItem("Open Steam Chat", () => { Process.Start("steam://friends/message/" + info.SteamId); }, true)); menu.Insert(1, new PlayerContextMenuItem("Show Steam Profile", () => { Process.Start("http://steamcommunity.com/profiles/" + info.SteamId + "/"); })); menu.Insert(2, new PlayerContextMenuItem("Add to Steam Friends", () => { Process.Start("steam://friends/add/" + info.SteamId); })); menu.Add(new PlayerContextMenuItem("Copy Steam-ID to Clipboard", () => { Clipboard.SetText(info.SteamId); })); }
// refresh single server #region RefreshSingleServer() public void RefreshSingleServer(ServerRow row) { if (this.IsUpdating) { return; } row.Status = "updating..."; var req = new UpdateRequest(this.currentRequest.AppId, 1, this.currentRequest.Timeout, this.currentRequest.GameExtension, true); req.PendingTasks = new CountdownEvent(1); this.currentRequest = req; ThreadPool.QueueUserWorkItem(dummy => this.UpdateServerAndDetails(req, row, true)); }
public override int?GetMaxClients(ServerRow row) { var cli = row.GetRule("sv_maxclients"); int val; if (!string.IsNullOrEmpty(cli) && int.TryParse(cli, out val)) { return(val); } // QL currently returns the sv_maxclients in MaxPlayers (instead of teamsize * 2) return(row.ServerInfo?.MaxPlayers); }
public override bool FilterServerRow(ServerRow row) { if (this.skillClassFilter == 0 || row.Rules == null) { return(false); } // remove server rows which are outside the skill class var min = int.Parse(row.GetRule(ToxikkSkillInfo.MinSkillClass)); var max = int.Parse(row.GetRule(ToxikkSkillInfo.MaxSkillClass)); return(this.skillClassFilter < min || this.skillClassFilter > max); }
public override void Refresh(ServerRow row = null, Action callback = null) { LoadQlstatsPersonalRating(); LoadQlstatsServerRatings(); if (row == null) { this.qlstatsPlayerlists.Clear(); } else { this.LoadQlstatsPlayerList(row, callback); } }
public override void CustomizePlayerContextMenu(ServerRow server, Player player, List <PlayerContextMenuItem> menu) { this.UpdatePlayerInfos(server); ToxikkPlayerInfo info; if (!this.playerInfos.TryGetValue(player.Name, out info)) { return; } menu.Insert(0, new PlayerContextMenuItem("Open Steam Chat", () => { Process.Start("steam://friends/message/" + info.SteamId); }, true)); menu.Insert(1, new PlayerContextMenuItem("Show Steam Profile", () => { Process.Start("http://steamcommunity.com/profiles/" + info.SteamId + "/"); })); menu.Insert(2, new PlayerContextMenuItem("Add to Steam Friends", () => { Process.Start("steam://friends/add/" + info.SteamId); })); menu.Add(new PlayerContextMenuItem("Copy Steam-ID to Clipboard", () => { Clipboard.SetText(info.SteamId); })); }
public override bool IsValidPlayer(ServerRow server, Player player) { var list = qlstatsPlayerlists.GetValueOrDefault(server, null); if (list?.players != null) { var cleanName = this.GetCleanPlayerName(player.Name, true); return(list.players.Count(p => this.GetCleanPlayerName(p.name) == cleanName) > 0); } // hack to remove ghost players which are not really on the server var status = server.GetRule("g_gameStatus"); return(status != "IN_PROGRESS" || player.Score > 0 || player.Time < TimeSpan.FromHours(1)); }
public override object GetServerCellValue(ServerRow row, string fieldName) { if (fieldName == "_gametype") { var parts = row.ServerInfo?.Extra.Keywords?.Split(',', '|'); return(parts?[0]); } if (fieldName == "_location") { var parts = row.ServerInfo?.Extra.Keywords?.Split(',', '|'); return(parts?.Length > 1 ? parts[1] : null); } return(base.GetServerCellValue(row, fieldName)); }
public override int?GetBotCount(ServerRow row) { if (row.ServerInfo == null) { return(null); } int bots = row.ServerInfo.Bots; if (bots != 0) { return(bots); } if (row.Rules != null && int.TryParse(row.GetRule(MinCombatants), out bots)) { return(bots); } return(0); }
private decimal GetBestPlayerSC(ServerRow row) { if (row.Players == null || row.Rules == null) { return(0); } decimal maxSc = 0; foreach (var player in row.Players) { var sc = this.GetPlayerCellValue(row, player, "SC"); if (sc is decimal) { maxSc = Math.Max(maxSc, (decimal)sc); } } return(maxSc); }
public override object GetServerCellValue(ServerRow row, string fieldName) { if (fieldName == "_gametype") { if (row.ServerInfo == null || row.ServerInfo.Extra == null || row.ServerInfo.Extra.Keywords == null) return null; var parts = row.ServerInfo.Extra.Keywords.Split('|'); return parts[0]; } if (fieldName == "_location") { if (row.ServerInfo == null || row.ServerInfo.Extra == null || row.ServerInfo.Extra.Keywords == null) return null; var parts = row.ServerInfo.Extra.Keywords.Split('|'); return parts.Length > 1 ? parts[1] : null; } return base.GetServerCellValue(row, fieldName); }
public override bool Connect(ServerRow server, string password, bool spectate) { if (this.startExtraQL) { var extraQlExe = this.GetExtaQlPath(); if (extraQlExe != null) { Process.Start(extraQlExe, "-background"); } } if (this.useKeystrokesToConnect) { // don't use the ThreadPool b/c it might be full with waiting server update requests new Thread(ctx => { ConnectInBackground(server, password, spectate); }).Start(); return(true); } return(base.Connect(server, password, spectate)); }
public override int?GetRealPlayerCount(ServerRow row) { var info = this.skillInfo.GetValueOrDefault(row.EndPoint.ToString(), null); if (info != null) { return(info.pc + info.sc); } // minqlx bots are not correctly counted as bots in the server info if (row.Players != null) { var c = row.Players.Count(p => p.Name.StartsWith("(Bot)")); if (c > 0) { return(row.Players.Count - c); } } return(base.GetRealPlayerCount(row)); }
public override object GetPlayerCellValue(ServerRow server, Player player, string fieldName) { if (fieldName[0] != '_') { return(base.GetPlayerCellValue(server, player, fieldName)); } QlstatsPlayerList list; QlstatsPlayerList.Player playerInfo = null; this.qlstatsPlayerlists.TryGetValue(server, out list); if (list?.players != null) { var cleanName = this.GetCleanPlayerName(player.Name, true); playerInfo = list.players.FirstOrDefault(p => this.GetCleanPlayerName(p.name) == cleanName); } if (playerInfo == null) { if (fieldName == "_time") { return(player.Time.ToString("hh\\:mm\\:ss")); } return(null); } if (fieldName == "_team") { return(TeamNames[playerInfo.team + 1]); } if (fieldName == "_skill") { return(playerInfo.rating); //(playerInfo.rating+50)/100; } if (fieldName == "_time") { return((DateTime.UtcNow - new DateTime(1970, 1, 1).AddMilliseconds(playerInfo.time)).ToString("hh\\:mm\\:ss")); } return(null); }
public override void CustomizePlayerContextMenu(ServerRow server, Player player, List <PlayerContextMenuItem> menu) { QlstatsPlayerList list; if (!this.qlstatsPlayerlists.TryGetValue(server, out list) || list.players == null) { return; } var cleanName = this.GetCleanPlayerName(player); var info = list.players.FirstOrDefault(p => this.GetCleanPlayerName(p.name) == cleanName); if (info == null) { return; } menu.Insert(0, new PlayerContextMenuItem("Open Steam Chat", () => { Process.Start("steam://friends/message/" + info.steamid); }, true)); menu.Insert(1, new PlayerContextMenuItem("Show Steam Profile", () => { Process.Start("http://steamcommunity.com/profiles/" + info.steamid + "/"); })); menu.Insert(2, new PlayerContextMenuItem("Show QLStats Profile", () => { Process.Start("http://qlstats.net/player/" + info.steamid); })); menu.Insert(3, new PlayerContextMenuItem("Add to Steam Friends", () => { Process.Start("steam://friends/add/" + info.steamid); })); menu.Add(new PlayerContextMenuItem("Copy Steam-ID to Clipboard", () => { Clipboard.SetText(info.steamid); })); }
private void ConnectInBackground(ServerRow server, string password, bool spectate) { var hWnd = FindGameWindow(); if (hWnd == IntPtr.Zero) { hWnd = StartQuakeLive(); if (hWnd == IntPtr.Zero) { return; } SkipIntro(hWnd); } // console key Win32.PostMessage(hWnd, Win32.WM_KEYDOWN, 0, 0x29 << 16); Win32.PostMessage(hWnd, Win32.WM_KEYUP, 0, 0x29 << 16); Thread.Sleep(100); var msg = "/"; if (!string.IsNullOrEmpty(password)) { msg += "set password \"" + password + "\";"; } msg += "connect " + server.EndPoint.Address + ":" + server.ServerInfo.Extra.Port; foreach (var c in msg) { Win32.PostMessage(hWnd, Win32.WM_CHAR, c, 0); Thread.Sleep(10); } Win32.PostMessage(hWnd, Win32.WM_KEYDOWN, (int)Keys.Return, 0x1C << 16); Win32.PostMessage(hWnd, Win32.WM_KEYUP, (int)Keys.Return, 0x1C << 16); this.ActivateGameWindow(hWnd); }
public override bool Connect(ServerRow server, string password, bool spectate) { if (consoleKey == Keys.None && (this.useKeystrokesToConnect || spectate)) { using (var dlg = new KeyBindForm("Please press your TOXIKK console key...")) { if (dlg.ShowDialog(Application.OpenForms[0]) == DialogResult.Cancel) { return(false); } this.consoleKey = dlg.Key; } } if (this.useKeystrokesToConnect || spectate) { // don't use the ThreadPool b/c it might be full with waiting server update requests new Thread(ctx => { ConnectInBackground(server, password, spectate); }).Start(); return(true); } return(base.Connect(server, password, false)); }
private void UpdateRules(UpdateRequest request, ServerRow row, Server server) { if (!request.QueryServerRules) return; bool ok = ExecuteUpdate(request, row, server, retryCallback => { row.Rules = new List<Rule>(server.GetRules(retryCallback)); }); if (!ok) row.Rules = null; }
private void UpdatePlayers(UpdateRequest request, ServerRow row, Server server) { bool ok = ExecuteUpdate(request, row, server, retryCallback => { var players = server.GetPlayers(retryCallback); row.Players = players == null ? null : new List<Player>(players); }); if (!ok) row.Players = null; }
/// <summary> /// Template method for common code needed in UpdateServerInfo, UpdatePlayers and UpdateRules /// </summary> private bool ExecuteUpdate(UpdateRequest request, ServerRow row, Server server, Action<Action<int>> updater) { if (request.IsCancelled) return false; try { row.Status = "updating " + row.Retries; request.DataModified = 1; updater(retry => { if (request.IsCancelled) throw new OperationCanceledException(); if (row.Retries == 0) Interlocked.Increment(ref request.TasksWithRetries); row.Status = "updating " + (++row.Retries + 1); request.DataModified = 1; }); return true; } catch (TimeoutException) { return false; } catch { return true; } }
private void btnAddGameServer_Click(object sender, EventArgs e) { try { string[] parts = this.txtServerQuery.Text.Split(':'); var addr = Dns.GetHostAddresses(parts[0]); if (addr.Length == 0) return; var endpoint = new IPEndPoint(addr[0], parts.Length > 1 ? int.Parse(parts[1]) : 25785); ServerRow serverRow = null; foreach (var row in this.servers) { if (row.EndPoint.Equals(endpoint)) { serverRow = row; break; } } if (serverRow == null) { this.gvServers.BeginDataUpdate(); serverRow = new ServerRow(endpoint); this.servers.Add(serverRow); this.gvServers.EndDataUpdate(); this.gvServers.FocusedRowHandle = this.gvServers.GetRowHandle(this.servers.Count - 1); } this.queryLogic.RefreshSingleServer(serverRow); } catch { } }
private void SendRconCommand(ServerRow row, int port, string pass, string text) { row.GameExtension?.Rcon(row, port, pass, text); }
private void SetViewModel(TabViewModel vm) { this.viewModel = vm; if (vm.Source == TabViewModel.SourceType.Favorites) { vm.servers = new List<ServerRow>(); foreach (var fav in this.favServers) { var row = new ServerRow(fav.Key, this.extenders.Get(0)); row.CachedName = fav.Value; vm.servers.Add(row); } } var info = vm.MasterServer; if (string.IsNullOrEmpty(info)) info = "hl2master.steampowered.com:27011"; this.comboMasterServer.Text = info; this.SetSteamAppId(vm.InitialGameID); this.txtTagInclude.Text = vm.TagsInclude; this.txtTagExclude.Text = vm.TagsExclude; this.txtMod.Text = vm.FilterMod; this.txtMap.Text = vm.FilterMap; this.cbGetEmpty.Checked = vm.GetEmptyServers; this.cbGetFull.Checked = vm.GetFullServers; this.comboQueryLimit.Text = vm.MasterServerQueryLimit.ToString(); this.gvServers.ActiveFilterString = vm.GridFilter; UpdatePanelVisibility(); this.miFindServers.Enabled = vm.Source == TabViewModel.SourceType.MasterServer; }
private void ConnectToGameServer(ServerRow row, bool spectate) { if (row?.ServerInfo == null) return; string password = null; if (row.ServerInfo.IsPrivate) { password = this.PromptForServerPassword(row); if (password == null) return; } this.Cursor = Cursors.WaitCursor; this.SetStatusMessage("Connecting to game server " + row.ServerInfo.Name + " ..."); row.GameExtension.Connect(row, password, spectate); this.Cursor = Cursors.Default; }
private bool ConnectInBackground(ServerRow server, string password, bool spectate) { var win = FindQuakeWindow(); if (win == IntPtr.Zero) { win = StartQuakeLive(); if (win == IntPtr.Zero) return false; SkipIntro(win); } // console key Win32.PostMessage(win, Win32.WM_KEYDOWN, 0, 0x29 << 16); Win32.PostMessage(win, Win32.WM_KEYUP, 0, 0x29 << 16); Thread.Sleep(100); var msg = "/"; if (!string.IsNullOrEmpty(password)) msg += "set password \"" + password + "\";"; msg += "connect " + server.EndPoint.Address + ":" + server.ServerInfo.Extra.Port; foreach (var c in msg) { Win32.PostMessage(win, Win32.WM_CHAR, c, 0); Thread.Sleep(10); } Win32.PostMessage(win, Win32.WM_KEYDOWN, (int) Keys.Return, 0x1C << 16); Win32.PostMessage(win, Win32.WM_KEYUP, (int) Keys.Return, 0x1C << 16); return true; }
public override void Rcon(ServerRow row, int port, string password, string command) { using (var ctx = ZContext.Create()) { ZSocket client, monitor; var endpoint = new IPEndPoint(row.EndPoint.Address, port); this.CreateClientAndMonitorSockets(ctx, endpoint, password, out client, out monitor); using (client) using (monitor) { while (true) { ZMessage msg = new ZMessage(); ZError err; var poll = ZPollItem.CreateReceiver(); var ev = client.Poll(poll, ZPoll.In | ZPoll.Out | ZPoll.Err, ref msg, out err, TimeSpan.FromMilliseconds(500)); if (err == ZError.ETERM) break; var evMonitor = CheckMonitor(monitor); if (evMonitor != null) { if (evMonitor.Item1 == ZMonitorEvents.Connected) { client.Send(new ZFrame("register")); client.Send(new ZFrame(command)); return; } if (evMonitor.Item1 == ZMonitorEvents.Closed || evMonitor.Item1 == ZMonitorEvents.Disconnected) return; } if (!ev) continue; while (true) { client.ReceiveMessage(ref msg, ZSocketFlags.DontWait, out err); if (err != ZError.None) { if (err != ZError.EAGAIN) Console.WriteLine(err); break; } Console.WriteLine(msg); } } } } }
private void gvServers_FocusedRowChanged(object sender, DevExpress.XtraGrid.Views.Base.FocusedRowChangedEventArgs e) { try { var row = (ServerRow)this.gvServers.GetFocusedRow(); if (row == null || row == this.lastSelectedServer) // prevent consecutive updates due to row-reordering return; if (this.ignoreUiEvents == 0) this.lastSelectedServer = row; this.UpdateGridDataSources(); if (!this.cbRefreshSelectedServer.Checked) return; if (this.queryLogic.IsUpdating) return; Application.DoEvents(); this.queryLogic.RefreshSingleServer(row); } catch (Exception ex) { this.txtStatus.Text = ex.Message; } }
private string GetServerAddress(ServerRow row) { return this.showGamePortInAddress && row.ServerInfo != null && row.ServerInfo.Extra != null ? row.EndPoint.Address + ":" + row.ServerInfo.Extra.Port : row.EndPoint.ToString(); }
private void ConnectToGameServer(ServerRow row, bool spectate) { if (row.ServerInfo == null) return; string password = null; if (row.ServerInfo.IsPrivate) { if (this.passwordForm.ShowDialog(this) == DialogResult.Cancel) return; password = this.passwordForm.Password; } this.Cursor = Cursors.WaitCursor; this.gameExtension.Connect(row, password, spectate); this.Cursor = Cursors.Default; }
private void UpdateServerAndDetails(UpdateRequest request, ServerRow row, bool fireRefreshSingleServerComplete) { try { if (request.IsCancelled) return; string status; using (Server server = ServerQuery.GetServerInstance(EngineType.Source, row.EndPoint, false, 500, 500)) { row.Retries = 0; server.SendFirstPacketTwice = this.sendFirstUdpPacketTwice; server.Retries = 3; status = "timeout"; if (this.UpdateServerInfo(request, row, server)) { this.UpdatePlayers(request, row, server); this.UpdateRules(request, row, server); status = "ok"; } row.RequestTimestamp = request.Timestamp; } if (request.IsCancelled) // status might have changed return; if (row.Retries > 0) status += " (" + row.Retries + ")"; row.Status = status; row.Update(); request.DataModified = 1; if (fireRefreshSingleServerComplete && this.RefreshSingleServerComplete != null) this.RefreshSingleServerComplete(this, new ServerEventArgs(row)); } finally { request.PendingTasks.Signal(); } }
private void GeoIpReceived(ServerRow server, GeoInfo geoInfo) { server.GeoInfo = geoInfo; Interlocked.Exchange(ref this.geoIpModified, 1); }
private bool UpdateServerInfo(UpdateRequest request, ServerRow row, Server server) { bool ok = ExecuteUpdate(request, row, server, retryCallback => { row.ServerInfo = server.GetInfo(retryCallback); }); if (!ok) row.ServerInfo = null; return ok; }
public void LoadFromIni(IniFile iniFile, IniFile.Section ini, GameExtensionPool pool) { this.Source = (SourceType) ini.GetInt("Type"); this.MasterServer = ini.GetString("MasterServer") ?? "hl2master.steampowered.com:27011"; this.InitialGameID = ini.GetInt("InitialGameID"); this.FilterMod = ini.GetString("FilterMod"); this.FilterMap = ini.GetString("FilterMap"); this.TagsInclude = ini.GetString("TagsInclude"); this.TagsExclude = ini.GetString("TagsExclude"); this.GetEmptyServers = ini.GetBool("GetEmptyServers", true); this.GetFullServers = ini.GetBool("GetFullServers", true); this.MasterServerQueryLimit = ini.GetInt("MasterServerQueryLimit", 500); this.GridFilter = ini.GetString("GridFilter"); var layout = ini.GetString("GridLayout"); if (!string.IsNullOrEmpty(layout)) this.ServerGridLayout = new MemoryStream(Convert.FromBase64String(layout)); this.gameExtension = pool.Get((Game) this.InitialGameID); if (this.Source == SourceType.CustomList) { this.servers = new List<ServerRow>(); // new config format var sec = iniFile.GetSection(ini.Name + "_Servers"); if (sec != null) { foreach (var key in sec.Keys) { var row = new ServerRow(Ip4Utils.ParseEndpoint(key), this.gameExtension); row.CachedName = sec.GetString(key); this.servers.Add(row); } } else { // old config format var oldSetting = ini.GetString("Servers") ?? ""; foreach (var server in oldSetting.Split('\n', ' ')) { var s = server.Trim(); if (s == "") continue; this.servers.Add(new ServerRow(Ip4Utils.ParseEndpoint(s), this.gameExtension)); } } } }
private bool UpdateServerInfo(UpdateRequest request, ServerRow row, Server server) { bool ok = ExecuteUpdate(request, row, server, retryCallback => { row.ServerInfo = server.GetInfo(retryCallback); if (row.ServerInfo == null) return false; var gameId = row.ServerInfo.Extra?.GameId ?? 0; if (gameId == 0) gameId = row.ServerInfo.Id; if (gameId == 0) gameId = (int)request.AppId; var extension = this.gameExtensions.Get((Game)gameId); row.GameExtension = extension; row.QueryPlayers = extension.SupportsPlayersQuery(row); row.QueryRules = extension.SupportsRulesQuery(row); return true; }); if (!ok) row.ServerInfo = null; return ok; }
public void RefreshSingleServer(ServerRow row) { row.Status = "updating..."; this.currentRequest = new UpdateRequest(1, this.currentRequest.QueryServerRules); this.currentRequest.PendingTasks = new CountdownEvent(1); ThreadPool.QueueUserWorkItem(dummy => this.UpdateServerAndDetails(this.currentRequest, row, true)); }
private void UpdateServerAndDetails(UpdateRequest request, ServerRow row, bool fireRefreshSingleServerComplete) { string status = ""; try { if (request.IsCancelled) return; using (Server server = ServerQuery.GetServerInstance(EngineType.Source, row.EndPoint, false, request.Timeout, request.Timeout)) { row.Retries = 0; server.SendFirstPacketTwice = this.sendFirstUdpPacketTwice; server.Retries = 3; status = "timeout"; var oldPing = row.ServerInfo?.Ping ?? 0; if (this.UpdateServerInfo(request, row, server)) { if (request.KeepPreviousPing && row.ServerInfo != null) row.ServerInfo.Ping = oldPing; // keep old ping so that the row isn't immediately resorted and moved this.UpdatePlayers(request, row, server); this.UpdateRules(request, row, server); status = "ok"; } row.RequestTimestamp = request.Timestamp; } if (request.IsCancelled) // status might have changed return; if (row.Retries > 0) status += " (" + row.Retries + ")"; } catch { // this happens when you hibernate windows and the program resumes before the network connection has be reestablished status = "network error"; } finally { row.Status = status; row.Update(); request.SetDataModified(); if (fireRefreshSingleServerComplete) this.RefreshSingleServerComplete?.Invoke(this, new ServerEventArgs(row)); if (!request.PendingTasks.IsSet) request.PendingTasks.Signal(); } }
public ServerEventArgs(ServerRow server) { this.Server = server; }
public override bool Connect(ServerRow server, string password, bool spectate) { ThreadPool.QueueUserWorkItem(context => ConnectInBackground(server, password, spectate), null); return true; //return base.Connect(server, password, spectate); }
private string GetServerAddress(ServerRow row) { return this.showAddressMode == 2 && row.ServerInfo?.Extra != null ? row.EndPoint.Address + ":" + row.ServerInfo.Extra.Port : row.EndPoint.ToString(); }
private void txtGameServer_ButtonClick(object sender, ButtonPressedEventArgs e) { try { string[] parts = this.txtGameServer.Text.Split(':'); if (parts[0].Length == 0) return; // get IPv4 address var addr = Dns.GetHostAddresses(parts[0]); int i; for (i = 0; i < addr.Length; i++) { if (addr[i].AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork) break; } if (i >= addr.Length) return; var endpoint = new IPEndPoint(addr[i], parts.Length > 1 ? int.Parse(parts[1]) : 27015); if (endpoint.Address.ToString() == "0.0.0.0") return; ServerRow serverRow = null; foreach (var row in this.viewModel.servers) { if (row.EndPoint.Equals(endpoint)) { serverRow = row; break; } } if (serverRow == null) { this.gvServers.BeginDataUpdate(); serverRow = new ServerRow(endpoint, this.extenders.Get(0)); this.viewModel.servers.Add(serverRow); this.gvServers.EndDataUpdate(); var handle = this.gvServers.GetRowHandle(this.viewModel.servers.Count - 1); this.gvServers.FocusedRowHandle = handle; this.gvServers.SelectRow(handle); } this.queryLogic.RefreshSingleServer(serverRow); } catch { } }
public override object GetPlayerCellValue(ServerRow server, Player player, string fieldName) { if (fieldName == "NameWithoutColorCodes") return NameColors.Replace(player.Name, ""); return base.GetPlayerCellValue(server, player, fieldName); }
public PlayerCountInfo(ServerRow row) { this.row = row; this.Update(); }
protected virtual string PromptForServerPassword(ServerRow row) { if (this.passwordForm.ShowDialog(this) == DialogResult.Cancel) return null; return this.passwordForm.Password; }