@@ -2594,6 +2594,38 @@ void Writer::createDynamicRelocs() {
25942594 LOAD_CONFIG_TABLE * sizeof (data_directory) +
25952595 offsetof (data_directory, Size),
25962596 0 );
2597+
2598+ // Insert a 64-bit relocation for CHPEMetadataPointer. Its value will be set
2599+ // later in prepareLoadConfig to match the value in the EC load config.
2600+ // However, a base relocation must be allocated in advance, so we handle it
2601+ // here.
2602+ if (ctx.symtab .loadConfigSym && ctx.hybridSymtab ->loadConfigSym &&
2603+ ctx.symtab .loadConfigSize >=
2604+ offsetof (coff_load_configuration64, CHPEMetadataPointer) +
2605+ sizeof (coff_load_configuration64::CHPEMetadataPointer)) {
2606+ DefinedRegular *sym = ctx.symtab .loadConfigSym ;
2607+ SectionChunk *chunk = sym->getChunk ();
2608+ ArrayRef<coff_relocation> curRelocs = chunk->getRelocs ();
2609+ MutableArrayRef<coff_relocation> newRelocs (
2610+ bAlloc ().Allocate <coff_relocation>(curRelocs.size () + 1 ),
2611+ curRelocs.size () + 1 );
2612+ size_t chpeOffset = sym->getValue () + offsetof (coff_load_configuration64,
2613+ CHPEMetadataPointer);
2614+ size_t i;
2615+ for (i = 0 ;
2616+ i < curRelocs.size () && curRelocs[i].VirtualAddress < chpeOffset; ++i)
2617+ newRelocs[i] = curRelocs[i];
2618+ newRelocs[i].VirtualAddress = chpeOffset;
2619+ // The specific symbol used here is irrelevant as long as it's valid, since
2620+ // it will be overridden by prepareLoadConfig. Use the load config symbol
2621+ // itself.
2622+ newRelocs[i].SymbolTableIndex =
2623+ chunk->file ->getCOFFObj ()->getSymbolIndex (sym->getCOFFSymbol ());
2624+ newRelocs[i].Type = IMAGE_REL_ARM64_ADDR64;
2625+ for (; i < curRelocs.size (); ++i)
2626+ newRelocs[i + 1 ] = curRelocs[i];
2627+ chunk->setRelocs (newRelocs);
2628+ }
25972629}
25982630
25992631PartialSection *Writer::createPartialSection (StringRef name,
0 commit comments