/*
#ident "@(#)smail/src:RELEASE-3_2_0_121:list.c,v 1.13 2005/07/11 19:22:09 woods Exp"
*/
/*
* Copyright (C) 1987, 1988 Ronald S. Karr and Landon Curt Noll
* Copyright (C) 1992 Ronald S. Karr
*
* See the file COPYING, distributed with smail, for restriction
* and warranty information.
*/
/*
* list.c:
*
* external functions: add_intlist, remove_intlist_matching, remove_intlist_at
*/
#include "defs.h"
#include <sys/types.h>
#include <stdio.h>
#ifdef STDC_HEADERS
# include <stdlib.h>
# include <stddef.h>
#else
# ifdef HAVE_STDLIB_H
# include <stdlib.h>
# endif
#endif
#ifdef HAVE_STRING_H
# if !defined(STDC_HEADERS) && defined(HAVE_MEMORY_H)
# include <memory.h>
# endif
# include <string.h>
#endif
#ifdef HAVE_STRINGS_H
# include <strings.h>
#endif
#ifdef __STDC__
# include <stdarg.h>
#else
# include <varargs.h>
#endif
#if defined(HAVE_UNISTD_H)
# include <unistd.h>
#endif
#include "smail.h"
#include "smailstring.h"
#include "addr.h" /* for "log.h" */
#include "exitcodes.h"
#include "log.h"
#include "main.h"
#include "alloc.h"
#include "list.h"
#include "debug.h"
#include "smailport.h"
/*
* add_intlist - add a (long int) value to a list of (long int) values
*
* Look through the list headed by lp for unused entries and record the given
* value in the data field of the list note. If no unused entry is found then
* add a new entry to the head of the list and use it.
*
* Returns the (possibly new) head of the list.
*/
intlist_t *
add_intlist(lp, val)
intlist_t *lp;
long int val;
{
register intlist_t *nc;
for (nc = lp; nc; nc = nc->succ) {
if (!nc->i_used) {
nc->i_val = val; /* store it here */
nc->i_used = TRUE; /* mark this one re-used */
return lp; /* return old header */
}
}
/*
* no unused entries -- add a new one to the head of the list
*/
nc = (intlist_t *) xmalloc(sizeof(intlist_t)); /* create it */
nc->i_val = val; /* store it */
nc->i_used = TRUE; /* mark it used */
nc->succ = lp; /* link it in at the head */
return nc; /* return new list header */
}
/*
* remove_intlist_matching - remove an item from a list of (long int) values
*
* We don't bother actually try to free allocated list nodes -- instead we just
* mark entries as "unused". First match wins, but we assume the values stored
* to be unique.
*
* Returns TRUE if the item was found in the list, FALSE otherwise.
*/
int
remove_intlist_matching(lp, val)
register intlist_t *lp;
register long int val;
{
register intlist_t *nc;
for (nc = lp; nc; nc = nc->succ) {
if (nc->i_used && nc->i_val == val) {
nc->i_used = FALSE; /* mark this entry unused */
return TRUE;
}
}
/* note this function is called for every child, not just runq's... */
return FALSE;
}
/*
* free_intlist - free up a whole list
*/
void
free_intlist(donelst)
intlist_t *donelst;
{
register intlist_t *cur;
register intlist_t *next;
for (cur = donelst; cur; cur = next) {
next = cur->succ;
xfree((char *) cur);
}
}
/*
* add_charplist - add a char * value to a list of char * values
*
* Returns the (possibly new) head of the list.
*/
charplist_t *
add_charplist(lp, val)
charplist_t *lp;
char *val;
{
register charplist_t *nc;
nc = (charplist_t *) xmalloc(sizeof(charplist_t)); /* create it */
nc->text = val; /* store it */
nc->succ = lp; /* link it in at the head */
return nc; /* return new list header */
}
/*
* free_charplist - free up a whole list, and its values
*/
void
free_charplist(donelst)
charplist_t *donelst;
{
register charplist_t *cur;
register charplist_t *next;
for (cur = donelst; cur; cur = next) {
next = cur->succ;
xfree(cur->text);
xfree((char *) cur);
}
}
/*
* add_voidplist - add a void * value to a list of void * values
*
* Returns the (possibly new) head of the list.
*/
voidplist_t *
add_voidplist(lp, storage, freefn)
voidplist_t *lp;
char *storage;
void (*freefn) __P((void *));
{
register voidplist_t *nc;
nc = (voidplist_t *) xmalloc(sizeof(voidplist_t)); /* create it */
nc->storage = storage; /* store it */
nc->freefn = freefn; /* remember how to free storage */
nc->succ = lp; /* link it in at the head */
return nc; /* return new list header */
}
/*
* free_voidplist - free up a whole list, and its values
*/
void
free_voidplist(donelst)
voidplist_t *donelst;
{
register voidplist_t *cur;
register voidplist_t *next;
for (cur = donelst; cur; cur = next) {
next = cur->succ;
(*(cur->freefn))(cur->storage);
xfree((char *) cur);
}
}
#ifndef NODEBUG
/*
* Some debuggging and diagnostic functions
*/
size_t
count_intlist(lp)
register intlist_t *lp;
{
register intlist_t *nc;
register size_t i = 0;
register size_t j = 0;
for (nc = lp; nc; nc = nc->succ) {
i++;
if (nc->i_used != 0) {
j++;
}
}
DEBUG2(DBG_MAIN_LO, "count_int_list(): found %lu entries, %lu valid numbers\n",
(unsigned long int) i,
(unsigned long int) j);
return i;
}
void
print_intlist(lp)
register intlist_t *lp;
{
register intlist_t *nc;
register size_t i = 0;
int odebug = debug;
debug = DBG_MAIN_LO; /* force the issue */
for (nc = lp; nc; nc = nc->succ) {
i++;
if (nc->i_used != 0) {
DEBUG2(DBG_MAIN_LO, "print_int_list(): lp entry # %lu = %ld\n", (unsigned long int) i, nc->i_val);
}
}
debug = odebug;
return;
}
size_t
count_charplist(lp)
register charplist_t *lp;
{
register charplist_t *nc;
register size_t i = 0;
register size_t j = 0;
for (nc = lp; nc; nc = nc->succ) {
i++;
if (nc->text) {
j++;
}
}
DEBUG2(DBG_MAIN_LO, "count_charp_list(): found %lu entries, %lu valid strings\n",
(unsigned long int) i,
(unsigned long int) j);
return i;
}
void
print_charplist(lp)
register charplist_t *lp;
{
register charplist_t *nc;
register size_t i = 0;
int odebug = debug;
debug = DBG_MAIN_LO; /* force the issue */
for (nc = lp; nc; nc = nc->succ) {
i++;
if (nc->text) {
DEBUG2(DBG_MAIN_LO, "print_charp_list(): lp entry # %lu = '%v'\n", (unsigned long int) i, nc->text);
}
}
debug = odebug;
return;
}
size_t
count_voidplist(lp)
register voidplist_t *lp;
{
register voidplist_t *nc;
register size_t i = 0;
register size_t j = 0;
for (nc = lp; nc; nc = nc->succ) {
i++;
if (nc->storage) {
j++;
}
}
DEBUG2(DBG_MAIN_LO, "count_voidp_list(): found %lu entries, %lu valid strings\n",
(unsigned long int) i,
(unsigned long int) j);
return i;
}
void
print_voidplist(lp)
register voidplist_t *lp;
{
register voidplist_t *nc;
register size_t i = 0;
int odebug = debug;
debug = DBG_MAIN_LO; /* force the issue */
for (nc = lp; nc; nc = nc->succ) {
i++;
if (nc->storage) {
DEBUG2(DBG_MAIN_LO, "print_voidp_list(): lp entry # %lu = '%v'\n", (unsigned long int) i, nc->storage);
}
}
debug = odebug;
return;
}
#endif /* NODEBUG */
/*
* Local Variables:
* c-file-style: "smail"
* End:
*/
syntax highlighted by Code2HTML, v. 0.9.1