Some instruction selection is now happening.
This commit is contained in:
		
							parent
							
								
									c8fcbe282a
								
							
						
					
					
						commit
						629e0ddfc6
					
				
					 15 changed files with 264 additions and 55 deletions
				
			
		| 
						 | 
					@ -33,7 +33,11 @@ struct ir
 | 
				
			||||||
		const char* lvalue;
 | 
							const char* lvalue;
 | 
				
			||||||
		struct basicblock* bvalue;
 | 
							struct basicblock* bvalue;
 | 
				
			||||||
	} u;
 | 
						} u;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						void* state_label; /* used by the iburg instruction selector */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	bool is_sequence : 1;
 | 
						bool is_sequence : 1;
 | 
				
			||||||
 | 
						bool is_generated : 1;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
extern const char* ir_names[];
 | 
					extern const char* ir_names[];
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -37,9 +37,10 @@ bool tracing(char k)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
    switch (k)
 | 
					    switch (k)
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
 | 
					        case 0:   return true;
 | 
				
			||||||
        case 'E': return false;
 | 
					        case 'E': return false;
 | 
				
			||||||
        case '0': return false;
 | 
					        case '0': return false;
 | 
				
			||||||
        case '1': return true;
 | 
					        case '1': return false;
 | 
				
			||||||
        case '2': return true;
 | 
					        case '2': return true;
 | 
				
			||||||
        default:  return true;
 | 
					        default:  return true;
 | 
				
			||||||
    }
 | 
					    }
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -119,6 +119,7 @@ extern void tb_regvar(arith offset, int size, int type, int priority);
 | 
				
			||||||
extern void pass_convert_stack_ops(struct procedure* proc);
 | 
					extern void pass_convert_stack_ops(struct procedure* proc);
 | 
				
			||||||
extern void pass_remove_dead_blocks(struct procedure* proc);
 | 
					extern void pass_remove_dead_blocks(struct procedure* proc);
 | 
				
			||||||
extern void pass_eliminate_trivial_blocks(struct procedure* proc);
 | 
					extern void pass_eliminate_trivial_blocks(struct procedure* proc);
 | 
				
			||||||
 | 
					extern void pass_instruction_selector(struct procedure* proc);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
extern void procedure_compile(struct procedure* proc);
 | 
					extern void procedure_compile(struct procedure* proc);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -19,6 +19,7 @@ static void dumpCover(NODEPTR_TYPE p, int goalnt, int indent) {
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#if 0
 | 
				
			||||||
static NODEPTR_TYPE tree(int op, NODEPTR_TYPE l, NODEPTR_TYPE r) {
 | 
					static NODEPTR_TYPE tree(int op, NODEPTR_TYPE l, NODEPTR_TYPE r) {
 | 
				
			||||||
	NODEPTR_TYPE p = malloc(sizeof *p);
 | 
						NODEPTR_TYPE p = malloc(sizeof *p);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -48,4 +49,5 @@ int main(void) {
 | 
				
			||||||
	dumpCover(p, 1, 0);
 | 
						dumpCover(p, 1, 0);
 | 
				
			||||||
	return 0;
 | 
						return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -1,32 +1,20 @@
 | 
				
			||||||
#include <stdio.h>
 | 
					#include "mcg.h"
 | 
				
			||||||
#include <assert.h>
 | 
					#include "mcgg.h"
 | 
				
			||||||
#include <stdlib.h>
 | 
					 | 
				
			||||||
#include <stdbool.h>
 | 
					 | 
				
			||||||
#include <limits.h>
 | 
					 | 
				
			||||||
#include <stdlib.h>
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define TRACE
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define STATE_TYPE void*
 | 
					 | 
				
			||||||
typedef struct tree {
 | 
					 | 
				
			||||||
	int op;
 | 
					 | 
				
			||||||
	struct tree *kids[2];
 | 
					 | 
				
			||||||
	STATE_TYPE state_label;
 | 
					 | 
				
			||||||
} *NODEPTR_TYPE;
 | 
					 | 
				
			||||||
#define OP_LABEL(p) ((p)->op)
 | 
					 | 
				
			||||||
#define LEFT_CHILD(p) ((p)->kids[0])
 | 
					 | 
				
			||||||
#define RIGHT_CHILD(p) ((p)->kids[1])
 | 
					 | 
				
			||||||
#define STATE_LABEL(p) ((p)->state_label)
 | 
					 | 
				
			||||||
#define PANIC printf
 | 
					#define PANIC printf
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void burm_trace(NODEPTR_TYPE p, int eruleno, int cost, int bestcost) {
 | 
					static int OP_LABEL(struct ir* ir)
 | 
				
			||||||
#ifdef TRACE
 | 
					{
 | 
				
			||||||
	extern const char *burm_string[];
 | 
						if (ir->is_generated)
 | 
				
			||||||
 | 
							return ir_to_esn(IR_REG, ir->size);
 | 
				
			||||||
	fprintf(stderr, "0x%p matched %s with cost %d vs. %d\n", p,
 | 
						return ir_to_esn(ir->opcode, ir->size);
 | 
				
			||||||
		burm_string[eruleno], cost, bestcost);
 | 
					 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#define burm_assert(b, s) assert(b && s)
 | 
					#define LEFT_CHILD(p) ((p)->left)
 | 
				
			||||||
 | 
					#define RIGHT_CHILD(p) ((p)->right)
 | 
				
			||||||
 | 
						 
 | 
				
			||||||
 | 
					#define burm_assert(b, s) assert(b)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern void burm_panic_cannot_match(struct ir* ir);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										87
									
								
								mach/proto/mcg/pass_instsel.c
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										87
									
								
								mach/proto/mcg/pass_instsel.c
									
										
									
									
									
										Normal file
									
								
							| 
						 | 
					@ -0,0 +1,87 @@
 | 
				
			||||||
 | 
					#include "mcg.h"
 | 
				
			||||||
 | 
					#include "mcgg.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#if 0
 | 
				
			||||||
 | 
					static void dumpCover(NODEPTR_TYPE p, int goalnt, int indent) {
 | 
				
			||||||
 | 
					#ifdef TRACE
 | 
				
			||||||
 | 
						int eruleno = burm_rule(STATE_LABEL(p), goalnt);
 | 
				
			||||||
 | 
						const short *nts = burm_nts[eruleno];
 | 
				
			||||||
 | 
						NODEPTR_TYPE kids[10];
 | 
				
			||||||
 | 
						int i;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						for (i = 0; i < indent; i++)
 | 
				
			||||||
 | 
							fprintf(stderr, " ");
 | 
				
			||||||
 | 
						fprintf(stderr, "%s\n", burm_string[eruleno]);
 | 
				
			||||||
 | 
						burm_kids(p, eruleno, kids);
 | 
				
			||||||
 | 
						for (i = 0; nts[i]; i++)
 | 
				
			||||||
 | 
						{
 | 
				
			||||||
 | 
							if (kids[i])
 | 
				
			||||||
 | 
								dumpCover(kids[i], nts[i], indent + 1);
 | 
				
			||||||
 | 
							else
 | 
				
			||||||
 | 
								fprintf(stderr, "failed!\n");
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void burm_trace(struct ir* p, int ruleno, int cost, int bestcost) {
 | 
				
			||||||
 | 
						tracef('I', "I: 0x%p matched %s with cost %d vs. %d\n", p,
 | 
				
			||||||
 | 
							burm_string[ruleno], cost, bestcost);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void burm_panic_cannot_match(struct ir* ir)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						fprintf(stderr, "could not find any patterns to match:\n");
 | 
				
			||||||
 | 
						ir_print(0, ir);
 | 
				
			||||||
 | 
						fprintf(stderr, "aborting!\n");
 | 
				
			||||||
 | 
						exit(1);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void queue_instructions(struct ir* ir, int goal)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						struct ir* children[10];
 | 
				
			||||||
 | 
						int ruleno = burm_rule(ir->state_label, goal);
 | 
				
			||||||
 | 
						const short* nts = burm_nts[ruleno];
 | 
				
			||||||
 | 
						int i;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						burm_kids(ir, ruleno, children);
 | 
				
			||||||
 | 
						for (i=0; nts[i]; i++)
 | 
				
			||||||
 | 
							queue_instructions(children[i], nts[i]);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						printf("selected insn %d: %s\n", ruleno, burm_string[ruleno]);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void select_instructions(struct basicblock* bb)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						int i;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						tracef('I', "I: BLOCK: %s\n", bb->name);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						for (i=0; i<bb->irs_count; i++)
 | 
				
			||||||
 | 
						{
 | 
				
			||||||
 | 
							int insnno;
 | 
				
			||||||
 | 
							struct ir* ir = bb->irs[i];
 | 
				
			||||||
 | 
							burm_label(ir);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							insnno = burm_rule(ir->state_label, 1);
 | 
				
			||||||
 | 
							if (!insnno)
 | 
				
			||||||
 | 
								burm_panic_cannot_match(ir);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							queue_instructions(ir, 1);
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void pass_instruction_selector(struct procedure* proc)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					    int i;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    for (i=0; i<proc->blocks_count; i++)
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					        struct basicblock* bb = proc->blocks[i];
 | 
				
			||||||
 | 
					        select_instructions(bb);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
						exit(1);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* vim: set sw=4 ts=4 expandtab : */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -31,6 +31,8 @@ void procedure_compile(struct procedure* proc)
 | 
				
			||||||
    pass_convert_stack_ops(proc);
 | 
					    pass_convert_stack_ops(proc);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    print_blocks('2', proc);
 | 
					    print_blocks('2', proc);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    pass_instruction_selector(proc);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/* vim: set sw=4 ts=4 expandtab : */
 | 
					/* vim: set sw=4 ts=4 expandtab : */
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -1,5 +1,33 @@
 | 
				
			||||||
PATTERNS
 | 
					PATTERNS
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Special */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						PAIR(BLOCK4, BLOCK4);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Miscellaneous special things */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						PUSH4(in:reg)
 | 
				
			||||||
 | 
							emit "push %in"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = POP4
 | 
				
			||||||
 | 
							outs out:ANY
 | 
				
			||||||
 | 
							emit "pop %out"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						RET
 | 
				
			||||||
 | 
							emit "ret"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						SETRET4(in:reg)
 | 
				
			||||||
 | 
							emit "mov r0, %in"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Memory operations */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	STORE4(addr:address, value:reg)
 | 
						STORE4(addr:address, value:reg)
 | 
				
			||||||
		ins value:GPR
 | 
							ins value:GPR
 | 
				
			||||||
		emit "str %value, %addr"
 | 
							emit "str %value, %addr"
 | 
				
			||||||
| 
						 | 
					@ -7,9 +35,33 @@ PATTERNS
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	reg = LOAD4(addr:address)
 | 
						reg = LOAD4(addr:address)
 | 
				
			||||||
		outs dest:ANY
 | 
							outs dest:ANY
 | 
				
			||||||
		emit "ld %dest, %addr"
 | 
							emit "ldr %dest, %addr"
 | 
				
			||||||
		cost 4;
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = LOAD1(addr:address)
 | 
				
			||||||
 | 
							outs dest:ANY
 | 
				
			||||||
 | 
							emit "ldrb %dest, %addr"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = CIU14(LOAD1(addr:address))
 | 
				
			||||||
 | 
							outs dest:ANY
 | 
				
			||||||
 | 
							emit "ldrb %dest, %addr"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Locals */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = in:LOCAL4
 | 
				
			||||||
 | 
							outs out:GPR
 | 
				
			||||||
 | 
							emit "add %out, fp, #%in.ivalue"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						address = in:LOCAL4
 | 
				
			||||||
 | 
							fragment "[fp, #%in.ivalue]";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Memory addressing modes */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	address = ADD4(addr:reg, offset:CONST)
 | 
						address = ADD4(addr:reg, offset:CONST)
 | 
				
			||||||
		ins addr:GPR
 | 
							ins addr:GPR
 | 
				
			||||||
		fragment "[%addr, #%offset.ivalue]";
 | 
							fragment "[%addr, #%offset.ivalue]";
 | 
				
			||||||
| 
						 | 
					@ -18,7 +70,47 @@ PATTERNS
 | 
				
			||||||
		ins addr:GPR
 | 
							ins addr:GPR
 | 
				
			||||||
		fragment "[%addr]";
 | 
							fragment "[%addr]";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	reg;
 | 
					
 | 
				
			||||||
 | 
					/* Branches */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						JUMP(addr:BLOCK4)
 | 
				
			||||||
 | 
							emit "b %addr.bvalue"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						CJUMPEQ(value:tristate, PAIR(true:BLOCK4, false:BLOCK4))
 | 
				
			||||||
 | 
							emit "beq %trueblock.bvalue"
 | 
				
			||||||
 | 
							emit "bne %falseblock.bvalue"
 | 
				
			||||||
 | 
							cost 8;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Comparisons */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						tristate = COMPARES4(val1:reg, val2:aluparam)
 | 
				
			||||||
 | 
							outs CC
 | 
				
			||||||
 | 
							emit "cmp %val1, %val2"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = tristate
 | 
				
			||||||
 | 
							emit "mov %out, #0"
 | 
				
			||||||
 | 
							emit "movlt %out, #-1"
 | 
				
			||||||
 | 
							emit "movgt %out, #1"
 | 
				
			||||||
 | 
							cost 12;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Conversions */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = CII14(CIU41(value:reg))
 | 
				
			||||||
 | 
							outs out:GPR
 | 
				
			||||||
 | 
							emit "sxtb %out, %value"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = CIU41(in:reg)
 | 
				
			||||||
 | 
							outs out:GPR
 | 
				
			||||||
 | 
							emit "and %out, %in, #0xff"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* ALU operations */
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	reg = ADD4(left:reg, right:aluparam)
 | 
						reg = ADD4(left:reg, right:aluparam)
 | 
				
			||||||
		ins left:GPR, right:GPR
 | 
							ins left:GPR, right:GPR
 | 
				
			||||||
| 
						 | 
					@ -33,7 +125,6 @@ PATTERNS
 | 
				
			||||||
		cost 4;
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	aluparam = value:CONST4
 | 
						aluparam = value:CONST4
 | 
				
			||||||
		when { return false; }
 | 
					 | 
				
			||||||
		fragment "#%value.ivalue";
 | 
							fragment "#%value.ivalue";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	aluparam = reg;
 | 
						aluparam = reg;
 | 
				
			||||||
| 
						 | 
					@ -45,7 +136,12 @@ PATTERNS
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	reg = value:LABEL4
 | 
						reg = value:LABEL4
 | 
				
			||||||
		outs out:GPR
 | 
							outs out:GPR
 | 
				
			||||||
		emit "adr %out, #value.lvalue"
 | 
							emit "adr %out, %value.lvalue"
 | 
				
			||||||
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						reg = value:BLOCK4
 | 
				
			||||||
 | 
							outs out:GPR
 | 
				
			||||||
 | 
							emit "adr %out, %value.bvalue"
 | 
				
			||||||
		cost 4;
 | 
							cost 4;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	reg = value:CONST4
 | 
						reg = value:CONST4
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -231,9 +231,9 @@ static void simple_branch2(int opcode, int size,
 | 
				
			||||||
    materialise_stack();
 | 
					    materialise_stack();
 | 
				
			||||||
    appendir(
 | 
					    appendir(
 | 
				
			||||||
        new_ir2(
 | 
					        new_ir2(
 | 
				
			||||||
            IR_CJUMP, 0,
 | 
					            irop, 0,
 | 
				
			||||||
            new_ir2(
 | 
					            new_ir2(
 | 
				
			||||||
                irop,  size,
 | 
					                IR_COMPARES,  size,
 | 
				
			||||||
                left, right
 | 
					                left, right
 | 
				
			||||||
            ),
 | 
					            ),
 | 
				
			||||||
            new_ir2(
 | 
					            new_ir2(
 | 
				
			||||||
| 
						 | 
					@ -260,13 +260,13 @@ static void insn_bvalue(int opcode, struct basicblock* leftbb, struct basicblock
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
    switch (opcode)
 | 
					    switch (opcode)
 | 
				
			||||||
    {
 | 
					    {
 | 
				
			||||||
        case op_zeq: compare0_branch2(opcode, leftbb, rightbb, IR_IFEQ); break;
 | 
					        case op_zeq: compare0_branch2(opcode, leftbb, rightbb, IR_CJUMPEQ); break;
 | 
				
			||||||
        case op_zlt: compare0_branch2(opcode, leftbb, rightbb, IR_IFLT); break;
 | 
					        case op_zlt: compare0_branch2(opcode, leftbb, rightbb, IR_CJUMPLT); break;
 | 
				
			||||||
        case op_zle: compare0_branch2(opcode, leftbb, rightbb, IR_IFLE); break;
 | 
					        case op_zle: compare0_branch2(opcode, leftbb, rightbb, IR_CJUMPLE); break;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        case op_zne: compare0_branch2(opcode, rightbb, leftbb, IR_IFEQ); break;
 | 
					        case op_zne: compare0_branch2(opcode, rightbb, leftbb, IR_CJUMPEQ); break;
 | 
				
			||||||
        case op_zge: compare0_branch2(opcode, rightbb, leftbb, IR_IFLT); break;
 | 
					        case op_zge: compare0_branch2(opcode, rightbb, leftbb, IR_CJUMPLT); break;
 | 
				
			||||||
        case op_zgt: compare0_branch2(opcode, rightbb, leftbb, IR_IFLE); break;
 | 
					        case op_zgt: compare0_branch2(opcode, rightbb, leftbb, IR_CJUMPLE); break;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
        case op_bra:
 | 
					        case op_bra:
 | 
				
			||||||
        {
 | 
					        {
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -28,7 +28,8 @@ clibrary {
 | 
				
			||||||
		matching(filenamesof("+ircodes"), "%.c$")
 | 
							matching(filenamesof("+ircodes"), "%.c$")
 | 
				
			||||||
	},
 | 
						},
 | 
				
			||||||
	hdrs = {
 | 
						hdrs = {
 | 
				
			||||||
		matching(filenamesof("+ircodes"), "%.h$")
 | 
							matching(filenamesof("+ircodes"), "%.h$"),
 | 
				
			||||||
 | 
							"./mcgg.h"
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -40,7 +41,7 @@ cprogram {
 | 
				
			||||||
		matching(filenamesof("+yacc"), "%.c$")
 | 
							matching(filenamesof("+yacc"), "%.c$")
 | 
				
			||||||
	},
 | 
						},
 | 
				
			||||||
	deps = {
 | 
						deps = {
 | 
				
			||||||
		"./*.h",
 | 
							"./iburg.h",
 | 
				
			||||||
		"+lib",
 | 
							"+lib",
 | 
				
			||||||
		"+yacc"
 | 
							"+yacc"
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -419,7 +419,7 @@ static void print(char* fmt, ...)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void printlineno(void)
 | 
					void printlineno(void)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	print("#line %d\n", yylineno);
 | 
						//print("#line %d\n", yylineno);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/* reach - mark all non-terminals in tree t as reachable */
 | 
					/* reach - mark all non-terminals in tree t as reachable */
 | 
				
			||||||
| 
						 | 
					@ -451,6 +451,9 @@ static void emitcase(Term p, int ntnumber)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	Rule r;
 | 
						Rule r;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (!p->rules)
 | 
				
			||||||
 | 
							return;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	print("%1case %d: /* %S */\n", p->esn, p);
 | 
						print("%1case %d: /* %S */\n", p->esn, p);
 | 
				
			||||||
	switch (p->arity)
 | 
						switch (p->arity)
 | 
				
			||||||
	{
 | 
						{
 | 
				
			||||||
| 
						 | 
					@ -823,7 +826,8 @@ static void emitstate(Term terms, Nonterm start, int ntnumber)
 | 
				
			||||||
	for (p = terms; p; p = p->link)
 | 
						for (p = terms; p; p = p->link)
 | 
				
			||||||
		emitcase(p, ntnumber);
 | 
							emitcase(p, ntnumber);
 | 
				
			||||||
	print("%1default:\n"
 | 
						print("%1default:\n"
 | 
				
			||||||
	      "%2%Passert(0, PANIC(\"Bad operator %%d in %Pstate\\n\", op));\n%1}\n"
 | 
					          "%2%Ppanic_cannot_match(node);\n"
 | 
				
			||||||
 | 
							  "%1}\n"
 | 
				
			||||||
	      "%1return (STATE_TYPE)p;\n}\n\n");
 | 
						      "%1return (STATE_TYPE)p;\n}\n\n");
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -86,15 +86,6 @@ extern int yylineno;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
extern void printlineno(void);
 | 
					extern void printlineno(void);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/* Excruciating macro which packs ir opcodes and sizes into an int for iburg's benefit.
 | 
					#include "mcgg.h"
 | 
				
			||||||
 *
 | 
					 | 
				
			||||||
 * Sizes are mapped as: 0=1, 1=1, 2=2, 4=3, 8=4.
 | 
					 | 
				
			||||||
 */
 | 
					 | 
				
			||||||
#define ir_to_esn(iropcode, size) \
 | 
					 | 
				
			||||||
	((iropcode)*4 + \
 | 
					 | 
				
			||||||
		(((size) == 4) ? 2 : \
 | 
					 | 
				
			||||||
		 ((size) == 8) ? 3 : \
 | 
					 | 
				
			||||||
		 ((size) == 0) ? 0 : \
 | 
					 | 
				
			||||||
		  (size-1)))
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -7,7 +7,7 @@ S CONST
 | 
				
			||||||
S REG
 | 
					S REG
 | 
				
			||||||
S LABEL
 | 
					S LABEL
 | 
				
			||||||
S BLOCK
 | 
					S BLOCK
 | 
				
			||||||
S PAIR
 | 
					V PAIR
 | 
				
			||||||
S ANY
 | 
					S ANY
 | 
				
			||||||
S LOCAL
 | 
					S LOCAL
 | 
				
			||||||
S PHI
 | 
					S PHI
 | 
				
			||||||
| 
						 | 
					@ -64,7 +64,9 @@ V CALL
 | 
				
			||||||
 
 | 
					 
 | 
				
			||||||
# Flow control --- these never return
 | 
					# Flow control --- these never return
 | 
				
			||||||
V JUMP
 | 
					V JUMP
 | 
				
			||||||
V CJUMP
 | 
					V CJUMPEQ
 | 
				
			||||||
 | 
					V CJUMPLT
 | 
				
			||||||
 | 
					V CJUMPLE
 | 
				
			||||||
V RET
 | 
					V RET
 | 
				
			||||||
 
 | 
					 
 | 
				
			||||||
# Special
 | 
					# Special
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
							
								
								
									
										30
									
								
								util/mcgg/mcgg.h
									
										
									
									
									
										Normal file
									
								
							
							
						
						
									
										30
									
								
								util/mcgg/mcgg.h
									
										
									
									
									
										Normal file
									
								
							| 
						 | 
					@ -0,0 +1,30 @@
 | 
				
			||||||
 | 
					#ifndef MCGG_H
 | 
				
			||||||
 | 
					#define MCGG_H
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* Excruciating macro which packs ir opcodes and sizes into an int for iburg's benefit.
 | 
				
			||||||
 | 
					 *
 | 
				
			||||||
 | 
					 * Sizes are mapped as: 0=1, 1=1, 2=2, 4=3, 8=4.
 | 
				
			||||||
 | 
					 */
 | 
				
			||||||
 | 
					#define ir_to_esn(iropcode, size) \
 | 
				
			||||||
 | 
						((iropcode)*4 + \
 | 
				
			||||||
 | 
							(((size) == 4) ? 2 : \
 | 
				
			||||||
 | 
							 ((size) == 8) ? 3 : \
 | 
				
			||||||
 | 
							 ((size) == 0) ? 0 : \
 | 
				
			||||||
 | 
							  (size-1)))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#define STATE_TYPE void*
 | 
				
			||||||
 | 
					typedef struct ir* NODEPTR_TYPE;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#define STATE_LABEL(p) ((p)->state_label)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					extern void* burm_label(struct ir* ir);
 | 
				
			||||||
 | 
					extern int burm_rule(void* state, int goalnt);
 | 
				
			||||||
 | 
					extern const char* burm_string[];
 | 
				
			||||||
 | 
					extern const short *burm_nts[];
 | 
				
			||||||
 | 
					extern struct ir** burm_kids(struct ir* p, int eruleno, struct ir* kids[]);
 | 
				
			||||||
 | 
					extern void burm_trace(struct ir* p, int ruleno, int cost, int bestcost);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/* vim: set sw=4 ts=4 expandtab : */
 | 
				
			||||||
| 
						 | 
					@ -22,7 +22,7 @@ static int braces = 0;
 | 
				
			||||||
<ECHO>[^%\n]*               fputs(yytext, outfp);
 | 
					<ECHO>[^%\n]*               fputs(yytext, outfp);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
<INITIAL>"{"                {
 | 
					<INITIAL>"{"                {
 | 
				
			||||||
                                yylval.string = stringf("#line %d\n", yylineno);
 | 
					                                yylval.string = ""; //stringf("#line %d\n", yylineno);
 | 
				
			||||||
                                braces = 1;
 | 
					                                braces = 1;
 | 
				
			||||||
                                BEGIN(CSTRING);
 | 
					                                BEGIN(CSTRING);
 | 
				
			||||||
                                return CFRAGMENT;
 | 
					                                return CFRAGMENT;
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
	Add table
		
		Reference in a new issue