/* * dlist.c -- double linked list data structure * (C)Copyright 1998, 99 by Hiroshi Takekawa * This file is not part of any package. * * Last Modified: Mon Oct 18 21:28:47 1999. * $Id: dlist.c,v 1.5 1999/10/18 12:29:11 sian Exp $ * * Enfle 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. * * Enfle 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 the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ #include "dlist.h" Dlist * dlist_create(void) { return (Dlist *)calloc(1, sizeof(Dlist)); } int dlist_destroy(Dlist *p, int f) { Dlist_data *t, *tn; for (t = p->top; t != NULL; t = tn) { tn = t->next; if (!dlist_delete(p, t, f)) return 0; } free(p); return 1; } Dlist_data * dlist_add(Dlist *p, void *d) { Dlist_data *t; if ((t = (Dlist_data *)calloc(1, sizeof(Dlist_data))) == NULL) return NULL; t->data = d; if (p->top == NULL) p->top = t; else { p->head->next = t; t->prev = p->head; } p->head = t; p->ndata++; return t; } Dlist_data * dlist_stradd(Dlist *p, char *str) { Dlist_data *t; if (str == NULL) return NULL; if ((t = (Dlist_data *)calloc(1, sizeof(Dlist_data))) == NULL) return NULL; if ((t->data = strdup(str)) == NULL) { free(t); return NULL; } if (p->top == NULL) p->top = t; else { p->head->next = t; t->prev = p->head; } p->head = t; p->ndata++; return t; } static void detach(Dlist *p, Dlist_data *t) { if (t) { if (t->prev == NULL && t->next == NULL) p->top = p->head = NULL; else { if (t->prev) t->prev->next = t->next; else { t->next->prev = NULL; p->top = t->next; } if (t->next) t->next->prev = t->prev; else { t->prev->next = NULL; p->head = t->prev; } } } else fprintf(stderr, "attempt to detach NULL\n"); } int dlist_delete(Dlist *p, Dlist_data *t, int f) { if (p == NULL || t == NULL) return 0; detach(p, t); if (f && t->data != NULL) free(t->data); free(t); p->ndata--; return 1; } int dlist_move_to_top(Dlist *p, Dlist_data *t) { if (p == NULL || t == NULL) return 0; if (p->top == t) return 1; detach(p, t); t->prev = NULL; p->top->prev = t; t->next = p->top; p->top = t; return 1; } Dlist_data * dlist_gettop(Dlist *p) { return p->top; } Dlist_data * dlist_gethead(Dlist *p) { return p->head; } int dlist_getndata(Dlist *p) { return p->ndata; }