int add_defined (struct fsm *net, char *string) {
  struct defined *defined, *defined_prev;
  int redefine;

  redefine = 0;
  if (net == NULL) { return 0; }
  fsm_count(net);
  if (defines == NULL) {
    defined = xxmalloc(sizeof(struct defined));
    defines = defined;
    defined->next = NULL;
  } else {
    for (defined = defines; defined != NULL; defined = defined->next) {
      defined_prev = defined;
      if (strcmp(defined->name, string) == 0) {
	redefine = 1;
	break;
      }
    }
    if (redefine == 0) {
      defined_prev->next = xxmalloc(sizeof(struct defined));
      defined = defined_prev->next;
      defined->next = NULL;
    }
  }
  if (redefine) {
      fsm_destroy(defined->net);
      xxfree(defined->name);
  }
  defined->name = xxstrdup(string);
  defined->net = net;
  return(redefine);
}
Beispiel #2
0
int remove_defined(struct defined_networks *def, char *string) {
    struct defined_networks *d, *d_prev, *d_next;
    int exists = 0;
    /* Undefine all */
    if (string == NULL) {
	for (d = def; d != NULL; d = d_next) {
	    d_next = d->next;	    
	    fsm_destroy(d->net);
	    xxfree(d->name);
	}
	return 0;
    }
    d_prev = NULL; 
    for (d = def; d != NULL; d_prev = d, d = d->next) {
	if (d->name != NULL && strcmp(d->name, string) == 0) {
	    exists = 1;
	    break;
	}
    }
    if (exists == 0) {
	return 1;
    }
    if (d == def) {
	if (d->next != NULL) {
	    fsm_destroy(d->net);
	    xxfree(d->name);
	    d->name = d->next->name;
	    d->net = d->next->net;
	    d_next = d->next->next;
	    xxfree(d->next);
	    d->next = d_next;
	} else {
	    fsm_destroy(d->net);
	    xxfree(d->name);
	    d->next = NULL;
	    d->name = NULL;
	}
    } else {
	fsm_destroy(d->net);
	xxfree(d->name);
	d_prev->next = d->next;
	xxfree(d);
    }
    return 0;
}
Beispiel #3
0
void
zs_lex_destroy (zs_lex_t **self_p)
{
    assert (self_p);
    if (*self_p) {
        zs_lex_t *self = *self_p;
        fsm_destroy (&self->fsm);
        free (self);
        *self_p = NULL;
    }
}
int remove_defined (char *string) {
  struct defined *defined, *defined_prev;
  int exists = 0;
  defined_prev = NULL;
  /* Undefine all */
  if (string == NULL) {
      for (defined = defines; defined != NULL; ) {
          fsm_destroy(defined->net);
          defined_prev = defined;
          defined = defined->next;
	  xxfree(defined_prev->name);
          xxfree(defined_prev);
          defines = NULL;
      }
      return(0);
  }
  for (defined = defines; defined != NULL; defined = defined->next) {
      if (strcmp(defined->name, string) == 0) {
          exists = 1;
          break;
      }
      defined_prev = defined;
  }
  if (exists == 0) { 
      //if (mode == 1) printf("*** Error: %s has no network definition.\n", string);
      return 1;
  }
  if (defined_prev != NULL) {
      defined_prev->next = defined->next;
  } else {
      defines = defined->next;
  }
  fsm_destroy(defined->net);
  xxfree(defined->name);
  xxfree(defined);
  return(0);
}
Beispiel #5
0
static ssize_t fsm_exec(CwtFsm *fsm, int state_cur, const void *data, size_t len)
{
	const char *ptr;
	ssize_t nchars_processed;
	size_t nchars_total_processed;
	size_t nchars_total_accepted;
	CwtFsmTransition *trans;
	BOOL accepted;

	ptr = (const char*)data;
	nchars_processed = (ssize_t)-1;
	nchars_total_processed = (size_t)0;
	nchars_total_accepted  = (size_t)0;
	accepted = FALSE;

	trans = &fsm->trans_tab[state_cur];

	CWT_ASSERT(trans);

	do /*while( TRUE )*/ {

		switch( trans->match_type ) {

		case Cwt_Fsm_Match_Nl:
			if (fsm->nl) {
				size_t nl_len = cwt_str_ns()->strLen(fsm->nl);

				if (fsm->exact_char_fn(ptr, CWT_MIN(len, nl_len), fsm->nl, nl_len)) {
					nchars_processed = nl_len;
				}
			} else {
				nchars_processed = 0;
			}
			break;


		case Cwt_Fsm_Match_Seq:
			if( len >= trans->condition.str.len )
				nchars_processed = (ssize_t)trans->condition.str.len;
			break;

		case Cwt_Fsm_Match_Str:
			if( len >= trans->condition.str.len
					&& fsm->exact_char_fn(ptr, CWT_MIN(len, trans->condition.str.len)
					, trans->condition.str.chars, trans->condition.str.len) ) {
				nchars_processed = (ssize_t)trans->condition.str.len;
			}
			break;

		case Cwt_Fsm_Match_Char:
			if( len > 0 && fsm->belong_char_fn(ptr, trans->condition.str.chars, trans->condition.str.len) ) {
				nchars_processed = 1;
			}
			break;

		case Cwt_Fsm_Match_Range:
			if( len > 0 && fsm->range_char_fn(ptr, trans->condition.range.from, trans->condition.range.to) ) {
				nchars_processed = 1;
			}
			break;

		case Cwt_Fsm_Match_Fsm: {
				CwtFsm inner_fsm;
				fsm_reproduce(&inner_fsm, fsm, trans->condition.trans_tab.tab);
				nchars_processed = fsm_exec(&inner_fsm, 0, ptr, len);
				fsm_destroy(&inner_fsm);
			}
			break;

		case Cwt_Fsm_Match_Func:
			nchars_processed = trans->condition.trans_fn.fn(fsm, trans->condition.trans_fn.fn_context, ptr, len);
			break;

		case Cwt_Fsm_Match_Rpt: {
				CwtFsm inner_fsm;

				memcpy(&inner_fsm, fsm, sizeof(inner_fsm));
				inner_fsm.trans_tab = trans->condition.trans_tab.tab;
				nchars_processed = cwt_fsm_repetition(&inner_fsm, trans->condition.trans_tab.bounds, ptr, len);
			}
			break;

		case Cwt_Fsm_Match_Nothing:
			nchars_processed = 0;
			break;
		}

		if( nchars_processed >= 0 ) {
			if( trans->action )
				trans->action(ptr
				, (size_t)(nchars_processed)
				, fsm->context
				, trans->action_args);

			if( trans->status == FSM_ACCEPT ) {
				accepted = TRUE;
			}

			ptr += (fsm->sizeof_char * nchars_processed);
			len -= nchars_processed;
			nchars_total_processed += nchars_processed;

			if( trans->status == FSM_ACCEPT )
				nchars_total_accepted = nchars_total_processed;

			state_cur = trans->state_next;
		} else {
			state_cur = trans->state_fail;

			if( trans->status != FSM_ACCEPT ) {
				accepted = FALSE;
			}

			ptr -= (fsm->sizeof_char * nchars_total_processed);
			len += nchars_total_processed;
			nchars_total_processed = nchars_total_accepted;
		}

		if( state_cur < 0 )
			break;

		trans = &fsm->trans_tab[state_cur];
		nchars_processed = (ssize_t)-1;

		if( trans->status == FSM_REJECT ) {
			if( trans->action )
				trans->action(ptr
				, len
				, fsm->context
				, trans->action_args);

			return (ssize_t)-1;
		}

	} while( TRUE );

	CWT_ASSERT(nchars_total_accepted <= CWT_SSIZE_T_MAX);

	return accepted
			? (ssize_t)nchars_total_accepted
			: (ssize_t)-1;
}
Beispiel #6
0
int main(int argc, char *argv[]) {
    int opt = 1;
    char *infilename, line[LINE_LIMIT], *result, *separator = "\t";
    struct fsm *net;
    //struct apply_handle *ah;
    struct apply_med_handle *medh;
    FILE *INFILE;
    extern g_med_limit;
    extern g_med_cutoff;

    while ((opt = getopt(argc, argv, "l:c:h")) != -1) {
        switch(opt) {
        case 'l':
	   if(atoi(optarg) == 0)
	    {
	     printf("Maximum number of suggestions can not be zero! Using default value (5).\n");
	     //because med search won't terminate with g_med_limit = 0*/
	      break;
	    }
	   else
	   {
	    g_med_limit = atoi(optarg);
	    break;
	   }
        case 'c':
	   g_med_cutoff = atoi(optarg);
	  break;
	case 'h':
	    printf("%s%s\n", usagestring,helpstring);
            exit(0);
	default:
            fprintf(stderr, "%s", usagestring);
            exit(EXIT_FAILURE);
    }}

    infilename = argv[optind];
    net = fsm_read_binary_file(infilename);
    if (net == NULL) {
	fprintf(stderr, "%s: %s\n", "File error", infilename);
	exit(EXIT_FAILURE);
    }
    medh = apply_med_init(net);
    INFILE = stdin;
    while (fgets(line, LINE_LIMIT, INFILE) != NULL) {
	line[strcspn(line, "\n")] = '\0'; /* chomp */
	//result = apply_med(medh, line);
	    apply_med_set_heap_max(medh,4194304+1);
	    apply_med_set_med_limit(medh,g_med_limit);
	    apply_med_set_med_cutoff(medh,g_med_cutoff);

	result = apply_med(medh, line);
	    if (result == NULL) {
		printf("???\n");
		printf("%s\n\n", line);
		} 
	    else {
	      printf("%s\n",result);
	      printf("%s\n", apply_med_get_instring(medh));
	      printf("Cost[f]: %i\n\n", apply_med_get_cost(medh));
	    
	      while ((result = apply_med(medh,NULL)) != NULL) {
		printf("%s\n",result);
		printf("%s\n", apply_med_get_instring(medh));
		printf("Cost[f]: %i\n\n", apply_med_get_cost(medh));
		}
	      }
  

    }
    if (medh != NULL) {
	apply_med_clear(medh);
    }
    if (net != NULL) {
	fsm_destroy(net);
    }
    exit(0);
}
Beispiel #7
0
struct fsm *fsm_construct_done(struct fsm_construct_handle *handle) {
    int i, emptyfsm;
    struct fsm *net;
    struct fsm_state_list *sl;
    struct fsm_trans_list *trans, *transnext;
    struct fsm_sigma_hash *sigmahash, *sigmahashnext;

    sl = handle->fsm_state_list;
    if (handle->maxstate == -1 || handle->numfinals == 0 || handle->hasinitial == 0) {
        return(fsm_empty_set());
    }
    fsm_state_init((handle->maxsigma)+1);

    for (i=0, emptyfsm = 1; i <= handle->maxstate; i++) {
        fsm_state_set_current_state(i, (sl+i)->is_final, (sl+i)->is_initial);
	if ((sl+i)->is_initial && (sl+i)->is_final)
	    emptyfsm = 0; /* We want to keep track of if FSM has (a) something outgoing from initial, or (b) initial is final */
        for (trans = (sl+i)->fsm_trans_list; trans != NULL; trans = trans->next) {
	    if ((sl+i)->is_initial)
		emptyfsm = 0;
            fsm_state_add_arc(i, trans->in, trans->out, trans->target, (sl+i)->is_final, (sl+i)->is_initial);
        }
        fsm_state_end_state();
    }
    net = fsm_create("");
    sprintf(net->name, "%X",rand());
    xxfree(net->sigma);
    fsm_state_close(net);
    
    net->sigma = fsm_construct_convert_sigma(handle);
    if (handle->name != NULL) {        
        strncpy(net->name, handle->name, 40);
        xxfree(handle->name);
    } else {
        sprintf(net->name, "%X",rand());
    }

    /* Free transitions */
    for (i=0; i < handle->fsm_state_list_size; i++) {
        trans = (((handle->fsm_state_list)+i)->fsm_trans_list);
        while (trans != NULL) {
            transnext = trans->next;
            xxfree(trans);
            trans = transnext;
        }
    }
    /* Free hash table */
    for (i=0; i < SIGMA_HASH_SIZE; i++) {
        sigmahash = (((handle->fsm_sigma_hash)+i)->next);
        while (sigmahash != NULL) {
            sigmahashnext = sigmahash->next;
            xxfree(sigmahash);
            sigmahash = sigmahashnext;
        }
    }
    xxfree(handle->fsm_sigma_list);
    xxfree(handle->fsm_sigma_hash);
    xxfree(handle->fsm_state_list);
    xxfree(handle);
    sigma_sort(net);
    if (emptyfsm) {
	fsm_destroy(net);
	return(fsm_empty_set());
    }
    return(net);
}
Beispiel #8
0
Datei: io.c Projekt: JSefara/foma
struct fsm *io_net_read(struct io_buf_handle *iobh, char **net_name) {

    char buf[READ_BUF_SIZE];
    struct fsm *net;
    struct fsm_state *fsm;
    
    char *new_symbol;
    int i, items, new_symbol_number, laststate, lineint[5], *cm;
    int extras;
    char last_final = '1';

    if (io_gets(iobh, buf) == 0) {
        return NULL;
    }
    
    net = fsm_create("");

    if (strcmp(buf, "##foma-net 1.0##") != 0) {
	fsm_destroy(net);
        perror("File format error foma!\n");
        return NULL;
    }
    io_gets(iobh, buf);
    if (strcmp(buf, "##props##") != 0) {
        perror("File format error props!\n");
	fsm_destroy(net);
        return NULL;
    }
    /* Properties */
    io_gets(iobh, buf);
    extras = 0;
    sscanf(buf, "%i %i %i %i %i %lld %i %i %i %i %i %i %s", &net->arity, &net->arccount, &net->statecount, &net->linecount, &net->finalcount, &net->pathcount, &net->is_deterministic, &net->is_pruned, &net->is_minimized, &net->is_epsilon_free, &net->is_loop_free, &extras, buf);
    strcpy(net->name, buf);
    *net_name = xxstrdup(buf);
    io_gets(iobh, buf);

    net->is_completed = (extras & 3);
    net->arcs_sorted_in = (extras & 12) >> 2;
    net->arcs_sorted_out = (extras & 48) >> 4;

    /* Sigma */
    while (strcmp(buf, "##sigma##") != 0) { /* Loop until we encounter ##sigma## */
        if (buf[0] == '\0') {
	  printf("File format error at sigma definition!\n");
	  fsm_destroy(net);
	  return NULL;
        }
        io_gets(iobh, buf);
    }

    for (;;) {
        io_gets(iobh, buf);
        if (buf[0] == '#') break;
        if (buf[0] == '\0') continue;
        new_symbol = strstr(buf, " ");
	new_symbol[0] = '\0';
	new_symbol++;
	if (new_symbol[0] == '\0') {
	    sscanf(buf,"%i", &new_symbol_number);
	    sigma_add_number(net->sigma, "\n", new_symbol_number);
	} else {
	    sscanf(buf,"%i", &new_symbol_number);
	    sigma_add_number(net->sigma, new_symbol, new_symbol_number);
	}
    }

    /* States */
    if (strcmp(buf, "##states##") != 0) {
        printf("File format error!\n");
        return NULL;
    }
    net->states = xxmalloc(net->linecount*sizeof(struct fsm_state));
    fsm = net->states;
    laststate = -1;
    for (i=0; ;i++) {
        io_gets(iobh, buf);
        if (buf[0] == '#') break;

        /* scanf is just too slow here */

        //items = sscanf(buf, "%i %i %i %i %i",&lineint[0], &lineint[1], &lineint[2], &lineint[3], &lineint[4]);

        items = explode_line(buf, &lineint[0]);

        switch (items) {
        case 2:
            (fsm+i)->state_no = laststate;
            (fsm+i)->in = lineint[0];
            (fsm+i)->out = lineint[0];
            (fsm+i)->target = lineint[1];
            (fsm+i)->final_state = last_final;
            break;
        case 3:
            (fsm+i)->state_no = laststate;
            (fsm+i)->in = lineint[0];
            (fsm+i)->out = lineint[1];
            (fsm+i)->target = lineint[2];
            (fsm+i)->final_state = last_final;
            break;
        case 4:
            (fsm+i)->state_no = lineint[0];
            (fsm+i)->in = lineint[1];
            (fsm+i)->out = lineint[1];
            (fsm+i)->target = lineint[2];
            (fsm+i)->final_state = lineint[3];
            laststate = lineint[0];
            last_final = lineint[3];
            break;
        case 5:
            (fsm+i)->state_no = lineint[0];
            (fsm+i)->in = lineint[1];
            (fsm+i)->out = lineint[2];
            (fsm+i)->target = lineint[3];
            (fsm+i)->final_state = lineint[4];
            laststate = lineint[0];
            last_final = lineint[4];
            break;
        default:
            printf("File format error\n");
            return NULL;
        }
        if (laststate > 0) {
            (fsm+i)->start_state = 0;
        } else if (laststate == -1) {
            (fsm+i)->start_state = -1;
        } else {
            (fsm+i)->start_state = 1;
        }

    }
    if (strcmp(buf, "##cmatrix##") == 0) {
        cmatrix_init(net);
        cm = net->medlookup->confusion_matrix;
        for (;;) {
            io_gets(iobh, buf);
            if (buf[0] == '#') break;
            sscanf(buf,"%i", &i);
            *cm = i;
            cm++;
        }
    }
    if (strcmp(buf, "##end##") != 0) {
        printf("File format error!\n");
        return NULL;
    }
    return(net);
}
Beispiel #9
0
static struct fsm *fsm_minimize_hop(struct fsm *net) {

    struct e *temp_E;
    struct trans_array *tptr;
    struct trans_list *transitions;
    int i,j,minsym,next_minsym,current_i, stateno, thissize, source;  
    unsigned int tail;

    fsm_count(net);
    if (net->finalcount == 0)  {
	fsm_destroy(net);
	return(fsm_empty_set());
    }

    num_states = net->statecount;
    
    P = NULL;

    /* 
       1. generate the inverse lookup table
       2. generate P and E (partitions, states linked list)
       3. Init Agenda = {Q, Q-F}
       4. Split until Agenda is empty
    */
    
    sigma_to_pairs(net);
    
    init_PE();

    if (total_states == num_states) {
        goto bail;
    }

    generate_inverse(net);


    Agenda_head->index = 0;
    if (Agenda_head->next != NULL)
        Agenda_head->next->index = 0;

    for (Agenda = Agenda_head; Agenda != NULL; ) {
        /* Remove current_w from agenda */
        current_w = Agenda->p;
        current_i = Agenda->index;
        Agenda->p->agenda = NULL;
        Agenda = Agenda->next;

        /* Store current group state number in tmp_group */
        /* And figure out minsym */
        /* If index is 0 we start splitting from the first symbol */
        /* Otherwise we split from where we left off last time */

        thissize = 0;
        minsym = INT_MAX;
        for (temp_E = current_w->first_e; temp_E != NULL; temp_E = temp_E->right) {
            stateno = temp_E - E;
            *(temp_group+thissize) = stateno;
            thissize++;
            tptr = trans_array+stateno;
            /* Clear tails if symloop should start from 0 */
            if (current_i == 0)
                tptr->tail = 0;
            
            tail = tptr->tail;
            transitions = (tptr->transitions)+tail;
            if (tail < tptr->size && transitions->inout < minsym) {
                minsym = transitions->inout;
            }
        }

        for (next_minsym = INT_MAX; minsym != INT_MAX ; minsym = next_minsym, next_minsym = INT_MAX) {

            /* Add states to temp_move */
            for (i = 0, j = 0; i < thissize; i++) {
                tptr = trans_array+*(temp_group+i);
                tail = tptr->tail;
                transitions = (tptr->transitions)+tail;
                while (tail < tptr->size && transitions->inout == minsym) {
                    source = transitions->source;
                    if (*(memo_table+(source)) != mainloop) {
                        *(memo_table+(source)) = mainloop;
                        *(temp_move+j) = source;
                        j++;
                    }
                    tail++;
                    transitions++;
                }
                tptr->tail = tail;
                if (tail < tptr->size && transitions->inout < next_minsym) {
                    next_minsym = transitions->inout;
                }
            }
            if (j == 0) {
                continue;
            }
            mainloop++;
            if (refine_states(j) == 1) {
                break; /* break loop if we split current_w */
            }
        }
        if (total_states == num_states) {
            break;
        }
    }

    net = rebuild_machine(net);

    xxfree(trans_array);
    xxfree(trans_list);

 bail:
    
    xxfree(Agenda_top);
    
    xxfree(memo_table);
    xxfree(temp_move);
    xxfree(temp_group);


    xxfree(finals);
    xxfree(E);
    xxfree(Phead);
    xxfree(single_sigma_array);
    xxfree(double_sigma_array);
    
    return(net);
}
Beispiel #10
0
int main(int argc, char *argv[]) {
    int opt, sortarcs = 1;
    char *infilename;
    struct fsm *net;

    setvbuf(stdout, buffer, _IOFBF, sizeof(buffer));

    while ((opt = getopt(argc, argv, "abhHiI:qs:uw:vx")) != -1) {
        switch(opt) {
        case 'a':
	    apply_alternates = 1;
	    break;
        case 'b':
	    buffered_output = 0;
	    break;
        case 'h':
	    printf("%s%s\n", usagestring,helpstring);
            exit(0);
        case 'i':
	    direction = DIR_DOWN;
	    applyer = &apply_down;
	    break;
        case 'q':
	    sortarcs = 0;
	    break;
	case 'I':
	    if (strcmp(optarg, "f") == 0) {
		index_flag_states = 1;
		index_arcs = 1;
	    } else if (strstr(optarg, "k") != NULL && strstr(optarg,"K") != NULL) {
		/* k limit */
		index_mem_limit = 1024*atoi(optarg);
		index_arcs = 1;
	    } else if (strstr(optarg, "m") != NULL && strstr(optarg,"M") != NULL) {
		/* m limit */
		index_mem_limit = 1024*1024*atoi(optarg);
		index_arcs = 1;
	    } else if (isdigit(*optarg)) {
		index_arcs = 1;
		index_cutoff = atoi(optarg);
	    }
	    break;
	case 's':
	    separator = strdup(optarg);
	    break;
	case 'u':
	    mark_uppercase = 1;
	    if (!setlocale(LC_CTYPE, "")) {
		fprintf(stderr, "Check uppercase flag is on, but can't set locale!\n");
	    }
	    break;
	case 'w':
	    wordseparator = strdup(optarg);
	    break;
        case 'v':
	    printf("cgflookup 1.03 (foma library version %s)\n", fsm_get_library_version_string());
	    exit(0);
	default:
            fprintf(stderr, "%s", usagestring);
            exit(EXIT_FAILURE);
	}
    }
    if (optind == argc) {
	fprintf(stderr, "%s", usagestring);
	exit(EXIT_FAILURE);
    }

    infilename = argv[optind];

    if ((fsrh = fsm_read_binary_file_multiple_init(infilename)) == NULL) {
        perror("File error");
	exit(EXIT_FAILURE);
    }
    chain_head = chain_tail = NULL;

    while ((net = fsm_read_binary_file_multiple(fsrh)) != NULL) {
	numnets++;
	chain_new = xxmalloc(sizeof(struct lookup_chain));	
	if (direction == DIR_DOWN && net->arcs_sorted_in != 1 && sortarcs) {
	    fsm_sort_arcs(net, 1);
	}
	if (direction == DIR_UP && net->arcs_sorted_out != 1 && sortarcs) {
	    fsm_sort_arcs(net, 2);
	}
	chain_new->net = net;
	chain_new->ah = apply_init(net);
	if (direction == DIR_DOWN && index_arcs) {
	    apply_index(chain_new->ah, APPLY_INDEX_INPUT, index_cutoff, index_mem_limit, index_flag_states);
	}
	if (direction == DIR_UP && index_arcs) {
	    apply_index(chain_new->ah, APPLY_INDEX_OUTPUT, index_cutoff, index_mem_limit, index_flag_states);
	}

	chain_new->next = NULL;
	chain_new->prev = NULL;
	if (chain_tail == NULL) {
	    chain_tail = chain_head = chain_new;
	} else if (direction == DIR_DOWN || apply_alternates == 1) {
	    chain_tail->next = chain_new;
	    chain_new->prev = chain_tail;
	    chain_tail = chain_new;
	} else {
	    chain_new->next = chain_head;
	    chain_head->prev = chain_new;
	    chain_head = chain_new;
	}
    }

    if (numnets < 1) {
	fprintf(stderr, "%s: %s\n", "File error", infilename);
	exit(EXIT_FAILURE);
    }

    /* Standard read from stdin */
    line = xxcalloc(LINE_LIMIT, sizeof(char));
    INFILE = stdin;
    while (get_next_line() != NULL) {
	results = 0;
	handle_line(line);
	if (results == 0) {
	    app_print(NULL);
	}
	fprintf(stdout, "%s", wordseparator);
	if (!buffered_output) {
	    fflush(stdout);
	}
    }
    /* Cleanup */
    for (chain_pos = chain_head; chain_pos != NULL; chain_pos = chain_head) {
	chain_head = chain_pos->next;
	if (chain_pos->ah != NULL) {
	    apply_clear(chain_pos->ah);
	}
	if (chain_pos->net != NULL) {
	    fsm_destroy(chain_pos->net);
	}
	xxfree(chain_pos);
    }
    if (line != NULL)
    	xxfree(line);
    exit(0);
}
Beispiel #11
0
int main(int argc, char *argv[]) {
    int opt, sortarcs = 1;
    char *infilename;
    struct fsm *net;

    setvbuf(stdout, buffer, _IOFBF, sizeof(buffer));

    while ((opt = getopt(argc, argv, "abhHiI:qs:SA:P:w:vx")) != -1) {
        switch(opt) {
        case 'a':
	    apply_alternates = 1;
	    break;
        case 'b':
	    buffered_output = 0;
	    break;
        case 'h':
	    printf("%s%s\n", usagestring,helpstring);
            exit(0);
        case 'i':
	    direction = DIR_DOWN;
	    applyer = &apply_down;
	    break;
        case 'q':
	    sortarcs = 0;
	    break;
	case 'I':
	    if (strcmp(optarg, "f") == 0) {
		index_flag_states = 1;
		index_arcs = 1;
	    } else if (strcasestr(optarg, "k") != NULL) {
		/* k limit */
		index_mem_limit = 1024*atoi(optarg);
		index_arcs = 1;
	    } else if (strcasestr(optarg, "m") != NULL) {
		/* m limit */
		index_mem_limit = 1024*1024*atoi(optarg);
		index_arcs = 1;
	    } else if (isdigit(*optarg)) {
		index_arcs = 1;
		index_cutoff = atoi(optarg);
	    }
	    break;
	case 's':
	    separator = strdup(optarg);
	    break;
	case 'S':
	    mode_server = 1;
	    break;
	case 'A':
	    server_address = strdup(optarg);
	    break;
	case 'P':
	    port_number = atoi(optarg);
	    break;
	case 'w':
	    wordseparator = strdup(optarg);
	    break;
        case 'v':
	    printf("flookup 1.02 (foma library version %s)\n", fsm_get_library_version_string());
	    exit(0);
        case 'x':
	    echo = 0;
	    break;
	default:
            fprintf(stderr, "%s", usagestring);
            exit(EXIT_FAILURE);
	}
    }
    if (optind == argc) {
	fprintf(stderr, "%s", usagestring);
	exit(EXIT_FAILURE);
    }

    infilename = argv[optind];

    if ((fsrh = fsm_read_binary_file_multiple_init(infilename)) == NULL) {
        perror("File error");
	exit(EXIT_FAILURE);
    }
    chain_head = chain_tail = NULL;

    while ((net = fsm_read_binary_file_multiple(fsrh)) != NULL) {
	numnets++;
	chain_new = xxmalloc(sizeof(struct lookup_chain));	
	if (direction == DIR_DOWN && net->arcs_sorted_in != 1 && sortarcs) {
	    fsm_sort_arcs(net, 1);
	}
	if (direction == DIR_UP && net->arcs_sorted_out != 1 && sortarcs) {
	    fsm_sort_arcs(net, 2);
	}
	chain_new->net = net;
	chain_new->ah = apply_init(net);
	if (direction == DIR_DOWN && index_arcs) {
	    apply_index(chain_new->ah, APPLY_INDEX_INPUT, index_cutoff, index_mem_limit, index_flag_states);
	}
	if (direction == DIR_UP && index_arcs) {
	    apply_index(chain_new->ah, APPLY_INDEX_OUTPUT, index_cutoff, index_mem_limit, index_flag_states);
	}

	chain_new->next = NULL;
	chain_new->prev = NULL;
	if (chain_tail == NULL) {
	    chain_tail = chain_head = chain_new;
	} else if (direction == DIR_DOWN || apply_alternates == 1) {
	    chain_tail->next = chain_new;
	    chain_new->prev = chain_tail;
	    chain_tail = chain_new;
	} else {
	    chain_new->next = chain_head;
	    chain_head->prev = chain_new;
	    chain_head = chain_new;
	}
    }

    if (numnets < 1) {
	fprintf(stderr, "%s: %s\n", "File error", infilename);
	exit(EXIT_FAILURE);
    }

    if (mode_server) {
	server_init();
	serverstring = xxcalloc(UDP_MAX+1, sizeof(char));
	line = xxcalloc(UDP_MAX+1, sizeof(char));
	addrlen = sizeof(clientaddr);
	for (;;) {
	    numbytes = recvfrom(listen_sd, line, UDP_MAX, 0,(struct sockaddr *)&clientaddr, &addrlen);
	    if (numbytes == -1) {
		perror("recvfrom() failed, aborting");
		break;
	    }
	    line[numbytes] = '\0';
	    line[strcspn(line, "\n\r")] = '\0';
	    fflush(stdout);
	    results = 0;
	    udpsize = 0;
	    serverstring[0] = '\0';
	    handle_line(line);
	    if (results == 0) {
		app_print(NULL);
	    }
	    if (serverstring[0] != '\0') {
		numbytes = sendto(listen_sd, serverstring, strlen(serverstring), 0, (struct sockaddr *)&clientaddr, addrlen);
		if (numbytes < 0) {
		    perror("sendto() failed"); fflush(stdout);
		}
	    }
	}
    } else {
	/* Standard read from stdin */
	line = xxcalloc(LINE_LIMIT, sizeof(char));
	INFILE = stdin;
	while (get_next_line() != NULL) {
	    results = 0;
	    handle_line(line);
	    if (results == 0) {
		app_print(NULL);
	    }
	    fprintf(stdout, "%s", wordseparator);
	    if (!buffered_output) {
		fflush(stdout);
	    }
	}
    }
   /* Cleanup */
    for (chain_pos = chain_head; chain_pos != NULL; chain_pos = chain_head) {
	chain_head = chain_pos->next;
	if (chain_pos->ah != NULL) {
	    apply_clear(chain_pos->ah);
	}
	if (chain_pos->net != NULL) {
	    fsm_destroy(chain_pos->net);
	}
	xxfree(chain_pos);
    }
    if (serverstring != NULL)
	xxfree(serverstring);
    if (line != NULL)
    	xxfree(line);
    exit(0);
}