Exemple #1
0
        /*
        private long GetOffset(int rva) {
          for (int i=0; i < inputSections.Length; i++) {
            long offs = inputSections[i].GetOffset(rva);
            if (offs > 0) return offs;
          }
          return 0;
        }

        public bool ReadPadding(int boundary) {
          while ((Position % boundary) != 0) {
            if (buffer[index++] != 0) { return false; }
          }
          return true;
        }

        public String ReadName() {
          int len = NAMELEN;
          char [] nameStr = new char[NAMELEN];
          char ch = (char)ReadByte();
          int i=0;
          for (; (i < NAMELEN) && (ch != '\0'); i++) {
            nameStr[i] = ch;
            ch = (char)ReadByte();
          }
          return new String(nameStr,0,i);
        }

        internal String ReadString() {
          char [] str = new char[STRLEN];
          int i=0;
          char ch = (char)ReadByte();
          for (; ch != '\0'; i++) {
            str[i] = ch;
            ch = (char)ReadByte();
          }
          return new String(str,0,i);
        }

        public long GetPos() {
          return BaseStream.Position;
        }

        public void SetPos(int ix) {
          BaseStream.Position = ix;
        }
        */
        /*
        public void SetToRVA(int rva) {
          index = PESection.GetOffset(rva);
        //      Console.WriteLine("Setting buffer to rva " + PEConsts.Hex(rva) + " = index " + PEConsts.Hex(index));
        //      Console.WriteLine("Setting buffer to rva " + rva + " = index " + index);
        }

        public byte[] GetBuffer() {
          return buffer;
        }
        */
        private CILInstruction[] DoByteCodes(uint len, MethodDef thisMeth)
        {
            uint pos = 0;
            ArrayList instrList = new ArrayList();
            //int instrIx = 0;
            while (pos < len) {
                uint offset = pos;
                uint opCode = ReadByte();
                pos++;
                IType iType = IType.op;
                if (opCode == 0xFE) {
                    uint ix = ReadByte();
                    pos++;
                    opCode = (opCode << 8) + ix;
                    iType = FileImage.longInstrMap[ix];
                } else
                    iType = FileImage.instrMap[opCode];
                if (Diag.DiagOn) Console.WriteLine("Got instruction type " + iType);
                CILInstruction nextInstr = null;
                if (iType == IType.specialOp) {
                    pos += 4;
                    if (Diag.DiagOn) Console.WriteLine("Got instruction " + Hex.Byte((int)opCode));
                    switch (opCode) {
                        case ((int)SpecialOp.ldc_i8) :
                            nextInstr = new LongInstr((SpecialOp)opCode,ReadInt64());
                            pos += 4; break;
                        case ((int)SpecialOp.ldc_r4) :
                            nextInstr = new FloatInstr((SpecialOp)opCode,ReadSingle());
                            break;
                        case ((int)SpecialOp.ldc_r8) :
                            nextInstr = new DoubleInstr((SpecialOp)opCode,ReadDouble());
                            pos += 4; break;
                        case ((int)SpecialOp.calli) :
                            nextInstr = new SigInstr((SpecialOp)opCode,(CalliSig)GetTokenElement(ReadUInt32()));
                            break;
                        case ((int)SpecialOp.Switch) : // switch
                            uint count = ReadUInt32();
                            int[] offsets = new int[count];
                            for (uint i=0; i < count; i++)
                                offsets[i] = ReadInt32();
                            pos += (4 * count);
                            nextInstr = new SwitchInstr(offsets);
                            break;
                        case ((int)SpecialOp.ldstr) : // ldstr
                            uint strIx = ReadUInt32();
                            strIx = strIx & FileImage.ElementMask;
                            nextInstr = new StringInstr((SpecialOp)opCode,userstring.GetUserString(strIx));
                            break;
                        case ((int)MethodOp.ldtoken) :
                            MetaDataElement elem = GetTokenElement(ReadUInt32());
                            if (elem is Method)
                                nextInstr = new MethInstr((MethodOp)opCode,(Method)elem);
                            else if (elem is Field)
                                nextInstr = new FieldInstr((FieldOp)opCode,(Field)elem);
                            else
                                nextInstr =new TypeInstr((TypeOp)opCode,(Type)elem);
                            break;
                    }
                } else if (iType == IType.branchOp) {
                    if (Diag.DiagOn) Console.WriteLine("Got instruction " + Hex.Byte((int)opCode));
                    if ((opCode < 0x38) || (opCode == 0xDE)) { // br or leave.s
                        nextInstr = new BranchInstr(opCode,ReadSByte());
                        pos++;
                    } else {
                        nextInstr = new BranchInstr(opCode,ReadInt32());
                        pos += 4;
                    }
                } else {
                    if (Diag.DiagOn) Console.Write(Hex.Byte((int)opCode));
                    switch (iType) {
                        case (IType.op) :
                            if (Diag.DiagOn) Console.WriteLine("Got instruction " + (Op)opCode);
                            nextInstr = new Instr((Op)opCode); break;
                        case (IType.methOp) :
                            if (Diag.DiagOn) Console.WriteLine("Got instruction " + (MethodOp)opCode);
                            nextInstr = new MethInstr((MethodOp)opCode,(Method)GetTokenElement(ReadUInt32()));
                            pos += 4;
                            break;
                        case (IType.typeOp) :
                            if (Diag.DiagOn) Console.WriteLine("Got instruction " + (TypeOp)opCode);
                            uint ttok = ReadUInt32();
                            Type typeToken = (Type)GetTokenElement(ttok);
                            if (typeToken is GenericParTypeSpec)
                                typeToken = ((GenericParTypeSpec)typeToken).GetGenericParam(thisMeth);
                            nextInstr = new TypeInstr((TypeOp)opCode,typeToken);
                            pos += 4;
                            break;
                        case (IType.fieldOp) :
                            if (Diag.DiagOn) Console.WriteLine("Got instruction " + (FieldOp)opCode);
                            nextInstr = new FieldInstr((FieldOp)opCode,(Field)GetTokenElement(ReadUInt32()));
                            pos += 4;
                            break;
                        case (IType.int8Op) :
                            nextInstr = new IntInstr((IntOp)opCode,ReadSByte());
                            pos++;
                            break;
                        case (IType.uint8Op) :
                            nextInstr = new UIntInstr((IntOp)opCode,ReadByte());
                            pos++;
                            break;
                        case (IType.uint16Op) :
                            nextInstr =new UIntInstr((IntOp)opCode,ReadUInt16());
                            pos++;
                            break;
                        case (IType.int32Op) :
                            nextInstr =new IntInstr((IntOp)opCode,ReadInt32());
                            pos += 4;
                            break;
                    }
                }
                if (nextInstr != null) nextInstr.Resolve();
                instrList.Add(nextInstr);
            }
            CILInstruction[] instrs = new CILInstruction[instrList.Count];
            for (int i=0; i < instrs.Length; i++) {
                instrs[i] = (CILInstruction)instrList[i];
            }
            return instrs;
        }