1a7dea167SDimitry Andric //===--- Disasm.cpp - Disassembler for bytecode functions -------*- C++ -*-===// 2a7dea167SDimitry Andric // 3a7dea167SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4a7dea167SDimitry Andric // See https://llvm.org/LICENSE.txt for license information. 5a7dea167SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6a7dea167SDimitry Andric // 7a7dea167SDimitry Andric //===----------------------------------------------------------------------===// 8a7dea167SDimitry Andric // 9a7dea167SDimitry Andric // Dump method for Function which disassembles the bytecode. 10a7dea167SDimitry Andric // 11a7dea167SDimitry Andric //===----------------------------------------------------------------------===// 12a7dea167SDimitry Andric 1306c3fb27SDimitry Andric #include "Floating.h" 14a7dea167SDimitry Andric #include "Function.h" 15a7dea167SDimitry Andric #include "Opcode.h" 16a7dea167SDimitry Andric #include "PrimType.h" 17a7dea167SDimitry Andric #include "Program.h" 18a7dea167SDimitry Andric #include "clang/AST/DeclCXX.h" 19a7dea167SDimitry Andric #include "llvm/Support/Compiler.h" 205ffd83dbSDimitry Andric #include "llvm/Support/Format.h" 21a7dea167SDimitry Andric 22a7dea167SDimitry Andric using namespace clang; 23a7dea167SDimitry Andric using namespace clang::interp; 24a7dea167SDimitry Andric ReadArg(Program & P,CodePtr & OpPC)25bdd1243dSDimitry Andrictemplate <typename T> inline T ReadArg(Program &P, CodePtr &OpPC) { 26bdd1243dSDimitry Andric if constexpr (std::is_pointer_v<T>) { 27349cc55cSDimitry Andric uint32_t ID = OpPC.read<uint32_t>(); 28349cc55cSDimitry Andric return reinterpret_cast<T>(P.getNativePointer(ID)); 29bdd1243dSDimitry Andric } else { 30bdd1243dSDimitry Andric return OpPC.read<T>(); 31bdd1243dSDimitry Andric } 32349cc55cSDimitry Andric } 33349cc55cSDimitry Andric ReadArg(Program & P,CodePtr & OpPC)34*5f757f3fSDimitry Andrictemplate <> inline Floating ReadArg<Floating>(Program &P, CodePtr &OpPC) { 35*5f757f3fSDimitry Andric Floating F = Floating::deserialize(*OpPC); 36*5f757f3fSDimitry Andric OpPC += align(F.bytesToSerialize()); 37*5f757f3fSDimitry Andric return F; 38*5f757f3fSDimitry Andric } 39*5f757f3fSDimitry Andric dump() const40a7dea167SDimitry AndricLLVM_DUMP_METHOD void Function::dump() const { dump(llvm::errs()); } 41a7dea167SDimitry Andric dump(llvm::raw_ostream & OS) const42a7dea167SDimitry AndricLLVM_DUMP_METHOD void Function::dump(llvm::raw_ostream &OS) const { 4306c3fb27SDimitry Andric OS << getName() << " " << (const void *)this << "\n"; 44a7dea167SDimitry Andric OS << "frame size: " << getFrameSize() << "\n"; 45a7dea167SDimitry Andric OS << "arg size: " << getArgSize() << "\n"; 46a7dea167SDimitry Andric OS << "rvo: " << hasRVO() << "\n"; 47bdd1243dSDimitry Andric OS << "this arg: " << hasThisPointer() << "\n"; 48a7dea167SDimitry Andric 49a7dea167SDimitry Andric auto PrintName = [&OS](const char *Name) { 50a7dea167SDimitry Andric OS << Name; 5106c3fb27SDimitry Andric long N = 30 - strlen(Name); 5206c3fb27SDimitry Andric if (N > 0) 5306c3fb27SDimitry Andric OS.indent(N); 54a7dea167SDimitry Andric }; 55a7dea167SDimitry Andric 56a7dea167SDimitry Andric for (CodePtr Start = getCodeBegin(), PC = Start; PC != getCodeEnd();) { 57a7dea167SDimitry Andric size_t Addr = PC - Start; 58a7dea167SDimitry Andric auto Op = PC.read<Opcode>(); 59a7dea167SDimitry Andric OS << llvm::format("%8d", Addr) << " "; 60a7dea167SDimitry Andric switch (Op) { 61a7dea167SDimitry Andric #define GET_DISASM 62a7dea167SDimitry Andric #include "Opcodes.inc" 63a7dea167SDimitry Andric #undef GET_DISASM 64a7dea167SDimitry Andric } 65a7dea167SDimitry Andric } 66a7dea167SDimitry Andric } 67a7dea167SDimitry Andric dump() const68a7dea167SDimitry AndricLLVM_DUMP_METHOD void Program::dump() const { dump(llvm::errs()); } 69a7dea167SDimitry Andric dump(llvm::raw_ostream & OS) const70a7dea167SDimitry AndricLLVM_DUMP_METHOD void Program::dump(llvm::raw_ostream &OS) const { 71bdd1243dSDimitry Andric OS << ":: Program\n"; 72bdd1243dSDimitry Andric OS << "Global Variables: " << Globals.size() << "\n"; 73bdd1243dSDimitry Andric OS << "Functions: " << Funcs.size() << "\n"; 74bdd1243dSDimitry Andric OS << "\n"; 75a7dea167SDimitry Andric for (auto &Func : Funcs) { 76a7dea167SDimitry Andric Func.second->dump(); 77a7dea167SDimitry Andric } 78a7dea167SDimitry Andric for (auto &Anon : AnonFuncs) { 79a7dea167SDimitry Andric Anon->dump(); 80a7dea167SDimitry Andric } 81a7dea167SDimitry Andric } 82