📄 c2asm.cpp
字号:
//It sometimes Happens that even -ve INDICES also points
//to some array element causing PROBLEMS
if(k<0) break;
index=args_identifier[k].binding;
}
return tot_len;
}
int calc_local_offset()
{
int counter=0;
//Chk For LOCAL's which are BINDED to LATEST "func_index"
for(unsigned int i=0;i<syn_identifier.size();i++)
if(syn_identifier[i].binding==func_index)
{
counter+=syn_identifier[i].datatype==0 ? 2 : 4;
syn_identifier[i].offset=counter;
}
return counter;
}
void syntax_box()
{
//Doing Initializations
syn_index=0;
input=tokens[syn_index];
scopecount=0;
scopestack.push(scopecount);
dump.index=-10;
dump.datatype=-10;
dump.whichtable=-10;
program();
//Check whether we've got our End Of Marker
//Yes,End Marker has Arrived,ACCEPT INPUT PROGRAM!
if(input.clas=="error")
{
error<<syn_index+1<<'\t'<<input.clas<<'\t'<<input.index<<'\t'<<scopestack.top()<<endl;
error.close();
//cout<<"\nParser Succeeded";
//cout<<"\nSee \"parser_log.txt\" For Details";
}
//No,End Marker hasn't Arrived,REJECT INPUT PROGRAM!
else
{
error<<syn_index+1<<'\t'<<input.clas<<'\t'<<input.index<<'\t'<<scopestack.top()<<endl;
error.close();
cout<<"\nParser Failed";
cout<<"\nParser has parsed "<< syn_index+1 <<" Tokens\n";
cout<<"See \"parser_log.txt\" For Details\n";
}
//If u wanna See IDENTIFERs LIST with ALL details,Remove Comments from the following Lines
/*
cout<<"\n\nIDENTIFIERS";
cout<<endl<<" name "<<" "<<"datatype"
<<" "<<"scope"<<" "<<"binding"<<" "<<"f_or_not"
<<" "<<"type"<<" "<<"offset ";
for(unsigned int j=0;j<syn_identifier.size();j++)
cout<<endl<<j<<" "<<syn_identifier[j].name<<'\t'
<<syn_identifier[j].datatype
<<'\t'<<syn_identifier[j].scope
<<'\t'<<syn_identifier[j].binding
<<'\t'<<syn_identifier[j].func_or_not
<<'\t'<<syn_identifier[j].type
<<'\t'<<syn_identifier[j].offset
<<'\t'<<syn_identifier[j].xtra;
*/
//If u wanna See What Paramters are Binded to Which Fucntion,Remove Comments from the
//following Lines
/*
cout<<"\n\nBINDINGS";
for(j=0;j<args_identifier.size();j++)
cout<<endl<<j<<" "<<args_identifier[j].name<<'\t'
<<args_identifier[j].datatype
<<'\t'<<args_identifier[j].scope
<<'\t'<<args_identifier[j].binding
<<'\t'<<args_identifier[j].func_or_not
<<'\t'<<args_identifier[j].type
<<'\t'<<args_identifier[j].offset
<<'\t'<<args_identifier[j].xtra;
*/
}
void program()
{
if(input.clas=="dt")
{
int type=input.index;
advanc();
if(input.clas=="id")
{
int index=input.index;
settype(index,type);
advanc();
}
else reject();
data_or_function(type);
program();
}
else if(input.clas=="void")
{
advanc();
function_or_main();
}
else reject();
}
void data_or_function(int type)
{
if(input.clas=="comma")
{
advanc();
if(input.clas=="id")
{
int index=input.index;
settype(index,type);
advanc();
}
else reject();
data_or_function(type);
}
else if(input.clas=="semicolon")
advanc();
else if(input.clas=="parenthesis_open")
{
/*Since This Fucntion Shld've a RETURN statement in it's
body,Therefore Setting "isreturn=false",To LET IT BE TURNED
to TRUE by a STATEMENT in Fucntion's body*/
isreturn=false;
advanc();
argument_list();
if(input.clas=="parenthesis_close")
advanc();
else reject();
function_body();
}
else reject();
}
void function_or_main()
{
if(input.clas=="main")
{
// Set FLAG to true,Since it's main STARTING
main_func=true;
advanc();
if(input.clas=="parenthesis_open")
advanc();
else reject();
if(input.clas=="void")
advanc();
else reject();
if(input.clas=="parenthesis_close")
advanc();
else reject();
function_body();
}
else if(input.clas=="id")
{
settype(input.index,22);
advanc();
if(input.clas=="parenthesis_open")
advanc();
else reject();
argument_list();
if(input.clas=="parenthesis_close")
advanc();
else reject();
function_body();
program();
}
else reject();
}
void function_body()
{
int start_atom,end_atom,total;
start_atom=end_atom=total=-10;
if(input.clas=="braces_open")
{
//
//Marking Begining Of Function
//
//Is it a main() function?
if(main_func==true)
{
expr temp;
temp.index=-1; //-1 For main() OR func_index For others
temp.datatype=1; //1 Shows Starting,0 Shows Ending
temp.whichtable=-10;
setatom(34,temp,dump,dump);
}
//It's an ORDINARY function
else
{
expr temp;
temp.index=func_index; //-1 For main() OR func_index For others
temp.datatype=1; //1 Shows Starting,0 Shows Ending
temp.whichtable=-10;
setatom(34,temp,dump,dump);
start_atom=atoms.size()-1; //Storing Index Of Starting ATOM
}
//Update scope_or_binding.
scopecount++;
scopestack.push(scopecount);
advanc();
variable_declarations();
statements();
if(input.clas=="braces_close")
{
if((scopestack.size()-1)>0)
scopestack.pop();
else
reject();
advanc();
}
else
reject();
//
//Marking Ending Of Function
//
//Is it a main() function?
if(main_func==true)
{
expr temp;
temp.index=-1; //-1 For main() OR func_index For others
temp.datatype=0; //1 Shows Starting,0 Shows Ending
temp.whichtable=-10;
setatom(34,temp,dump,dump);
}
//It's an ORDINARY function
else
{
expr temp;
temp.index=func_index; //-1 For main() OR func_index For others
temp.datatype=0; //1 Shows Starting,0 Shows Ending
temp.whichtable=-10;
setatom(34,temp,dump,dump);
end_atom=atoms.size()-1; //Storing Index Of Ending ATOM
}
//Setting LOCAL VARIABLES+TEMPoRARIES' OFFSETS.
if(func_index!=-10)
{
total=calc_local_offset();
//Now,Saving The TOTAL LENGTH of OFFSETS into the Starting
//and Ending PROC_MARKER ATOMS Of this Particular Fucntion
atoms[start_atom].arg1.whichtable=total;
atoms[end_atom].arg1.whichtable=total;
}
/*If this Fucntion has to return something,ASSURING that it
has done this ATLEAST one time!*/
if(func_index!=-10)
{
if(isreturn!=true&& syn_identifier[func_index].datatype!=22/*Shldn't Be void*/)
{
cout<<endl<<"Fucntion named "<< syn_identifier[func_index].name
<<" Shld return "<< syn_identifier[func_index].datatype <<endl;
reject();
}
}
main_func=false; //Main Fucntion Ended
func_index=-10; //De-Registering Fucntion if it was local
isreturn=false; //Re-Setting the Return Flag
}
else
reject();
}
void variable_declarations()
{
if(input.clas=="dt")
{
int type=input.index;
advanc();
if(input.clas=="id")
{
int index=input.index;
settype(index,type);
advanc();
}
else reject();
variable_list(type);
if(input.clas=="semicolon")
advanc();
else reject();
variable_declarations();
}
else if(input.clas=="id" || input.clas=="braces_open" || input.clas=="while" ||
input.clas=="for" || input.clas=="do" || input.clas=="return" ||
input.clas=="if" || input.clas=="square_open" || input.clas=="braces_close" )
{
}
else reject();
}
void variable_list(int type)
{
if(input.clas=="comma")
{
advanc();
if(input.clas=="id")
{
int index=input.index;
settype(index,type);
advanc();
}
else reject();
variable_list(type);
}
else if(input.clas=="semicolon")
{
}
else reject();
}
void argument_list()
{
if(input.clas=="void")
{
ident.name="void";
ident.datatype=22;
ident.scope=-10;
ident.binding=syn_identifier.size()-1;
ident.func_or_not=false;
ident.type=3; //For Parameters 3!.
ident.offset=-10; //We'll calculate it LATER
ident.xtra=-10;
args_identifier.push_back(ident);
//Since we got argument list for our recently entered identifier,
//therefore we need to recognize that as a FUNCTION NAME EXPLICITLY.
//Updating IDENTIFIER SYMBOL TABLE
int ind=syn_identifier.size()-1;
ident=syn_identifier[ind];
ident.func_or_not=true;
syn_identifier[ind]=ident;
//Registering This Fucntion's Start
func_index=ind;
advanc();
}
else if(input.clas=="dt")
{
int type=input.index;
advanc();
if(input.clas=="id")
{
int index=input.index;
settype_args(index,type);
advanc();
}
else reject();
argument();
//Since we got argument list for our recently entered identifier,
//therefore we need to recognize that as a FUNCTION NAME EXPLICITLY.
//Updating IDENTIFIER SYMBOL TABLE
int ind=syn_identifier.size()-1;
ident=syn_identifier[ind];
ident.func_or_not=true;
syn_identifier[ind]=ident;
//Registering This Fucntion's Start
func_index=ind;
//Caculating Fucntion Parameter's Offsets
int ret=calc_param_offset();
//Storing the Total SIZE of PARAMETERS
syn_identifier[ind].xtra=ret;
}
else reject();
}
void argument()
{
if(input.clas=="comma")
{
int type;
advanc();
if(input.clas=="dt")
{
type=input.index;
advanc();
}
else reject();
if(input.clas=="id")
{
int index=input.index;
settype_args(index,type);
advanc();
}
else reject();
argument();
}
else if(input.clas=="parenthesis_close")
{
}
else reject();
}
void compound_statement()
{
if(input.clas=="braces_open")
{
advanc();
statements();
if(input.clas=="braces_close")
advanc();
else reject();
}
else reject();
}
void statements()
{
if(input.clas=="id"||input.clas=="braces_open"||input.clas=="while"||
input.clas=="for"||input.clas=="do"||input.clas=="return"||
input.clas=="if"||input.clas=="square_open")
{
statement();
statements();
}
else if(input.clas=="braces_close")
{
}
else reject();
}
void statement()
{
if(input.clas=="id")
{
long ind=chk_ident(long(input.index));
if(ind==-10)
{
cout<<"\nFailed in <Statement>-->id=<right_hand_side>;";
cout<<"\nVariable Not Found ";
reject();
}
expr t;
t.index=ind;
t.whichtable=table;
if(table==0)
t.datatype=syn_identifier[ind].datatype;
else if(table==1)
t.datatype=args_identifier[ind].datatype;
advanc();
if(input.clas=="assignop")
advanc();
else reject();
expr r;
right_hand_side(r);
if(input.clas=="semicolon")
advanc();
else reject();
if(chk_types(t,r)==true)
{
setatom(26,r,dump,t);
}
else
{
cout<<"\nType of id != <right_hand_side>";
reject();
}
}
else if(input.clas=="braces_open")
{
compound_statement();
}
else if(input.clas=="while")
{
expr temp;
int start=newlabel();
int end=newlabel();
temp.datatype=25;
temp.index=start;
temp.whichtable=4; // For Labels;
setatom(25,dump,dump,temp);
advanc();
if(input.clas=="parenthesis_open")
advanc();
else reject();
expr k;
expression(k);
if(input.clas=="parenthesis_close")
advanc();
else reject();
temp.datatype=25;
temp.index=end;
temp.whichtable=4;
expr temp1;
temp1.datatype=0;
temp1.index=-10;
temp1.whichtable=-10;
setatom(27,k,temp1,temp);
statement();
temp.datatype=25;
temp.index=start;
temp.whichtable=4;
setatom(28,dump,dump,temp);
temp.datatype=25;
temp.index=end;
temp.whichtable=4;
setatom(25,dump,dump,temp);
}
else if(input.clas=="for")
{
int start=newlabel();
int end=newlabel();
int t_1=newlabel();
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -