diff --git a/include/base/SMPFunction.h b/include/base/SMPFunction.h index e7554b0ad40a521bcc2b0b25be339905b57af0aa..9d75c85c94bd021fd3df232db3e3ece935bc3adc 100644 --- a/include/base/SMPFunction.h +++ b/include/base/SMPFunction.h @@ -311,7 +311,7 @@ public: inline bool HasReducibleControlFlow(void) const { return HasReducibleCFG; }; inline bool HasPushAfterFrameAlloc(void) const { return PushAfterLocalVarAlloc; }; inline bool IsLinkerStub(void) const { return LinkerStub; }; - inline bool IsAddrInFunc(STARS_ea_t addr) { return ((addr >= FuncInfo->get_startEA()) && (addr <= FuncInfo->get_endEA())); } +// inline bool IsAddrInFunc(STARS_ea_t addr) { return ((addr >= FuncInfo->get_startEA()) && (addr <= FuncInfo->get_endEA())); } inline bool IsLibFunc(void) const { return LibFunc; }; inline bool IsLeaf(void) const { return (!IndirectCalls && DirectCallTargets.empty()); }; inline bool IsSafe(void) const { return SafeFunc; }; // safe to follow stack access DEF-USE chains diff --git a/include/base/SMPProgram.h b/include/base/SMPProgram.h index 3db42396690a08d30c1c5cbf692b2808ef2db17a..06c6c842a61d9d208a5f1ec991e16f447e1b7d2b 100644 --- a/include/base/SMPProgram.h +++ b/include/base/SMPProgram.h @@ -32,7 +32,7 @@ // // This header defines the interfaces needed for analyzing whole programs. -#include <string> // defines std::string. +#include <string> #include <utility> #include <list> #include <vector> @@ -41,8 +41,6 @@ #include <cstddef> -#include <string.h> // diff than <string> (which defines std::string). This defines strcmp, etc. - #include "interfaces/STARSTypes.h" #include "interfaces/SMPDBInterface.h" #include "base/SMPDataFlowAnalysis.h" @@ -63,16 +61,11 @@ extern STARS_ea_t HighestGlobalVarAddress; extern STARS_ea_t LowestCodeAddress; extern STARS_ea_t HighestCodeAddress; +//TODO: Move next three funcs to global_STARS_program, return false in base version, override IDA with these versions inline bool IsImmedGlobalAddress(STARS_ea_t ImmedValue) { return ((ImmedValue >= LowestGlobalVarAddress) && (ImmedValue <= HighestGlobalVarAddress)); } -// NOTE: Change this when we do targets with data (other than switch tables) in code. -// Call IsDataAddress() first to weed out data items in the code range. -inline bool IsImmedCodeAddress(STARS_ea_t ImmedValue) { - return ((ImmedValue >= LowestCodeAddress) && (ImmedValue <= HighestCodeAddress)); -} - #if 0 // Is the address in a data segment? // NOTE: If we do targets with interleaved code and data, we must change the implementation. @@ -80,7 +73,7 @@ bool IsDataAddress(STARS_ea_t Address); #endif inline bool IsImmedNumeric(uintptr_t ImmedValue) { - return (!(IsImmedGlobalAddress(ImmedValue) || IsImmedCodeAddress(ImmedValue))); + return (!(IsImmedGlobalAddress(ImmedValue) || global_STARS_program->IsImmedCodeAddress(ImmedValue))); } class LessOff { diff --git a/include/interfaces/abstract/STARSProgram.h b/include/interfaces/abstract/STARSProgram.h index 06824bad491d5c84ee92d522185a17f0b9196071..eaf68937e3f50b730f4f501f9a46c3dcfcadb2b7 100644 --- a/include/interfaces/abstract/STARSProgram.h +++ b/include/interfaces/abstract/STARSProgram.h @@ -83,6 +83,7 @@ class STARS_Program_t virtual void PrintAllCodeToCodeXrefs(STARS_ea_t InstAddr, std::size_t InstSize) = 0; // Analysis methods + virtual bool IsImmedCodeAddress(STARS_ea_t ImmedValue) { return false; }; // Is ImmedValue a code address? virtual void ReportTotalCodeSize(unsigned long long TotalCodeSize) = 0; // Set flags, take actions based on code size. virtual void InitStaticDataTable(SMPProgram *CurrProg) = 0; // Process global static data sections virtual void GetBlockSuccessorTargets(bool CallFlag, STARS_InstructionID_t LastBlockInst, std::size_t InstSize, std::list<STARS_InstructionID_t> &SuccList) = 0; // Get successors for LastBlockInst, omitting call targets diff --git a/include/interfaces/idapro/STARSFunction.h b/include/interfaces/idapro/STARSFunction.h index ae851ca9384fd50546c0569cc97927b8e21039dc..b6ffbf87ebcfc3969f39a36045cfbdf9f607d0d4 100644 --- a/include/interfaces/idapro/STARSFunction.h +++ b/include/interfaces/idapro/STARSFunction.h @@ -6,6 +6,8 @@ #include "interfaces/STARSTypes.h" +class SMPFunction; + class STARS_IDA_Function_t : public STARS_Function_t { public: @@ -20,8 +22,8 @@ public: // Accessor methods - virtual STARS_ea_t get_startEA() { return the_func->startEA; } - virtual STARS_ea_t get_endEA() { return the_func->endEA; } + virtual STARS_ea_t get_startEA() { return the_func->startEA; } + virtual STARS_ea_t get_endEA() { return the_func->endEA; } virtual char* GetFunctionName(const char* name, const int len) const { return ::get_func_name(the_func->startEA, (char *) name, len); }; virtual std::size_t GetFrameSize() { return frsize; } virtual void SetFrameSize(std::size_t fs) { frsize = fs; } diff --git a/include/interfaces/idapro/STARSProgram.h b/include/interfaces/idapro/STARSProgram.h index dccb0d331ff3489f4bfa79f2af295f335d9f094b..ba490b1735d8f3c64c1fa8f21d45c2606ac5e878 100644 --- a/include/interfaces/idapro/STARSProgram.h +++ b/include/interfaces/idapro/STARSProgram.h @@ -14,6 +14,8 @@ // #include "interfaces/STARSTypes.h" #include "interfaces/abstract/STARSProgram.h" +#include "base/SMPProgram.h" + class STARS_IDA_Program_t : public STARS_Program_t { public: // Data initialization @@ -32,6 +34,12 @@ public: virtual void PrintAllCodeToCodeXrefs(STARS_ea_t InstAddr, std::size_t InstSize); // Analysis methods + + // NOTE: Change this when we do targets with data (other than switch tables) in code. + // Call IsDataAddress() first to weed out data items in the code range. + bool IsImmedCodeAddress(STARS_ea_t ImmedValue) { + return ((ImmedValue >= LowestCodeAddress) && (ImmedValue <= HighestCodeAddress)); + } void ReportTotalCodeSize(unsigned long long TotalCodeSize); void InitStaticDataTable(SMPProgram *CurrProg); void GetBlockSuccessorTargets(bool CallFlag, STARS_InstructionID_t LastBlockInst, std::size_t InstSize, std::list<STARS_InstructionID_t> &SuccList); // Get successors for LastBlockInst, omitting call targets diff --git a/src/base/SMPDataFlowAnalysis.cpp b/src/base/SMPDataFlowAnalysis.cpp index 1cd7aaf4c3df06e4b1d4e9a9839c33cacd6383f6..8d529c2a6bda920d9d6a3881888b7f913f24a6b8 100644 --- a/src/base/SMPDataFlowAnalysis.cpp +++ b/src/base/SMPDataFlowAnalysis.cpp @@ -69,12 +69,12 @@ const char *RegNames[MAX_IDA_REG + 1] = "DS", "FS", "GS", "CF", "ZF", "SF", "OF", "PF", "AF", "TF", "IF", "DF", "EFLAGS", "FPU_ST0", "FPU_ST1", "FPU_ST2", "FPU_ST3", "FPU_ST4", "FPU_ST5", "FPU_ST6", "FPU_ST7", "FPU_CTRL", "FPU_STAT", "FPU_TAGS", - "MMX0", "MMX1", "MMX2", "MMX3", "MMX4", "MMX5", "MMX6", "MMX7", - "XMM0", "XMM1", "XMM2", "XMM3", "XMM4", "XMM5", "XMM6", "XMM7", - "XMM8", "XMM9", "XMM10", "XMM11", "XMM12", "XMM13", "XMM14", "XMM15", - "MXCSR", - "YMM0", "YMM1", "YMM2", "YMM3", "YMM4", "YMM5", "YMM6", "YMM7", - "YMM8", "YMM9", "YMM10", "YMM11", "YMM12", "YMM13", "YMM14", "YMM15", + "MMX0", "MMX1", "MMX2", "MMX3", "MMX4", "MMX5", "MMX6", "MMX7", + "XMM0", "XMM1", "XMM2", "XMM3", "XMM4", "XMM5", "XMM6", "XMM7", + "XMM8", "XMM9", "XMM10", "XMM11", "XMM12", "XMM13", "XMM14", "XMM15", + "MXCSR", + "YMM0", "YMM1", "YMM2", "YMM3", "YMM4", "YMM5", "YMM6", "YMM7", + "YMM8", "YMM9", "YMM10", "YMM11", "YMM12", "YMM13", "YMM14", "YMM15", "REG_ERROR" }; @@ -88,12 +88,12 @@ const unsigned char RegSizes[MAX_IDA_REG + 1] = 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 10, 10, 10, 10, 10, 10, 10, 10, 4, 4, 4, - 16, 16, 16, 16, 16, 16, 16, 16, - 16, 16, 16, 16, 16, 16, 16, 16, - 16, 16, 16, 16, 16, 16, 16, 16, - 4, - 32, 32, 32, 32, 32, 32, 32, 32, - 32, 32, 32, 32, 32, 32, 32, 32, + 16, 16, 16, 16, 16, 16, 16, 16, + 16, 16, 16, 16, 16, 16, 16, 16, + 16, 16, 16, 16, 16, 16, 16, 16, + 4, + 32, 32, 32, 32, 32, 32, 32, 32, + 32, 32, 32, 32, 32, 32, 32, 32, 4 }; diff --git a/src/base/SMPFunction.cpp b/src/base/SMPFunction.cpp index f71bd50b6d4c5ae0058aa1340c2c9b40188fd74c..3d413c7e58dd42b2916476cf857e7a8ff3bc0954 100644 --- a/src/base/SMPFunction.cpp +++ b/src/base/SMPFunction.cpp @@ -1853,7 +1853,7 @@ void SMPFunction::FindAllAllocsAndDeallocs(void) { // THE ASSUMPTION THAT WE HAVE ONLY PUSH INSTRUCTIONS BEFORE // THE ALLOCATING INSTR IS ONLY TRUE WHEN LOCALVARSSIZE == 0; else { - STARS_ea_t SaveAddr = this->FuncInfo->get_startEA(); + STARS_ea_t SaveAddr = this->GetStartAddr(); list<SMPInstr *>::iterator InstIter = this->Instrs.begin(); #if SMP_USE_SSA_FNOP_MARKER ++InstIter; // skip marker instruction @@ -2526,7 +2526,7 @@ void SMPFunction::SemiNaiveLocalVarID(void) { list<SMPInstr *>::iterator InstIter; this->SetLocalVarOffsetLimit(-20000); - STARS_Function_t *FuncPtr = SMP_get_func(this->FuncInfo->get_startEA()); + STARS_Function_t *FuncPtr = SMP_get_func(this->GetStartAddr()); if (NULL == FuncPtr) { SMP_msg("FATAL ERROR in SMPFunction::SemiNaiveLocalVarID; no func ptr\n"); } @@ -3884,7 +3884,7 @@ void SMPFunction::AnalyzeFunc(void) { #endif // Get some basic info from the FuncInfo structure. - this->Size = this->FuncInfo->get_endEA() - this->FuncInfo->get_startEA(); + this->Size = this->FuncInfo->get_endEA() - this->GetStartAddr(); this->UseFP = this->FuncInfo->FunctionUsesFP(); this->StaticFunc = this->FuncInfo->IsStaticFunction(); this->LibFunc = this->FuncInfo->IsLibraryFunction(); @@ -8115,11 +8115,11 @@ void SMPFunction::EmitAnnotations(FILE *AnnotFile, FILE *InfoAnnotFile) { || (this->HasUnresolvedIndirectJumps()) || (this->HasSharedChunks())); if (this->StaticFunc) { - SMP_fprintf(AnnotFile, "%10lx %6zu FUNC LOCAL %s ", (unsigned long) this->FuncInfo->get_startEA(), + SMP_fprintf(AnnotFile, "%10lx %6zu FUNC LOCAL %s ", (unsigned long) this->GetStartAddr(), this->Size, this->GetFuncName()); } else { - SMP_fprintf(AnnotFile, "%10lx %6zu FUNC GLOBAL %s ", (unsigned long) this->FuncInfo->get_startEA(), + SMP_fprintf(AnnotFile, "%10lx %6zu FUNC GLOBAL %s ", (unsigned long) this->GetStartAddr(), this->Size, this->GetFuncName()); } switch (this->GetReturnAddressStatus()) @@ -8165,7 +8165,7 @@ void SMPFunction::EmitAnnotations(FILE *AnnotFile, FILE *InfoAnnotFile) { SMP_fprintf(AnnotFile, "\n"); // Emit annotations about how to restore register values - SMP_fprintf(AnnotFile, "%10lx %6d FUNC FRAMERESTORE ", (unsigned long) this->FuncInfo->get_startEA(), 0); + SMP_fprintf(AnnotFile, "%10lx %6d FUNC FRAMERESTORE ", (unsigned long) this->GetStartAddr(), 0); for (int i = STARS_x86_R_ax; i <= global_STARS_program->GetSTARS_MD_LAST_SAVED_REG_NUM(); i++) { SMP_fprintf(AnnotFile, "%d %d %d ", i, this->SavedRegLoc[i], this->ReturnRegTypes[i]); } @@ -8173,7 +8173,7 @@ void SMPFunction::EmitAnnotations(FILE *AnnotFile, FILE *InfoAnnotFile) { // Print type left in the return register. if (MD_RETURN_VALUE_REG != STARS_x86_R_none) { - SMP_fprintf(InfoAnnotFile, "%10lx %6u FUNC RETURNTYPE ", (unsigned long) this->FuncInfo->get_startEA(), this->Size); + SMP_fprintf(InfoAnnotFile, "%10lx %6u FUNC RETURNTYPE ", (unsigned long) this->GetStartAddr(), this->Size); SMP_fprintf(InfoAnnotFile, "%s %d\n", MDGetRegNumName(MD_RETURN_VALUE_REG, global_STARS_program->GetSTARS_ISA_Bytewidth()), this->ReturnRegTypes[MD_RETURN_VALUE_REG]); } // Print types of incoming arguments, if any. @@ -8184,7 +8184,7 @@ void SMPFunction::EmitAnnotations(FILE *AnnotFile, FILE *InfoAnnotFile) { if (ArgLimit >= STARS_MAX_ARGS_PER_FUNC) { ArgLimit = STARS_MAX_ARGS_PER_FUNC - 1; } - SMP_fprintf(InfoAnnotFile, "%10lx %6u FUNC INARGS %4u ", (unsigned long) this->FuncInfo->get_startEA(), this->Size, + SMP_fprintf(InfoAnnotFile, "%10lx %6u FUNC INARGS %4u ", (unsigned long) this->GetStartAddr(), this->Size, ArgLimit + 1); for (ArgIndex = 0; ArgIndex <= ArgLimit; ++ArgIndex) { SMP_fprintf(InfoAnnotFile, "ARG%u %u ", ArgIndex, this->InArgTypes[ArgIndex]); @@ -8192,7 +8192,7 @@ void SMPFunction::EmitAnnotations(FILE *AnnotFile, FILE *InfoAnnotFile) { SMP_fprintf(InfoAnnotFile, "\n"); } - SMP_fprintf(AnnotFile, "%10lx %6d FUNC MMSAFENESS ", (unsigned long) this->FuncInfo->get_startEA(), 0); + SMP_fprintf(AnnotFile, "%10lx %6d FUNC MMSAFENESS ", (unsigned long) this->GetStartAddr(), 0); if (!IsSpecSafe()) SMP_fprintf(AnnotFile, "UNSAFE\n"); else if (!IsSafe()) @@ -8205,7 +8205,7 @@ void SMPFunction::EmitAnnotations(FILE *AnnotFile, FILE *InfoAnnotFile) { // If function has problems that limited our analyses, emit an information annotation so that // other tools can be aware of which analyses will be sound. if (FuncHasProblems) { - SMP_fprintf(InfoAnnotFile, "%10lx %6zu FUNC PROBLEM %s ", (unsigned long) this->FuncInfo->get_startEA(), + SMP_fprintf(InfoAnnotFile, "%10lx %6zu FUNC PROBLEM %s ", (unsigned long) this->GetStartAddr(), this->Size, this->GetFuncName()); if (!this->AnalyzedSP) { SMP_fprintf(InfoAnnotFile, "STACKANALYSIS "); @@ -8564,7 +8564,7 @@ void SMPFunction::MarkFunctionSafe() { #endif } - STARS_Function_t *FuncPtr = SMP_get_func(this->FuncInfo->get_startEA()); + STARS_Function_t *FuncPtr = SMP_get_func(this->GetStartAddr()); if (NULL == FuncPtr) { SMP_msg("FATAL ERROR in SMPFunction::SemiNaiveLocalVarID; no func ptr\n"); } diff --git a/src/base/SMPInstr.cpp b/src/base/SMPInstr.cpp index 4e92a8ae5f8e571d9591e28ada1739906ac5d11f..9423951e9e9ddb5bd3728b66e0ab4b180e779cd9 100644 --- a/src/base/SMPInstr.cpp +++ b/src/base/SMPInstr.cpp @@ -5583,7 +5583,13 @@ STARS_uval_t SMPInstr::MDGetShiftCount(void) const { SMPRegTransfer *CurrRT = this->RTL.GetRT(0); assert(CurrRT->HasRightSubTree()); CurrRT = CurrRT->GetRightTree(); + if (this->MDIsDoubleRegShift()) { + // RTL has extra level of depth. + assert(CurrRT->HasRightSubTree()); + CurrRT = CurrRT->GetRightTree(); + } STARSOpndTypePtr ShiftCountOp = CurrRT->GetRightOperand(); + assert(nullptr != ShiftCountOp); if (ShiftCountOp->IsImmedOp()) { ShiftCount = ShiftCountOp->GetImmedValue(); } @@ -6556,7 +6562,7 @@ void SMPInstr::SetImmedTypes(bool UseFP) { CurrUse = this->SetUseType(UseOp, POINTER); } #endif - else if (this->MDIsInterruptCall() || IsImmedCodeAddress((STARS_ea_t) ImmVal)) { + else if (this->MDIsInterruptCall() || global_STARS_program->IsImmedCodeAddress((STARS_ea_t)ImmVal)) { #if SMP_VERBOSE_DEBUG_BUILD_RTL if (DebugFlag) SMP_msg("Setting to CODEPTR\n"); #endif @@ -9721,7 +9727,7 @@ bool SMPInstr::InferOperatorFGInfo(SMPRegTransfer *CurrRT, bool FirstIter, struc // Data address (type GLOBALPTR) RightFG.SignMiscInfo |= FG_MASK_UNSIGNED; } - else if (this->MDIsInterruptCall() || IsImmedCodeAddress((STARS_ea_t) ImmVal)) { + else if (this->MDIsInterruptCall() || global_STARS_program->IsImmedCodeAddress((STARS_ea_t) ImmVal)) { // Code address (type GLOBALPTR) RightFG.SignMiscInfo |= FG_MASK_UNSIGNED; } diff --git a/src/interfaces/idapro/STARSInterface.cpp b/src/interfaces/idapro/STARSInterface.cpp index c90c214e5246255480774cabd69a64188a2d37f0..9b3203b77db6166de2bfd440a1bf09f57e80de1c 100644 --- a/src/interfaces/idapro/STARSInterface.cpp +++ b/src/interfaces/idapro/STARSInterface.cpp @@ -221,6 +221,7 @@ bool STARS_IDA_Interface_t::IsInstJumpTarget(STARS_InstructionID_t InstID) const // at its cross references and seeing if it has "TO" code xrefs. bool InstIsJumpTarget = false; SMP_xref_t xrefs; + // TODO: Why XREF_FAR? What about near jumps? for (bool ok = xrefs.SMP_first_to(InstID.GetIDWithinFile(), XREF_FAR); ok; ok = xrefs.SMP_next_to()) { if ((xrefs.GetFrom() != 0) && (xrefs.GetIscode())) { InstIsJumpTarget = true;