@@ -226,8 +226,18 @@ namespace {
226
226
}
227
227
228
228
// Conformance Cache.
229
-
229
+ # if defined(__APPLE__) && defined(__MACH__)
230
230
static void _initializeCallbacksToInspectDylib ();
231
+ #else
232
+ namespace swift {
233
+ void _swift_initializeCallbacksToInspectDylib (
234
+ void (*fnAddImageBlock)(const uint8_t *, size_t ),
235
+ const char *sectionName);
236
+ }
237
+
238
+ static void _addImageProtocolConformancesBlock (const uint8_t *conformances,
239
+ size_t conformancesSize);
240
+ #endif
231
241
232
242
struct ConformanceState {
233
243
ConcurrentMap<ConformanceCacheEntry> Cache;
@@ -237,7 +247,13 @@ struct ConformanceState {
237
247
ConformanceState () {
238
248
SectionsToScan.reserve (16 );
239
249
pthread_mutex_init (&SectionsToScanLock, nullptr );
250
+ #if defined(__APPLE__) && defined(__MACH__)
240
251
_initializeCallbacksToInspectDylib ();
252
+ #else
253
+ _swift_initializeCallbacksToInspectDylib (
254
+ _addImageProtocolConformancesBlock,
255
+ SWIFT_PROTOCOL_CONFORMANCES_SECTION);
256
+ #endif
241
257
}
242
258
243
259
void cacheSuccess (const void *type, const ProtocolDescriptor *proto,
@@ -297,6 +313,14 @@ static void _addImageProtocolConformancesBlock(const uint8_t *conformances,
297
313
recordsBegin, recordsEnd);
298
314
}
299
315
316
+ #if !defined(__APPLE__) || !defined(__MACH__)
317
+ // Common Structure
318
+ struct InspectArgs {
319
+ void (*fnAddImageBlock)(const uint8_t *, size_t );
320
+ const char *sectionName;
321
+ };
322
+ #endif
323
+
300
324
#if defined(__APPLE__) && defined(__MACH__)
301
325
static void _addImageProtocolConformances (const mach_header *mh,
302
326
intptr_t vmaddr_slide) {
@@ -319,16 +343,27 @@ static void _addImageProtocolConformances(const mach_header *mh,
319
343
320
344
_addImageProtocolConformancesBlock (conformances, conformancesSize);
321
345
}
346
+
347
+ static void _initializeCallbacksToInspectDylib () {
348
+ // Install our dyld callback.
349
+ // Dyld will invoke this on our behalf for all images that have already
350
+ // been loaded.
351
+ _dyld_register_func_for_add_image (_addImageProtocolConformances);
352
+ }
353
+
322
354
#elif defined(__ELF__)
323
355
static int _addImageProtocolConformances (struct dl_phdr_info *info,
324
- size_t size, void * /* data*/ ) {
356
+ size_t size, void *data) {
357
+ // inspectArgs contains addImage*Block function and the section name
358
+ InspectArgs *inspectArgs = reinterpret_cast <InspectArgs *>(data);
359
+
325
360
void *handle;
326
361
if (!info->dlpi_name || info->dlpi_name [0 ] == ' \0 ' ) {
327
362
handle = dlopen (nullptr , RTLD_LAZY);
328
363
} else
329
364
handle = dlopen (info->dlpi_name , RTLD_LAZY | RTLD_NOLOAD);
330
365
auto conformances = reinterpret_cast <const uint8_t *>(
331
- dlsym (handle, SWIFT_PROTOCOL_CONFORMANCES_SECTION ));
366
+ dlsym (handle, inspectArgs-> sectionName ));
332
367
333
368
if (!conformances) {
334
369
// if there are no conformances, don't hold this handle open.
@@ -340,14 +375,29 @@ static int _addImageProtocolConformances(struct dl_phdr_info *info,
340
375
auto conformancesSize = *reinterpret_cast <const uint64_t *>(conformances);
341
376
conformances += sizeof (conformancesSize);
342
377
343
- _addImageProtocolConformancesBlock (conformances, conformancesSize);
378
+ inspectArgs-> fnAddImageBlock (conformances, conformancesSize);
344
379
345
380
dlclose (handle);
346
381
return 0 ;
347
382
}
383
+
384
+ void swift::_swift_initializeCallbacksToInspectDylib (
385
+ void (*fnAddImageBlock)(const uint8_t *, size_t ),
386
+ const char *sectionName) {
387
+ InspectArgs inspectArgs = {fnAddImageBlock, sectionName};
388
+
389
+ // Search the loaded dls. Unlike the above, this only searches the already
390
+ // loaded ones.
391
+ // FIXME: Find a way to have this continue to happen after.
392
+ // rdar://problem/19045112
393
+ dl_iterate_phdr (_addImageProtocolConformances, &inspectArgs);
394
+ }
348
395
#elif defined(__CYGWIN__)
349
396
static int _addImageProtocolConformances (struct dl_phdr_info *info,
350
- size_t size, void * /* data*/ ) {
397
+ size_t size, void *data) {
398
+ InspectArgs *inspectArgs = (InspectArgs *)data;
399
+ // inspectArgs contains addImage*Block function and the section name
400
+
351
401
void *handle;
352
402
if (!info->dlpi_name || info->dlpi_name [0 ] == ' \0 ' ) {
353
403
handle = dlopen (nullptr , RTLD_LAZY);
@@ -356,40 +406,26 @@ static int _addImageProtocolConformances(struct dl_phdr_info *info,
356
406
357
407
unsigned long conformancesSize;
358
408
const uint8_t *conformances =
359
- _swift_getSectionDataPE (handle, SWIFT_PROTOCOL_CONFORMANCES_SECTION ,
409
+ _swift_getSectionDataPE (handle, inspectArgs-> sectionName ,
360
410
&conformancesSize);
361
411
362
- if (!conformances) {
363
- // if there are no conformances, don't hold this handle open.
364
- dlclose (handle);
365
- return 0 ;
366
- }
367
-
368
- _addImageProtocolConformancesBlock (conformances, conformancesSize);
412
+ if (conformances)
413
+ inspectArgs->fnAddImageBlock (conformances, conformancesSize);
369
414
370
415
dlclose (handle);
371
416
return 0 ;
372
417
}
373
- #endif
374
418
375
- static void _initializeCallbacksToInspectDylib () {
376
- #if defined(__APPLE__) && defined(__MACH__)
377
- // Install our dyld callback.
378
- // Dyld will invoke this on our behalf for all images that have already
379
- // been loaded.
380
- _dyld_register_func_for_add_image (_addImageProtocolConformances);
381
- #elif defined(__ELF__)
382
- // Search the loaded dls. Unlike the above, this only searches the already
383
- // loaded ones.
384
- // FIXME: Find a way to have this continue to happen after.
385
- // rdar://problem/19045112
386
- dl_iterate_phdr (_addImageProtocolConformances, nullptr );
387
- #elif defined(__CYGWIN__)
388
- _swift_dl_iterate_phdr (_addImageProtocolConformances, nullptr );
419
+ void swift::_swift_initializeCallbacksToInspectDylib (
420
+ void (*fnAddImageBlock)(const uint8_t *, size_t ),
421
+ const char *sectionName) {
422
+ InspectArgs inspectArgs = {fnAddImageBlock, sectionName};
423
+
424
+ _swift_dl_iterate_phdr (_addImageProtocolConformances, &inspectArgs);
425
+ }
389
426
#else
390
427
# error No known mechanism to inspect dynamic libraries on this platform.
391
428
#endif
392
- }
393
429
394
430
// This variable is used to signal when a cache was generated and
395
431
// it is correct to avoid a new scan.
0 commit comments