// file: grammar_compiler.cc
// 

// isip include files
//
#include "grammar_compiler.h"
#include "grammar_compiler_constants.h"

// Synopsis:
//   grammar_compiler.exe -probablistic -input inputfile -output
//   outputfile
//

// main program
//
int main(int_4 argc, char_1** argv) {
  
  // variables to hold command line parameters
  //
  char_1* input_file = new char_1[ISIP_MAX_STRING_LENGTH];
  char_1* output_file = new char_1[ISIP_MAX_STRING_LENGTH];
  logical_1 probablistic_flag = ISIP_FALSE;
  
  // read and decipher the command line
  //
  read_cmdline_cc(argc, argv, probablistic_flag, input_file, output_file);

  // create a memory manager and set it in the trace linked lists
  //
  Memory_manager* manager = new Memory_manager(GC_DEFAULT_BLOCK_SIZE,
                                               GC_NODE_BLOCK_SIZE);
  Link_list::set_manager_cc(manager);

  // create a hash cell
  //
  Hash_cell** hcells = (Hash_cell**)NULL;
  Hash_cell* next = (Hash_cell*)NULL;
  
  Hash_table* lnode_d = (Hash_table*)NULL;
  Lattice_node* ltn = (Lattice_node*)NULL;
  Word* word = (Word*)NULL;
  
  // node and arc parameters
  //  
  int_4 num_nodes =  (int_4)0;
  int_4 num_arcs = (int_4)0;
  
  // create a lattice
  //
  Lattice* lattice = new Lattice();
  Lattice_node* start_latn = (Lattice_node*)NULL;
  start_latn = create_latnode_cc((char_1*)WRD_NULL, num_nodes, lattice);
  lattice->set_start_node_cc(start_latn);
  Lattice_node* end_latn = (Lattice_node*)NULL;
  
  // read the grammar from file into an array of symobls
  //
  int_4 num = (int_4)0;
  char_1** symbols = (char_1**)NULL;
  symbols = new char_1*[GC_GRAM_MAX_SYMBOL_SIZE];


  int_4 buffer_size = GC_GRAM_MAX_SYMBOL_SIZE*GC_COMMON_SYMBOL_LEN+1;
  char_1* buffer = new char_1[buffer_size];
  read_grammar_cc(symbols, num, input_file, buffer, buffer_size);
  
  // parse the regular expression grammar and build the word graph
  //
  int_4 index = 0;
  logical_1 allprob_flag = ISIP_FALSE;
  build_net_cc(symbols, index, start_latn, end_latn, start_latn,
	       lattice, num_nodes, num_arcs, allprob_flag);
  
  lattice->set_num_nodes_cc(num_nodes);
  lattice->set_num_arcs_cc(num_arcs);
  
  // output the word graph into a lattice file
  //
  FILE* fpo = fopen((char*)output_file, "w");
  if (fpo == (FILE*)NULL) {
    fprintf(stdout, "Cannot open output file %s\n", output_file);
    fprintf(stdout, "output to the stdout\n");
  }
  lattice->write_lattice_cc(fpo, ISIP_TRUE, probablistic_flag, allprob_flag);
  
  fclose(fpo);
  
  // free memory
  //
  delete [] input_file;
  delete [] output_file;
  delete [] buffer;
  delete [] symbols;
  symbols = (char_1**)NULL;

  // get the table pointing to list of lattice nodes
  //
  lnode_d = lattice->get_lnodes_cc();
  hcells = lnode_d->get_cells_cc();
  int_4 hsize = lnode_d->get_size_cc();
  for (int_4 k = 0; k < hsize; k++) {
    for (Hash_cell* lcell = hcells[k]; lcell != (Hash_cell*)NULL;
	 lcell = next) {
      next = lcell->get_next_cc();
      ltn = (Lattice_node*)(lcell->get_item_cc());
      word = ltn->get_word_cc();
      delete word;
      word = (Word*)NULL;
      ltn->clear_cc();
      manager->delete_cc(ltn);
      manager->delete_cc(lcell);
    }
    hcells[k] = (Hash_cell*)NULL;
  }
  
  delete lattice;
  lattice = (Lattice*)NULL;
  delete manager;
  
  // exit gracefully
  //
  exit(ISIP_NO_ERROR);
}
