From 96d7d903140d11f31143647d5e6f8678016cbc41 Mon Sep 17 00:00:00 2001 From: Egor Bogatov Date: Wed, 2 Mar 2022 03:55:43 +0300 Subject: [PATCH] Fix div-by-zero introduced in https://github.com/dotnet/runtime/pull/65926 (#66035) --- src/coreclr/vm/eehash.inl | 4 ++-- src/coreclr/vm/util.hpp | 5 ++++- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/src/coreclr/vm/eehash.inl b/src/coreclr/vm/eehash.inl index ba49b191e6678..477df0dc1ae4a 100644 --- a/src/coreclr/vm/eehash.inl +++ b/src/coreclr/vm/eehash.inl @@ -198,7 +198,7 @@ BOOL EEHashTableBase::Init(DWORD dwNumBucke m_pVolatileBucketTable->m_pBuckets++; m_pVolatileBucketTable->m_dwNumBuckets = dwNumBuckets; #ifdef TARGET_64BIT - m_pVolatileBucketTable->m_dwNumBucketsMul = GetFastModMultiplier(dwNumBuckets); + m_pVolatileBucketTable->m_dwNumBucketsMul = dwNumBuckets == 0 ? 0 : GetFastModMultiplier(dwNumBuckets); #endif m_Heap = pHeap; @@ -786,7 +786,7 @@ BOOL EEHashTableBase::GrowHashTable() pNewBucketTable->m_pBuckets = pNewBuckets; pNewBucketTable->m_dwNumBuckets = dwNewNumBuckets; #ifdef TARGET_64BIT - pNewBucketTable->m_dwNumBucketsMul = GetFastModMultiplier(dwNewNumBuckets); + pNewBucketTable->m_dwNumBucketsMul = dwNewNumBuckets == 0 ? 0 : GetFastModMultiplier(dwNewNumBuckets); #endif // Add old table to the to free list. Note that the SyncClean thing will only diff --git a/src/coreclr/vm/util.hpp b/src/coreclr/vm/util.hpp index a8aa775b0facd..9c08c52b9becf 100644 --- a/src/coreclr/vm/util.hpp +++ b/src/coreclr/vm/util.hpp @@ -1017,7 +1017,10 @@ inline UINT64 GetFastModMultiplier(UINT32 divisor) inline UINT32 FastMod(UINT32 value, UINT32 divisor, UINT64 multiplier) { - return (UINT32)(((((multiplier * value) >> 32) + 1) * divisor) >> 32); + _ASSERTE(divisor <= INT_MAX); + UINT32 highbits = (UINT32)(((((multiplier * value) >> 32) + 1) * divisor) >> 32); + _ASSERTE(highbits == value % divisor); + return highbits; } #endif