diff options
author | Emma Pilkington <emma.pilkington95@gmail.com> | 2024-04-18 13:44:22 -0400 |
---|---|---|
committer | GitHub <noreply@github.com> | 2024-04-18 13:44:22 -0400 |
commit | 68e814d9114b6c8910642298714dad6fa79ccad2 (patch) | |
tree | cd772f143b4332dc1cf8bba508247599f5ca3eb9 /llvm/tools/llvm-objdump/llvm-objdump.cpp | |
parent | e9654880df9b30af11816782a83ebf960536309c (diff) | |
download | llvm-68e814d9114b6c8910642298714dad6fa79ccad2.zip llvm-68e814d9114b6c8910642298714dad6fa79ccad2.tar.gz llvm-68e814d9114b6c8910642298714dad6fa79ccad2.tar.bz2 |
[AMDGPU] Add disassembler diagnostics for invalid kernel descriptors (#87400)
These mostly are checking for various reserved bits being set. The diagnostics
for gpu-dependent reserved bits have a bit more context since they seem like the
most likely ones to be observed in practice.
This commit also improves the error handling mechanism for
MCDisassembler::onSymbolStart(). Previously it had a comment stream parameter
that was just being ignored by llvm-objdump, now it returns errors using
Expected<T>.
Diffstat (limited to 'llvm/tools/llvm-objdump/llvm-objdump.cpp')
-rw-r--r-- | llvm/tools/llvm-objdump/llvm-objdump.cpp | 65 |
1 files changed, 35 insertions, 30 deletions
diff --git a/llvm/tools/llvm-objdump/llvm-objdump.cpp b/llvm/tools/llvm-objdump/llvm-objdump.cpp index 9b65ea5..339822e 100644 --- a/llvm/tools/llvm-objdump/llvm-objdump.cpp +++ b/llvm/tools/llvm-objdump/llvm-objdump.cpp @@ -2051,41 +2051,46 @@ disassembleObject(ObjectFile &Obj, const ObjectFile &DbgObj, for (size_t SHI = 0; SHI < SymbolsHere.size(); ++SHI) { SymbolInfoTy Symbol = SymbolsHere[SHI]; - auto Status = DT->DisAsm->onSymbolStart( - Symbol, Size, Bytes.slice(Start, End - Start), SectionAddr + Start, - CommentStream); - - if (!Status) { - // If onSymbolStart returns std::nullopt, that means it didn't trigger - // any interesting handling for this symbol. Try the other symbols - // defined at this address. + Expected<bool> RespondedOrErr = DT->DisAsm->onSymbolStart( + Symbol, Size, Bytes.slice(Start, End - Start), SectionAddr + Start); + + if (RespondedOrErr && !*RespondedOrErr) { + // This symbol didn't trigger any interesting handling. Try the other + // symbols defined at this address. continue; } - if (*Status == MCDisassembler::Fail) { - // If onSymbolStart returns Fail, that means it identified some kind - // of special data at this address, but wasn't able to disassemble it - // meaningfully. So we fall back to disassembling the failed region - // as bytes, assuming that the target detected the failure before - // printing anything. - // - // Return values Success or SoftFail (i.e no 'real' failure) are - // expected to mean that the target has emitted its own output. - // - // Either way, 'Size' will have been set to the amount of data - // covered by whatever prologue the target identified. So we advance - // our own position to beyond that. Sometimes that will be the entire - // distance to the next symbol, and sometimes it will be just a - // prologue and we should start disassembling instructions from where - // it left off. - outs() << DT->Context->getAsmInfo()->getCommentString() - << " error in decoding " << SymNamesHere[SHI] - << " : decoding failed region as bytes.\n"; - for (uint64_t I = 0; I < Size; ++I) { - outs() << "\t.byte\t " << format_hex(Bytes[I], 1, /*Upper=*/true) - << "\n"; + // If onSymbolStart returned an Error, that means it identified some + // kind of special data at this address, but wasn't able to disassemble + // it meaningfully. So we fall back to printing the error out and + // disassembling the failed region as bytes, assuming that the target + // detected the failure before printing anything. + if (!RespondedOrErr) { + std::string ErrMsgStr = toString(RespondedOrErr.takeError()); + StringRef ErrMsg = ErrMsgStr; + do { + StringRef Line; + std::tie(Line, ErrMsg) = ErrMsg.split('\n'); + outs() << DT->Context->getAsmInfo()->getCommentString() + << " error decoding " << SymNamesHere[SHI] << ": " << Line + << '\n'; + } while (!ErrMsg.empty()); + + if (Size) { + outs() << DT->Context->getAsmInfo()->getCommentString() + << " decoding failed region as bytes\n"; + for (uint64_t I = 0; I < Size; ++I) + outs() << "\t.byte\t " << format_hex(Bytes[I], 1, /*Upper=*/true) + << '\n'; } } + + // Regardless of whether onSymbolStart returned an Error or true, 'Size' + // will have been set to the amount of data covered by whatever prologue + // the target identified. So we advance our own position to beyond that. + // Sometimes that will be the entire distance to the next symbol, and + // sometimes it will be just a prologue and we should start + // disassembling instructions from where it left off. Start += Size; break; } |