Push through clang-format.
This commit is contained in:
parent
a4f136f999
commit
3584ddb6e9
252
util/ego/cf/cf.c
252
util/ego/cf/cf.c
|
@ -32,14 +32,13 @@
|
|||
#include "cf_loop.h"
|
||||
|
||||
#define newcfbx() (bext_p) newstruct(bext_cf)
|
||||
#define oldcfbx(x) oldstruct(bext_cf,x)
|
||||
#define oldcfbx(x) oldstruct(bext_cf, x)
|
||||
|
||||
extern char em_flag[];
|
||||
|
||||
STATIC cset lpi_set; /* set of procedures used in LPI instruction */
|
||||
STATIC cset cai_set; /* set of all procedures doing a CAI */
|
||||
|
||||
|
||||
/* The procedure getbblocks reads the EM textfile and
|
||||
* partitions every procedure into a number of basic blocks.
|
||||
*/
|
||||
|
@ -52,7 +51,6 @@ STATIC cset cai_set; /* set of all procedures doing a CAI */
|
|||
#define AFTERPRO 5
|
||||
#define INIT 6
|
||||
|
||||
|
||||
/* These global variables are used by getbblocks and nextblock. */
|
||||
|
||||
STATIC bblock_p b, *bp; /* b is the current basic block, bp is
|
||||
|
@ -77,7 +75,6 @@ STATIC short state; /* We use a finite state machine with the
|
|||
* INIT: initial state
|
||||
*/
|
||||
|
||||
|
||||
STATIC nextblock()
|
||||
{
|
||||
/* allocate a new basic block structure and
|
||||
|
@ -94,11 +91,10 @@ STATIC nextblock()
|
|||
b->b_extend->bx_cf.bx_semi = 0;
|
||||
lp = &lnp->l_next;
|
||||
#ifdef TRACE
|
||||
fprintf(stderr,"new basic block, id = %d\n",lastbid);
|
||||
fprintf(stderr, "new basic block, id = %d\n", lastbid);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
STATIC short kind(lnp)
|
||||
line_p lnp;
|
||||
{
|
||||
|
@ -107,27 +103,32 @@ STATIC short kind(lnp)
|
|||
short instr;
|
||||
byte flow;
|
||||
|
||||
if ((instr = INSTR(lnp)) == op_lab) return (short) LABEL;
|
||||
if (instr == ps_end) return (short) END;
|
||||
if (instr > sp_lmnem) return (short) NORMAL; /* pseudo */
|
||||
if ((flow = (em_flag[instr-sp_fmnem] & EM_FLO)) == FLO_C ||
|
||||
flow == FLO_T) return (short) JUMP; /* conditional/uncond. jump */
|
||||
return (short) NORMAL;
|
||||
if ((instr = INSTR(lnp)) == op_lab)
|
||||
return (short)LABEL;
|
||||
if (instr == ps_end)
|
||||
return (short)END;
|
||||
if (instr > sp_lmnem)
|
||||
return (short)NORMAL; /* pseudo */
|
||||
if ((flow = (em_flag[instr - sp_fmnem] & EM_FLO)) == FLO_C || flow == FLO_T)
|
||||
return (short)JUMP; /* conditional/uncond. jump */
|
||||
return (short)NORMAL;
|
||||
}
|
||||
|
||||
|
||||
STATIC line_p doread_line(p_out)
|
||||
proc_p *p_out;
|
||||
proc_p* p_out;
|
||||
{
|
||||
/* read a line, and check pseudos for procedure addresses */
|
||||
|
||||
register line_p lnp = read_line(p_out);
|
||||
|
||||
if (lnp && TYPE(lnp) == OPLIST && INSTR(lnp) != ps_mes) {
|
||||
if (lnp && TYPE(lnp) == OPLIST && INSTR(lnp) != ps_mes)
|
||||
{
|
||||
register arg_p arg = ARG(lnp);
|
||||
|
||||
while (arg) {
|
||||
if (arg->a_type == ARGPROC) {
|
||||
while (arg)
|
||||
{
|
||||
if (arg->a_type == ARGPROC)
|
||||
{
|
||||
Cadd(arg->a_a.a_proc->p_id, &lpi_set);
|
||||
arg->a_a.a_proc->p_flags1 |= PF_LPI;
|
||||
}
|
||||
|
@ -137,31 +138,33 @@ STATIC line_p doread_line(p_out)
|
|||
return lnp;
|
||||
}
|
||||
|
||||
STATIC bool getbblocks(fp,kind_out,n_out,g_out,l_out)
|
||||
FILE *fp;
|
||||
short *kind_out;
|
||||
short *n_out;
|
||||
bblock_p *g_out;
|
||||
line_p *l_out;
|
||||
STATIC bool getbblocks(fp, kind_out, n_out, g_out, l_out)
|
||||
FILE* fp;
|
||||
short* kind_out;
|
||||
short* n_out;
|
||||
bblock_p* g_out;
|
||||
line_p* l_out;
|
||||
{
|
||||
bblock_p head = (bblock_p) 0;
|
||||
line_p headl = (line_p) 0;
|
||||
bblock_p head = (bblock_p)0;
|
||||
line_p headl = (line_p)0;
|
||||
|
||||
curproc = (proc_p) 0;
|
||||
curproc = (proc_p)0;
|
||||
/* curproc will get a value when we encounter a PRO pseudo.
|
||||
* If there is no such pseudo, we're reading only data
|
||||
* declarations or messages (outside any proc.).
|
||||
*/
|
||||
curinp = fp;
|
||||
lastbid = (block_id) 0; /* block identier */
|
||||
lastbid = (block_id)0; /* block identier */
|
||||
state = INIT; /* initial state */
|
||||
bp = &head;
|
||||
|
||||
for (;;) {
|
||||
for (;;)
|
||||
{
|
||||
#ifdef TRACE
|
||||
fprintf(stderr,"state = %d\n",state);
|
||||
fprintf(stderr, "state = %d\n", state);
|
||||
#endif
|
||||
switch(state) {
|
||||
switch (state)
|
||||
{
|
||||
case LABEL0:
|
||||
nextblock();
|
||||
/* Fall through !! */
|
||||
|
@ -172,21 +175,26 @@ STATIC bool getbblocks(fp,kind_out,n_out,g_out,l_out)
|
|||
*/
|
||||
lnp = doread_line(&curproc);
|
||||
state = kind(lnp);
|
||||
if (state != END) {
|
||||
if (state != END)
|
||||
{
|
||||
*lp = lnp;
|
||||
lp = &lnp->l_next;
|
||||
}
|
||||
break;
|
||||
case NORMAL:
|
||||
lnp = doread_line(&curproc);
|
||||
if ( (state = kind(lnp)) == LABEL) {
|
||||
if ((state = kind(lnp)) == LABEL)
|
||||
{
|
||||
/* If we come accross a label
|
||||
* here, it must be the beginning
|
||||
* of a new basic block.
|
||||
*/
|
||||
state = LABEL0;
|
||||
} else {
|
||||
if (state != END) {
|
||||
}
|
||||
else
|
||||
{
|
||||
if (state != END)
|
||||
{
|
||||
*lp = lnp;
|
||||
lp = &lnp->l_next;
|
||||
}
|
||||
|
@ -196,7 +204,8 @@ STATIC bool getbblocks(fp,kind_out,n_out,g_out,l_out)
|
|||
lnp = doread_line(&curproc);
|
||||
/* fall through ... */
|
||||
case AFTERPRO:
|
||||
switch(state = kind(lnp)) {
|
||||
switch (state = kind(lnp))
|
||||
{
|
||||
case LABEL:
|
||||
state = LABEL0;
|
||||
break;
|
||||
|
@ -209,24 +218,31 @@ STATIC bool getbblocks(fp,kind_out,n_out,g_out,l_out)
|
|||
case END:
|
||||
*lp = lnp;
|
||||
#ifdef TRACE
|
||||
fprintf(stderr,"at end of proc, %d blocks\n",lastbid);
|
||||
fprintf(stderr, "at end of proc, %d blocks\n", lastbid);
|
||||
#endif
|
||||
if (head == (bblock_p) 0) {
|
||||
if (head == (bblock_p)0)
|
||||
{
|
||||
*kind_out = LDATA;
|
||||
*l_out = headl;
|
||||
} else {
|
||||
}
|
||||
else
|
||||
{
|
||||
*kind_out = LTEXT;
|
||||
*g_out = head;
|
||||
*n_out = (short) lastbid;
|
||||
*n_out = (short)lastbid;
|
||||
/* number of basic blocks */
|
||||
}
|
||||
return TRUE;
|
||||
case INIT:
|
||||
lnp = doread_line(&curproc);
|
||||
if (feof(curinp)) return FALSE;
|
||||
if (INSTR(lnp) == ps_pro) {
|
||||
if (feof(curinp))
|
||||
return FALSE;
|
||||
if (INSTR(lnp) == ps_pro)
|
||||
{
|
||||
state = AFTERPRO;
|
||||
} else {
|
||||
}
|
||||
else
|
||||
{
|
||||
state = NORMAL;
|
||||
headl = lnp;
|
||||
lp = &lnp->l_next;
|
||||
|
@ -236,7 +252,6 @@ STATIC bool getbblocks(fp,kind_out,n_out,g_out,l_out)
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
STATIC interproc_analysis(p)
|
||||
proc_p p;
|
||||
{
|
||||
|
@ -265,20 +280,24 @@ STATIC interproc_analysis(p)
|
|||
p->p_change->c_ext = Cempty_set(olength);
|
||||
p->p_calling = Cempty_set(plength);
|
||||
|
||||
for (b = p->p_start; b != (bblock_p) 0; b = b->b_next) {
|
||||
for (b = p->p_start; b != (bblock_p)0; b = b->b_next)
|
||||
{
|
||||
inloop = (Lnrelems(b->b_loops) > 0);
|
||||
for (lnp = b->b_start; lnp != (line_p) 0; lnp = lnp->l_next) {
|
||||
for (lnp = b->b_start; lnp != (line_p)0; lnp = lnp->l_next)
|
||||
{
|
||||
/* for all instructions of p do */
|
||||
switch(INSTR(lnp)) {
|
||||
switch (INSTR(lnp))
|
||||
{
|
||||
case op_cal:
|
||||
Cadd(PROC(lnp)->p_id, &p->p_calling);
|
||||
/* add called proc to p_calling */
|
||||
if (inloop) {
|
||||
if (inloop)
|
||||
{
|
||||
CALLED_IN_LOOP(PROC(lnp));
|
||||
}
|
||||
break;
|
||||
case op_cai:
|
||||
Cadd(p->p_id,&cai_set);
|
||||
Cadd(p->p_id, &cai_set);
|
||||
break;
|
||||
case op_lpi:
|
||||
Cadd(PROC(lnp)->p_id, &lpi_set);
|
||||
|
@ -327,12 +346,14 @@ STATIC interproc_analysis(p)
|
|||
break;
|
||||
case op_lor:
|
||||
case op_str:
|
||||
if (SHORT(lnp) == 0) {
|
||||
if (SHORT(lnp) == 0)
|
||||
{
|
||||
curproc->p_flags1 |= PF_ENVIRON;
|
||||
}
|
||||
break;
|
||||
case ps_mes:
|
||||
if (aoff(ARG(lnp),0) == ms_gto) {
|
||||
if (aoff(ARG(lnp), 0) == ms_gto)
|
||||
{
|
||||
ENTERED_WITH_GTO(curproc);
|
||||
}
|
||||
break;
|
||||
|
@ -341,7 +362,6 @@ STATIC interproc_analysis(p)
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
STATIC cf_cleanproc(p)
|
||||
proc_p p;
|
||||
{
|
||||
|
@ -351,26 +371,26 @@ STATIC cf_cleanproc(p)
|
|||
register Lindex pi;
|
||||
loop_p lp;
|
||||
|
||||
for (b = p->p_start; b != (bblock_p) 0; b = b->b_next) {
|
||||
for (b = p->p_start; b != (bblock_p)0; b = b->b_next)
|
||||
{
|
||||
oldcfbx(b->b_extend);
|
||||
}
|
||||
for (pi = Lfirst(p->p_loops); pi != (Lindex) 0; pi = Lnext(pi,
|
||||
p->p_loops)) {
|
||||
lp = (loop_p) Lelem(pi);
|
||||
for (pi = Lfirst(p->p_loops); pi != (Lindex)0; pi = Lnext(pi,
|
||||
p->p_loops))
|
||||
{
|
||||
lp = (loop_p)Lelem(pi);
|
||||
oldcflpx(lp->lp_extend);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
#define CH_CHANGE_INDIR(ch) ((ch->c_flags & CF_INDIR) != 0)
|
||||
#define USE_INDIR(us) ((us->u_flags & UF_INDIR) != 0)
|
||||
#define CALLS_UNKNOWN(p) (p->p_flags1 & (byte) PF_CALUNKNOWN)
|
||||
#define ENVIRON(p) (p->p_flags1 & (byte) PF_ENVIRON)
|
||||
#define CALLS_UNKNOWN(p) (p->p_flags1 & (byte)PF_CALUNKNOWN)
|
||||
#define ENVIRON(p) (p->p_flags1 & (byte)PF_ENVIRON)
|
||||
|
||||
|
||||
STATIC bool add_info(q,p)
|
||||
proc_p q,p;
|
||||
STATIC bool add_info(q, p)
|
||||
proc_p q,
|
||||
p;
|
||||
{
|
||||
/* Determine the consequences for used/changed variables info
|
||||
* of the fact that p calls q. If e.g. q changes a variable X
|
||||
|
@ -389,32 +409,40 @@ STATIC bool add_info(q,p)
|
|||
usp = p->p_use;
|
||||
usq = q->p_use;
|
||||
|
||||
if (!BODY_KNOWN(q)) {
|
||||
if (!BODY_KNOWN(q))
|
||||
{
|
||||
/* q is a procedure of which the body is not available
|
||||
* as EM text.
|
||||
*/
|
||||
if (CALLS_UNKNOWN(p)) {
|
||||
if (CALLS_UNKNOWN(p))
|
||||
{
|
||||
return FALSE;
|
||||
/* p already called an unknown procedure */
|
||||
} else {
|
||||
}
|
||||
else
|
||||
{
|
||||
p->p_flags1 |= PF_CALUNKNOWN;
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
if (CALLS_UNKNOWN(q)) {
|
||||
if (CALLS_UNKNOWN(q))
|
||||
{
|
||||
/* q calls a procedure of which the body is not available
|
||||
* as EM text.
|
||||
*/
|
||||
if (!CALLS_UNKNOWN(p)) {
|
||||
if (!CALLS_UNKNOWN(p))
|
||||
{
|
||||
p->p_flags1 |= PF_CALUNKNOWN;
|
||||
diff = TRUE;
|
||||
}
|
||||
}
|
||||
if (IS_CALLED_IN_LOOP(p) && !IS_CALLED_IN_LOOP(q)) {
|
||||
if (IS_CALLED_IN_LOOP(p) && !IS_CALLED_IN_LOOP(q))
|
||||
{
|
||||
CALLED_IN_LOOP(q);
|
||||
diff = TRUE;
|
||||
}
|
||||
if (!Cis_subset(chq->c_ext, chp->c_ext)) {
|
||||
if (!Cis_subset(chq->c_ext, chp->c_ext))
|
||||
{
|
||||
/* q changes global variables (objects) that
|
||||
* p did not (yet) change. Add all variables
|
||||
* changed by q to the c_ext set of p.
|
||||
|
@ -422,21 +450,24 @@ STATIC bool add_info(q,p)
|
|||
Cjoin(chq->c_ext, &chp->c_ext);
|
||||
diff = TRUE;
|
||||
}
|
||||
if (CH_CHANGE_INDIR(chq) && !CH_CHANGE_INDIR(chp)) {
|
||||
if (CH_CHANGE_INDIR(chq) && !CH_CHANGE_INDIR(chp))
|
||||
{
|
||||
/* q does a change-indirect (sil etc.)
|
||||
* and p did not (yet).
|
||||
*/
|
||||
chp->c_flags |= CF_INDIR;
|
||||
diff = TRUE;
|
||||
}
|
||||
if (USE_INDIR(usq) && !USE_INDIR(usp)) {
|
||||
if (USE_INDIR(usq) && !USE_INDIR(usp))
|
||||
{
|
||||
/* q does a use-indirect (lil etc.)
|
||||
* and p dis not (yet).
|
||||
*/
|
||||
usp->u_flags |= UF_INDIR;
|
||||
diff = TRUE;
|
||||
}
|
||||
if (ENVIRON(q) && !ENVIRON(p)) {
|
||||
if (ENVIRON(q) && !ENVIRON(p))
|
||||
{
|
||||
/* q uses or changes local variables in its
|
||||
* environment while p does not (yet).
|
||||
*/
|
||||
|
@ -446,8 +477,6 @@ STATIC bool add_info(q,p)
|
|||
return diff;
|
||||
}
|
||||
|
||||
|
||||
|
||||
STATIC trans_clos(head)
|
||||
proc_p head;
|
||||
{
|
||||
|
@ -455,18 +484,23 @@ STATIC trans_clos(head)
|
|||
* variable information.
|
||||
*/
|
||||
|
||||
register proc_p p,q;
|
||||
register proc_p p, q;
|
||||
Cindex i;
|
||||
bool changes = TRUE;
|
||||
|
||||
while(changes) {
|
||||
while (changes)
|
||||
{
|
||||
changes = FALSE;
|
||||
for (p = head; p != (proc_p) 0; p = p->p_next) {
|
||||
if (!BODY_KNOWN(p)) continue;
|
||||
for (i = Cfirst(p->p_calling); i != (Cindex) 0;
|
||||
i = Cnext(i,p->p_calling)) {
|
||||
for (p = head; p != (proc_p)0; p = p->p_next)
|
||||
{
|
||||
if (!BODY_KNOWN(p))
|
||||
continue;
|
||||
for (i = Cfirst(p->p_calling); i != (Cindex)0;
|
||||
i = Cnext(i, p->p_calling))
|
||||
{
|
||||
q = pmap[Celem(i)];
|
||||
if (add_info(q,p)) {
|
||||
if (add_info(q, p))
|
||||
{
|
||||
changes = TRUE;
|
||||
}
|
||||
}
|
||||
|
@ -474,15 +508,13 @@ STATIC trans_clos(head)
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
indir_calls()
|
||||
{
|
||||
Cindex i;
|
||||
proc_p p;
|
||||
|
||||
for (i = Cfirst(cai_set); i != (Cindex) 0; i = Cnext(i,cai_set)) {
|
||||
for (i = Cfirst(cai_set); i != (Cindex)0; i = Cnext(i, cai_set))
|
||||
{
|
||||
p = pmap[Celem(i)]; /* p does a CAI */
|
||||
Cjoin(lpi_set, &p->p_calling);
|
||||
}
|
||||
|
@ -490,13 +522,10 @@ indir_calls()
|
|||
Cdeleteset(cai_set);
|
||||
}
|
||||
|
||||
|
||||
|
||||
main(argc,argv)
|
||||
int argc;
|
||||
char *argv[];
|
||||
main(argc, argv) int argc;
|
||||
char* argv[];
|
||||
{
|
||||
FILE *f, *f2, *gf2; /* The EM input, EM output, basic block output */
|
||||
FILE* f, *f2, *gf2; /* The EM input, EM output, basic block output */
|
||||
bblock_p g;
|
||||
short n, kind;
|
||||
line_p l;
|
||||
|
@ -506,34 +535,41 @@ main(argc,argv)
|
|||
fdblock = getdtable(dname); /* data block table */
|
||||
lpi_set = Cempty_set(plength);
|
||||
cai_set = Cempty_set(plength);
|
||||
if ((f = fopen(lname,"r")) == NULL) {
|
||||
if ((f = fopen(lname, "r")) == NULL)
|
||||
{
|
||||
error("cannot open %s", lname);
|
||||
}
|
||||
if ((f2 = fopen(lname2,"w")) == NULL) {
|
||||
if ((f2 = fopen(lname2, "w")) == NULL)
|
||||
{
|
||||
error("cannot open %s", lname2);
|
||||
}
|
||||
if ((gf2 = fopen(bname2,"w")) == NULL) {
|
||||
error("cannot open %s",bname2);
|
||||
if ((gf2 = fopen(bname2, "w")) == NULL)
|
||||
{
|
||||
error("cannot open %s", bname2);
|
||||
}
|
||||
while (getbblocks(f,&kind,&n,&g,&l)) {
|
||||
while (getbblocks(f, &kind, &n, &g, &l))
|
||||
{
|
||||
/* read EM text of one unit and
|
||||
* (if it is a procedure)
|
||||
* partition it into n basic blocks.
|
||||
*/
|
||||
if (kind == LDATA) {
|
||||
putunit(LDATA,(proc_p) 0,l,gf2,f2);
|
||||
} else {
|
||||
if (kind == LDATA)
|
||||
{
|
||||
putunit(LDATA, (proc_p)0, l, gf2, f2);
|
||||
}
|
||||
else
|
||||
{
|
||||
curproc->p_start = g;
|
||||
/* The global variable curproc points to the
|
||||
* current procedure. It is set by getbblocks
|
||||
*/
|
||||
control_flow(g); /* compute pred and succ */
|
||||
dominators(g,n); /* compute immediate dominators */
|
||||
dominators(g, n); /* compute immediate dominators */
|
||||
loop_detection(curproc); /* compute loops */
|
||||
interproc_analysis(curproc);
|
||||
/* Interprocedural analysis */
|
||||
cf_cleanproc(curproc);
|
||||
putunit(LTEXT,curproc,(line_p) 0,gf2,f2);
|
||||
putunit(LTEXT, curproc, (line_p)0, gf2, f2);
|
||||
/* output control flow graph + text */
|
||||
}
|
||||
}
|
||||
|
@ -545,13 +581,15 @@ main(argc,argv)
|
|||
/* Compute transitive closure of used/changed
|
||||
* variables information for every procedure.
|
||||
*/
|
||||
if ((f = fopen(dname2,"w")) == NULL) {
|
||||
error("cannot open %s",dname2);
|
||||
if ((f = fopen(dname2, "w")) == NULL)
|
||||
{
|
||||
error("cannot open %s", dname2);
|
||||
}
|
||||
putdtable(fdblock,f);
|
||||
if ((f = fopen(pname2,"w")) == NULL) {
|
||||
error("cannot open %s",pname2);
|
||||
putdtable(fdblock, f);
|
||||
if ((f = fopen(pname2, "w")) == NULL)
|
||||
{
|
||||
error("cannot open %s", pname2);
|
||||
}
|
||||
putptable(fproc,f,TRUE);
|
||||
putptable(fproc, f, TRUE);
|
||||
exit(0);
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue