#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "tm.h"
#include "flags.h"
#include "toplev.h"
#include "version.h"
#include "ggc.h"
#include "tree.h"
#include "cgraph.h"
#include "diagnostic.h"
#include "treelang.h"
#include "treetree.h"
#include "opts.h"
#include "options.h"
extern int yyparse (void);
static GTY(()) struct prod_token_parm_item *symbol_table = NULL;
const char *const language_string = "TREELANG - sample front end for GCC ";
void version (void);
extern struct cbl_tree_struct_parse_tree_top* parse_tree_top;
unsigned int option_parser_trace = 0;
unsigned int option_lexer_trace = 0;
static int version_done = 0;
static unsigned int work_nesting_level = 0;
unsigned int
treelang_init_options (unsigned int argc ATTRIBUTE_UNUSED,
const char **argv ATTRIBUTE_UNUSED)
{
return CL_Treelang;
}
int
treelang_handle_option (size_t scode, const char *arg ATTRIBUTE_UNUSED,
int value)
{
enum opt_code code = (enum opt_code) scode;
switch (code)
{
case OPT_v:
if (!version_done)
{
fputs (language_string, stdout);
fputs (version_string, stdout);
fputs ("\n", stdout);
version_done = 1;
}
break;
case OPT_y:
option_lexer_trace = 1;
option_parser_trace = 1;
break;
case OPT_fparser_trace:
option_parser_trace = value;
break;
case OPT_flexer_trace:
option_lexer_trace = value;
break;
default:
gcc_unreachable ();
}
return 1;
}
bool
treelang_init (void)
{
#ifndef USE_MAPPED_LOCATION
input_filename = main_input_filename;
#else
linemap_add (&line_table, LC_ENTER, false, main_input_filename, 1);
#endif
if (!input_filename || input_filename[0] == ' ' || !input_filename[0])
{
if (!version_done)
{
fprintf (stderr, "No input file specified, try --help for help\n");
exit (1);
}
return false;
}
yyin = fopen (input_filename, "r");
if (!yyin)
{
fprintf (stderr, "Unable to open input file %s\n", input_filename);
exit (1);
}
#ifdef USE_MAPPED_LOCATION
linemap_add (&line_table, LC_RENAME, false, "<built-in>", 1);
linemap_line_start (&line_table, 0, 1);
#endif
treelang_init_decl_processing ();
return true;
}
void
treelang_finish (void)
{
fclose (yyin);
}
void
treelang_parse_file (int debug_flag ATTRIBUTE_UNUSED)
{
#ifdef USE_MAPPED_LOCATION
source_location s;
linemap_add (&line_table, LC_RENAME, false, main_input_filename, 1);
s = linemap_line_start (&line_table, 1, 80);
input_location = s;
#else
input_line = 1;
#endif
treelang_debug ();
yyparse ();
cgraph_finalize_compilation_unit ();
#ifdef USE_MAPPED_LOCATION
linemap_add (&line_table, LC_LEAVE, false, NULL, 0);
#endif
cgraph_optimize ();
}
void *
my_malloc (size_t size)
{
void *mem;
mem = ggc_alloc (size);
if (!mem)
{
fprintf (stderr, "\nOut of memory\n");
abort ();
}
memset (mem, 0, size);
return mem;
}
struct prod_token_parm_item*
lookup_tree_name (struct prod_token_parm_item *prod)
{
struct prod_token_parm_item *this;
struct prod_token_parm_item *this_tok;
struct prod_token_parm_item *tok;
sanity_check (prod);
tok = SYMBOL_TABLE_NAME (prod);
sanity_check (tok);
for (this = symbol_table; this; this = this->tp.pro.next)
{
sanity_check (this);
this_tok = this->tp.pro.main_token;
sanity_check (this_tok);
if (tok->tp.tok.length != this_tok->tp.tok.length)
continue;
if (memcmp (tok->tp.tok.chars, this_tok->tp.tok.chars,
this_tok->tp.tok.length))
continue;
if (option_parser_trace)
fprintf (stderr, "Found symbol %s (%i:%i) as %i \n",
tok->tp.tok.chars, LOCATION_LINE (tok->tp.tok.location),
tok->tp.tok.charno, NUMERIC_TYPE (this));
return this;
}
if (option_parser_trace)
fprintf (stderr, "Not found symbol %s (%i:%i) as %i \n",
tok->tp.tok.chars, LOCATION_LINE (tok->tp.tok.location),
tok->tp.tok.charno, tok->type);
return NULL;
}
int
insert_tree_name (struct prod_token_parm_item *prod)
{
struct prod_token_parm_item *tok;
tok = SYMBOL_TABLE_NAME (prod);
sanity_check (prod);
if (lookup_tree_name (prod))
{
error ("%HDuplicate name %q.*s.", &tok->tp.tok.location,
tok->tp.tok.length, tok->tp.tok.chars);
return 1;
}
prod->tp.pro.next = symbol_table;
NESTING_LEVEL (prod) = work_nesting_level;
symbol_table = prod;
return 0;
}
struct prod_token_parm_item *
make_production (int type, struct prod_token_parm_item *main_tok)
{
struct prod_token_parm_item *prod;
prod = my_malloc (sizeof (struct prod_token_parm_item));
prod->category = production_category;
prod->type = type;
prod->tp.pro.main_token = main_tok;
return prod;
}
void
sanity_check (struct prod_token_parm_item *item)
{
switch (item->category)
{
case token_category:
case production_category:
case parameter_category:
break;
default:
gcc_unreachable ();
}
}
#include "gt-treelang-tree1.h"
#include "gtype-treelang.h"