mirror of
https://git.code.sf.net/p/quake/newtree
synced 2024-11-21 19:51:18 +00:00
cvars and cvar alias now use a hash table for lookups. commands and aliases
coming soon :)
This commit is contained in:
parent
365ece328b
commit
381f5b6df4
9 changed files with 249 additions and 18 deletions
|
@ -97,5 +97,8 @@
|
|||
/* Define this if fnmatch is prototyped in fnmatch.h */
|
||||
#undef HAVE_FNMATCH_PROTO
|
||||
|
||||
/* Define this to something appropriate for declaring 0 length arrays */
|
||||
#undef ZERO_LENGTH_ARRAY
|
||||
|
||||
@BOTTOM@
|
||||
#endif // __config_h_
|
||||
|
|
|
@ -152,6 +152,13 @@ AC_TRY_COMPILE(
|
|||
AC_MSG_RESULT(no)
|
||||
)
|
||||
|
||||
AC_MSG_CHECKING(for zero length array syntax)
|
||||
AC_TRY_COMPILE(
|
||||
[],
|
||||
[int foo[0];],
|
||||
AC_DEFINE(ZERO_LENGTH_ARRAY,0) AC_MSG_RESULT([0]),
|
||||
AC_DEFINE(ZERO_LENGTH_ARRAY,) AC_MSG_RESULT([])
|
||||
)
|
||||
|
||||
dnl ==================================================================
|
||||
dnl Checks for library functions.
|
||||
|
|
|
@ -118,6 +118,7 @@ void Cvar_WriteVariables (QFile *f);
|
|||
// Returns a pointer to the Cvar, NULL if not found
|
||||
cvar_t *Cvar_FindVar (char *var_name);
|
||||
|
||||
void Cvar_Init_Hash (void);
|
||||
void Cvar_Init();
|
||||
|
||||
void Cvar_Shutdown();
|
||||
|
|
54
include/hash.h
Normal file
54
include/hash.h
Normal file
|
@ -0,0 +1,54 @@
|
|||
/*
|
||||
hash.h
|
||||
|
||||
hash tables
|
||||
|
||||
Copyright (C) 1996-1997 Id Software, Inc.
|
||||
Copyright (C) 2000 Marcus Sundberg <mackan@stacken.kth.se>
|
||||
|
||||
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:
|
||||
|
||||
Free Software Foundation, Inc.
|
||||
59 Temple Place - Suite 330
|
||||
Boston, MA 02111-1307, USA
|
||||
|
||||
$Id$
|
||||
*/
|
||||
|
||||
#ifndef __hash_h
|
||||
#define __hash_h
|
||||
|
||||
#include <stdlib.h> // should be sys/types.h, but bc is stupid
|
||||
|
||||
typedef struct hashlink_s {
|
||||
struct hashlink_s *next;
|
||||
struct hashlink_s **prev;
|
||||
void *data;
|
||||
} hashlink_t;
|
||||
|
||||
typedef struct hashtab_s {
|
||||
size_t tab_size;
|
||||
char *(*get_key)(void*);
|
||||
void (*free_ele)(void*);
|
||||
hashlink_t *tab[ZERO_LENGTH_ARRAY];
|
||||
} hashtab_t;
|
||||
|
||||
hashtab_t *Hash_NewTable (int tsize, char *(*gk)(void*), void (*f)(void*));
|
||||
void Hash_DelTable (hashtab_t *tab);
|
||||
int Hash_Add (hashtab_t *tab, void *ele);
|
||||
void *Hash_Find (hashtab_t *tab, const char *key);
|
||||
int Hash_Del (hashtab_t *tab, const char *key);
|
||||
|
||||
#endif // __hash_h
|
|
@ -45,7 +45,8 @@ noinst_LIBRARIES= libqfcd.a libqfjs.a libqfsnd.a libqfsys_cl.a libqfsys_sv.a
|
|||
if ASM_ARCH
|
||||
math_ASM = math.S sys_x86.S
|
||||
endif
|
||||
common_SOURCES= buildnum.c checksum.c cmd.c com.c crc.c cvar.c info.c link.c \
|
||||
common_SOURCES= buildnum.c checksum.c cmd.c com.c crc.c cvar.c hash.c \
|
||||
info.c link.c \
|
||||
locs.c mathlib.c mdfour.c model.c model_brush.c msg.c \
|
||||
net_chan.c net_com.c net_udp.c pmove.c pmovetst.c qargs.c \
|
||||
qendian.c quakefs.c quakeio.c sizebuf.c va.c zone.c \
|
||||
|
|
|
@ -1641,6 +1641,7 @@ Host_Init (void)
|
|||
Sys_Error ("Only %4.1f megs of memory reported, can't execute game",
|
||||
host_parms.memsize / (float) 0x100000);
|
||||
|
||||
Cvar_Init_Hash ();
|
||||
Memory_Init (host_parms.membase, host_parms.memsize);
|
||||
Cvar_Init ();
|
||||
Sys_Init_Cvars ();
|
||||
|
|
|
@ -45,6 +45,7 @@
|
|||
#include "commdef.h"
|
||||
#include "cvar.h"
|
||||
#include "console.h"
|
||||
#include "hash.h"
|
||||
#include "qargs.h"
|
||||
#include "cmd.h"
|
||||
#include "commdef.h"
|
||||
|
@ -53,6 +54,8 @@ cvar_t *cvar_vars;
|
|||
char *cvar_null_string = "";
|
||||
extern cvar_t *developer;
|
||||
cvar_alias_t *calias_vars;
|
||||
hashtab_t *cvar_hash;
|
||||
hashtab_t *calias_hash;
|
||||
|
||||
/*
|
||||
============
|
||||
|
@ -62,13 +65,7 @@ Cvar_FindVar
|
|||
cvar_t *
|
||||
Cvar_FindVar (char *var_name)
|
||||
{
|
||||
cvar_t *var;
|
||||
|
||||
for (var = cvar_vars; var; var = var->next)
|
||||
if (!strcmp (var_name, var->name))
|
||||
return var;
|
||||
|
||||
return NULL;
|
||||
return (cvar_t*)Hash_Find (cvar_hash, var_name);
|
||||
}
|
||||
|
||||
cvar_t *
|
||||
|
@ -76,10 +73,10 @@ Cvar_FindAlias (char *alias_name)
|
|||
{
|
||||
cvar_alias_t *alias;
|
||||
|
||||
for (alias = calias_vars; alias; alias = alias->next)
|
||||
if (!strcmp (alias_name, alias->name))
|
||||
alias = (cvar_alias_t*)Hash_Find (calias_hash, alias_name);
|
||||
if (alias)
|
||||
return alias->cvar;
|
||||
return NULL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -104,6 +101,7 @@ Cvar_Alias_Get (char *name, cvar_t *cvar)
|
|||
calias_vars = alias;
|
||||
alias->name = strdup (name);
|
||||
alias->cvar = cvar;
|
||||
Hash_Add (calias_hash, alias);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -206,8 +204,7 @@ Cvar_Set (cvar_t *var, char *value)
|
|||
|
||||
free (var->string); // free the old value string
|
||||
|
||||
var->string = malloc (strlen (value) + 1);
|
||||
strcpy (var->string, value);
|
||||
var->string = strdup (value);
|
||||
var->value = atof (var->string);
|
||||
var->int_val = atoi (var->string);
|
||||
|
||||
|
@ -228,8 +225,7 @@ Cvar_SetROM (cvar_t *var, char *value)
|
|||
|
||||
free (var->string); // free the old value string
|
||||
|
||||
var->string = malloc (strlen (value) + 1);
|
||||
strcpy (var->string, value);
|
||||
var->string = strdup (value);
|
||||
var->value = atof (var->string);
|
||||
var->int_val = atoi (var->string);
|
||||
|
||||
|
@ -430,6 +426,44 @@ Cvar_CvarList_f (void)
|
|||
Con_Printf ("------------\n%d variables\n", i);
|
||||
}
|
||||
|
||||
static void
|
||||
cvar_free (void *c)
|
||||
{
|
||||
cvar_t *cvar = (cvar_t*)c;
|
||||
free (cvar->name);
|
||||
free (cvar->string);
|
||||
free (cvar);
|
||||
}
|
||||
|
||||
static char *
|
||||
cvar_get_key (void *c)
|
||||
{
|
||||
cvar_t *cvar = (cvar_t*)c;
|
||||
return cvar->name;
|
||||
}
|
||||
|
||||
static void
|
||||
calias_free (void *c)
|
||||
{
|
||||
cvar_alias_t *calias = (cvar_alias_t*)c;
|
||||
free (calias->name);
|
||||
free (calias);
|
||||
}
|
||||
|
||||
static char *
|
||||
calias_get_key (void *c)
|
||||
{
|
||||
cvar_alias_t *calias = (cvar_alias_t*)c;
|
||||
return calias->name;
|
||||
}
|
||||
|
||||
void
|
||||
Cvar_Init_Hash (void)
|
||||
{
|
||||
cvar_hash = Hash_NewTable (1021, cvar_get_key, cvar_free);
|
||||
calias_hash = Hash_NewTable (1021, calias_get_key, calias_free);
|
||||
}
|
||||
|
||||
void
|
||||
Cvar_Init (void)
|
||||
{
|
||||
|
@ -486,12 +520,12 @@ Cvar_Get (char *name, char *string, int cvarflags, char *description)
|
|||
v->next = cvar_vars;
|
||||
cvar_vars = v;
|
||||
v->name = strdup (name);
|
||||
v->string = malloc (strlen (string) + 1);
|
||||
strcpy (v->string, string);
|
||||
v->string = strdup (string);
|
||||
v->flags = cvarflags;
|
||||
v->description = description;
|
||||
v->value = atof (v->string);
|
||||
v->int_val = atoi (v->string);
|
||||
Hash_Add (cvar_hash, v);
|
||||
} else {
|
||||
// Cvar does exist, so we update the flags and return.
|
||||
v->flags &= ~CVAR_USER_CREATED;
|
||||
|
|
129
source/hash.c
Normal file
129
source/hash.c
Normal file
|
@ -0,0 +1,129 @@
|
|||
/*
|
||||
hash.h
|
||||
|
||||
hash tables
|
||||
|
||||
Copyright (C) 1996-1997 Id Software, Inc.
|
||||
Copyright (C) 2000 Marcus Sundberg <mackan@stacken.kth.se>
|
||||
|
||||
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:
|
||||
|
||||
Free Software Foundation, Inc.
|
||||
59 Temple Place - Suite 330
|
||||
Boston, MA 02111-1307, USA
|
||||
|
||||
$Id$
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#include "compat.h"
|
||||
#include "hash.h"
|
||||
|
||||
static unsigned long
|
||||
hash (const char *str)
|
||||
{
|
||||
unsigned long h = 0;
|
||||
while (*str) {
|
||||
h = (h << 4) + (unsigned char)*str++;
|
||||
if (h&0xf0000000)
|
||||
h = (h ^ (h >> 24)) & 0xfffffff;
|
||||
}
|
||||
return h;
|
||||
}
|
||||
|
||||
hashtab_t *
|
||||
Hash_NewTable (int tsize, char *(*gk)(void*), void (*f)(void*))
|
||||
{
|
||||
hashtab_t *tab = calloc (1, (size_t)&((hashtab_t*)0)->tab[tsize]);
|
||||
if (!tab)
|
||||
return 0;
|
||||
tab->tab_size = tsize;
|
||||
tab->get_key = gk;
|
||||
tab->free_ele = f;
|
||||
return tab;
|
||||
}
|
||||
|
||||
void
|
||||
Hash_DelTable (hashtab_t *tab)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < tab->tab_size; i++) {
|
||||
while (tab->tab[i]) {
|
||||
hashlink_t *t = tab->tab[i]->next;
|
||||
if (tab->free_ele)
|
||||
tab->free_ele (&tab->tab[i]->data);
|
||||
free (tab->tab[i]);
|
||||
tab->tab[i] = t;
|
||||
}
|
||||
}
|
||||
free (tab);
|
||||
}
|
||||
|
||||
int
|
||||
Hash_Add (hashtab_t *tab, void *ele)
|
||||
{
|
||||
unsigned long h = hash (tab->get_key(ele));
|
||||
size_t ind = h % tab->tab_size;
|
||||
hashlink_t *lnk = malloc (sizeof (hashlink_t));
|
||||
|
||||
if (!lnk)
|
||||
return -1;
|
||||
if (tab->tab[ind])
|
||||
tab->tab[ind]->prev = &lnk->next;
|
||||
lnk->next = tab->tab[ind];
|
||||
lnk->prev = &tab->tab[ind];
|
||||
lnk->data = ele;
|
||||
tab->tab[ind] = lnk;
|
||||
return 0;
|
||||
}
|
||||
|
||||
void *
|
||||
Hash_Find (hashtab_t *tab, const char *key)
|
||||
{
|
||||
unsigned long h = hash (key);
|
||||
size_t ind = h % tab->tab_size;
|
||||
hashlink_t *lnk = tab->tab[ind];
|
||||
|
||||
while (lnk) {
|
||||
if (strequal (key, tab->get_key (lnk->data)))
|
||||
return lnk->data;
|
||||
lnk = lnk->next;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
Hash_Del (hashtab_t *tab, const char *key)
|
||||
{
|
||||
unsigned long h = hash (key);
|
||||
size_t ind = h % tab->tab_size;
|
||||
hashlink_t *lnk = tab->tab[ind];
|
||||
|
||||
while (lnk) {
|
||||
if (strequal (key, tab->get_key (lnk->data))) {
|
||||
if (lnk->next)
|
||||
lnk->next->prev = lnk->prev;
|
||||
*lnk->prev = lnk->next;
|
||||
free (lnk);
|
||||
return 0;
|
||||
}
|
||||
lnk = lnk->next;
|
||||
}
|
||||
return -1;
|
||||
}
|
|
@ -1867,6 +1867,7 @@ SV_Init (void)
|
|||
SV_Error ("Only %4.1f megs of memory reported, can't execute game",
|
||||
host_parms.memsize / (float) 0x100000);
|
||||
|
||||
Cvar_Init_Hash ();
|
||||
Memory_Init (host_parms.membase, host_parms.memsize);
|
||||
Cvar_Init ();
|
||||
Sys_Init_Cvars ();
|
||||
|
|
Loading…
Reference in a new issue