changeset 586:3fb4081164bd

*** empty log message ***
author kono
date Wed, 18 Jan 2006 13:36:50 +0900
parents a5b902b20300
children c991b82e6849
files Changes mc-code-ia32.c
diffstat 2 files changed, 48 insertions(+), 97 deletions(-) [+]
line wrap: on
line diff
--- a/Changes	Wed Jan 18 12:26:48 2006 +0900
+++ b/Changes	Wed Jan 18 13:36:50 2006 +0900
@@ -8516,4 +8516,15 @@
 だいたい動いているんだけど、かなり怪しい。その方がコード
 は良いんだが.... これは read only creg なんだよね。
 
-
+終りました。tosop は、いい加減だが、あんなもので動くのか。
+要は「tosop に入る前に確保するレジスタは emit_push で確保する」
+「use_register では、code_save_register で使うレジスタを確保する」
+ってことだね。
+
+register は0からでなく1から始める。code_gexpr では、creg に
+レジスタが入っている場合は、creg を clear。free_register する
+場合には、register variable かどうかをチェック。
+
+他のも、これにする方が正しそう。
+
+
--- a/mc-code-ia32.c	Wed Jan 18 12:26:48 2006 +0900
+++ b/mc-code-ia32.c	Wed Jan 18 13:36:50 2006 +0900
@@ -241,12 +241,13 @@
 
 /*
     creg   current register
+	ireg  current register for integer (int mode)
+	lreg  current register for long long (long long mode)
 
     regs[]        register usage
-    regv[]        value in register flag
 
     freg    current floating point register
-    fregv   value in floating point register
+	kept in FPU stack (no register)
  */
 
 #define REAL_MAX_LREGISTER 2
@@ -259,6 +260,13 @@
 static int *fregs  = ia32fregs;
 static int freg;
 
+// register number should start 1
+// regs[] value
+//    0 for not ready
+//   -1 use currrent register 
+//    1 used
+//    2 pointer cache (not used in ia32)
+//    3 (REG_VAR) register variable
 
 #define REG_EAX   1
 #define REG_EBX   2
@@ -273,13 +281,13 @@
 #define REG_L     10
 #define REG_fp REG_EBP
 
-#define DATA_REG 0    
-#define POINTER_REG 3    
-
+//  return value register
 #define RET_FREGISTER
 #define RET_DREGISTER
 #define RET_LREGISTER   REG_LCREG
 #define RET_REGISTER    REG_EAX
+
+//  defalut current register
 #define CREG_REGISTER   REG_EAX
 
 static char *reg_name[8+1]; 
@@ -336,7 +344,6 @@
 	if reg1 is used, reg0 contains old value.
      */
 
-
     char *move_op;
     code_clear_stack_reg(reg1); 
     move_op = (regs[reg1]||regs[reg1])?"\txchg %s,%s\n":"\tmovl %s,%s\n";
@@ -401,6 +408,7 @@
     int i = reg==USING_REG?creg:reg;
     if (ireg) { if (regs[ireg]!=REG_VAR) free_register(ireg); ireg=0; }
     if (!lreg||!regs[lreg]) {
+	// long long mode use all registers
 	code_save_stacks();
     }
     i = lreg = (reg==USE_CREG)?REG_LCREG:reg;
@@ -488,14 +496,6 @@
     }
 }
 
-/*
-int use_int(int i) { return i;}
-int use_float(int i) { return i;}
-int use_double(int i) { return i;}
-int use_longlong(int i) { return i; }
- */
-
-
 void
 gexpr_code_init(void){
     // use_register(creg,REG_EAX,0);
@@ -580,6 +580,11 @@
     error(-1);
 }
 
+/*
+    ESI,EDI are used as register variable
+    (both in integer and long long mode)
+ */
+
 int 
 get_input_register_var(int i,NMTBL *nptr,int is_code)
 {
@@ -848,31 +853,6 @@
     return xreg;
 }
 
-#if 0
-static int
-stack_top(int type)
-{
-    int xreg;
-    if (type==INT) {
-        xreg = reg_stack[reg_sp];
-        if (xreg<= -REG_LVAR_OFFSET) {
-            return list3(LVAR,REG_LVAR_OFFSET+xreg,0);
-        } else {
-            return list2(REGISTER,xreg);
-        }
-    } else {
-        xreg = freg_stack[freg_sp];
-        if (xreg<= -REG_LVAR_OFFSET) {
-            return list3(LVAR,REG_LVAR_OFFSET+xreg,0);
-        } else {
-            return list2(DREGISTER,xreg);
-        }
-    }
-    return xreg;
-}
-#endif
-
-
 void 
 code_label(int labelno)
 {
@@ -891,7 +871,6 @@
 
 }
 
-
 void
 code_rgvar(int e1,int creg) {
     use_int(creg);
@@ -903,7 +882,11 @@
 
 }
 
-static char *cload(int sign,int sz) { return sz==1?(sign?"movsbl":"movzbl"):sz==SIZE_OF_SHORT?(sign?"movswl":"movzwl"):"movl"; }
+static char *
+cload(int sign,int sz) {
+    return sz==1?(sign?"movsbl":"movzbl"):
+	    sz==SIZE_OF_SHORT?(sign?"movswl":"movzwl"):"movl";
+}
 
 void
 code_crgvar(int e1,int creg,int sign,int sz){
@@ -941,7 +924,6 @@
 extern void
 code_i2c(int reg)
 {
-    use_int(reg);
     use_data_reg(reg,1);
     printf("\t%s %s,%s\n",cload(1,1),
 	register_name(reg,1),register_name(reg,0));
@@ -950,7 +932,6 @@
 extern void
 code_i2s(int reg)
 {
-    use_int(reg);
     use_data_reg(reg,1);
     printf("\t%s %s,%s\n",cload(1,SIZE_OF_SHORT),
 	register_name(reg,2),register_name(reg,0));
@@ -959,7 +940,6 @@
 extern void
 code_u2uc(int reg)
 {   
-    use_int(reg);
     use_data_reg(reg,1);
     printf("\t%s %s,%s\n",cload(0,1),
 	register_name(reg,1),register_name(reg,0));
@@ -968,7 +948,6 @@
 extern void
 code_u2us(int reg)
 {   
-    use_int(reg);
     use_data_reg(reg,1);
     printf("\t%s %s,%s\n",cload(0,SIZE_OF_SHORT),
 	register_name(reg,2),register_name(reg,0));
@@ -1468,12 +1447,9 @@
 
 void
 code_fix_frame_pointer(int disp_offset) {
-#if 0
-    printf("\tlea %d(%%ebp),%%ebp\n",disp_offset);
-#endif
+    // must be empty
 }
 
-
 void
 code_jmp(char *s) {
     printf("\tjmp %s\n",s);
@@ -1606,9 +1582,6 @@
     char *orn,*crn;
     // creg = creg op oreg
 
-#if 0
-    int q;
-#endif
     use_int(reg);
 
     if(oreg==-1) {
@@ -1659,12 +1632,8 @@
 	break;
     case DIV:
     case UDIV:
-#if 0
-	q = list3(REG_EAX,0,reg);
-	q = list3(REG_ECX,q,oreg);
-	parallel_rassign(q);
-	orn = "%ecx";
-#else
+    case MOD:
+    case UMOD:
 	use_register(reg,REG_EAX,1);
 	if (oreg==REG_EAX) oreg=reg;
 	if (oreg==REG_EDX) {
@@ -1672,35 +1641,10 @@
 	    oreg = REG_ECX;
 	}
 	orn = register_name(oreg,0);
-#endif
-	if (op==DIV)
-	    printf("\tcltd\n\tidivl %s\n",orn);
-	else 
-	    printf("\txor %%edx,%%edx\n\tdivl %s\n",orn);
-	set_ireg(REG_EAX,0);
-	set_ireg(reg,1);
-	break;
-    case MOD:
-    case UMOD:
-#if 0
-	q = list3(REG_EAX,0,reg);
-	q = list3(REG_ECX,q,oreg);
-	parallel_rassign(q);
-	orn = "%ecx";
-#else
-	use_register(reg,REG_EAX,1);
-	if (oreg==REG_EAX) oreg=reg;
-	if (oreg==REG_EDX) {
-	    use_register(oreg,REG_ECX,1);
-	    oreg = REG_ECX;
-	}
-	orn = register_name(oreg,0);
-#endif
-	if (op==MOD)
-	    printf("\tcltd\n\tidivl %s\n",orn);
-	else 
-	    printf("\txor %%edx,%%edx\n\tdivl %s\n",orn);
-	set_ireg(REG_EDX,0);
+	printf((op==DIV||op==MOD)?
+	    "\tcltd\n\tidivl %s\n":
+	    "\txor %%edx,%%edx\n\tdivl %s\n",orn);
+	set_ireg((op==MOD||op==UMOD)?REG_EDX:REG_EAX,0);
 	set_ireg(reg,1);
 	break;
     }
@@ -1779,8 +1723,6 @@
 }
 
 
-
-
 void
 shift(char *op, int oreg,int reg)
 {
@@ -1958,7 +1900,6 @@
 enter1()
 {
     text_mode(0);
-    /* if(disp) printf("\tsubl $%d,%%esp\n",-disp); */
 }
 
 void
@@ -2046,6 +1987,7 @@
 
 void
 code_set_return_register(int mode) {
+    // before goto leave code, set return register
     if (cadr(fnptr->ty)==FLOAT) {
         // set_freg(RET_FREGISTER,mode);
     } else if (cadr(fnptr->ty)==DOUBLE) {
@@ -2061,10 +2003,7 @@
 void
 gen_gdecl(char *n, int gpc)
 {
-    /*
-    if (stmode!=STATIC)
-	printf(".globl %s\n",n); 
-     */
+    // must be empty
 }
 
 extern void
@@ -2312,7 +2251,7 @@
 {
     if (output_mode!=TEXT_EMIT_MODE) {
 	printf(".text\n");
-	printf("\t.align 2\n");
+	// printf("\t.align 2\n");
 	output_mode = TEXT_EMIT_MODE;
     }
 }
@@ -2723,7 +2662,7 @@
 code_clear_stack_reg(int reg1)
 {
     /* specified registers stacks are saved in local variable */
-    /* temporal registers or stacks in fpu are saved in local variable */
+    /* temporal registers are saved in local variable */
     int i,reg;
     for(i=0;i<reg_sp;i++) {
         if ((reg=reg_stack[i])>=0 && reg==reg1) {
@@ -2739,6 +2678,7 @@
 void
 code_save_fstacks()
 {
+    /* stacks in fpu are saved in local variable */
     int xreg,sp,uses;
     uses = use; use = 0;
     sp=freg_sp;