// b.h                          1048                           3/2/00

// Header file for "b?.c".

// NOTE: This is a somewhat non-standard 32-bit "C" compiler for use
// with the excellent "dos" extender "WDOSX" written by Michael Tippach,
// or with "flat real" mode. ("F" command-line option).
// See the file "b-flat.doc" for more information.

// B is copyright (C) 1998,1999 by Ken Martwick.

// Version 0.40 8/25/99

//  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.

FILE *bsfile;
FILE *code;
FILE *data;
FILE *infile;
FILE *libhead;
FILE *libfile;

struct CVAR                   // structure for variables
     {
     char name[50];           // "real" variable name
     int size;                // 1: byte, 2: word, 3: byte string, 4: int string
     int ptsize;              // ptr "size" 1: byte, 2: word
     int value;               // for byte or word
     int length;              // for byte (or pointer) array
     int isptr;               // set if variable is (32-bit) pointer
     int saved;               // set when written to output file
     int instruc;             // set to "tempsize"if variable is in a structure
     int addbytes;            // byte count to add for structure array
     char text[80];           // for defined byte string
     } cvar[1000], var;
 
struct LOCAL                  // structure for "local" variables
     {
     char name[50];           // name used internally (name + suffix)
     char callname[40];       // "visible" name used in program
     int size;
     int ptsize;
     int isptr;               // set if (char) pointer
     } local[200];

struct LOOP
     {
     char loop_start[50];     // starting label of loop     
     char loopend[50];        // exit label of loop
     char endcode[10][100];   // code for end of loop
     int endcount;            // count of "endcode" lines
     } loop[10];

struct PROTO                  // structure for function prototypes
     {
     char name[40];           // function name
     char callname[5][20];    // param "name" known by function
     int callcount;           // number of calling params
     int callsize[5];         // param size (bytes)
     int entered;             // set when code compiled to program
     int gettail;             // set if function has "argument list"
     int isptr[5];            // set if param is a pointer
     int inuse;               // set if "library" function is called
     int localndx;            // index of first "local" variable
     int libfunc;             // set if "library" function
     int localvar;            // count of "local" variables
     int retsize;             // size of return value (bytes)
     } proto[200];
 
struct TEMPLATE               // structure for structure definiition
     {
     char tempname[50];       // "typedef" name
     int tempsize;            // byte count of entire structure
     int varnum;              // number of variables defined
     char name[25][50];       // variable names
     int size[25];            // variable sizes
     int length[25];          // non-zero for character strings only
     } template[10];

char copy[100];               // copy for parsing
char *iptr[5000];             // pointers for program lines
char *ptr;
char inname[20], libheadname[20], libname[20], outname[20];
char text[100];               // global text string
int lines;                    // source program line count
int lvcount;                  // count of "local" variables
int dcount, foundmain, havereturn, libcount, m, n, pcount, result;
int linecount;                // count of lines in "b" file     
int needlib;                  // show library code needed
int tempcount;                // count of structure definitions
time_t now;                   // for "time stamp"

// Variables for code generation:

char token[50];               // token for isfunc() and isvar()
char subname[50];             // subscript variable name
int codecount, gotcode, infunc, inloop[10], inmain, labelnum, level;
int gotparam;                 // set if parameter(s) in function calls
int inlib;                    // set while libray data is being read
int ostype;                   // target operating system

// Variables for "if-else" code:

char ifexit[10][20];          // exit labels for failed "if" tests
char pastelse[10][20];        // exit labels for successful "if" tests
int inelse[10], inif[10];

// Variables for "switch" sequence:

char casecode[20];            // beginning of code after multiple cases
char exitlabel[20];           // exit after "case" completed
char nextlabel[20];           // label for next "case" test
char swname[50];              // name of variable to test
int indefault[10];            // set if "default" code at "level"
int inswitch[10];             // set if in "switch" sequence at "level"
int multicase;                // set if "sequential" case statements

// Function Prototypes:
 
int begin_function(void);     // start new function
void begin_switch(void);      // set up for "switch" sequence
void call_function(int num);  // code call to specified function
void clear_if(void);          // clear "if-else" variables
void clear_loop(int lvl);     // clear loop structure
void clear_loops(void);       // clear used loop structures
void clear_var(void);         // clear "var" structure
int define_structure(void);   // make structure "template"
void do_add(int size);        // encode addition operation
void do_and(int size);        // encode bitwise "and" operation
void do_assembly(void);       // transfer in-line assembler code
void do_default(void);        // start "default" code
void do_div(int size);        // encode division operation
void do_exit(void);           // write exit code for OS specified
void do_lbreak(int lvl);      // insert "loop" break code
void do_math(int op);         // code math operation with specified variables
void do_mod(int size);        // encode modulus operation
void do_mul(int size);        // encode multipllcation operation
void do_or(int size);         // encode bitwise "or" operation
void do_return(void);         // encode return from function
void do_sbreak(void);         // insert "switch" break code
void do_start(void);          // write "startup" code for OS specified
void do_sub(int size);        // encode subtraction operation
void early_exit(void);        // encode early exit
void end_else(void);          // provide label to bypass "else" code
void end_function(void);      // insert return code for function
void end_if(int lvl);         // exit label for failed "if" test
void end_loop(void);          // "loop" back to start of current loop
void end_switch(void);        // terminate "switch" sequence
int find_function(int retval); // find/call function returning "retval"
int find_local(int fnum);     // find local variable
void free_memory(void);       // free memory allocated by "malloc"
int get_code(void);           // get and translate "C" code
int get_data(void);           // transfer global data to "temp" file
int get_lib_code(void);       // read and translate "library" code
int get_lib_data(void);       // transfer library data to "temp" file
int get_local_data(int func); // enter local data
int get_proto(void);          // get function prototypes
int get_tail(void);           // get "argument list" for "printf()" call
void increment(int inc, int ndx); // increment (or decrement) variable
void init_pointers(void);     // initialise source pointers
int isfunc(void);             // test if "token" is a function
int isop(void);               // return "operation code" if valid operation
void is_saved(void);          // show variable has been saved
int isvar(void);              // test if "token" is a variable
void jump_back(void);         // return to start of loop
int make_structure(void);     // create structure
int next_level(void);         // find next "higher" loop level
void parse_case(void);        // generate "case" test with label
void parse_for(void);         // parse / code "for" loop
void parse_if(void);          // parse / code "if" statement
void parse_math(int num);     // parse "math" code line
void parse_while(void);       // begin "while" loop
void read_lib(void);          // read code in "libfile"
void save_string(void);       // save/point to character string
void setup_parse(void);       // enter code to parse "command tail"
void scopy(char *source, char *dest); // copy string without comments
void shift_left(int size);    // shift variable left
void shift_right(int size);   // shift variable right
int test_and(void);           // test if variable is address
int test_comp(void);          // test "comparison" operator
int test_copy(void);          // test for blank line or comment
int test_star(void);          // test if variable is "starred"
int test_subscript(void);     // test for / get variable subscript

// Definitions for mathematical / logical operations:

#define BADD   1
#define BSUB   2
#define BMUL   3
#define BDIV   4
#define BMOD   5
#define BSHL   6
#define BSHR   7
#define BAND   8
#define BOR    9
#define WADD   11
#define WSUB   12
#define WMUL   13
#define WDIV   14
#define WMOD   15
#define WSHL   16
#define WSHR   17
#define WAND   18
#define WOR    19

// Definitions for comparisons:

#define LT     1
#define LE     2
#define EQ     3
#define NE     4
#define GE     5
#define GT     6
