diff options
Diffstat (limited to 'plugins/rtti')
| -rw-r--r-- | plugins/rtti/itanium.cpp | 19 | ||||
| -rw-r--r-- | plugins/rtti/microsoft.cpp | 42 |
2 files changed, 55 insertions, 6 deletions
diff --git a/plugins/rtti/itanium.cpp b/plugins/rtti/itanium.cpp index dae85b46..63f2c563 100644 --- a/plugins/rtti/itanium.cpp +++ b/plugins/rtti/itanium.cpp @@ -9,6 +9,7 @@ using namespace BinaryNinja::RTTI::Itanium; // TODO: Itanium doesnt really say anything about the sizing of these fields, i assume they are all u32 for thje most part. constexpr const char *TYPE_SOURCE_ITANIUM = "rtti_itanium"; +constexpr int MAX_FAILED_SCAN_ATTEMPTS = 10; Ref<Symbol> GetRealSymbol(BinaryView *view, uint64_t relocAddr, uint64_t symAddr) @@ -737,6 +738,7 @@ void ItaniumRTTIProcessor::ProcessRTTI() uint64_t maxTypeInfoSize = TypeInfoSize(m_view); auto scan = [&](const Ref<Section> §ion) { + int failedAttempts = 0; for (uint64_t currAddr = section->GetStart(); currAddr <= section->GetEnd() - maxTypeInfoSize; currAddr += addrSize) { if (bgTask->IsCancelled()) @@ -748,9 +750,14 @@ void ItaniumRTTIProcessor::ProcessRTTI() } catch (std::exception& e) { + if (failedAttempts++; failedAttempts > MAX_FAILED_SCAN_ATTEMPTS) + break; m_logger->LogWarnForException(e, "Failed to process object at %llx... skipping", currAddr); } } + + if (failedAttempts > MAX_FAILED_SCAN_ATTEMPTS) + m_logger->LogWarn("Too many failed scans for section %llx... skipping", section->GetStart()); }; m_view->BeginBulkModifySymbols(); @@ -763,8 +770,16 @@ void ItaniumRTTIProcessor::ProcessRTTI() // Some RTTI unfortunately will get put into a DefaultSectionSemantics section, so we have to check those. if (sectionSemantics == ReadOnlyDataSectionSemantics || sectionSemantics == DefaultSectionSemantics) { - m_logger->LogDebug("Attempting to find RTTI in section %llx", section->GetStart()); - scan(section); + // If a malformed binary makes the binary view set up unbacked sections we should not attempt to read in them. + if (m_view->ReadBuffer(section->GetStart(), 4).GetLength() == 4) + { + m_logger->LogDebug("Attempting to find RTTI in section %llx", section->GetStart()); + scan(section); + } + else + { + m_logger->LogDebug("Unbacked start for section %llx... skipping", section->GetStart()); + } } } m_view->EndBulkModifySymbols(); diff --git a/plugins/rtti/microsoft.cpp b/plugins/rtti/microsoft.cpp index 86875b25..ad9eb2e4 100644 --- a/plugins/rtti/microsoft.cpp +++ b/plugins/rtti/microsoft.cpp @@ -694,14 +694,34 @@ void MicrosoftRTTIProcessor::ProcessRTTI() { if (segment->GetFlags() == (SegmentReadable | SegmentContainsData)) { + // If a malformed binary makes the binary view set up unbacked segments we should not attempt to read in them. + if (m_view->ReadBuffer(segment->GetStart(), 4).GetLength() != 4) + { + m_logger->LogInfo("Unbacked start for segment %llx... skipping", segment->GetStart()); + continue; + } m_logger->LogDebug("Attempting to find RTTI in segment %llx", segment->GetStart()); - scan(segment); + try + { + scan(segment); + } + catch (std::exception &e) + { + m_logger->LogWarn("Unhandled exception in segment scan %llx %s", segment->GetStart(), e.what()); + } } else if (checkWritableRData && rdataSection && rdataSection->GetStart() == segment->GetStart()) { m_logger->LogDebug("Attempting to find RTTI in writable rdata segment %llx", segment->GetStart()); - scan(segment); + try + { + scan(segment); + } + catch (std::exception &e) + { + m_logger->LogWarn("Unhandled exception in writable segment scan %llx %s", segment->GetStart(), e.what()); + } } } @@ -757,13 +777,27 @@ void MicrosoftRTTIProcessor::ProcessVFT() if (segment->GetFlags() == (SegmentReadable | SegmentContainsData)) { m_logger->LogDebug("Attempting to find VirtualFunctionTables in segment %llx", segment->GetStart()); - scan(segment); + try + { + scan(segment); + } + catch (std::exception &e) + { + m_logger->LogWarn("Unhandled exception in vtable segment scan %llx %s", segment->GetStart(), e.what()); + } } else if (checkWritableRData && rdataSection && rdataSection->GetStart() == segment->GetStart()) { m_logger->LogDebug("Attempting to find VirtualFunctionTables in writable rdata segment %llx", segment->GetStart()); - scan(segment); + try + { + scan(segment); + } + catch (std::exception &e) + { + m_logger->LogWarn("Unhandled exception in vtable writable segment scan %llx %s", segment->GetStart(), e.what()); + } } } } |
