This commit is contained in:
hyung-hwan 2008-08-27 02:50:12 +00:00
parent b6d38c892a
commit 0590924941
7 changed files with 290 additions and 175 deletions

View File

@ -92,8 +92,8 @@ extern "C" {
ase_dll_t* ase_dll_open ( ase_dll_t* ase_dll_open (
ase_mmgr_t* mmgr /* memory manager */ , ase_mmgr_t* mmgr /* memory manager */ ,
ase_size_t extension /* size of extension area in bytes */, ase_size_t ext /* size of extension area in bytes */,
void (*initializer) (ase_dll_t*) /* extension initializer */ void (*init) (ase_dll_t*) /* extension initializer */
); );
/* /*

View File

@ -1,5 +1,5 @@
/* /*
* $Id: map.h 344 2008-08-22 15:23:09Z baconevi $ * $Id: map.h 345 2008-08-26 08:50:12Z baconevi $
* *
* {License} * {License}
*/ */
@ -43,11 +43,11 @@ typedef int (*ase_map_comper_t) (
ase_size_t klen2 /* the length of a key in bytes */ ase_size_t klen2 /* the length of a key in bytes */
); );
/* pair visitor */ /* pair visitor - should return ASE_MAP_WALK_STOP or ASE_MAP_WALK_FORWARD */
typedef int (*ase_map_walker_t) ( typedef int (*ase_map_walker_t) (
ase_map_t* map, ase_map_t* map /* a map */,
ase_map_pair_t* pair, ase_map_pair_t* pair /* the pointer to a key/value pair */,
void* arg void* arg /* the pointer to user-defined data */
); );
struct ase_map_pair_t struct ase_map_pair_t
@ -85,12 +85,16 @@ struct ase_map_t
ase_map_pair_t** buck; ase_map_pair_t** buck;
/*
void (*freeval) (void* owner,void* val);
*/
void (*sameval) (void* owner, void* vptr, ase_size_t vlen); void (*sameval) (void* owner, void* vptr, ase_size_t vlen);
}; };
/* values that can be returned by ase_map_walker_t */
enum ase_map_walk_t
{
ASE_MAP_WALK_STOP = 0,
ASE_MAP_WALK_FORWARD = 1
};
#define ASE_MAP_COPIER_INLINE ase_map_copyinline #define ASE_MAP_COPIER_INLINE ase_map_copyinline
#define ASE_MAP_KPTR(p) ((p)->kptr) #define ASE_MAP_KPTR(p) ((p)->kptr)
@ -104,13 +108,11 @@ extern "C" {
#endif #endif
/* /*
* Creates a hashed map with a dynamic array bucket and a list of values linked * NAME: create a map
*/ *
/* * DESCRIPTION:
ase_map_t* ase_map_open ( * The ase_map_open() function creates a hashed map with a dynamic array
void* owner, ase_size_t capa, unsigned int factor, * bucket and a list of values linked.
void(*freeval)(void*,void*), void(*sameval)(void*,void*),
ase_mmgr_t* mmgr);
*/ */
ase_map_t* ase_map_open ( ase_map_t* ase_map_open (
ase_mmgr_t* mmgr, ase_mmgr_t* mmgr,
@ -119,30 +121,109 @@ ase_map_t* ase_map_open (
); );
/* destroy a map */ /* destroy a map */
void ase_map_close (ase_map_t* map); void ase_map_close (
ase_map_t* map /* a map */
);
/* clear a map */ /* clear a map */
void ase_map_clear (ase_map_t* map); void ase_map_clear (
ase_map_t* map /* a map */
);
/* get the number of key/value pairs in a map /*
ase_size_t ase_map_getsize (ase_map_t* map); * NAME: specifies how to clone an element
*
* DESCRIPTION:
* A special copier ASE_MAP_COPIER_INLINE is provided. This copier enables
* you to copy the data inline to the internal node. No freeer is invoked
* when the node is freeed.
*
* You may set the copier to ASE_NULL to perform no special operation
* when the data pointer is rememebered.
*/
void ase_map_setcopier (
ase_map_t* map /* a map */,
int id /* ASE_MAP_KEY or ASE_MAP_VAL */,
ase_map_copier_t copier /* a element copier */
);
ase_map_pair_t* ase_map_get ( ase_map_copier_t ase_map_getcopier (
ase_map_t* map /* a map */,
int id /* ASE_MAP_KEY or ASE_MAP_VAL */
);
/*
* NAME: specifies how to destroy an element
*
* DESCRIPTION
* The freeer is called when a node containing the element is destroyed.
*/
void ase_map_setfreeer (
ase_map_t* map /* a map */,
int id /* ASE_MAP_KEY or ASE_MAP_VAL */,
ase_map_freeer_t freeer /* a element freeer */
);
ase_map_freeer_t ase_map_getfreeer (
ase_map_t* map /* a map */,
int id /* ASE_MAP_KEY or ASE_MAP_VAL */
);
ase_map_hasher_t ase_map_gethasher (
ase_map_t* map
);
void ase_map_sethasher (
ase_map_t* map, ase_map_t* map,
ase_map_hasher_t hasher
);
ase_map_comper_t ase_map_getcomper (
ase_map_t* map
);
void ase_map_setcomper (
ase_map_t* map,
ase_map_comper_t comper
);
void* ase_map_getextension (
ase_map_t* map
);
ase_mmgr_t* ase_map_getmmgr (
ase_map_t* map
);
void ase_map_setmmgr (
ase_map_t* map,
ase_mmgr_t* mmgr
);
/* get the number of key/value pairs in a map */
ase_size_t ase_map_getsize (
ase_map_t* map /* a map */
);
/* get the pointer to the pair with a matching key */
ase_map_pair_t* ase_map_get (
ase_map_t* map /* a map */,
const void* kptr, const void* kptr,
ase_size_t klen ase_size_t klen
); );
/* insert or update a pair with a matching key */
ase_map_pair_t* ase_map_put ( ase_map_pair_t* ase_map_put (
ase_map_t* map, ase_map_t* map /* a map */,
const void* kptr, void* kptr /* the pointer to the beginning of a key */,
ase_size_t klen, ase_size_t klen /* the length of the key in bytes */,
void* vptr, void* vptr /* the pointer to the beginning of a value */,
ase_size_t vlen ase_size_t vlen /* the length of the value in bytes */
); );
int ase_map_putx ( int ase_map_putx (
ase_map_t* map, ase_map_t* map /* a map */,
void* kptr, void* kptr,
ase_size_t klen, ase_size_t klen,
void* vptr, void* vptr,
@ -151,25 +232,39 @@ int ase_map_putx (
); );
ase_map_pair_t* ase_map_set ( ase_map_pair_t* ase_map_set (
ase_map_t* map, ase_map_t* map /* a map */,
void* kptr, void* kptr,
ase_size_t klen, ase_size_t klen,
void* vptr, void* vptr,
ase_size_t vlen ase_size_t vlen
); );
/* remove a pair with a matching key */
int ase_map_remove ( int ase_map_remove (
ase_map_t* map, const void* kptr, ase_size_t klen); ase_map_t* map /* a map */,
const void* kptr,
ase_size_t klen
);
/* traverse a map */ /* traverse a map */
int ase_map_walk (ase_map_t* map, ase_map_walker_t walker, void* arg); void ase_map_walk (
ase_map_t* map /* a map */,
ase_map_walker_t walker /* the pointer to the function for each pair */,
void* arg /* a pointer to user-specific data */
);
/* get the pointer to the first pair in the map. */ /* get the pointer to the first pair in the map. */
ase_map_pair_t* ase_map_getfirstpair (ase_map_t* map, ase_size_t* buckno); ase_map_pair_t* ase_map_getfirstpair (
ase_map_t* map /* a map */,
ase_size_t* buckno
);
/* get the pointer to the next pair in the map. */ /* get the pointer to the next pair in the map. */
ase_map_pair_t* ase_map_getnextpair ( ase_map_pair_t* ase_map_getnextpair (
ase_map_t* map, ase_map_pair_t* pair, ase_size_t* buckno); ase_map_t* map /* a map */,
ase_map_pair_t* pair,
ase_size_t* buckno
);
void* ase_map_copyinline (ase_map_t* map, void* dptr, ase_size_t dlen); void* ase_map_copyinline (ase_map_t* map, void* dptr, ase_size_t dlen);

View File

@ -91,8 +91,8 @@ extern "C" {
ase_sll_t* ase_sll_open ( ase_sll_t* ase_sll_open (
ase_mmgr_t* mmgr /* memory manager */ , ase_mmgr_t* mmgr /* memory manager */ ,
ase_size_t extension /* size of extension area in bytes */, ase_size_t ext /* size of extension area in bytes */,
void (*initializer) (ase_sll_t*) /* extension initializer */ void (*init) (ase_sll_t*) /* extension initializer */
); );
/* /*
@ -112,7 +112,7 @@ void ase_sll_clear (
/* /*
* NAME: specifies how to clone an element * NAME: specifies how to clone an element
* *
* DESCRIPTION * DESCRIPTION:
* A special copier ASE_SLL_COPIER_INLINE is provided. This copier enables * A special copier ASE_SLL_COPIER_INLINE is provided. This copier enables
* you to copy the data inline to the internal node. No freeer is invoked * you to copy the data inline to the internal node. No freeer is invoked
* when the node is freeed. * when the node is freeed.

View File

@ -10,10 +10,40 @@
#include <ctype.h> #include <ctype.h>
static ase_bool_t is_upper (ase_cint_t c) { return isupper(c); }
static ase_bool_t is_lower (ase_cint_t c) { return islower(c); }
static ase_bool_t is_alpha (ase_cint_t c) { return isalpha(c); }
static ase_bool_t is_digit (ase_cint_t c) { return isdigit(c); }
static ase_bool_t is_xdigit (ase_cint_t c) { return isxdigit(c); }
static ase_bool_t is_alnum (ase_cint_t c) { return isalnum(c); }
static ase_bool_t is_space (ase_cint_t c) { return isspace(c); }
static ase_bool_t is_print (ase_cint_t c) { return isprint(c); }
static ase_bool_t is_graph (ase_cint_t c) { return isgraph(c); }
static ase_bool_t is_cntrl (ase_cint_t c) { return iscntrl(c); }
static ase_bool_t is_punct (ase_cint_t c) { return ispunct(c); }
ase_bool_t ase_ccls_is (ase_cint_t c, int type) ase_bool_t ase_ccls_is (ase_cint_t c, int type)
{ {
/* TODO: use GetStringTypeW/A for WIN32 to implement these */ /* TODO: use GetStringTypeW/A for WIN32 to implement these */
#error NOT IMPLEMENTED YET.
static ase_bool_t (*f[]) (ase_cint_t) =
{
is_upper,
is_lower,
is_alpha,
is_digit,
is_xdigit,
is_alnum,
is_space,
is_print,
is_graph,
is_cntrl,
is_punct
};
ASE_ASSERTX (type >= ASE_CCLS_UPPER && type <= ASE_CCLS_PUNCT,
"The character type should be one of ase_ccls_type_t values");
return f[type] (c);
} }
ase_cint_t ase_ccls_to (ase_cint_t c, int type) ase_cint_t ase_ccls_to (ase_cint_t c, int type)

View File

@ -8,8 +8,7 @@
#include "mem.h" #include "mem.h"
ase_dll_t* ase_dll_open ( ase_dll_t* ase_dll_open (
ase_mmgr_t* mmgr, ase_size_t extension, ase_mmgr_t* mmgr, ase_size_t ext, void (*init) (ase_dll_t*))
void (*initializer) (ase_dll_t*))
{ {
ase_dll_t* dll; ase_dll_t* dll;
@ -23,13 +22,13 @@ ase_dll_t* ase_dll_open (
if (mmgr == ASE_NULL) return ASE_NULL; if (mmgr == ASE_NULL) return ASE_NULL;
} }
dll = ASE_MMGR_ALLOC (mmgr, ASE_SIZEOF(ase_dll_t) + extension); dll = ASE_MMGR_ALLOC (mmgr, ASE_SIZEOF(ase_dll_t) + ext);
if (dll == ASE_NULL) return ASE_NULL; if (dll == ASE_NULL) return ASE_NULL;
ASE_MEMSET (dll, 0, ASE_SIZEOF(ase_dll_t) + extension); ASE_MEMSET (dll, 0, ASE_SIZEOF(ase_dll_t) + ext);
dll->mmgr = mmgr; dll->mmgr = mmgr;
if (initializer) initializer (dll); if (init) init (dll);
return dll; return dll;
} }

View File

@ -1,5 +1,5 @@
/* /*
* $Id: map.c 344 2008-08-22 15:23:09Z baconevi $ * $Id: map.c 345 2008-08-26 08:50:12Z baconevi $
* *
* {License} * {License}
*/ */
@ -216,6 +216,34 @@ map_t* ase_map_open (mmgr_t* mmgr, size_t ext, void (*init) (map_t*))
return map; return map;
} }
void ase_map_close (map_t* map)
{
ase_map_clear (map);
ASE_MMGR_FREE (map->mmgr, map->buck);
ASE_MMGR_FREE (map->mmgr, map);
}
void ase_map_clear (map_t* map)
{
size_t i;
pair_t* pair, * next;
for (i = 0; i < map->capa; i++)
{
pair = map->buck[i];
while (pair != ASE_NULL)
{
next = ASE_MAP_NEXT(pair);
free_pair (map, pair);
map->size--;
pair = next;
}
map->buck[i] = ASE_NULL;
}
}
copier_t ase_map_getcopier (map_t* map, int id) copier_t ase_map_getcopier (map_t* map, int id)
{ {
ASE_ASSERTX (id == ASE_MAP_KEY || id == ASE_MAP_VAL, ASE_ASSERTX (id == ASE_MAP_KEY || id == ASE_MAP_VAL,
@ -279,34 +307,6 @@ void ase_map_setmmgr (map_t* map, mmgr_t* mmgr)
map->mmgr = mmgr; map->mmgr = mmgr;
} }
void ase_map_close (map_t* map)
{
ase_map_clear (map);
ASE_MMGR_FREE (map->mmgr, map->buck);
ASE_MMGR_FREE (map->mmgr, map);
}
void ase_map_clear (map_t* map)
{
size_t i;
pair_t* pair, * next;
for (i = 0; i < map->capa; i++)
{
pair = map->buck[i];
while (pair != ASE_NULL)
{
next = ASE_MAP_NEXT(pair);
free_pair (map, pair);
map->size--;
pair = next;
}
map->buck[i] = ASE_NULL;
}
}
size_t ase_map_getsize (map_t* map) size_t ase_map_getsize (map_t* map)
{ {
return map->size; return map->size;
@ -323,9 +323,10 @@ pair_t* ase_map_get (
while (pair != ASE_NULL) while (pair != ASE_NULL)
{ {
if (map->comper (map, if (map->comper (map, KPTR(pair), KLEN(pair), kptr, klen) == 0)
KPTR(pair), KLEN(pair), {
kptr, klen) == 0) return pair; return pair;
}
pair = ASE_MAP_NEXT(pair); pair = ASE_MAP_NEXT(pair);
} }
@ -358,9 +359,7 @@ int ase_map_putx (
{ {
next = ASE_MAP_NEXT(pair); next = ASE_MAP_NEXT(pair);
if (map->comper (map, if (map->comper (map, KPTR(pair), KLEN(pair), kptr, klen) == 0)
KPTR(pair), KLEN(pair),
kptr, klen) == 0)
{ {
p = change_pair_val (map, pair, vptr, vlen); p = change_pair_val (map, pair, vptr, vlen);
if (p == ASE_NULL) return -1; /* change error */ if (p == ASE_NULL) return -1; /* change error */
@ -427,9 +426,7 @@ pair_t* ase_map_set (map_t* map,
while (pair != ASE_NULL) while (pair != ASE_NULL)
{ {
if (map->comper (map, if (map->comper (map, KPTR(pair), KLEN(pair), kptr, klen) == 0)
KPTR(pair), KLEN(pair),
kptr, klen) == 0)
{ {
/*TODO: this is wrong... change code .... same way as putx... */ /*TODO: this is wrong... change code .... same way as putx... */
return change_pair_val (map, pair, vptr, vlen); return change_pair_val (map, pair, vptr, vlen);
@ -440,22 +437,6 @@ pair_t* ase_map_set (map_t* map,
return ASE_NULL; return ASE_NULL;
} }
#if 0
pair_t* ase_map_getpair (
map_t* map, const void* kptr, size_t klen,
void** val, size_t* vptr)
{
pair_t* pair;
pair = ase_map_get (map, kptr, klen);
if (pair == ASE_NULL) return ASE_NULL;
if (val) *val = VPTR(pair);
if (vptr) *vptr = VLEN(pair);
return pair;
}
#endif
int ase_map_remove ( int ase_map_remove (
map_t* map, const void* kptr, size_t klen) map_t* map, const void* kptr, size_t klen)
{ {
@ -468,9 +449,7 @@ int ase_map_remove (
while (pair != ASE_NULL) while (pair != ASE_NULL)
{ {
if (map->comper (map, if (map->comper (map, KPTR(pair), KLEN(pair), kptr, klen) == 0)
KPTR(pair), KLEN(pair),
kptr, klen) == 0)
{ {
if (prev == ASE_NULL) if (prev == ASE_NULL)
map->buck[hc] = ASE_MAP_NEXT(pair); map->buck[hc] = ASE_MAP_NEXT(pair);
@ -489,7 +468,7 @@ int ase_map_remove (
return -1; return -1;
} }
int ase_map_walk (map_t* map, walker_t walker, void* arg) void ase_map_walk (map_t* map, walker_t walker, void* arg)
{ {
size_t i; size_t i;
pair_t* pair, * next; pair_t* pair, * next;
@ -501,13 +480,10 @@ int ase_map_walk (map_t* map, walker_t walker, void* arg)
while (pair != ASE_NULL) while (pair != ASE_NULL)
{ {
next = ASE_MAP_NEXT(pair); next = ASE_MAP_NEXT(pair);
/* TODO: ASE_MAP_WALK_STOP ASE_MAP_WALK_FORWARD */ if (walker(map, pair, arg) == ASE_MAP_WALK_STOP) return;
if (walker(map, pair, arg) == -1) return -1;
pair = next; pair = next;
} }
} }
return 0;
} }
pair_t* ase_map_getfirstpair (map_t* map, size_t* buckno) pair_t* ase_map_getfirstpair (map_t* map, size_t* buckno)

View File

@ -7,11 +7,26 @@
#include <ase/cmn/sll.h> #include <ase/cmn/sll.h>
#include "mem.h" #include "mem.h"
ase_sll_t* ase_sll_open ( #define sll_t ase_sll_t
ase_mmgr_t* mmgr, ase_size_t extension, #define node_t ase_sll_node_t
void (*initializer) (ase_sll_t*)) #define copier_t ase_sll_copier_t
#define freeer_t ase_sll_freeer_t
#define walker_t ase_sll_walker_t
#define HEAD(s) ASE_SLL_HEAD(s)
#define TAIL(s) ASE_SLL_TAIL(s)
#define SIZE(s) ASE_SLL_SIZE(s)
#define DPTR(n) ASE_SLL_DPTR(n)
#define DLEN(n) ASE_SLL_DLEN(n)
#define NEXT(n) ASE_SLL_NEXT(n)
#define size_t ase_size_t
#define mmgr_t ase_mmgr_t
sll_t* ase_sll_open (mmgr_t* mmgr, size_t ext, void (*init) (sll_t*))
{ {
ase_sll_t* sll; sll_t* sll;
if (mmgr == ASE_NULL) if (mmgr == ASE_NULL)
{ {
@ -23,220 +38,220 @@ ase_sll_t* ase_sll_open (
if (mmgr == ASE_NULL) return ASE_NULL; if (mmgr == ASE_NULL) return ASE_NULL;
} }
sll = ASE_MMGR_ALLOC (mmgr, ASE_SIZEOF(ase_sll_t) + extension); sll = ASE_MMGR_ALLOC (mmgr, ASE_SIZEOF(sll_t) + ext);
if (sll == ASE_NULL) return ASE_NULL; if (sll == ASE_NULL) return ASE_NULL;
ASE_MEMSET (sll, 0, ASE_SIZEOF(ase_sll_t) + extension); ASE_MEMSET (sll, 0, ASE_SIZEOF(sll_t) + ext);
sll->mmgr = mmgr; sll->mmgr = mmgr;
if (initializer) initializer (sll); if (init) init (sll);
return sll; return sll;
} }
void ase_sll_close (ase_sll_t* sll) void ase_sll_close (sll_t* sll)
{ {
ase_sll_clear (sll); ase_sll_clear (sll);
ASE_MMGR_FREE (sll->mmgr, sll); ASE_MMGR_FREE (sll->mmgr, sll);
} }
void ase_sll_clear (ase_sll_t* sll) void ase_sll_clear (sll_t* sll)
{ {
while (sll->head != ASE_NULL) ase_sll_delete (sll, sll->head); while (HEAD(sll) != ASE_NULL) ase_sll_delete (sll, HEAD(sll));
ASE_ASSERT (sll->tail == ASE_NULL); ASE_ASSERT (TAIL(sll) == ASE_NULL);
} }
void* ase_sll_getextension (ase_sll_t* sll) void* ase_sll_getextension (sll_t* sll)
{ {
return sll + 1; return sll + 1;
} }
ase_mmgr_t* ase_sll_getmmgr (ase_sll_t* sll) mmgr_t* ase_sll_getmmgr (sll_t* sll)
{ {
return sll->mmgr; return sll->mmgr;
} }
void ase_sll_setmmgr (ase_sll_t* sll, ase_mmgr_t* mmgr) void ase_sll_setmmgr (sll_t* sll, mmgr_t* mmgr)
{ {
sll->mmgr = mmgr; sll->mmgr = mmgr;
} }
ase_size_t ase_sll_getsize (ase_sll_t* sll) size_t ase_sll_getsize (sll_t* sll)
{ {
return sll->size; return SIZE(sll);
} }
ase_sll_node_t* ase_sll_gethead (ase_sll_t* sll) node_t* ase_sll_gethead (sll_t* sll)
{ {
return sll->head; return HEAD(sll);
} }
ase_sll_node_t* ase_sll_gettail (ase_sll_t* sll) node_t* ase_sll_gettail (sll_t* sll)
{ {
return sll->tail; return TAIL(sll);
} }
ase_sll_copier_t ase_sll_getcopier (ase_sll_t* sll) copier_t ase_sll_getcopier (sll_t* sll)
{ {
return sll->copier; return sll->copier;
} }
void ase_sll_setcopier (ase_sll_t* sll, ase_sll_copier_t copier) void ase_sll_setcopier (sll_t* sll, copier_t copier)
{ {
sll->copier = copier; sll->copier = copier;
} }
ase_sll_freeer_t ase_sll_getfreeer (ase_sll_t* sll) freeer_t ase_sll_getfreeer (sll_t* sll)
{ {
return sll->freeer; return sll->freeer;
} }
void ase_sll_setfreeer (ase_sll_t* sll, ase_sll_freeer_t freeer) void ase_sll_setfreeer (sll_t* sll, freeer_t freeer)
{ {
sll->freeer = freeer; sll->freeer = freeer;
} }
static ase_sll_node_t* alloc_node (ase_sll_t* sll, void* dptr, ase_size_t dlen) static node_t* alloc_node (sll_t* sll, void* dptr, size_t dlen)
{ {
ase_sll_node_t* n; node_t* n;
if (sll->copier == ASE_NULL) if (sll->copier == ASE_NULL)
{ {
n = ASE_MMGR_ALLOC (sll->mmgr, ASE_SIZEOF(ase_sll_node_t)); n = ASE_MMGR_ALLOC (sll->mmgr, ASE_SIZEOF(node_t));
if (n == ASE_NULL) return ASE_NULL; if (n == ASE_NULL) return ASE_NULL;
n->dptr = dptr; DPTR(n) = dptr;
} }
else if (sll->copier == ASE_SLL_COPIER_INLINE) else if (sll->copier == ASE_SLL_COPIER_INLINE)
{ {
n = ASE_MMGR_ALLOC (sll->mmgr, ASE_SIZEOF(ase_sll_node_t) + dlen); n = ASE_MMGR_ALLOC (sll->mmgr, ASE_SIZEOF(node_t) + dlen);
if (n == ASE_NULL) return ASE_NULL; if (n == ASE_NULL) return ASE_NULL;
ASE_MEMCPY (n + 1, dptr, dlen); ASE_MEMCPY (n + 1, dptr, dlen);
n->dptr = n + 1; DPTR(n) = n + 1;
} }
else else
{ {
n = ASE_MMGR_ALLOC (sll->mmgr, ASE_SIZEOF(ase_sll_node_t)); n = ASE_MMGR_ALLOC (sll->mmgr, ASE_SIZEOF(node_t));
if (n == ASE_NULL) return ASE_NULL; if (n == ASE_NULL) return ASE_NULL;
n->dptr = sll->copier (sll, dptr, dlen); DPTR(n) = sll->copier (sll, dptr, dlen);
if (n->dptr == ASE_NULL) if (DPTR(n) == ASE_NULL)
{ {
ASE_MMGR_FREE (sll->mmgr, n); ASE_MMGR_FREE (sll->mmgr, n);
return ASE_NULL; return ASE_NULL;
} }
} }
n->dlen = dlen; DLEN(n) = dlen;
n->next = ASE_NULL; NEXT(n) = ASE_NULL;
return n; return n;
} }
ase_sll_node_t* ase_sll_insert ( node_t* ase_sll_insert (
ase_sll_t* sll, ase_sll_node_t* pos, void* dptr, ase_size_t dlen) sll_t* sll, node_t* pos, void* dptr, size_t dlen)
{ {
ase_sll_node_t* n = alloc_node (sll, dptr, dlen); node_t* n = alloc_node (sll, dptr, dlen);
if (n == ASE_NULL) return ASE_NULL; if (n == ASE_NULL) return ASE_NULL;
if (pos == ASE_NULL) if (pos == ASE_NULL)
{ {
/* insert at the end */ /* insert at the end */
if (sll->head == ASE_NULL) if (HEAD(sll) == ASE_NULL)
{ {
ASE_ASSERT (sll->tail == ASE_NULL); ASE_ASSERT (TAIL(sll) == ASE_NULL);
sll->head = n; HEAD(sll) = n;
} }
else sll->tail->next = n; else NEXT(TAIL(sll)) = n;
sll->tail = n; TAIL(sll) = n;
} }
else else
{ {
/* insert in front of the positional node */ /* insert in front of the positional node */
n->next = pos; NEXT(n) = pos;
if (pos == sll->head) sll->head = n; if (pos == HEAD(sll)) HEAD(sll) = n;
else else
{ {
/* take note of performance penalty */ /* take note of performance penalty */
ase_sll_node_t* n2 = sll->head; node_t* n2 = HEAD(sll);
while (n2->next != pos) n2 = n2->next; while (NEXT(n2) != pos) n2 = NEXT(n2);
n2->next = n; NEXT(n2) = n;
} }
} }
sll->size++; SIZE(sll)++;
return n; return n;
} }
ase_sll_node_t* ase_sll_pushhead (ase_sll_t* sll, void* data, ase_size_t size) node_t* ase_sll_pushhead (sll_t* sll, void* data, size_t size)
{ {
return ase_sll_insert (sll, sll->head, data, size); return ase_sll_insert (sll, HEAD(sll), data, size);
} }
ase_sll_node_t* ase_sll_pushtail (ase_sll_t* sll, void* data, ase_size_t size) node_t* ase_sll_pushtail (sll_t* sll, void* data, size_t size)
{ {
return ase_sll_insert (sll, ASE_NULL, data, size); return ase_sll_insert (sll, ASE_NULL, data, size);
} }
void ase_sll_delete (ase_sll_t* sll, ase_sll_node_t* pos) void ase_sll_delete (sll_t* sll, node_t* pos)
{ {
if (pos == ASE_NULL) return; /* not a valid node */ if (pos == ASE_NULL) return; /* not a valid node */
if (pos == sll->head) if (pos == HEAD(sll))
{ {
/* it is simple to delete the head node */ /* it is simple to delete the head node */
sll->head = pos->next; HEAD(sll) = NEXT(pos);
if (sll->head == ASE_NULL) sll->tail = ASE_NULL; if (HEAD(sll) == ASE_NULL) TAIL(sll) = ASE_NULL;
} }
else else
{ {
/* but deletion of other nodes has significant performance /* but deletion of other nodes has significant performance
* penalty as it has look for the predecessor of the * penalty as it has look for the predecessor of the
* target node */ * target node */
ase_sll_node_t* n2 = sll->head; node_t* n2 = HEAD(sll);
while (n2->next != pos) n2 = n2->next; while (NEXT(n2) != pos) n2 = NEXT(n2);
n2->next = pos->next; NEXT(n2) = NEXT(pos);
/* update the tail node if necessary */ /* update the tail node if necessary */
if (pos == sll->tail) sll->tail = n2; if (pos == TAIL(sll)) TAIL(sll) = n2;
} }
if (sll->freeer != ASE_NULL) if (sll->freeer != ASE_NULL)
{ {
/* free the actual data */ /* free the actual data */
sll->freeer (sll, pos->dptr, pos->dlen); sll->freeer (sll, DPTR(pos), DLEN(pos));
} }
/* free the node */ /* free the node */
ASE_MMGR_FREE (sll->mmgr, pos); ASE_MMGR_FREE (sll->mmgr, pos);
/* decrement the number of elements */ /* decrement the number of elements */
sll->size--; SIZE(sll)--;
} }
void ase_sll_pophead (ase_sll_t* sll) void ase_sll_pophead (sll_t* sll)
{ {
ase_sll_delete (sll, sll->head); ase_sll_delete (sll, HEAD(sll));
} }
void ase_sll_poptail (ase_sll_t* sll) void ase_sll_poptail (sll_t* sll)
{ {
ase_sll_delete (sll, sll->tail); ase_sll_delete (sll, TAIL(sll));
} }
void ase_sll_walk (ase_sll_t* sll, ase_sll_walker_t walker, void* arg) void ase_sll_walk (sll_t* sll, walker_t walker, void* arg)
{ {
ase_sll_node_t* n = sll->head; node_t* n = HEAD(sll);
while (n != ASE_NULL) while (n != ASE_NULL)
{ {
if (walker(sll,n,arg) == ASE_SLL_WALK_STOP) return; if (walker(sll,n,arg) == ASE_SLL_WALK_STOP) return;
n = n->next; n = NEXT(n);
} }
} }
void* ase_sll_copyinline (ase_sll_t* sll, void* dptr, ase_size_t dlen) void* ase_sll_copyinline (sll_t* sll, void* dptr, size_t dlen)
{ {
/* this is a dummy copier */ /* this is a dummy copier */
return ASE_NULL; return ASE_NULL;