@@ -173,13 +173,14 @@ static PTR_VOID GetUnwindDataBlob(TADDR moduleBase, PTR_RUNTIME_FUNCTION pRuntim
173
173
#define INDEX_ALIGNMENT 64
174
174
175
175
CoffNativeCodeManager::CoffNativeCodeManager (TADDR moduleBase,
176
- PTR_VOID pvManagedCodeStartRange, uint32_t cbManagedCodeRange,
177
- PTR_RUNTIME_FUNCTION pRuntimeFunctionTable, uint32_t nRuntimeFunctionTable,
178
- PTR_PTR_VOID pClasslibFunctions, uint32_t nClasslibFunctions)
176
+ PTR_VOID pvManagedCodeStartRange, uint32_t cbManagedCodeRange,
177
+ PTR_RUNTIME_FUNCTION pRuntimeFunctionTable, uint32_t nRuntimeFunctionTable,
178
+ PTR_PTR_VOID pClasslibFunctions, uint32_t nClasslibFunctions)
179
179
: m_moduleBase(moduleBase),
180
180
m_pvManagedCodeStartRange(pvManagedCodeStartRange), m_cbManagedCodeRange(cbManagedCodeRange),
181
181
m_pRuntimeFunctionTable(pRuntimeFunctionTable), m_nRuntimeFunctionTable(nRuntimeFunctionTable),
182
- m_pClasslibFunctions(pClasslibFunctions), m_nClasslibFunctions(nClasslibFunctions), m_indexCount(0 )
182
+ m_pClasslibFunctions(pClasslibFunctions), m_nClasslibFunctions(nClasslibFunctions),
183
+ m_initializedIndices(0 ), m_indexCount(0 ), m_indices{ 0 }
183
184
{
184
185
}
185
186
@@ -198,19 +199,40 @@ CoffNativeCodeManager::~CoffNativeCodeManager()
198
199
m_indexCount = 0 ;
199
200
}
200
201
201
- bool CoffNativeCodeManager::InitFuncTableIndex ()
202
+ bool CoffNativeCodeManager::AllocFuncTableIndex ()
202
203
{
203
- // max offset is beyond the range of managed methods.
204
- int maxOffset = (int )((TADDR)m_pvManagedCodeStartRange + m_cbManagedCodeRange - m_moduleBase);
205
-
206
- // lets build the index for the runtime table. for every granule that has elements we will have an index entry
207
204
uint32_t indexSize = (m_nRuntimeFunctionTable + FUNCTABLE_INDEX_GRANULARITY - 1 ) / FUNCTABLE_INDEX_GRANULARITY;
208
205
uint32_t * index = m_indices[m_indexCount] = (uint32_t *)_aligned_malloc (indexSize * sizeof (uint32_t ), INDEX_ALIGNMENT);
209
206
if (!index)
210
207
return false ;
211
208
212
209
m_indexCount++;
213
210
211
+ while (indexSize > INDEX_BRANCHING_FACTOR)
212
+ {
213
+ uint32_t prevSize = indexSize;
214
+ indexSize = (indexSize + INDEX_BRANCHING_FACTOR - 1 ) / INDEX_BRANCHING_FACTOR;
215
+ index = m_indices[m_indexCount] = (uint32_t *)_aligned_malloc (indexSize * sizeof (uint32_t ), INDEX_ALIGNMENT);
216
+ if (!index)
217
+ return false ;
218
+
219
+ m_indexCount++;
220
+ }
221
+
222
+ return true ;
223
+ }
224
+
225
+ NOINLINE
226
+ uint32_t ** CoffNativeCodeManager::InitFuncTableIndex ()
227
+ {
228
+ // max offset is beyond the range of managed methods.
229
+ int maxOffset = (int )((TADDR)m_pvManagedCodeStartRange + m_cbManagedCodeRange - m_moduleBase);
230
+
231
+ // lets build the index for the runtime table. for every granule that has elements we will have an index entry
232
+ uint32_t indexSize = (m_nRuntimeFunctionTable + FUNCTABLE_INDEX_GRANULARITY - 1 ) / FUNCTABLE_INDEX_GRANULARITY;
233
+ uint32_t indexCount = 0 ;
234
+ uint32_t * index = m_indices[indexCount++];
235
+
214
236
// in every index N we will put the lowest value from the granule N + 1
215
237
// when we will scan the value N in the indices and see that it is higher than the target, we will know
216
238
// that the granule N must be scanned for the entry as the next granule will have higher addresses.
@@ -231,11 +253,7 @@ bool CoffNativeCodeManager::InitFuncTableIndex()
231
253
{
232
254
uint32_t prevSize = indexSize;
233
255
indexSize = (indexSize + INDEX_BRANCHING_FACTOR - 1 ) / INDEX_BRANCHING_FACTOR;
234
- index = m_indices[m_indexCount] = (uint32_t *)_aligned_malloc (indexSize * sizeof (uint32_t ), INDEX_ALIGNMENT);
235
- if (!index)
236
- return false ;
237
-
238
- m_indexCount++;
256
+ index = m_indices[indexCount++];
239
257
240
258
for (uint32_t i = 1 ; i < indexSize; i++)
241
259
{
@@ -247,7 +265,8 @@ bool CoffNativeCodeManager::InitFuncTableIndex()
247
265
prevIdx = index;
248
266
}
249
267
250
- return true ;
268
+ WriteRelease64 ((LONG64*)&m_initializedIndices, (LONG64)m_indices);
269
+ return m_initializedIndices;
251
270
}
252
271
253
272
struct CoffNativeMethodInfo
@@ -262,10 +281,14 @@ static_assert(sizeof(CoffNativeMethodInfo) <= sizeof(MethodInfo), "CoffNativeMet
262
281
263
282
int CoffNativeCodeManager::LookupUnwindInfoIdx (uint32_t relativePc)
264
283
{
284
+ uint32_t ** indices = m_initializedIndices;
285
+ if (!indices)
286
+ indices = InitFuncTableIndex ();
287
+
265
288
uint32_t idx = 0 ;
266
289
for (int j = m_indexCount - 1 ; j >= 0 ; j--)
267
290
{
268
- uint32_t * index = m_indices [j];
291
+ uint32_t * index = indices [j];
269
292
idx *= INDEX_BRANCHING_FACTOR;
270
293
271
294
while ((uint32_t )index[idx] < relativePc)
@@ -1054,7 +1077,7 @@ bool RhRegisterOSModule(void * pModule,
1054
1077
if (pCoffNativeCodeManager == nullptr )
1055
1078
return false ;
1056
1079
1057
- if (!pCoffNativeCodeManager->InitFuncTableIndex ())
1080
+ if (!pCoffNativeCodeManager->AllocFuncTableIndex ())
1058
1081
return false ;
1059
1082
1060
1083
RegisterCodeManager (pCoffNativeCodeManager, pvManagedCodeStartRange, cbManagedCodeRange);
0 commit comments