#define MAXCLIENTS 256                  // in a multiplayer game, can be arbitrarily changed
#define MAXPLAYERS 32                   // in a multiplayer game, can be arbitrarily changed
#define DEFAULTCLIENTS 6
#define MAXTRANS 5000                   // max amount of data to swallow in 1 go
#define CUBE_DEFAULT_SERVER_PORT 28763
#define CUBE_SERVINFO_PORT_LAN 28762
#define CUBE_SERVINFO_PORT(serverport) (serverport+1)
#define CUBE_SERVINFO_TO_SERV_PORT(servinfoport) (servinfoport-1)
#define CLIENTIPCENSOR 12               // blank out the last 12 bits of client's IPs before telling them to others (compromise between "16" from AC 0.9x and "8" from AC 1.1)
#define PROTOCOL_VERSION 1300           // bump when protocol changes (use negative numbers for mods!)
#define DEMO_VERSION 2                  // bump when demo format changes
#define DEMO_MAGIC "ASSAULTCUBE_DEMO"
#define DEMO_MINTIME 10000              // don't keep demo recordings with less than 10 seconds
#define MAXMAPNAMELEN 31
#define MAXMAPSENDSIZE 65536
#define MAXCFGFILESIZE 65536
#define MAXDEMOSENDSIZE 10240001
#define MAXGZMSGSIZE 65536
#define MAXMEDIADOWNLOADFILESIZE 1024000 // hard cap on filesizes (raw and unzipped) - to limit the effect of zip bombs - no nice error messages: just cap
#define MAXMODDOWNLOADSIZE 1024000      // hard cap on the filesize of downloaded mod packages - to keep stuff reasonable
#define MAXFILESINADZIP 21              // max number of files extracted from a zip by autodownload

extern bool modprotocol;
#define CUR_PROTOCOL_VERSION (modprotocol ? -PROTOCOL_VERSION : PROTOCOL_VERSION)

// network messages codes, c2s, c2c, s2c
enum
{
    SV_SERVINFO = 0, SV_SERVINFO_RESPONSE, SV_SERVINFO_CONTD, SV_WELCOME, SV_INITCLIENT, SV_POS, SV_POSC, SV_POSC2, SV_POSC3, SV_POSC4, SV_POSN, SV_TEXT, SV_TEAMTEXT, SV_TEXTME, SV_TEAMTEXTME, SV_TEXTPRIVATE,
    SV_SOUND, SV_VOICECOM, SV_VOICECOMTEAM, SV_CDIS,
    SV_SHOOT, SV_EXPLODE, SV_SUICIDE, SV_AKIMBO, SV_RELOAD,
    SV_GIBDIED, SV_DIED, SV_GIBDAMAGE, SV_DAMAGE, SV_HITPUSH, SV_SHOTFX, SV_THROWNADE,
    SV_TRYSPAWN, SV_SPAWNSTATE, SV_SPAWN, SV_SPAWNDENY, SV_FORCEDEATH, SV_RESUME,
    SV_DISCSCORES, SV_TIMEUP, SV_EDITENT, SV_ITEMACC,
    SV_MAPCHANGE, SV_ITEMSPAWN, SV_ITEMPICKUP,
    SV_PING, SV_PONG, SV_CLIENTPING,
    SV_EDITMODE, SV_EDITXY, SV_EDITARCH, SV_EDITBLOCK, SV_EDITD, SV_EDITE, SV_NEWMAP,
    SV_SENDMAP, SV_RECVMAP, SV_REMOVEMAP,
    SV_SERVMSG, SV_SERVMSGVERB, SV_ITEMLIST, SV_WEAPCHANGE, SV_PRIMARYWEAP,
    SV_FLAGACTION, SV_FLAGINFO, SV_FLAGMSG, SV_FLAGCNT,
    SV_ARENAWIN,
    SV_SETADMIN, SV_SERVOPINFO,
    SV_CALLVOTE, SV_CALLVOTESUC, SV_CALLVOTEERR, SV_VOTE, SV_VOTERESULT,
    SV_SETTEAM, SV_TEAMDENY, SV_SERVERMODE,
    SV_IPLIST, SV_SPECTCN,
    SV_LISTDEMOS, SV_SENDDEMOLIST, SV_GETDEMO, SV_SENDDEMO, SV_DEMOPLAYBACK,
    SV_CONNECT,
    SV_SWITCHNAME, SV_SWITCHSKIN, SV_SWITCHTEAM,
    SV_CLIENT,
    SV_EXTENSION,
    SV_MAPIDENT, SV_DEMOCHECKSUM, SV_DEMOSIGNATURE,
    SV_PAUSEMODE,
    SV_GETVITA, SV_VITADATA,
    SV_NUM
};

#ifdef _DEBUG

extern void protocoldebug(bool enable);

// converts message code to char
extern const char *messagenames[SV_NUM];
#endif

enum { SA_KICK = 0, SA_BAN, SA_REMBANS, SA_MASTERMODE, SA_AUTOTEAM, SA_FORCETEAM, SA_GIVEADMIN, SA_MAP, SA_RECORDDEMO, SA_STOPDEMO, SA_CLEARDEMOS, SA_SERVERDESC, SA_SHUFFLETEAMS, SA_PAUSE, SA_NUM};
enum { VOTE_NEUTRAL = 0, VOTE_YES, VOTE_NO, VOTE_NUM };
enum { VOTEE_DISABLED = 0, VOTEE_CUR, VOTEE_MUL, VOTEE_MAX, VOTEE_AREA, VOTEE_PERMISSION, VOTEE_INVALID, VOTEE_WEAK, VOTEE_NEXT, VOTEE_NUM };
enum { MM_OPEN = 0, MM_PRIVATE, MM_MATCH, MM_NUM }; enum { MM_MASK = 0x03 };
enum { AT_DISABLED = 0, AT_ENABLED = 1, AT_SHUFFLE = 2, AT_NUM };
enum { FA_PICKUP = 0, FA_STEAL, FA_DROP, FA_LOST, FA_RETURN, FA_SCORE, FA_NUM, FA_RESET };
enum { FM_PICKUP = 0, FM_DROP, FM_LOST, FM_RETURN, FM_SCORE, FM_KTFSCORE, FM_SCOREFAIL, FM_RESET, FM_NUM };
enum { FTR_INFO = 0, FTR_PLAYERWISH, FTR_AUTOTEAM, FTR_SILENTFORCE, FTR_NUM }; // forceteam-reasons
enum { SP_OK = 0, SP_REFILLMATCH, SP_OK_NUM, SP_WRONGMAP, SP_SPECT, SP_NUM }; // spawn permission (<OK_NUM && isspect: change to active team allowed)
enum { HX_UNUSED = 0, HX_MAPINFO, HX_MODEINFO, HX_ARTIST, HX_EDITUNDO, HX_CONFIG, HX_VANTAGEPOINT, HX_NUM, HX_TYPEMASK = 0x3f, HX_FLAG_PERSIST = 0x40 };
enum { EDITXY_HEIGHT = 0, EDITXY_TEX, EDITXY_TYPE, EDITXY_VDELTA, EDITXY_EQUALISE, EDITXY_TAG, EDITXY_SLOPE, EDITXY_STAIRS, EDITXY_FLIPROT, EDITXY_NUM };

#define DMF 16.0f
#define DNF 100.0f
#define DVELF 4.0f
#define MAXPITCH 90.0f
#define PITCHBITS 8
#define YAWBITS 10
#define FLAGBITS 11

enum { DISC_PROTOCOL = 0, DISC_EOP, DISC_CN, DISC_TAGT, DISC_DUP, DISC_OVERFLOW, DISC_RANDOM, DISC_VOODOO, DISC_SYNC, DISC_AUTH,     // div. protocol errors
       DISC_REFUSED = 16, DISC_BANNED, DISC_BLACKLISTED, DISC_WRONGPW, DISC_MAXCLIENTS, DISC_PRIVATE, DISC_OVERLOAD,                 // connection refused
       DISC_REMOVED = 32, DISC_SOPLOGINFAIL, DISC_BADNICK, DISC_ANNOY, DISC_SPAM, DISC_DOS, DISC_SPEEDING, DISC_FISHSLAP, DISC_AFK,  // disconnected
       DISC_KICK = 48, DISC_BAN,  DISC_VOTEKICK, DISC_VOTEBAN,  DISC_OPKICK, DISC_OPBAN,  DISC_TKKICK, DISC_TKBAN,  DISC_FFKICK, DISC_FFBAN,  DISC_AUTOKICK, DISC_AUTOBAN,
       DISC_UNKNOWN = 99, DISC_BECAUSE };
enum { BAN_NONE = 0, BAN_VOTE, BAN_AUTO, BAN_BLACKLIST, BAN_VITA, BAN_MASTER };

#define EXT_ACK                         -1
#define EXT_VERSION                     104
#define EXT_ERROR_NONE                  0
#define EXT_ERROR                       1
#define EXT_PLAYERSTATS_RESP_IDS        -10
#define EXT_UPTIME                      0
#define EXT_PLAYERSTATS                 1
#define EXT_TEAMSCORE                   2
#define EXT_PLAYERSTATS_RESP_STATS      -11

enum { PONGFLAG_PASSWORD = 0, PONGFLAG_BANNED, PONGFLAG_BLACKLIST, PONGFLAG_MASTERMODE = 6, PONGFLAG_NUM };
enum { EXTPING_NOP = 0, EXTPING_NAMELIST, EXTPING_SERVERINFO, EXTPING_MAPROT, EXTPING_UPLINKSTATS, EXTPING_NUM };

enum
{
    GMODE_DEMO = -1,
    GMODE_TEAMDEATHMATCH = 0,           // 0
    GMODE_COOPEDIT,
    GMODE_DEATHMATCH,
    GMODE_SURVIVOR,
    GMODE_TEAMSURVIVOR,
    GMODE_CTF,                          // 5
    GMODE_PISTOLFRENZY,
    GMODE_BOTTEAMDEATHMATCH,
    GMODE_BOTDEATHMATCH,
    GMODE_LASTSWISSSTANDING,
    GMODE_ONESHOTONEKILL,               // 10
    GMODE_TEAMONESHOTONEKILL,
    GMODE_BOTONESHOTONEKILL,
    GMODE_HUNTTHEFLAG,
    GMODE_TEAMKEEPTHEFLAG,
    GMODE_KEEPTHEFLAG,                  // 15
    GMODE_TEAMPF,
    GMODE_TEAMLSS,
    GMODE_BOTPISTOLFRENZY,
    GMODE_BOTLSS,
    GMODE_BOTTEAMSURVIVOR,              // 20
    GMODE_BOTTEAMONESHOTONKILL,
    GMODE_NUM
};

enum
{
    GMMASK_TEAMDEATHMATCH       = 1 << GMODE_TEAMDEATHMATCH,               // 0
    GMMASK_COOPEDIT             = 1 << GMODE_COOPEDIT,
    GMMASK_DEATHMATCH           = 1 << GMODE_DEATHMATCH,
    GMMASK_SURVIVOR             = 1 << GMODE_SURVIVOR,
    GMMASK_TEAMSURVIVOR         = 1 << GMODE_TEAMSURVIVOR,
    GMMASK_CTF                  = 1 << GMODE_CTF,                          // 5
    GMMASK_PISTOLFRENZY         = 1 << GMODE_PISTOLFRENZY,
    GMMASK_BOTTEAMDEATHMATCH    = 1 << GMODE_BOTTEAMDEATHMATCH,
    GMMASK_BOTDEATHMATCH        = 1 << GMODE_BOTDEATHMATCH,
    GMMASK_LASTSWISSSTANDING    = 1 << GMODE_LASTSWISSSTANDING,
    GMMASK_ONESHOTONEKILL       = 1 << GMODE_ONESHOTONEKILL,               // 10
    GMMASK_TEAMONESHOTONEKILL   = 1 << GMODE_TEAMONESHOTONEKILL,
    GMMASK_BOTONESHOTONEKILL    = 1 << GMODE_BOTONESHOTONEKILL,
    GMMASK_HUNTTHEFLAG          = 1 << GMODE_HUNTTHEFLAG,
    GMMASK_TEAMKEEPTHEFLAG      = 1 << GMODE_TEAMKEEPTHEFLAG,
    GMMASK_KEEPTHEFLAG          = 1 << GMODE_KEEPTHEFLAG,                  // 15
    GMMASK_TEAMPF               = 1 << GMODE_TEAMPF,
    GMMASK_TEAMLSS              = 1 << GMODE_TEAMLSS,
    GMMASK_BOTPISTOLFRENZY      = 1 << GMODE_BOTPISTOLFRENZY,
    GMMASK_BOTLSS               = 1 << GMODE_BOTLSS,
    GMMASK_BOTTEAMSURVIVOR      = 1 << GMODE_BOTTEAMSURVIVOR,              // 20
    GMMASK_BOTTEAMONESHOTONKILL = 1 << GMODE_BOTTEAMONESHOTONKILL,
    GMMASK__ALL       = (1 << GMODE_NUM) - 1,
    GMMASK__FLAGS     = GMMASK_CTF | GMMASK_HUNTTHEFLAG | GMMASK_KEEPTHEFLAG | GMMASK_TEAMKEEPTHEFLAG,
    GMMASK__FLAGENTS  = GMMASK_CTF | GMMASK_KEEPTHEFLAG | GMMASK_TEAMKEEPTHEFLAG,
    GMMASK__BOT       = GMMASK_BOTDEATHMATCH | GMMASK_BOTLSS | GMMASK_BOTONESHOTONEKILL | GMMASK_BOTPISTOLFRENZY | GMMASK_BOTTEAMDEATHMATCH | GMMASK_BOTTEAMONESHOTONKILL | GMMASK_BOTTEAMSURVIVOR,
    GMMASK__MP        = GMMASK_TEAMDEATHMATCH | GMMASK_COOPEDIT | GMMASK_DEATHMATCH | GMMASK_SURVIVOR | GMMASK_TEAMSURVIVOR | GMMASK_CTF | GMMASK_PISTOLFRENZY | GMMASK_LASTSWISSSTANDING
                      | GMMASK_ONESHOTONEKILL | GMMASK_TEAMONESHOTONEKILL | GMMASK_HUNTTHEFLAG | GMMASK_TEAMKEEPTHEFLAG | GMMASK_KEEPTHEFLAG | GMMASK_TEAMPF | GMMASK_TEAMLSS,
    GMMASK__MPNOCOOP  = GMMASK__MP & ~GMMASK_COOPEDIT,
    GMMASK__TEAM      = GMMASK_BOTTEAMDEATHMATCH | GMMASK_BOTTEAMONESHOTONKILL | GMMASK_BOTTEAMSURVIVOR | GMMASK_TEAMDEATHMATCH | GMMASK_TEAMSURVIVOR | GMMASK_CTF
                      | GMMASK_TEAMONESHOTONEKILL | GMMASK_HUNTTHEFLAG | GMMASK_TEAMKEEPTHEFLAG | GMMASK_TEAMPF | GMMASK_TEAMLSS,
    GMMASK__TEAMSPAWN = GMMASK_BOTTEAMDEATHMATCH | GMMASK_BOTTEAMONESHOTONKILL | GMMASK_BOTTEAMSURVIVOR | GMMASK_TEAMDEATHMATCH | GMMASK_TEAMSURVIVOR | GMMASK_CTF
                      | GMMASK_TEAMONESHOTONEKILL | GMMASK_HUNTTHEFLAG | GMMASK_TEAMPF | GMMASK_TEAMLSS,
    GMMASK__FFA       = GMMASK_BOTDEATHMATCH | GMMASK_BOTLSS | GMMASK_BOTONESHOTONEKILL | GMMASK_BOTPISTOLFRENZY | GMMASK_COOPEDIT | GMMASK_DEATHMATCH | GMMASK_SURVIVOR
                      | GMMASK_PISTOLFRENZY | GMMASK_LASTSWISSSTANDING | GMMASK_ONESHOTONEKILL | GMMASK_KEEPTHEFLAG,
    GMMASK__FFASPAWN  = GMMASK_BOTDEATHMATCH | GMMASK_BOTLSS | GMMASK_BOTONESHOTONEKILL | GMMASK_BOTPISTOLFRENZY | GMMASK_COOPEDIT | GMMASK_DEATHMATCH | GMMASK_SURVIVOR
                      | GMMASK_PISTOLFRENZY | GMMASK_LASTSWISSSTANDING | GMMASK_ONESHOTONEKILL | GMMASK_KEEPTHEFLAG | GMMASK_TEAMKEEPTHEFLAG
};

#define m_lms         (gamemode==3 || gamemode==4 || gamemode==20)
#define m_ctf         (gamemode==5)
#define m_pistol      (gamemode==6 || gamemode==16 || gamemode==18)
#define m_lss         (gamemode==9 || gamemode==17 || gamemode==19)
#define m_osok        ((gamemode>=10 && gamemode<=12) || gamemode==21)
#define m_htf         (gamemode==13)
#define m_ktf         (gamemode==14 || gamemode==15)

#define m_noitems     (m_lms || m_osok)
#define m_noitemsnade (m_lss)
#define m_nopistol    (m_osok || m_lss)
#define m_noprimary   (m_pistol || m_lss)
#define m_noguns      (m_nopistol && m_noprimary)
#define m_arena       (m_lms || m_lss || m_osok)
#define m_autospawn   (gamemode == 0 || gamemode == 2 || gamemode == 6 || gamemode == 13 || gamemode == 16)
#define m_teammode    (gamemode==0 || gamemode==4 || gamemode==5 || gamemode==7 || gamemode==11 || gamemode==13 || gamemode==14 || gamemode==16 || gamemode==17 || gamemode==20 || gamemode==21)
#define m_tarena      (m_arena && m_teammode)
#define m_botmode     (gamemode==7 || gamemode == 8 || gamemode==12 || (gamemode>=18 && gamemode<=21))
#define m_valid(mode) (((mode)>=0 && (mode)<GMODE_NUM) || (mode) == -1)
#define m_mp(mode)    (m_valid(mode) && (mode)>=0 && (mode)!=7 && (mode)!=8 && (mode)!=12 && ((mode)<18 || (mode)>21))
#define m_demo        (gamemode==-1)
#define m_coop        (gamemode==1)
#define m_flags_      (m_ctf || m_htf || m_ktf) // trailing underscore is required to prevent name clash on FreeBSD systems
#define m_isdemo(x)   ((x) == -1)

// single filter modes
#define FTXT_NOWHITE     (1<<8)
#define FTXT_ALLOWBLANKS (1<<9)
#define FTXT_ALLOWNL     (1<<10)
#define FTXT_ALLOWTAB    (1<<11)
#define FTXT_NOCOLOR     (1<<12)
#define FTXT_TABTOBLANK  (1<<13)
#define FTXT_FILLBLANKS  (1<<14)
#define FTXT_SAFECS      (1<<15)
#define FTXT_LEET        (1<<16)
#define FTXT_TOUPPER     (1<<17)
#define FTXT_TOLOWER     (1<<18)
#define FTXT_FILENAME    (1<<19)
#define FTXT_ALLOWSLASH  (1<<20)
#define FTXT_MAPNAME     (1<<21)
#define FTXT_CROPWHITE_LEAD  (1<<22)
#define FTXT_CROPWHITE_TRAIL (1<<23)
// character classes
#define FTXT__ALIAS      (FTXT_NOWHITE | FTXT_NOCOLOR | FTXT_SAFECS | FTXT_MAPNAME)
#define FTXT__SERVDESC   (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_TABTOBLANK)
#define FTXT__MAPMSG     (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_TABTOBLANK)
#define FTXT__MAPINFO_LICENSE (FTXT_NOWHITE | FTXT_NOCOLOR | FTXT_TOLOWER | FTXT_MAPNAME)
#define FTXT__MAPINFO_COMMENT (FTXT_NOWHITE | FTXT_NOCOLOR | FTXT_ALLOWBLANKS | FTXT_TABTOBLANK)
#define FTXT__MAPNAME    (FTXT_NOCOLOR | FTXT_MAPNAME | FTXT_ALLOWSLASH | FTXT_TOLOWER)
#define FTXT__MDLATTR    (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_TABTOBLANK | FTXT_NOCOLOR | FTXT_SAFECS)
#define FTXT__DEMONAME   (FTXT_NOCOLOR | FTXT_MAPNAME | FTXT_ALLOWSLASH)
#define FTXT__DEMOINFO   (FTXT_NOCOLOR | FTXT_NOWHITE | FTXT_ALLOWBLANKS)
#define FTXT__PLAYERNAME (FTXT_NOWHITE | FTXT_NOCOLOR)
#define FTXT__SERVERINFOLINE (FTXT_ALLOWTAB | FTXT_CROPWHITE_LEAD | FTXT_CROPWHITE_TRAIL)
#define FTXT__SERVERINFO (FTXT_ALLOWTAB | FTXT_ALLOWNL)
#define FTXT__MOTD       (FTXT_TABTOBLANK)
#define FTXT__CHAT       (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_NOCOLOR | FTXT_TABTOBLANK | FTXT_CROPWHITE_TRAIL)
#define FTXT__LOG        (FTXT_NOCOLOR | FTXT_TABTOBLANK)
#define FTXT__LOGIDENT      (FTXT_NOCOLOR | FTXT_NOWHITE | FTXT_FILENAME)
#define FTXT__PREFERENCES   (FTXT_NOCOLOR | FTXT_NOWHITE | FTXT_FILENAME)
#define FTXT__AUTH          (FTXT_NOCOLOR | FTXT_NOWHITE)
#define FTXT__KICKBANREASON (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_NOCOLOR | FTXT_TABTOBLANK | FTXT_CROPWHITE_LEAD | FTXT_CROPWHITE_TRAIL)
#define FTXT__FAVCATEGORY   (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_NOCOLOR)
#define FTXT__GLOBALNAME    (FTXT_NOWHITE | FTXT_NOCOLOR | FTXT_FILLBLANKS)
#define FTXT__MEDIAFILENAME (FTXT_FILENAME)
#define FTXT__MEDIAFILEPATH (FTXT_FILENAME | FTXT_ALLOWSLASH)
#define FTXT__ZIPDESC       (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_TABTOBLANK | FTXT_NOCOLOR | FTXT_SAFECS)
#define FTXT__CERTFILENAME  (FTXT_MAPNAME | FTXT_ALLOWSLASH | FTXT_TOLOWER)
#define FTXT__CONSOLEPASTE  (FTXT_TABTOBLANK)
#define FTXT__AUTOKEYMAPNAME (FTXT_SAFECS)
#define FTXT__VITACOMMENT   (FTXT_NOWHITE | FTXT_ALLOWBLANKS | FTXT_NOCOLOR | FTXT_TABTOBLANK)
#define FTXT__VITACLAN      (FTXT_NOWHITE | FTXT_NOCOLOR)
#define FTXT__MAPROT        (FTXT_NOWHITE | FTXT_NOCOLOR | FTXT_TOLOWER)
#define FTXT__SERVPARNAME   (FTXT_NOWHITE | FTXT_NOCOLOR | FTXT_SAFECS)
#define FTXT__FORMATSTRING  (FTXT_NOWHITE | FTXT_NOCOLOR)

