1 /*
2  * Copyright (c) 2023 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "ecmascript/compiler/aot_file/elf_reader.h"
17 
18 namespace panda::ecmascript {
VerifyELFHeader(uint32_t version, bool strictMatch)19 bool ElfReader::VerifyELFHeader(uint32_t version, bool strictMatch)
20 {
21     llvm::ELF::Elf64_Ehdr header = *(reinterpret_cast<llvm::ELF::Elf64_Ehdr *>(fileMapMem_.GetOriginAddr()));
22     if (header.e_ident[llvm::ELF::EI_MAG0] != llvm::ELF::ElfMagic[llvm::ELF::EI_MAG0]
23         || header.e_ident[llvm::ELF::EI_MAG1] != llvm::ELF::ElfMagic[llvm::ELF::EI_MAG1]
24         || header.e_ident[llvm::ELF::EI_MAG2] != llvm::ELF::ElfMagic[llvm::ELF::EI_MAG2]
25         || header.e_ident[llvm::ELF::EI_MAG3] != llvm::ELF::ElfMagic[llvm::ELF::EI_MAG3]) {
26         LOG_ECMA(ERROR) << "ELF format error, expected magic is " << llvm::ELF::ElfMagic
27                         << ", but got " << header.e_ident[llvm::ELF::EI_MAG0] << header.e_ident[llvm::ELF::EI_MAG1]
28                         << header.e_ident[llvm::ELF::EI_MAG2] << header.e_ident[llvm::ELF::EI_MAG3];
29         return false;
30     }
31     if (!base::FileHeaderBase::VerifyVersion("Elf", header.e_version, version, strictMatch)) {
32         return false;
33     }
34     if (ElfChecker(fileMapMem_).CheckValidElf() == false) {
35         LOG_ECMA(ERROR) << "ELF file content is not valid";
36         return false;
37     }
38     return true;
39 }
40 
GetCurModuleInfo(uint32_t i, llvm::ELF::Elf64_Off offset)41 ModuleSectionDes::ModuleRegionInfo *ElfReader::GetCurModuleInfo(uint32_t i, llvm::ELF::Elf64_Off offset)
42 {
43     uint64_t codeAddress = reinterpret_cast<uint64_t>(fileMapMem_.GetOriginAddr());
44     uint64_t info = codeAddress + offset + i * sizeof(ModuleSectionDes::ModuleRegionInfo);
45     return reinterpret_cast<ModuleSectionDes::ModuleRegionInfo *>(info);
46 }
47 
ParseELFSections(ModuleSectionDes &des, std::vector<ElfSecName> &secs)48 void ElfReader::ParseELFSections(ModuleSectionDes &des, std::vector<ElfSecName> &secs)
49 {
50     llvm::ELF::Elf64_Ehdr *ehdr = reinterpret_cast<llvm::ELF::Elf64_Ehdr *>(fileMapMem_.GetOriginAddr());
51     char *addr = reinterpret_cast<char *>(ehdr);
52     llvm::ELF::Elf64_Shdr *shdr = reinterpret_cast<llvm::ELF::Elf64_Shdr *>(addr + ehdr->e_shoff);
53     ASSERT(ehdr->e_shstrndx != static_cast<llvm::ELF::Elf64_Half>(-1));
54     llvm::ELF::Elf64_Shdr strdr = shdr[ehdr->e_shstrndx];
55     for (size_t j = 0; j < secs.size(); ++j) {
56         int secId = -1;
57         ElfSecName sec = secs[j];
58         std::string sectionName = ModuleSectionDes::GetSecName(sec);
59         for (size_t i = 0; i < ehdr->e_shnum; ++i) {
60             llvm::ELF::Elf64_Word shName = shdr[i].sh_name;
61             char *curShName = reinterpret_cast<char *>(addr) + shName + strdr.sh_offset;
62             if (sectionName.compare(curShName) == 0) {
63                 secId = static_cast<int>(i);
64                 break;
65             }
66         }
67         if (secId == -1) {
68             LOG_COMPILER(DEBUG) << "sectionName: " << sectionName << " not found in strtab";
69             continue;
70         }
71         ASSERT(secId > 0 && secId < ehdr->e_shnum);
72         llvm::ELF::Elf64_Shdr secShdr = shdr[secId];
73         uintptr_t secAddr = reinterpret_cast<uintptr_t>(addr + secShdr.sh_offset);
74         uint32_t secSize = secShdr.sh_size;
75         if (sec == ElfSecName::ARK_FUNCENTRY) {
76             ASSERT((secSize > 0) && (secSize % sizeof(AOTFileInfo::FuncEntryDes) == 0));
77         }
78         if (sec == ElfSecName::ARK_STACKMAP) {
79             des.SetArkStackMapPtr(reinterpret_cast<uint8_t *>(secAddr));
80             des.SetArkStackMapSize(secSize);
81         } else {
82             des.SetSecAddrAndSize(sec, secAddr, secSize);
83         }
84     }
85 }
86 
ParseELFSections(std::vector<ModuleSectionDes> &des, std::vector<ElfSecName> &secs)87 void ElfReader::ParseELFSections(std::vector<ModuleSectionDes> &des, std::vector<ElfSecName> &secs)
88 {
89     llvm::ELF::Elf64_Ehdr *ehdr = reinterpret_cast<llvm::ELF::Elf64_Ehdr *>(fileMapMem_.GetOriginAddr());
90     char *addr = reinterpret_cast<char *>(ehdr);
91     llvm::ELF::Elf64_Shdr *shdrs = reinterpret_cast<llvm::ELF::Elf64_Shdr *>(addr + ehdr->e_shoff);
92     ASSERT(ehdr->e_shstrndx != static_cast<llvm::ELF::Elf64_Half>(-1));
93     llvm::ELF::Elf64_Shdr strdr = shdrs[ehdr->e_shstrndx];
94     ASSERT(ehdr->e_flags != static_cast<llvm::ELF::Elf64_Word>(-1));
95     llvm::ELF::Elf64_Shdr moduledr = shdrs[ehdr->e_flags];
96     size_t moduleInfoSize = moduledr.sh_size;
97     uint32_t moduleNum = GetModuleNum(moduleInfoSize);
98     des.resize(moduleNum);
99     std::set<ElfSecName> secSet(secs.begin(), secs.end());
100     for (ElfSecName sec : secSet) {
101         int secId = -1;
102         std::string sectionName = ModuleSectionDes::GetSecName(sec);
103         for (size_t i = 0; i < ehdr->e_shnum; ++i) {
104             llvm::ELF::Elf64_Word shName = shdrs[i].sh_name;
105             char *curShName = reinterpret_cast<char *>(addr) + shName + strdr.sh_offset;
106             if (sectionName.compare(curShName) == 0) {
107                 secId = static_cast<int>(i);
108                 break;
109             }
110         }
111         if (secId == -1) {
112             LOG_COMPILER(DEBUG) << "sectionName: " << sectionName << " not found in strtab";
113             continue;
114         }
115         ASSERT(secId > 0 && secId < ehdr->e_shnum);
116         llvm::ELF::Elf64_Shdr secShdr = shdrs[secId];
117         uintptr_t secAddr = reinterpret_cast<uintptr_t>(addr + secShdr.sh_offset);
118         uint32_t secSize = secShdr.sh_size;
119         switch (sec) {
120             case ElfSecName::TEXT: {
121                 llvm::ELF::Elf64_Off secOffset = 0;
122                 SeparateTextSections(des, secAddr, secOffset, moduledr.sh_offset);
123                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
124                 break;
125             }
126             case ElfSecName::ARK_STACKMAP: {
127                 llvm::ELF::Elf64_Off secOffset = 0;
128                 SeparateArkStackMapSections(des, secAddr, secOffset, moduledr.sh_offset);
129                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
130                 break;
131             }
132             case ElfSecName::STRTAB: {
133                 llvm::ELF::Elf64_Off secOffset = 0;
134                 SeparateStrtabSections(des, secAddr, secOffset, moduledr.sh_offset);
135                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
136                 break;
137             }
138             case ElfSecName::SYMTAB: {
139                 llvm::ELF::Elf64_Off secOffset = 0;
140                 SeparateSymtabSections(des, secAddr, secOffset, moduledr.sh_offset);
141                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
142                 break;
143             }
144             case ElfSecName::SHSTRTAB:
145             case ElfSecName::ARK_FUNCENTRY:
146             case ElfSecName::ARK_ASMSTUB:
147             case ElfSecName::ARK_MODULEINFO: {
148                 if (sec == ElfSecName::ARK_FUNCENTRY) {
149                     ASSERT((secSize > 0) && (secSize % sizeof(AOTFileInfo::FuncEntryDes) == 0));
150                 }
151                 des[0].SetSecAddrAndSize(sec, secAddr, secSize);
152                 break;
153             }
154             default: {
155                 LOG_ECMA(FATAL) << "this section should not dump to stub file";
156                 break;
157             }
158         }
159     }
160 }
161 
ParseELFSections(BinaryBufferParser &parser, std::vector<ModuleSectionDes> &des, std::vector<ElfSecName> &secs)162 void ElfReader::ParseELFSections(BinaryBufferParser &parser,
163                                  std::vector<ModuleSectionDes> &des,
164                                  std::vector<ElfSecName> &secs)
165 {
166     ASSERT(des.size() == ASMSTUB_MODULE_NUM);
167     uint64_t codeAddress = reinterpret_cast<uint64_t>(stubsMem_.addr_);
168     llvm::ELF::Elf64_Ehdr ehdr;
169     parser.ParseBuffer(&ehdr, sizeof(ehdr), 0);
170     std::vector<llvm::ELF::Elf64_Shdr> shdrs(ehdr.e_shnum);
171     parser.ParseBuffer(shdrs.data(), sizeof(llvm::ELF::Elf64_Shdr) * ehdr.e_shnum, ehdr.e_shoff);
172 
173     ASSERT(ehdr.e_shstrndx != static_cast<llvm::ELF::Elf64_Half>(-1));
174     llvm::ELF::Elf64_Shdr strdr = shdrs[ehdr.e_shstrndx];
175     ASSERT(ehdr.e_flags != static_cast<llvm::ELF::Elf64_Word>(-1));
176     llvm::ELF::Elf64_Shdr moduledr = shdrs[ehdr.e_flags];
177     [[maybe_unused]] size_t moduleInfoSize = moduledr.sh_size;
178     uint32_t moduleNum = GetModuleNum(moduleInfoSize);
179     ASSERT(moduleNum == ASMSTUB_MODULE_NUM);
180     moduleInfo_.resize(moduleNum);
181     parser.ParseBuffer(moduleInfo_.data(), moduleInfoSize, moduledr.sh_offset);
182     std::set<ElfSecName> secSet(secs.begin(), secs.end());
183     for (ElfSecName sec : secSet) {
184         int secId = -1;
185         std::string sectionName = ModuleSectionDes::GetSecName(sec);
186         for (size_t i = 0; i < ehdr.e_shnum; ++i) {
187             llvm::ELF::Elf64_Word shName = shdrs[i].sh_name;
188             char *curShName = reinterpret_cast<char *>(parser.GetAddr()) + shName + strdr.sh_offset;
189             if (sectionName.compare(curShName) == 0) {
190                 secId = static_cast<int>(i);
191                 break;
192             }
193         }
194         if (secId == -1) {
195             LOG_COMPILER(DEBUG) << "sectionName: " << sectionName << " not found in strtab";
196             continue;
197         }
198         ASSERT(secId > 0 && secId < ehdr.e_shnum);
199         llvm::ELF::Elf64_Shdr secShdr = shdrs[secId];
200         uint64_t secAddr = static_cast<uint64_t>(codeAddress + secShdr.sh_offset);
201         uint32_t secSize = secShdr.sh_size;
202         switch (sec) {
203             case ElfSecName::TEXT: {
204                 llvm::ELF::Elf64_Off secOffset = 0;
205                 SeparateTextSections(parser, des, secAddr, secOffset, secShdr.sh_offset);
206                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
207                 break;
208             }
209             case ElfSecName::ARK_STACKMAP: {
210                 llvm::ELF::Elf64_Off secOffset = 0;
211                 SeparateArkStackMapSections(parser, des, secAddr, secOffset, secShdr.sh_offset);
212                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
213                 break;
214             }
215             case ElfSecName::STRTAB: {
216                 llvm::ELF::Elf64_Off secOffset = 0;
217                 SeparateStrtabSections(parser, des, secAddr, secOffset, secShdr.sh_offset);
218                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
219                 break;
220             }
221             case ElfSecName::SYMTAB: {
222                 llvm::ELF::Elf64_Off secOffset = 0;
223                 SeparateSymtabSections(parser, des, secAddr, secOffset, secShdr.sh_offset);
224                 ASSERT(static_cast<uint32_t>(secOffset) == secSize);
225                 break;
226             }
227             case ElfSecName::SHSTRTAB:
228             case ElfSecName::ARK_FUNCENTRY:
229             case ElfSecName::ARK_ASMSTUB:
230             case ElfSecName::ARK_MODULEINFO: {
231                 if (sec == ElfSecName::ARK_FUNCENTRY) {
232                     ASSERT((secSize > 0) && (secSize % sizeof(AOTFileInfo::FuncEntryDes) == 0));
233                 }
234                 parser.ParseBuffer(reinterpret_cast<void *>(secAddr), secSize, secShdr.sh_offset);
235                 des[0].SetSecAddrAndSize(sec, secAddr, secSize);
236                 break;
237             }
238             default: {
239                 LOG_ECMA(FATAL) << "this section should not dump to stub file";
240                 break;
241             }
242         }
243     }
244 }
245 
ParseELFSegment()246 bool ElfReader::ParseELFSegment()
247 {
248     if (fileMapMem_.GetOriginAddr() == nullptr) {
249         return false;
250     }
251     char *addr = reinterpret_cast<char *>(fileMapMem_.GetOriginAddr());
252     llvm::ELF::Elf64_Ehdr *ehdr = reinterpret_cast<llvm::ELF::Elf64_Ehdr *>(fileMapMem_.GetOriginAddr());
253     llvm::ELF::Elf64_Phdr *phdr = reinterpret_cast<llvm::ELF::Elf64_Phdr *>(addr + ehdr->e_phoff);
254     for (int i = 0; i < ehdr->e_phnum; ++i) {
255         if (phdr[i].p_type != llvm::ELF::PT_LOAD) {
256             continue;
257         }
258         if (phdr[i].p_filesz > phdr[i].p_memsz) {
259             LOG_COMPILER(ERROR) << " p_filesz:0x" << std::hex << phdr[i].p_filesz << " > p_memsz:0x"
260                 << phdr[i].p_memsz;
261             return false;
262         }
263         if (!phdr[i].p_filesz) {
264             continue;
265         }
266         unsigned char *virtualAddr = reinterpret_cast<unsigned char *>(addr + phdr[i].p_vaddr);
267         ASSERT(phdr[i].p_offset % PageSize() == 0);
268         if ((phdr[i].p_flags & llvm::ELF::PF_X) != 0) {
269             ASSERT(reinterpret_cast<uintptr_t>(virtualAddr) % PageSize() == 0);
270             if (!PageProtect(virtualAddr, phdr[i].p_memsz, PAGE_PROT_EXEC_READ)) {
271                 return false;
272             }
273         }
274     }
275     return true;
276 }
277 
SeparateTextSections(std::vector<ModuleSectionDes> &des, const uintptr_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &moduleInfoOffset)278 void ElfReader::SeparateTextSections(std::vector<ModuleSectionDes> &des,
279                                      const uintptr_t &secAddr,
280                                      llvm::ELF::Elf64_Off &secOffset,
281                                      const llvm::ELF::Elf64_Off &moduleInfoOffset)
282 {
283     for (size_t i = 0; i < des.size(); ++i) {
284         auto moduleInfo = GetCurModuleInfo(i, moduleInfoOffset);
285         secOffset = AlignUp(secOffset, AOTFileInfo::PAGE_ALIGN);
286         uint32_t rodataSizeBeforeText = moduleInfo->rodataSizeBeforeText;
287         uint32_t rodataSizeAfterText = moduleInfo->rodataSizeAfterText;
288         if (rodataSizeBeforeText != 0) {
289             secOffset += rodataSizeBeforeText;
290             secOffset = AlignUp(secOffset, AOTFileInfo::TEXT_SEC_ALIGN);
291         }
292         uint32_t textSize = moduleInfo->textSize;
293         des[i].SetSecAddrAndSize(ElfSecName::TEXT, secAddr + secOffset, textSize);
294         secOffset += textSize;
295         if (rodataSizeAfterText != 0) {
296             secOffset = AlignUp(secOffset, AOTFileInfo::DATA_SEC_ALIGN);
297             secOffset += rodataSizeAfterText;
298         }
299     }
300 }
301 
SeparateArkStackMapSections(std::vector<ModuleSectionDes> &des, const uintptr_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &moduleInfoOffset)302 void ElfReader::SeparateArkStackMapSections(std::vector<ModuleSectionDes> &des,
303                                             const uintptr_t &secAddr,
304                                             llvm::ELF::Elf64_Off &secOffset,
305                                             const llvm::ELF::Elf64_Off &moduleInfoOffset)
306 {
307     for (size_t i = 0; i < des.size(); ++i) {
308         auto moduleInfo = GetCurModuleInfo(i, moduleInfoOffset);
309         uint32_t stackMapSize = moduleInfo->stackMapSize;
310         des[i].SetArkStackMapPtr(reinterpret_cast<uint8_t *>(secAddr + secOffset));
311         des[i].SetArkStackMapSize(stackMapSize);
312         uint32_t index = moduleInfo->startIndex;
313         uint32_t cnt = moduleInfo->funcCount;
314         des[i].SetStartIndex(index);
315         des[i].SetFuncCount(cnt);
316         secOffset += stackMapSize;
317     }
318 }
319 
SeparateStrtabSections(std::vector<ModuleSectionDes> &des, const uintptr_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &moduleInfoOffset)320 void ElfReader::SeparateStrtabSections(std::vector<ModuleSectionDes> &des,
321                                        const uintptr_t &secAddr,
322                                        llvm::ELF::Elf64_Off &secOffset,
323                                        const llvm::ELF::Elf64_Off &moduleInfoOffset)
324 {
325     for (size_t i = 0; i < des.size(); ++i) {
326         auto moduleInfo = GetCurModuleInfo(i, moduleInfoOffset);
327         uint32_t strtabSize = moduleInfo->strtabSize;
328         des[i].SetSecAddrAndSize(ElfSecName::STRTAB, secAddr + secOffset, strtabSize);
329         secOffset += strtabSize;
330     }
331 }
332 
SeparateSymtabSections(std::vector<ModuleSectionDes> &des, const uintptr_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &moduleInfoOffset)333 void ElfReader::SeparateSymtabSections(std::vector<ModuleSectionDes> &des,
334                                        const uintptr_t &secAddr,
335                                        llvm::ELF::Elf64_Off &secOffset,
336                                        const llvm::ELF::Elf64_Off &moduleInfoOffset)
337 {
338     for (size_t i = 0; i < des.size(); ++i) {
339         auto moduleInfo = GetCurModuleInfo(i, moduleInfoOffset);
340         uint32_t symtabSize = moduleInfo->symtabSize;
341         des[i].SetSecAddrAndSize(ElfSecName::SYMTAB, secAddr + secOffset, symtabSize);
342         secOffset += symtabSize;
343     }
344 }
345 
SeparateTextSections(BinaryBufferParser &parser, std::vector<ModuleSectionDes> &des, const uint64_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &curShOffset)346 void ElfReader::SeparateTextSections(BinaryBufferParser &parser,
347                                      std::vector<ModuleSectionDes> &des,
348                                      const uint64_t &secAddr,
349                                      llvm::ELF::Elf64_Off &secOffset,
350                                      const llvm::ELF::Elf64_Off &curShOffset)
351 {
352     for (size_t i = 0; i < des.size(); ++i) {
353         auto moduleInfo = moduleInfo_[i];
354         secOffset = AlignUp(secOffset, AOTFileInfo::PAGE_ALIGN);
355         uint32_t rodataSizeBeforeText = moduleInfo.rodataSizeBeforeText;
356         uint32_t rodataSizeAfterText = moduleInfo.rodataSizeAfterText;
357         if (rodataSizeBeforeText != 0) {
358             parser.ParseBuffer(reinterpret_cast<void *>(secAddr + secOffset), rodataSizeBeforeText,
359                                curShOffset + secOffset);
360             secOffset += rodataSizeBeforeText;
361             secOffset = AlignUp(secOffset, AOTFileInfo::TEXT_SEC_ALIGN);
362         }
363         uint32_t textSize = moduleInfo.textSize;
364         parser.ParseBuffer(reinterpret_cast<void *>(secAddr + secOffset), textSize, curShOffset + secOffset);
365         des[i].SetSecAddrAndSize(ElfSecName::TEXT, secAddr + secOffset, textSize);
366         secOffset += textSize;
367         if (rodataSizeAfterText != 0) {
368             secOffset = AlignUp(secOffset, AOTFileInfo::DATA_SEC_ALIGN);
369             parser.ParseBuffer(reinterpret_cast<void *>(secAddr + secOffset), rodataSizeAfterText,
370                                curShOffset + secOffset);
371             secOffset += rodataSizeAfterText;
372         }
373     }
374 }
375 
SeparateArkStackMapSections(BinaryBufferParser &parser, std::vector<ModuleSectionDes> &des, const uint64_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &curShOffset)376 void ElfReader::SeparateArkStackMapSections(BinaryBufferParser &parser,
377                                             std::vector<ModuleSectionDes> &des,
378                                             const uint64_t &secAddr,
379                                             llvm::ELF::Elf64_Off &secOffset,
380                                             const llvm::ELF::Elf64_Off &curShOffset)
381 {
382     for (size_t i = 0; i < des.size(); ++i) {
383         auto moduleInfo = moduleInfo_[i];
384         uint32_t stackMapSize = moduleInfo.stackMapSize;
385         parser.ParseBuffer(reinterpret_cast<void *>(secAddr + secOffset), stackMapSize, curShOffset + secOffset);
386         des[i].SetArkStackMapPtr(reinterpret_cast<uint8_t *>(secAddr + secOffset));
387         des[i].SetArkStackMapSize(stackMapSize);
388         uint32_t index = moduleInfo.startIndex;
389         uint32_t cnt = moduleInfo.funcCount;
390         des[i].SetStartIndex(index);
391         des[i].SetFuncCount(cnt);
392         secOffset += stackMapSize;
393     }
394 }
395 
SeparateStrtabSections(BinaryBufferParser &parser, std::vector<ModuleSectionDes> &des, const uintptr_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &curShOffset)396 void ElfReader::SeparateStrtabSections(BinaryBufferParser &parser,
397                                        std::vector<ModuleSectionDes> &des,
398                                        const uintptr_t &secAddr,
399                                        llvm::ELF::Elf64_Off &secOffset,
400                                        const llvm::ELF::Elf64_Off &curShOffset)
401 {
402     for (size_t i = 0; i < des.size(); ++i) {
403         auto moduleInfo = moduleInfo_[i];
404         uint32_t strtabSize = moduleInfo.strtabSize;
405         parser.ParseBuffer(reinterpret_cast<void *>(secAddr + secOffset), strtabSize, curShOffset + secOffset);
406         des[i].SetSecAddrAndSize(ElfSecName::STRTAB, secAddr + secOffset, strtabSize);
407         secOffset += strtabSize;
408     }
409 }
410 
SeparateSymtabSections(BinaryBufferParser &parser, std::vector<ModuleSectionDes> &des, const uintptr_t &secAddr, llvm::ELF::Elf64_Off &secOffset, const llvm::ELF::Elf64_Off &curShOffset)411 void ElfReader::SeparateSymtabSections(BinaryBufferParser &parser,
412                                        std::vector<ModuleSectionDes> &des,
413                                        const uintptr_t &secAddr,
414                                        llvm::ELF::Elf64_Off &secOffset,
415                                        const llvm::ELF::Elf64_Off &curShOffset)
416 {
417     for (size_t i = 0; i < des.size(); ++i) {
418         auto moduleInfo = moduleInfo_[i];
419         uint32_t symtabSize = moduleInfo.symtabSize;
420         parser.ParseBuffer(reinterpret_cast<void *>(secAddr + secOffset), symtabSize, curShOffset + secOffset);
421         des[i].SetSecAddrAndSize(ElfSecName::SYMTAB, secAddr + secOffset, symtabSize);
422         secOffset += symtabSize;
423     }
424 }
425 }  // namespace panda::ecmascript
426