summaryrefslogtreecommitdiff
path: root/src/game/g_cmds.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/game/g_cmds.c')
-rw-r--r--src/game/g_cmds.c159
1 files changed, 155 insertions, 4 deletions
diff --git a/src/game/g_cmds.c b/src/game/g_cmds.c
index 390c6a5b..13d27f4f 100644
--- a/src/game/g_cmds.c
+++ b/src/game/g_cmds.c
@@ -642,6 +642,152 @@ void Cmd_Team_f( gentity_t *ent )
G_ChangeTeam( ent, team );
}
+/*
+==================
+G_CensorString
+==================
+*/
+static char censors[ 20000 ];
+static int numcensors;
+
+void G_LoadCensors( void )
+{
+ char *text_p, *token;
+ char text[ 20000 ];
+ char *term;
+ int len;
+ fileHandle_t f;
+
+ numcensors = 0;
+
+ if( !g_censorship.string[ 0 ] )
+ return;
+
+ len = trap_FS_FOpenFile( g_censorship.string, &f, FS_READ );
+ if( len < 0 )
+ {
+ Com_Printf( S_COLOR_RED "ERROR: Censors file %s doesn't exist\n",
+ g_censorship.string );
+ return;
+ }
+ if( len == 0 || len >= sizeof( text ) - 1 )
+ {
+ trap_FS_FCloseFile( f );
+ Com_Printf( S_COLOR_RED "ERROR: Censors file %s is %s\n",
+ g_censorship.string, len == 0 ? "empty" : "too long" );
+ return;
+ }
+ trap_FS_Read( text, len, f );
+ trap_FS_FCloseFile( f );
+ text[ len ] = 0;
+
+ term = censors;
+
+ text_p = text;
+ while( 1 )
+ {
+ token = COM_Parse( &text_p );
+ if( !*token || sizeof( censors ) - ( term - censors ) < 4 )
+ break;
+ Q_strncpyz( term, token, sizeof( censors ) - ( term - censors ) );
+ Q_strlwr( term );
+ term += strlen( term ) + 1;
+ if( sizeof( censors ) - ( term - censors ) == 0 )
+ break;
+ token = COM_ParseExt( &text_p, qfalse );
+ Q_strncpyz( term, token, sizeof( censors ) - ( term - censors ) );
+ term += strlen( term ) + 1;
+ numcensors++;
+ }
+ G_Printf( "Parsed %d string replacements\n", numcensors );
+}
+
+void G_CensorString( char *out, const char *in, int len, gentity_t *ent )
+{
+ const char *s, *m;
+ int i;
+
+ if( !numcensors || G_admin_permission( ent, ADMF_NOCENSORFLOOD) )
+ {
+ Q_strncpyz( out, in, len );
+ return;
+ }
+
+ len--;
+ while( *in )
+ {
+ if( Q_IsColorString( in ) )
+ {
+ if( len < 2 )
+ break;
+ *out++ = *in++;
+ *out++ = *in++;
+ len -= 2;
+ continue;
+ }
+ if( !isalnum( *in ) )
+ {
+ if( len < 1 )
+ break;
+ *out++ = *in++;
+ len--;
+ continue;
+ }
+ m = censors;
+ for( i = 0; i < numcensors; i++, m++ )
+ {
+ s = in;
+ while( *s && *m )
+ {
+ if( Q_IsColorString( s ) )
+ {
+ s += 2;
+ continue;
+ }
+ if( !isalnum( *s ) )
+ {
+ s++;
+ continue;
+ }
+ if( tolower( *s ) != *m )
+ break;
+ s++;
+ m++;
+ }
+ // match
+ if( !*m )
+ {
+ in = s;
+ m++;
+ while( *m )
+ {
+ if( len < 1 )
+ break;
+ *out++ = *m++;
+ len--;
+ }
+ break;
+ }
+ else
+ {
+ while( *m )
+ m++;
+ m++;
+ while( *m )
+ m++;
+ }
+ }
+ if( len < 1 )
+ break;
+ // no match
+ if( i == numcensors )
+ {
+ *out++ = *in++;
+ len--;
+ }
+ }
+ *out = 0;
+}
/*
==================
@@ -720,7 +866,7 @@ void G_Say( gentity_t *ent, saymode_t mode, const char *chatText )
break;
}
- Q_strncpyz( text, chatText, sizeof( text ) );
+ G_CensorString( text, chatText, sizeof( text ), ent );
// send it to all the apropriate clients
for( j = 0; j < level.maxclients; j++ )
@@ -807,6 +953,7 @@ Cmd_VSay_f
void Cmd_VSay_f( gentity_t *ent )
{
char arg[MAX_TOKEN_CHARS];
+ char text[ MAX_TOKEN_CHARS ];
voiceChannel_t vchan;
voice_t *voice;
voiceCmd_t *cmd;
@@ -900,6 +1047,7 @@ void Cmd_VSay_f( gentity_t *ent )
// optional user supplied text
trap_Argv( 2, arg, sizeof( arg ) );
+ G_CensorString( text, arg, sizeof( text ), ent );
switch( vchan )
{
@@ -907,12 +1055,12 @@ void Cmd_VSay_f( gentity_t *ent )
case VOICE_CHAN_LOCAL:
trap_SendServerCommand( -1, va(
"voice %d %d %d %d \"%s\"\n",
- ent-g_entities, vchan, cmdNum, trackNum, arg ) );
+ ent-g_entities, vchan, cmdNum, trackNum, text ) );
break;
case VOICE_CHAN_TEAM:
G_TeamCommand( ent->client->pers.teamSelection, va(
"voice %d %d %d %d \"%s\"\n",
- ent-g_entities, vchan, cmdNum, trackNum, arg ) );
+ ent-g_entities, vchan, cmdNum, trackNum, text ) );
break;
default:
break;
@@ -3035,6 +3183,7 @@ void Cmd_PrivateMessage_f( gentity_t *ent )
char name[ MAX_NAME_LENGTH ];
char cmd[ 12 ];
char str[ MAX_STRING_CHARS ];
+ char text[ MAX_STRING_CHARS ];
char *msg;
char color;
int i, pcount;
@@ -3073,12 +3222,14 @@ void Cmd_PrivateMessage_f( gentity_t *ent )
Com_sprintf( str, sizeof( str ), "^%csent to %i player%s", color, count,
( count == 1 ) ? "" : "s" );
+ G_CensorString( text, msg, sizeof( text ), ent );
+
if( !count )
ADMP( va( "^3No player matching ^7\'%s^7\' ^3to send message to.\n",
name ) );
else
{
- ADMP( va( "^%cPrivate message: ^7%s\n", color, msg ) );
+ ADMP( va( "^%cPrivate message: ^7%s\n", color, text ) );
ADMP( va( "%s\n", str ) );
G_LogPrintf( "%s: %d \"%s" S_COLOR_WHITE "\" \"%s\": ^%c%s\n",