#include <ctype.h>
#include <FTreg.h>

#include "al.h"
#include "bool.h"
#include "memory.h"

/*
  typedef char * CHAR_PTR;
  const CHAR_PTR name="SubString"; 
*/

static int Obsolete_warning = 0;


/*------------------*/
static char * parser(s) 
char *s;
{
  char *r, *r2;

  if (Obsolete_warning == 0) {
    Al_warning("The Substring Field Type is obsolescent; use Same-Case-Text\nor Any-Case-Text instead.");
    Obsolete_warning = 1;
  }

  r2=r=(char *)Memory_allocate(strlen(s)+2);
  while (*s != '\0') {
    if (isprint(*s))
      *r++ = *s;
    ++s;
  }
  *r = '\0';
  return r2;
}

/*------------------*/
static char * un_parser(s)
char *s;
{
  char *r;
  r=(char *)Memory_allocate(strlen(s)+2);
  strcpy(r,s);
  return(r);
}

static struct PMNode {
  struct PMNode *succeed;
  struct PMNode *fail;
  char c;
};
/*---------*/ /* ### ### replace with FA code for efficency ### ### */
static int substring_equal(text,pat)
char *pat, *text;
{
  int i, l, LPat;

  LPat=strlen(pat);
  l=strlen(text)-LPat+1;
  if (l<0)
    return(0);
  else {
    for (i=0;i<l;i++) {
      if (strncmp(pat,&(text[i]),LPat)==0) {
	return(1);
      }
    }
  }
  return(0);
}

/*------------------*/
static int IsNonWord(c)
char c;
{
  return (ispunct(c) || isspace(c)) ? 1 : 0 ;
}
/*------------------*/
static int IsWord(c)
char c;
{
  return (isalnum(c)) ? 1 : 0 ;
}


/*---------------------*/
static int substring_word_equal(text,pat)
char *text, *pat;
{
  char *word, c, Tempc;
  int index, TextL, PatL, Space;

  TextL=strlen(text);
  PatL=strlen(pat);
  Space=TextL-PatL;
  if (Space<0) return(0);
  index=0;
  while (IsNonWord(text[index])) index++;
  while (strlen(&(text[index]))>=PatL) {
    Tempc=text[index+PatL];
    text[index+PatL]='\0';
    if (strcmp(pat,&(text[index]))==0) {
      text[index+PatL]=Tempc;
      return(1);
    }
    text[index+PatL]=Tempc;
    while (IsWord(text[index])) index++;
    while (IsNonWord(text[index])) index++;
  }
  return(0);
}

static FieldOpArg fieldOpList[]={
  { "=",substring_equal },
  { "equal",substring_equal },
  { "equals",substring_equal },
  { "word=",substring_word_equal },
  { (char *)NULL, NULL},
};

/*---------------------*/
static char * substring_concat(a,b)  /* ### doesn't free a or b TTD:1 */
char *a,*b;
{
  char *c;
  c=(char *)Memory_allocate(strlen(a)+strlen(b)+2);
  strcpy(c,a);
  c[strlen(a)]='\n';
  strcpy(&(c[strlen(a)]),b);
  return(c);
}

static IndexOpArg indexOpList[]={
  { "^",substring_concat },
  { (char *)NULL,  NULL },
};

static InterFieldOpArg interFieldOpList[]={
  { (char *)NULL, NULL },
};

/*----------------------*/
static void substring_free(data)
char *data;
{
  Memory_free(data);
}


static struct AlFieldTypeRegistry_str  substring_FTrec={
  "SubString",
  parser,
  un_parser,
  fieldOpList,
  indexOpList,
  interFieldOpList,
  substring_free,
};

struct AlFieldTypeRegistry_str  *substring_FTrecptr = &substring_FTrec;
