/* Autoconf patching by David Hedbor, neotron@lysator.liu.se */
/*********************************************************************/
/* file: llist.c - linked-list datastructure */
/* TINTIN III */
/* (T)he K(I)cki(N) (T)ickin D(I)kumud Clie(N)t */
/* coded by peter unold 1992 */
/*********************************************************************/
#ifdef HAVE_STRING_H
#include <string.h>
#else
#ifdef HAVE_STRINGS_H
#include <strings.h>
#endif
#endif
#include "tintin.h"
#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif
void insertnode_list();
int match();
/***************************************/
/* init list - return: ptr to listhead */
/***************************************/
struct listnode *init_list()
{
struct listnode *listhead;
if ((listhead = (struct listnode *) (malloc(sizeof(struct listnode)))) == NULL) {
fprintf(stderr, "couldn't alloc listhead\n");
exit(1);
}
listhead->next = NULL;
return (listhead);
}
/************************************************/
/* kill list - run throught list and free nodes */
/************************************************/
void kill_list(nptr)
struct listnode *nptr;
{
struct listnode *nexttodel;
nexttodel = nptr->next;
free(nptr);
for (nptr = nexttodel; nptr; nptr = nexttodel) {
nexttodel = nptr->next;
free(nptr->left);
free(nptr->right);
free(nptr->pr);
free(nptr);
}
}
/********************************************************************
** This function will clear all lists associated with a session **
********************************************************************/
void kill_all(ses, mode)
struct session *ses;
int mode;
{
switch (mode) {
case END:
if (ses != NULL) {
kill_list(ses->aliases);
kill_list(ses->actions);
kill_list(ses->myvars);
kill_list(ses->highs);
kill_list(ses->subs);
kill_list(ses->antisubs);
kill_list(ses->path);
kill_list(ses->pathdirs);
}
break;
case CLEAN:
if (ses != NULL) {
kill_list(ses->aliases);
kill_list(ses->actions);
kill_list(ses->myvars);
kill_list(ses->highs);
kill_list(ses->subs);
kill_list(ses->antisubs);
kill_list(ses->path);
kill_list(ses->pathdirs);
ses->aliases = init_list();
ses->actions = init_list();
ses->myvars = init_list();
ses->highs = init_list();
ses->subs = init_list();
ses->antisubs = init_list();
ses->path = init_list();
ses->pathdirs = init_list();
tintin_puts("Lists cleared.", ses);
prompt(NULL);
}
else {
tintin_puts("Can't clean the common lists (yet):", NULL);
prompt(NULL);
}
break;
}
}
/***********************************************/
/* make a copy of a list - return: ptr to copy */
/***********************************************/
struct listnode *copy_list(sourcelist, mode)
struct listnode *sourcelist;
{
struct listnode *resultlist;
resultlist = init_list();
while ((sourcelist = sourcelist->next)) {
insertnode_list(resultlist, sourcelist->left, sourcelist->right,
sourcelist->pr, mode);
}
return (resultlist);
}
/*****************************************************************/
/* create a node containing the ltext, rtext fields and stuff it */
/* into the list - in lexicographical order, or by numerical */
/* priority (dependent on mode) - Mods by Joann Ellsworth 2/2/94 */
/*****************************************************************/
void insertnode_list(listhead, ltext, rtext, prtext, mode)
struct listnode *listhead;
char *ltext;
char *rtext;
char *prtext;
int mode;
{
struct listnode *nptr, *nptrlast, *newnode;
if ((newnode = (struct listnode *) (malloc(sizeof(struct listnode)))) == NULL) {
fprintf(stderr, "couldn't malloc listhead");
exit(1);
}
newnode->left = (char *) malloc(strlen(ltext) + 1);
newnode->right = (char *) malloc(strlen(rtext) + 1);
newnode->pr = (char *) malloc(strlen(prtext) + 1);
strcpy(newnode->left, ltext);
strcpy(newnode->right, rtext);
strcpy(newnode->pr, prtext);
nptr = listhead;
switch (mode) {
case PRIORITY:
while ((nptrlast = nptr) && (nptr = nptr->next)) {
if (strcmp(prtext, nptr->pr) < 0) {
newnode->next = nptr;
nptrlast->next = newnode;
return;
}
else if (strcmp(prtext, nptr->pr) == 0) {
while ((nptrlast) && (nptr) &&
(strcmp(prtext, nptr->pr) == 0)) {
if (strcmp(ltext, nptr->left) <= 0) {
newnode->next = nptr;
nptrlast->next = newnode;
return;
}
nptrlast = nptr;
nptr = nptr->next;
}
nptrlast->next = newnode;
newnode->next = nptr;
return;
}
}
nptrlast->next = newnode;
newnode->next = NULL;
return;
break;
case ALPHA:
while ((nptrlast = nptr) && (nptr = nptr->next)) {
if (strcmp(ltext, nptr->left) <= 0) {
newnode->next = nptr;
nptrlast->next = newnode;
return;
}
}
nptrlast->next = newnode;
newnode->next = NULL;
return;
break;
} /* Switch */
}
/*****************************/
/* delete a node from a list */
/*****************************/
/* @@@changed -- perry */
struct listnode *deletenode_list(listhead, nptr)
struct listnode *listhead;
struct listnode *nptr;
{
struct listnode *lastnode = listhead;
while ((listhead = listhead->next)) {
if (listhead == nptr) {
lastnode->next = listhead->next;
free(listhead->left);
free(listhead->right);
free(listhead->pr);
free(listhead);
return lastnode->next;
}
lastnode = listhead;
}
return lastnode;
}
/********************************************************/
/* search for a node containing the ltext in left-field */
/* return: ptr to node on succes / NULL on failure */
/********************************************************/
struct listnode *searchnode_list(listhead, cptr)
struct listnode *listhead;
char *cptr;
{
int i;
while ((listhead = listhead->next)) {
if ((i = strcmp(listhead->left, cptr)) == 0)
return listhead;
/* CHANGED to fix bug when list isn't alphabetically sorted
else if(i>0)
return NULL;
*/
}
return NULL;
}
/********************************************************/
/* search for a node that has cptr as a beginning */
/* return: ptr to node on succes / NULL on failure */
/* Mods made by Joann Ellsworth - 2/2/94 */
/********************************************************/
struct listnode *searchnode_list_begin(listhead, cptr, mode)
struct listnode *listhead;
char *cptr;
int mode;
{
int i;
switch (mode) {
case PRIORITY:
while ((listhead = listhead->next)) {
if ((i = strncmp(listhead->left, cptr, strlen(cptr))) == 0 &&
(*(listhead->left + strlen(cptr)) == ' ' ||
*(listhead->left + strlen(cptr)) == '\0'))
return listhead;
}
return NULL;
break;
case ALPHA:
while ((listhead = listhead->next)) {
if ((i = strncmp(listhead->left, cptr, strlen(cptr))) == 0 &&
(*(listhead->left + strlen(cptr)) == ' ' ||
*(listhead->left + strlen(cptr)) == '\0'))
return listhead;
else if (i > 0)
return NULL;
}
return NULL;
break;
}
}
/************************************/
/* show contens of a node on screen */
/************************************/
void shownode_list(nptr)
struct listnode *nptr;
{
char temp[BUFFER_SIZE];
sprintf(temp, "{%s}={%s}", nptr->left, nptr->right);
tintin_puts2(temp, (struct session *) NULL);
}
void shownode_list_action(nptr)
struct listnode *nptr;
{
char temp[BUFFER_SIZE];
sprintf(temp, "{%s}={%s} @ {%s}", nptr->left, nptr->right, nptr->pr);
tintin_puts2(temp, (struct session *) NULL);
}
/************************************/
/* list contens of a list on screen */
/************************************/
void show_list(listhead)
struct listnode *listhead;
{
if (!listhead)
return;
while ((listhead = listhead->next))
shownode_list(listhead);
}
void show_list_action(listhead)
struct listnode *listhead;
{
if (!listhead)
return;
while ((listhead = listhead->next))
shownode_list_action(listhead);
}
struct listnode *search_node_with_wild(listhead, cptr)
struct listnode *listhead;
char *cptr;
{
while (listhead) {
if (match(cptr, listhead->left))
return listhead;
listhead = listhead->next;
}
return NULL;
}
/* @@@deleted -- perry (unused)
* int check_one_node(text, action)
*/
/*********************************************************************/
/* create a node containint the ltext, rtext fields and place at the */
/* end of a list - as insertnode_list(), but not alphabetical */
/*********************************************************************/
void addnode_list(listhead, ltext, rtext, prtext)
struct listnode *listhead;
char *ltext;
char *rtext;
char *prtext;
{
struct listnode *newnode;
if ((newnode = (struct listnode *) malloc(sizeof(struct listnode))) == NULL) {
fprintf(stderr, "couldn't malloc listhead");
exit(1);
}
newnode->left = (char *) malloc(strlen(ltext) + 1);
newnode->right = (char *) malloc(strlen(rtext) + 1);
newnode->pr = (char *) malloc(strlen(prtext) + 1);
newnode->next = NULL;
strcpy(newnode->left, ltext);
strcpy(newnode->right, rtext);
strcpy(newnode->pr, prtext);
while (listhead->next != NULL)
(listhead = listhead->next);
listhead->next = newnode;
}
int count_list(listhead)
struct listnode *listhead;
{
int count = 0;
struct listnode *nptr;
nptr = listhead;
while (nptr = nptr->next)
++count;
return (count);
}