Fixed Dan's confusion regarding alignment of fields. Modified the
authorbdemsky <bdemsky>
Thu, 26 Feb 2004 20:13:49 +0000 (20:13 +0000)
committerbdemsky <bdemsky>
Thu, 26 Feb 2004 20:13:49 +0000 (20:13 +0000)
OpExpr class to support more operations, and to actually perform the
operations when possible.  (I like readable code!)

Wrote code to write to data structures...Should be the last major
component..

Repair/RepairCompiler/MCC/IR/DotExpr.java
Repair/RepairCompiler/MCC/IR/OpExpr.java
Repair/RepairCompiler/MCC/IR/Opcode.java
Repair/RepairCompiler/MCC/IR/RepairGenerator.java
Repair/RepairCompiler/MCC/IR/StructureTypeDescriptor.java
Repair/RepairCompiler/MCC/IR/UpdateNode.java

index 8253991..c7ed42f 100755 (executable)
@@ -212,7 +212,7 @@ public class DotExpr extends Expr {
                 writer.outputline("int " + dest.getSafeSymbol() + 
                                   " = " + ptr + "(" + leftd.getSafeSymbol() + " + " + offset.getSafeSymbol() + ");");  
                 dotypecheck = true;
-            }            
+            }
         }
 
 
index 5325c3b..7a256bd 100755 (executable)
@@ -8,12 +8,81 @@ public class OpExpr extends Expr {
     Expr right;
     Opcode opcode;
 
-    public OpExpr(Opcode opcode, Expr left, Expr right) {
-        this.opcode = opcode;
-        this.left = left;
-        this.right = right;
+    public static boolean isInt(Expr e) {
+       if ((e instanceof IntegerLiteralExpr)||
+           ((e instanceof OpExpr)&&(((OpExpr)e).getLeftExpr() instanceof IntegerLiteralExpr)))
+           return true;
+       return false;
+    }
 
-        assert (right == null && opcode == Opcode.NOT) || (right != null);
+    public static int getInt(Expr e) {
+       if (e instanceof IntegerLiteralExpr)
+           return ((IntegerLiteralExpr)e).getValue();
+       else if ((e instanceof OpExpr) && (((OpExpr)e).getLeftExpr() instanceof IntegerLiteralExpr))
+           return ((IntegerLiteralExpr)((OpExpr)e).getLeftExpr()).getValue();
+       else throw new Error();
+    }
+
+    public OpExpr(Opcode opcode, Expr left, Expr right) {
+       if ((isInt(left)&&isInt(right))||
+           (isInt(left)&&(opcode==Opcode.NOT))||
+           (isInt(left)&&(opcode==Opcode.RND))) {
+           this.opcode=Opcode.NOP;
+           this.right=null;
+           int lint=getInt(left);
+           int rint=getInt(right);
+           int value=0;
+           if (opcode==Opcode.ADD) {
+               value=lint+rint;
+           } else if (opcode==Opcode.SUB) {
+               value=lint-rint;
+           } else if (opcode==Opcode.SHL) {
+               value=lint<<rint;
+           } else if (opcode==Opcode.SHR) {
+               value=lint>>rint;
+           } else if (opcode==Opcode.MULT) {
+               value=lint*rint;
+           } else if (opcode==Opcode.DIV) {
+               value=lint/rint;
+           } else if (opcode==Opcode.GT) {
+               if (lint>rint)
+                   value=1;
+           } else if (opcode==Opcode.GE) {
+               if (lint>=rint)
+                   value=1;
+           } else if (opcode==Opcode.LT) {
+               if (lint<rint)
+                   value=1;
+           } else if (opcode==Opcode.LE) {
+               if (lint<=rint)
+                   value=1;
+           } else if (opcode==Opcode.EQ) {
+               if (lint==rint)
+                   value=1;
+           } else if (opcode==Opcode.NE) {
+               if (lint!=rint)
+                   value=1;
+           } else if (opcode==Opcode.AND) {
+               if ((lint!=0)&&(rint!=0))
+                   value=1;
+           } else if (opcode==Opcode.OR) {
+               if ((lint!=0)||(rint!=0))
+                   value=1;
+           } else if (opcode==Opcode.NOT) {
+               if (lint==0)
+                   value=1;
+           } else if (opcode==Opcode.RND) {
+               value=((lint>>3)<<3);
+               if ((lint % 8)!=0)
+                   value+=8;
+           } else throw new Error("Unrecognized Opcode");
+           this.left=new IntegerLiteralExpr(value);
+           } else {
+           this.opcode = opcode;
+           this.left = left;
+           this.right = right;
+           assert (right == null && (opcode == Opcode.NOT||opcode==Opcode.RND)) || (right != null);
+       }
     }
 
     public Expr getRightExpr() {
@@ -39,6 +108,10 @@ public class OpExpr extends Expr {
     public String name() {
        if (opcode==Opcode.NOT)
            return "!("+left.name()+")";
+       if (opcode==Opcode.NOP)
+           return left.name();
+       if (opcode==Opcode.RND)
+           return "Round("+left.name()+")";
        String name=left.name()+opcode.toString();
        if (right!=null)
            name+=right.name();
@@ -60,7 +133,7 @@ public class OpExpr extends Expr {
            return false;
        if (!left.equals(remap,oe.left))
            return false;
-       if (opcode!=Opcode.NOT)
+       if ((opcode!=Opcode.NOT)&&(opcode!=Opcode.RND)&&(opcode!=Opcode.NOP))
            if (!right.equals(remap,oe.right))
                return false;
        return true;
@@ -169,7 +242,14 @@ public class OpExpr extends Expr {
         }
 
         String code;
-        if (opcode != Opcode.NOT) { /* two operands */
+       if (opcode == Opcode.RND) {
+           writer.outputline("int " +dest.getSafeSymbol() + " = (" +
+                             ld.getSafeSymbol() + ">>3)<<3; ");
+           writer.outputline("if ("+ld.getSafeSymbol()+" % 8) "+dest.getSafeSymbol()+"+=8;");
+       } else if (opcode == Opcode.NOP) {
+           writer.outputline("int " +dest.getSafeSymbol() + " = " +
+                             ld.getSafeSymbol() +"; ");
+       } else if (opcode != Opcode.NOT) { /* two operands */
             assert rd != null;
             writer.outputline("int " + dest.getSafeSymbol() + " = " + 
                               ld.getSafeSymbol() + " " + opcode.toString() + " " + rd.getSafeSymbol() + ";");
@@ -181,6 +261,12 @@ public class OpExpr extends Expr {
     public void prettyPrint(PrettyPrinter pp) {
         pp.output("(");
         if (opcode == Opcode.NOT) {
+           pp.output("!");
+            left.prettyPrint(pp);
+       } else if (opcode == Opcode.NOP) {
+            left.prettyPrint(pp);
+       } else if (opcode == Opcode.RND) {
+           pp.output("RND ");
             left.prettyPrint(pp);
         } else {           
             left.prettyPrint(pp);
index bc062b8..eed9bba 100755 (executable)
@@ -23,6 +23,10 @@ public class Opcode {
     public static final Opcode AND = new Opcode("&&");
     public static final Opcode OR = new Opcode("||");
     public static final Opcode NOT = new Opcode("!");
+    public static final Opcode RND = new Opcode("RND");
+    public static final Opcode NOP = new Opcode("NOP");
+    public static final Opcode SHL = new Opcode("<<");
+    public static final Opcode SHR = new Opcode(">>");
 
     public static Opcode decodeFromString(String opname) {
         Opcode opcode;
index bcf68f5..c38860d 100755 (executable)
@@ -88,6 +88,13 @@ public class RepairGenerator {
        String repairtable="repairtable";
        String left="left";
        String right="right";
+       /* Rewrite globals */
+
+       for (Iterator it=this.state.stGlobals.descriptors();it.hasNext();) {
+           VarDescriptor vd=(VarDescriptor)it.next();
+           craux.outputline("#define "+vd.getSafeSymbol()+" "+state+"->"+vd.getSafeSymbol());
+       }
+
        for(Iterator it=termination.updatenodes.iterator();it.hasNext();) {
            GraphNode gn=(GraphNode) it.next();
            TermNode tn=(TermNode) gn.getOwner();
@@ -108,7 +115,11 @@ public class RepairGenerator {
                        craux.outputline("void "+methodname+"("+name+"_state * "+state+","+name+" * "+model+", RepairHash * "+repairtable+", int "+left+")");
                    }
                    craux.startblock();
-                   un.generate(craux, false, left,right);
+                   final SymbolTable st = un.getRule().getSymbolTable();                
+                   CodeWriter cr = new StandardCodeWriter(outputaux) {
+                        public SymbolTable getSymbolTable() { return st; }
+                    };
+                   un.generate(cr, false, left,right);
                    craux.endblock();
                    break;
                case MultUpdateNode.REMOVE:
@@ -133,7 +144,11 @@ public class RepairGenerator {
                    crhead.outputline(methodcall+";");
                    craux.outputline(methodcall);
                    craux.startblock();
-                   un.generate(craux, true, null,null);
+                   final SymbolTable st2 = un.getRule().getSymbolTable();                
+                   CodeWriter cr2 = new StandardCodeWriter(outputaux) {
+                        public SymbolTable getSymbolTable() { return st2; }
+                    };
+                   un.generate(cr2, true, null,null);
                    craux.endblock();
                    break;
                case MultUpdateNode.MODIFY:
index 7296606..222c6c1 100755 (executable)
@@ -28,66 +28,61 @@ public class StructureTypeDescriptor extends TypeDescriptor {
         return fields.keys();
     }
    
-    private Vector getFieldSizes() {
-        Vector fieldsizes = new Vector();
-                
+    
+    public Expr getSizeExpr() {        
+        return getOffsetExpr(null);
+    }
+
+    public Expr getOffsetExpr(FieldDescriptor field) {
+       
+       boolean aligned=true;
+        Expr size = new IntegerLiteralExpr(0);
+        
         for (int i = 0; i < fieldlist.size(); i++) {
-            FieldDescriptor fd = (FieldDescriptor) fieldlist.elementAt(i);
+            FieldDescriptor fd = (FieldDescriptor)fieldlist.elementAt(i);
+
             TypeDescriptor td = fd.getType();
             boolean ptr = fd.getPtr();
-
             Expr basesize; 
             if (ptr) { /* ptrs are 32bits */
-                basesize = new IntegerLiteralExpr(32);
+               
+               basesize = new IntegerLiteralExpr(32);
             } else {
-                basesize = td.getSizeExpr();
+               basesize = td.getSizeExpr();
             }
-
+           Expr fieldsize;
             if (fd instanceof ArrayDescriptor) {
                 Expr totalsize = new OpExpr(Opcode.MULT, basesize, ((ArrayDescriptor) fd).getIndexBound());
-                fieldsizes.addElement(totalsize);
+               fieldsize=totalsize;
             } else {
-                fieldsizes.addElement(basesize);
+                fieldsize=basesize;
             }
-        }
-
-        return fieldsizes;
-    }
-    
-    public Expr getSizeExpr() {        
-        Vector fieldsizes = getFieldSizes();
-
-        /* we've got the field sizes! now return the addition! */
-        Expr size = new IntegerLiteralExpr(0);
-        
-        for (int i = 0; i < fieldsizes.size(); i++) {
-            Expr fieldsize = (Expr) fieldsizes.elementAt(i);
-            size = new OpExpr(Opcode.ADD, fieldsize, size);
-        }
-        
-        return size;
-    }
-
-    public Expr getOffsetExpr(FieldDescriptor field) {
-        Vector fieldsizes = getFieldSizes();
-
-        // #ATTN#: getOffsetExpr needs to be called with the fielddescriptor obect that is in teh vector list
-        // this means that if the field is an arraydescriptor you have to call getOffsetExpr with the array 
-
-        /* we've got the field sizes! now return the addition! */
-        Expr size = new IntegerLiteralExpr(0);
-        
-        for (int i = 0; i < fieldsizes.size(); i++) {
-            FieldDescriptor fd = (FieldDescriptor)fieldlist.elementAt(i);
+           if (td instanceof ReservedTypeDescriptor) {
+               ReservedTypeDescriptor rtd=(ReservedTypeDescriptor) td;
+               if (rtd==ReservedTypeDescriptor.BIT) {
+                   aligned=false;
+               } else {
+                   if (!aligned) {
+                       size=new OpExpr(Opcode.RND, size,null);
+                       aligned=true;
+                   }
+               }
+           } else {
+               if (!aligned) {
+                   size=new OpExpr(Opcode.RND, size,null);
+                   aligned=true;
+               }
+           }
 
             if (fd == field) { /* stop, reached target field */
                 break; 
             }
 
-            Expr fieldsize = (Expr) fieldsizes.elementAt(i);
             size = new OpExpr(Opcode.ADD, fieldsize, size);
         }
-        
+
+        if ((field==null)&&(!aligned))
+           return new OpExpr(Opcode.RND, size, null);
         return size;
     }
 
index 8eee4a8..0f11463 100755 (executable)
@@ -240,11 +240,67 @@ class UpdateNode {
                cr.outputline(vd.getSafeSymbol()+"="+right.getSafeSymbol()+";");
            } else if (u.isField()) {
                /* NEED TO FIX */
+               Expr subexpr=((DotExpr)u.getLeftExpr()).getExpr();
+               Expr intindex=((DotExpr)u.getLeftExpr()).getIndex();
+               VarDescriptor subvd=VarDescriptor.makeNew("subexpr");
+               VarDescriptor indexvd=VarDescriptor.makeNew("index");
+               subexpr.generate(cr,subvd);
+               if (intindex!=null)
+                   intindex.generate(cr,indexvd);
+               FieldDescriptor fd=(FieldDescriptor)u.getDescriptor();
+               StructureTypeDescriptor std=(StructureTypeDescriptor)subexpr.getType();
+               if (fd instanceof ArrayDescriptor) {
+                   fd = ((ArrayDescriptor) fd).getField();
+               }
+
+               Expr offsetbits = std.getOffsetExpr(fd);
+               if (intindex != null) {
+                   Expr basesize = fd.getBaseSizeExpr();
+                   offsetbits = new OpExpr(Opcode.ADD, offsetbits, new OpExpr(Opcode.MULT, basesize, intindex));
+               }
+               Expr offsetbytes = new OpExpr(Opcode.SHR, offsetbits,new IntegerLiteralExpr(3));
+               Expr byteaddress=new OpExpr(Opcode.ADD, offsetbytes, subexpr);
+               VarDescriptor addr=VarDescriptor.makeNew("byteaddress");
+               byteaddress.generate(cr,addr);
+
+               if (fd.getType() instanceof ReservedTypeDescriptor && !fd.getPtr()) {
+                   ReservedTypeDescriptor rtd=(ReservedTypeDescriptor)fd.getType();
+                   if (rtd==ReservedTypeDescriptor.INT) {
+                       cr.outputline("*((int *) "+addr.getSafeSymbol()+")="+right.getSafeSymbol()+";");
+                   } else if (rtd==ReservedTypeDescriptor.SHORT) {
+                       cr.outputline("*((short *) "+addr.getSafeSymbol()+")="+right.getSafeSymbol()+";");
+                   } else if (rtd==ReservedTypeDescriptor.BYTE) {
+                       cr.outputline("*((char *) "+addr.getSafeSymbol()+")="+right.getSafeSymbol()+";");
+                   } else if (rtd==ReservedTypeDescriptor.BIT) {
+                       Expr tmp = new OpExpr(Opcode.SHL, offsetbytes, new IntegerLiteralExpr(3));
+                       Expr offset=new OpExpr(Opcode.SUB, offsetbits, tmp);
+                       Expr mask=new OpExpr(Opcode.SHR, new IntegerLiteralExpr(1), offset);
+                       VarDescriptor maskvar=VarDescriptor.makeNew("mask");
+                       mask.generate(cr,maskvar);
+                       cr.outputline("*((char *) "+addr.getSafeSymbol()+")|="+maskvar.getSafeSymbol()+";");
+                       cr.outputline("if (!"+right.getSafeSymbol()+")");
+                       cr.outputline("*((char *) "+addr.getSafeSymbol()+")^="+maskvar.getSafeSymbol()+";");
+                   } else throw new Error();
+               } else {
+                   /* Pointer */
+                   cr.outputline("*((int *) "+addr.getSafeSymbol()+")="+right.getSafeSymbol()+";");
+               }
            }
            cr.endblock();
-           
        }
     }
+
+    private int bitmask(int bits) {
+        int mask = 0;
+        
+        for (int i = 0; i < bits; i++) {
+            mask <<= 1;
+            mask += 1;
+        }
+
+        return mask;            
+    }
+
     private void generate_bindings(CodeWriter cr, String slot0, String slot1) {
        for(int i=0;i<bindings.size();i++) {
            Binding b=(Binding)bindings.get(i);