/*  This file is part of the program psim.

    Copyright (C) 1994-1996, Andrew Cagney <cagney@highland.com.au>

    This program 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.

    This program 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 <stdio.h>

#include "config.h"

#ifdef HAVE_STRING_H
#include <string.h>
#else
#ifdef HAVE_STRINGS_H
#include <strings.h>
#endif
#endif

#include "misc.h"
#include "lf.h"
#include "filter.h"

struct _filter {
  char *member;
  filter *next;
};


void
filter_parse (filter **filters,
	      const char *filt)
{
  while (strlen (filt) > 0)
    {
      filter *new_filter;
      filter **last;
      /* break out a member of the filter list */
      const char *flag = filt;
      unsigned /*size_t*/ len;
      filt = strchr (filt, ',');
      if (filt == NULL)
	{
	  filt = strchr (flag, '\0');
	  len = strlen (flag);
	}
      else
	{
	  len = filt - flag;
	  filt = filt + 1;
	}
      /* find an insertion point - sorted order */
      last = filters;
      while (*last != NULL
	     && strncmp (flag, (*last)->member, len) > 0)
	last = &(*last)->next;
      if (*last != NULL
	  && strncmp (flag, (*last)->member, len) == 0
	  && strlen ((*last)->member) == len)
	continue; /* duplicate */
      /* create an entry for that member */
      new_filter = ZALLOC (filter);
      new_filter->member = NZALLOC (char, len + 1);
      strncpy (new_filter->member, flag, len);
      /* insert it */
      new_filter->next = *last;
      *last = new_filter;
    }
}


void
filter_add (filter **set,
	    filter *add)
{
  while (add != NULL)
    {
      int cmp;
      if (*set == NULL)
	cmp = 1; /* set->member > add->member */
      else
	cmp = strcmp ((*set)->member, add->member);
      if (cmp > 0)
	{
	  /* insert it here */
	  filter *new = ZALLOC (filter);
	  new->member = NZALLOC (char, strlen (add->member) + 1);
	  strcpy (new->member, add->member);
	  new->next = *set;
	  *set = new;
	  add = add->next;
	}
      else if (cmp == 0)
	{
	  /* already in set */
	  add = add->next;
	}
      else /* cmp < 0 */
	{
	  /* not reached insertion point */
	  set = &(*set)->next;
	}
    }
}


int
filter_is_subset (filter *superset,
		  filter *subset)
{
  while (1)
    {
      int cmp;
      if (subset == NULL)
	return 1;
      if (superset == NULL)
	return 0; /* subset isn't finished */
      cmp = strcmp (subset->member, superset->member);
      if (cmp < 0)
	return 0; /* not found */
      else if (cmp == 0)
	subset = subset->next; /* found */
      else if (cmp > 0)
	superset = superset->next; /* later in list? */
    }
}


int
filter_is_common (filter *l,
		  filter *r)
{
  while (1)
    {
      int cmp;
      if (l == NULL)
	return 0;
      if (r == NULL)
	return 0;
      cmp = strcmp (l->member, r->member);
      if (cmp < 0)
	l = l->next;
      else if (cmp == 0)
	return 1; /* common member */
      else if (cmp > 0)
	r = r->next;
    }
}


int
filter_is_member (filter *filt,
		  const char *flag)
{
  int index = 1;
  while (filt != NULL)
    {
      if (strcmp (flag, filt->member) == 0)
	return index;
      filt = filt->next;
      index++;
    }
  return 0;
}


int
is_filtered_out (filter *filters,
		 const char *flags)
{
  while (strlen(flags) > 0) {
    int present;
    filter *filt = filters;
    /* break the string up */
    char *end = strchr(flags, ',');
    char *next;
    unsigned /*size_t*/ len;
    if (end == NULL) {
      end = strchr(flags, '\0');
      next = end;
    }
    else {
      next = end + 1;
    }
    len = end - flags;
    /* check that it is present */
    present = 0;
    filt = filters;
    while (filt != NULL) {
      if (strncmp(flags, filt->member, len) == 0
	  && strlen(filt->member) == len) {
	present = 1;
	break;
      }
      filt = filt->next;
    }
    if (!present)
      return 1;
    flags = next;
  }
  return 0;
}


#if 0
int
it_is (const char *flag,
       const char *flags)
{
  int flag_len = strlen(flag);
  while (*flags != '\0') {
    if (!strncmp(flags, flag, flag_len)
	&& (flags[flag_len] == ',' || flags[flag_len] == '\0'))
      return 1;
    while (*flags != ',') {
      if (*flags == '\0')
	return 0;
      flags++;
    }
    flags++;
  }
  return 0;
}
#endif


char *
filter_next (filter *set,
	     char *member)
{
  while (set != NULL)
    {
      if (strcmp (set->member, member) > 0)
	return set->member;
      set = set->next;
    }
  return NULL;
}


void
dump_filter (lf *file,
	     char *prefix, 
	     filter *set,
	     char *suffix)
{
  char *member;
  lf_printf (file, "%s", prefix);
  member = filter_next (set, "");
  if (member != NULL)
    {
      while (1)
	{
	  lf_printf (file, "%s", member);
	  member = filter_next (set, member);
	  if (member == NULL)
	    break;
	  lf_printf (file, ",");
	}
    }
  lf_printf (file, "%s", suffix);
}


#ifdef MAIN
int
main(int argc, char **argv)
{
  filter *subset = NULL;
  filter *superset = NULL;
  lf *l;
  int i;
  if (argc < 2) {
    printf("Usage: filter <subset> <filter> ...\n");
    exit (1);
  }

  /* load the filter up */
  filter_parse (&subset, argv[1]);
  for (i = 2; i < argc; i++) 
    filter_parse (&superset, argv[i]);

  /* dump various info */
  l = lf_open ("-", "stdout", lf_omit_references, lf_is_text, "tmp-filter");
#if 0
  if (is_filtered_out (argv[1], superset))
    lf_printf (l, "excluded\n");
  else
    lf_printf (l, "included\n");
#endif
  /* subset */
  {
    dump_filter (l, "{", subset, " }");
    if (filter_is_subset (superset, subset))
      lf_printf (l, " subset of ");
    else
      lf_printf (l, " !subset of ");
    dump_filter (l, "{", superset, " }");
    lf_printf (l, "\n");
  }
  /* intersection */
  {
    dump_filter (l, "{", subset, " }");
    if (filter_is_common (subset, superset))
      lf_printf (l, " intersects ");
    else
      lf_printf (l, " !intersects ");
    dump_filter (l, "{", superset, " }");
    lf_printf (l, "\n");
  }
  /* membership */
  {
    filter *memb = subset;
    while (memb != NULL)
      {
	lf_printf (l, "%s", memb->member);
	if (filter_is_member (superset, memb->member))
	  lf_printf (l, " in ");
	else
	  lf_printf (l, " !in ");
	dump_filter (l, "{", superset, " }");
	lf_printf (l, "\n");
	memb = memb->next;
      }
  }
  /* addition */
  {
    filter *add = NULL;
    filter_add (&add, superset);
    filter_add (&add, subset);
    dump_filter (l, "{", add, " }");
    lf_printf (l, " = ");
    dump_filter (l, "{", subset, " }");
    lf_printf (l, " + ");
    dump_filter (l, "{", superset, " }");
    lf_printf (l, "\n");
  }
      
  return 0;
}
#endif
