/* lp_lists.c
 * Neil Moore <neil@cs.uky.edu>
 * 30 Mar 1999
 *
 * Part of liblp.  See COPYRIGHT for copyright information.
 */
#include <lp_util.h>
#include <lp_lists.h>


/* Add the rule r to the beginning of a linked list.
 */
void lp_rl_add(struct lp_rlist **list, struct lp_rule *r) 
{
	struct lp_rlist *curr;
	
	lp_assert(list != NULL);
	lp_assert(r != NULL);
	
	curr = lp_malloc(sizeof(struct lp_rlist));
	curr->next = *list;
	curr->rule = r;
	*list = curr;
}


/* Add the atom a to the beginning of a linked list.
 */
void lp_al_add(struct lp_alist **list, struct lp_atom *a) 
{
	struct lp_alist *curr;
	
	lp_assert(list != NULL);
	lp_assert(a != NULL);
	
	curr = lp_malloc(sizeof(struct lp_alist));
	curr->next = *list;
	curr->atom = a;
	*list = curr;
}


/* Add the vertex v to the beginning of a linked list.
 */
void lp_vl_add(struct lp_vlist **list, struct lp_vtx *v) 
{
	struct lp_vlist *curr;
	
	lp_assert(list != NULL);
	lp_assert(v != NULL);
	
	curr = lp_malloc(sizeof(struct lp_vlist));
	curr->next = *list;
	curr->vertex = v;
	*list = curr;
}


/* Remove the first element of a rule list, and return it.  **list is a
 * pointer to the list (a pointer to a pointer to its first node).
 *
 */
struct lp_rule *lp_rl_pop(struct lp_rlist **list) 
{
	struct lp_rlist *old;
	struct lp_rule *r;

	old = *list;
	r = old->rule;
	*list = old->next;
	free(old);

	return r;
}


/* Remove the first element of an atom list, and return it.  **list is a
 * pointer to the list (a pointer to a pointer to its first node).
 *
 */
struct lp_atom *lp_al_pop(struct lp_alist **list) 
{
	struct lp_alist *old;
	struct lp_atom *a;

	old = *list;
	a = old->atom;
	*list = old->next;
	free(old);

	return a;
}


/* Remove the first element of an vertex list, and return it.  **list is a
 * pointer to the list (a pointer to a pointer to its first node).
 *
 */
struct lp_vtx *lp_vl_pop(struct lp_vlist **list) 
{
	struct lp_vlist *old;
	struct lp_vtx *v;

	old = *list;
	v = old->vertex;
	*list = old->next;
	free(old);

	return v;
}


/* Recursively free all memory associated with a linked list.  This
 * function does not free the rules in the list.
 *
 */
void lp_rl_free(struct lp_rlist *l) 
{
	struct lp_rlist *old;
	while(l != NULL) {
		old = l;
		l = l->next;
		free(old);
	}
}


/* Recursively free all memory associated with a linked list.  This
 * function does not free the atoms in the list.
 *
 */
void lp_al_free(struct lp_alist *l) 
{
	struct lp_alist *old;
	while(l != NULL) {
		old = l;
		l = l->next;
		free(old);
	}
}


/* Recursively free all memory associated with a linked list.  This
 * function does not free the vertices in the list.
 *
 */
void lp_vl_free(struct lp_vlist *l) 
{
	struct lp_vlist *old;
	while(l != NULL) {
		old = l;
		l = l->next;
		free(old);
	}
}
