⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ladder.c

📁 打魔兽战网的都知道他是什么
💻 C
📖 第 1 页 / 共 5 页
字号:
/* * Copyright (C) 1999  Rob Crittenden (rcrit@greyoak.com) * Copyright (C) 1999,2000  Ross Combs (rocombs@cs.nmsu.edu) * Copyright (C) 1999,2000  D.Moreaux (vapula@linuxbe.org) * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA. */#define LADDER_INTERNAL_ACCESS#include "common/setup_before.h"#ifdef HAVE_STDDEF_H# include <stddef.h>#else# ifndef NULL#  define NULL ((void *)0)# endif#endif#ifdef STDC_HEADERS# include <stdlib.h>#else# ifdef HAVE_MALLOC_H#  include <malloc.h># endif#endif#ifdef HAVE_STRING_H# include <string.h>#else# ifdef HAVE_STRINGS_H#  include <strings.h># endif#endif#include <errno.h>#include <compat/strerror.h>#include "common/field_sizes.h"#include "account.h"#include "account_wrap.h"#include "common/eventlog.h"#include "common/util.h"#include "game.h"#include "common/tag.h"#include "common/list.h"#include "common/bnettime.h"#include "prefs.h"#include "common/hashtable.h"#include "ladder_calc.h"#include "ladder.h"#include "compat/strcasecmp.h"#include "compat/strncasecmp.h"#include "ladder_binary.h"#include "storage.h"#include "account.h"#include "common/bnet_protocol.h"#include "common/xalloc.h"#include "common/setup_after.h"#define MaxRankKeptInLadder 1000/* for War3 XP computations */static t_xpcalc_entry  * xpcalc;static t_xplevel_entry * xplevels;int w3_xpcalc_maxleveldiff;const char * WAR3_solo_file = "WAR3_solo";const char * W3XP_solo_file = "W3XP_solo";const char * WAR3_team_file = "WAR3_team";const char * W3XP_team_file = "W3XP_team";const char * WAR3_ffa_file  = "WAR3_ffa";const char * W3XP_ffa_file  = "W3XP_ffa";const char * WAR3_at_file   = "WAR3_atteam";const char * W3XP_at_file   = "W3XP_atteam";const char * STAR_ar_file   = "STAR_active_rating";const char * STAR_cr_file   = "STAR_current_rating";const char * SEXP_ar_file   = "SEXP_active_rating";const char * SEXP_cr_file   = "SEXP_current_rating";const char * W2BN_ar_file   = "W2BN_active_rating";const char * W2BN_cr_file   = "W2BN_current_rating";const char * W2BN_ari_file   = "W2BN_active_rating_iron";const char * W2BN_cri_file   = "W2BN_current_rating_iron";const char * std_end   = ".dat";const char * xml_end   = ".xml";char * ladder_id_str[] = {"0","1","","3","","solo","team","ffa"};char * WAR3_solo_filename, * WAR3_team_filename, * WAR3_ffa_filename, * WAR3_at_filename;char * W3XP_solo_filename, * W3XP_team_filename, * W3XP_ffa_filename, * W3XP_at_filename;char * STAR_ar_filename, * STAR_cr_filename, * SEXP_ar_filename, * SEXP_cr_filename;char * W2BN_ar_filename, * W2BN_cr_filename, * W2BN_ari_filename, * W2BN_cri_filename;t_ladder WAR3_solo_ladder, WAR3_team_ladder, WAR3_ffa_ladder, WAR3_at_ladder;t_ladder W3XP_solo_ladder, W3XP_team_ladder, W3XP_ffa_ladder, W3XP_at_ladder;t_ladder STAR_active_rating,          STAR_active_wins,          STAR_active_games,          STAR_current_rating,         STAR_current_wins,         STAR_current_games;t_ladder SEXP_active_rating,          SEXP_active_wins,          SEXP_active_games,          SEXP_current_rating,         SEXP_current_wins,         SEXP_current_games;t_ladder W2BN_active_rating,          W2BN_active_wins,          W2BN_active_games,         W2BN_active_rating_ironman,  W2BN_active_wins_ironman,  W2BN_active_games_ironman;t_ladder W2BN_current_rating,         W2BN_current_wins,         W2BN_current_games,         W2BN_current_rating_ironman, W2BN_current_wins_ironman, W2BN_current_games_ironman;t_ladder_internal * last_internal = NULL;t_ladder	     * last_ladder   = NULL;int 		       last_rank     = 0;/* * Make the current ladder statistics the active ones. */extern int ladder_make_active(t_ladder *current, t_ladder *active,int set_attributes);extern int ladderlist_make_all_active(void){	ladder_make_active(ladder_cr(CLIENTTAG_STARCRAFT_UINT,ladder_id_normal), ladder_ar(CLIENTTAG_STARCRAFT_UINT,ladder_id_normal),1);	ladder_make_active(ladder_cw(CLIENTTAG_STARCRAFT_UINT,ladder_id_normal), ladder_aw(CLIENTTAG_STARCRAFT_UINT,ladder_id_normal),0);	ladder_make_active(ladder_cg(CLIENTTAG_STARCRAFT_UINT,ladder_id_normal), ladder_ag(CLIENTTAG_STARCRAFT_UINT,ladder_id_normal),0);	ladder_make_active(ladder_cr(CLIENTTAG_BROODWARS_UINT,ladder_id_normal), ladder_ar(CLIENTTAG_BROODWARS_UINT,ladder_id_normal),1);	ladder_make_active(ladder_cw(CLIENTTAG_BROODWARS_UINT,ladder_id_normal), ladder_aw(CLIENTTAG_BROODWARS_UINT,ladder_id_normal),0);	ladder_make_active(ladder_cg(CLIENTTAG_BROODWARS_UINT,ladder_id_normal), ladder_ag(CLIENTTAG_BROODWARS_UINT,ladder_id_normal),0);	ladder_make_active(ladder_cr(CLIENTTAG_WARCIIBNE_UINT,ladder_id_normal), ladder_ar(CLIENTTAG_WARCIIBNE_UINT,ladder_id_normal),1);	ladder_make_active(ladder_cw(CLIENTTAG_WARCIIBNE_UINT,ladder_id_normal), ladder_aw(CLIENTTAG_WARCIIBNE_UINT,ladder_id_normal),0);	ladder_make_active(ladder_cg(CLIENTTAG_WARCIIBNE_UINT,ladder_id_normal), ladder_ag(CLIENTTAG_WARCIIBNE_UINT,ladder_id_normal),0);	ladder_make_active(ladder_cr(CLIENTTAG_WARCIIBNE_UINT,ladder_id_ironman),ladder_ar(CLIENTTAG_WARCIIBNE_UINT,ladder_id_ironman),1);	ladder_make_active(ladder_cw(CLIENTTAG_WARCIIBNE_UINT,ladder_id_ironman),ladder_aw(CLIENTTAG_WARCIIBNE_UINT,ladder_id_ironman),0);	ladder_make_active(ladder_cg(CLIENTTAG_WARCIIBNE_UINT,ladder_id_ironman),ladder_ag(CLIENTTAG_WARCIIBNE_UINT,ladder_id_ironman),0);	ladder_update_all_accounts();    return 0;}/* * Prepare an account for first ladder play if necessary. */extern int ladder_init_account(t_account * account, t_clienttag clienttag, t_ladder_id id){    int uid;    char clienttag_str[5];        if (!account)    {	eventlog(eventlog_level_error,__FUNCTION__,"got NULL account");	return -1;    }    if (!clienttag)    {	eventlog(eventlog_level_error,__FUNCTION__,"got bad clienttag");	return -1;    }        if (account_get_ladder_rating(account,clienttag,id)==0)    {	if (account_get_ladder_wins(account,clienttag,id)+	    account_get_ladder_losses(account,clienttag,id)>0) /* no ladder games so far... */	{	    eventlog(eventlog_level_warn,__FUNCTION__,"account for \"%s\" (%s) has %u wins and %u losses but has zero rating",account_get_name(account),clienttag,account_get_ladder_wins(account,clienttag,id),account_get_ladder_losses(account,clienttag,id));	    return -1;	}	account_adjust_ladder_rating(account,clienttag,id,prefs_get_ladder_init_rating());	uid = account_get_uid(account);	war3_ladder_add(ladder_cr(clienttag,id),uid,0,account_get_ladder_rating(account,clienttag,id),account,0,clienttag);	war3_ladder_add(ladder_cw(clienttag,id),uid,0,0,account,0,clienttag);	war3_ladder_add(ladder_cg(clienttag,id),uid,0,0,account,0,clienttag);	eventlog(eventlog_level_info,__FUNCTION__,"initialized account for \"%s\" for \"%s\" ladder",account_get_name(account),tag_uint_to_str(clienttag_str,clienttag));    }    return 0;}/* * Update player ratings, rankings, etc due to game results. */extern int ladder_update(t_clienttag clienttag, t_ladder_id id, unsigned int count, t_account * * players, t_game_result * results, t_ladder_info * info, t_ladder_option opns){    unsigned int curr;    unsigned int winners=0;    unsigned int losers=0;    unsigned int draws=0;	int uid;        if (count<1 || count>8)    {	eventlog(eventlog_level_error,__FUNCTION__,"got invalid player count %u",count);	return -1;    }    if (!players)    {	eventlog(eventlog_level_error,__FUNCTION__,"got NULL players");	return -1;    }    if (!results)    {	eventlog(eventlog_level_error,__FUNCTION__,"got NULL results");	return -1;    }    if (!clienttag)    {	eventlog(eventlog_level_error,__FUNCTION__,"got bad clienttag");	return -1;    }    if (!info)    {	eventlog(eventlog_level_error,__FUNCTION__,"got NULL info");	return -1;    }        for (curr=0; curr<count; curr++)    {	if (!players[curr])	{	    eventlog(eventlog_level_error,__FUNCTION__,"got NULL player[%u] (of %u)",curr,count);	    return -1;	}		switch (results[curr])	{	case game_result_win:	    winners++;	    break;	case game_result_loss:	    losers++;	    break;	case game_result_draw:	    draws++;	    break;	case game_result_disconnect:	    if (opns&ladder_option_disconnectisloss)		losers++;	    break;	default:	    eventlog(eventlog_level_error,__FUNCTION__,"bad results[%u]=%u",curr,(unsigned int)results[curr]);	    return -1;	}    }        if (draws>0)    {	if (draws!=count)	{	    eventlog(eventlog_level_error,__FUNCTION__,"some, but not all players had a draw count=%u (winners=%u losers=%u draws=%u)",count,winners,losers,draws);	    return -1;	}		return 0; /* no change in case of draw */    }    if ((losers<1) || (winners<1) || (winners>1 && (winners!=losers)))    {	eventlog(eventlog_level_info,__FUNCTION__,"missing winner or loser for count=%u (winners=%u losers=%u draws=%u) - discarding result",count,winners,losers,draws);	return 0;    }        if (ladder_calc_info(clienttag,id,count,players,results,info)<0)    {	eventlog(eventlog_level_error,__FUNCTION__,"unable to calculate info from game results");	return -1;    }        for (curr=0; curr<count; curr++)	{	  int won,wins,games;	  t_account * account;	  if (results[curr]==game_result_win) won=1; else won=0;	  	  account = players[curr];	  uid = account_get_uid(account);	  wins = account_get_ladder_wins(account,clienttag,id);	  games = wins + account_get_ladder_losses(account,clienttag,id) + account_get_ladder_disconnects(account,clienttag,id);	  	  account_adjust_ladder_rating(account,clienttag,id,info[curr].adj);	  	  war3_ladder_update(ladder_cr(clienttag,id),uid,won,account_get_ladder_rating(account,clienttag,id),players[curr],0);	  if (results[curr]!=game_result_draw)	        war3_ladder_update(ladder_cg(clienttag,id),uid,info[curr].adj,games,players[curr],0);			  if (results[curr]==game_result_win)		war3_ladder_update(ladder_cw(clienttag,id),uid,info[curr].adj,wins,players[curr],0);	}		ladder_update_all_accounts();        return 0;}extern int ladder_check_map(char const * mapname, t_game_maptype maptype, t_clienttag clienttag){    if (!mapname)    {	eventlog(eventlog_level_error,__FUNCTION__,"got NULL mapname");	return -1;    }    if (!clienttag)    {	eventlog(eventlog_level_error,__FUNCTION__,"got bad clienttag");	return -1;    }        eventlog(eventlog_level_debug,__FUNCTION__,"checking mapname \"%s\" maptype=%d",mapname,(int)maptype);    if (maptype==game_maptype_ladder) /* FIXME: what about Ironman? */	return 1;        return 0;}extern t_account * ladder_get_account_by_rank(unsigned int rank, t_ladder_sort lsort, t_ladder_time ltime, t_clienttag clienttag, t_ladder_id id){    unsigned int dummy;        if (rank<1)    {	eventlog(eventlog_level_error,__FUNCTION__,"got zero rank");	return NULL;    }    if (!clienttag)    {	eventlog(eventlog_level_error,__FUNCTION__,"got bad clienttag");	return NULL;    }        switch (lsort)    {    case ladder_sort_highestrated:		if (ltime == ladder_time_current)			return ladder_get_account(ladder_cr(clienttag,id),rank,&dummy,clienttag);		else			return ladder_get_account(ladder_ar(clienttag,id),rank,&dummy,clienttag);    case ladder_sort_mostwins:		if (ltime == ladder_time_current)			return ladder_get_account(ladder_cw(clienttag,id),rank,&dummy,clienttag);		else			return ladder_get_account(ladder_aw(clienttag,id),rank,&dummy,clienttag);    case ladder_sort_mostgames:		if (ltime == ladder_time_current)			return ladder_get_account(ladder_cg(clienttag,id),rank,&dummy,clienttag);		else			return ladder_get_account(ladder_ag(clienttag,id),rank,&dummy,clienttag);    default:	eventlog(eventlog_level_error,__FUNCTION__,"got bad ladder sort %u",(unsigned int)lsort);    }    return NULL;}extern unsigned int ladder_get_rank_by_account(t_account * account, t_ladder_sort lsort, t_ladder_time ltime, t_clienttag clienttag, t_ladder_id id){    int uid;    if (!account)    {	eventlog(eventlog_level_error,__FUNCTION__,"got NULL account");	return 0;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -