diff --git a/compiler-rt/lib/scudo/standalone/combined.h b/compiler-rt/lib/scudo/standalone/combined.h --- a/compiler-rt/lib/scudo/standalone/combined.h +++ b/compiler-rt/lib/scudo/standalone/combined.h @@ -927,12 +927,25 @@ auto *Depot = reinterpret_cast(DepotPtr); size_t NextErrorReport = 0; + + // Check for OOB in the current block and the two surrounding blocks. Beyond + // that, UAF is more likely. if (extractTag(FaultAddr) != 0) getInlineErrorInfo(ErrorInfo, NextErrorReport, FaultAddr, Depot, RegionInfoPtr, Memory, MemoryTags, MemoryAddr, - MemorySize); + MemorySize, 0, 2); + + // Check the ring buffer. For primary allocations this will only find UAF; + // for secondary allocations we can find either UAF or OOB. getRingBufferErrorInfo(ErrorInfo, NextErrorReport, FaultAddr, Depot, RingBufferPtr); + + // Check for OOB in the 28 blocks surrounding the 3 we checked earlier. + // Beyond that we are likely to hit false positives. + if (extractTag(FaultAddr) != 0) + getInlineErrorInfo(ErrorInfo, NextErrorReport, FaultAddr, Depot, + RegionInfoPtr, Memory, MemoryTags, MemoryAddr, + MemorySize, 2, 16); } private: @@ -1247,7 +1260,8 @@ const StackDepot *Depot, const char *RegionInfoPtr, const char *Memory, const char *MemoryTags, uintptr_t MemoryAddr, - size_t MemorySize) { + size_t MemorySize, size_t MinDistance, + size_t MaxDistance) { uptr UntaggedFaultAddr = untagPointer(FaultAddr); u8 FaultAddrTag = extractTag(FaultAddr); BlockInfo Info = @@ -1308,12 +1322,10 @@ return NextErrorReport == NumErrorReports; }; - if (CheckOOB(Info.BlockBegin)) + if (MinDistance == 0 && CheckOOB(Info.BlockBegin)) return; - // Check for OOB in the 30 surrounding blocks. Beyond that we are likely to - // hit false positives. - for (int I = 1; I != 16; ++I) + for (size_t I = Max(MinDistance, 1); I != MaxDistance; ++I) if (CheckOOB(Info.BlockBegin + I * Info.BlockSize) || CheckOOB(Info.BlockBegin - I * Info.BlockSize)) return;