10b57cec5SDimitry Andric //===- llvm/CodeGen/DwarfExpression.cpp - Dwarf Debug Framework -----------===// 20b57cec5SDimitry Andric // 30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information. 50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 60b57cec5SDimitry Andric // 70b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 80b57cec5SDimitry Andric // 90b57cec5SDimitry Andric // This file contains support for writing dwarf debug info into asm files. 100b57cec5SDimitry Andric // 110b57cec5SDimitry Andric //===----------------------------------------------------------------------===// 120b57cec5SDimitry Andric 130b57cec5SDimitry Andric #include "DwarfExpression.h" 140b57cec5SDimitry Andric #include "DwarfCompileUnit.h" 150b57cec5SDimitry Andric #include "llvm/ADT/APInt.h" 160b57cec5SDimitry Andric #include "llvm/ADT/SmallBitVector.h" 170b57cec5SDimitry Andric #include "llvm/BinaryFormat/Dwarf.h" 188bcb0991SDimitry Andric #include "llvm/CodeGen/Register.h" 190b57cec5SDimitry Andric #include "llvm/CodeGen/TargetRegisterInfo.h" 20e8d8bef9SDimitry Andric #include "llvm/IR/DataLayout.h" 210b57cec5SDimitry Andric #include "llvm/Support/ErrorHandling.h" 220b57cec5SDimitry Andric #include <algorithm> 230b57cec5SDimitry Andric 240b57cec5SDimitry Andric using namespace llvm; 250b57cec5SDimitry Andric 26e8d8bef9SDimitry Andric #define DEBUG_TYPE "dwarfdebug" 27e8d8bef9SDimitry Andric 280b57cec5SDimitry Andric void DwarfExpression::emitConstu(uint64_t Value) { 290b57cec5SDimitry Andric if (Value < 32) 300b57cec5SDimitry Andric emitOp(dwarf::DW_OP_lit0 + Value); 310b57cec5SDimitry Andric else if (Value == std::numeric_limits<uint64_t>::max()) { 320b57cec5SDimitry Andric // Only do this for 64-bit values as the DWARF expression stack uses 330b57cec5SDimitry Andric // target-address-size values. 340b57cec5SDimitry Andric emitOp(dwarf::DW_OP_lit0); 350b57cec5SDimitry Andric emitOp(dwarf::DW_OP_not); 360b57cec5SDimitry Andric } else { 370b57cec5SDimitry Andric emitOp(dwarf::DW_OP_constu); 380b57cec5SDimitry Andric emitUnsigned(Value); 390b57cec5SDimitry Andric } 400b57cec5SDimitry Andric } 410b57cec5SDimitry Andric 420b57cec5SDimitry Andric void DwarfExpression::addReg(int DwarfReg, const char *Comment) { 430b57cec5SDimitry Andric assert(DwarfReg >= 0 && "invalid negative dwarf register number"); 440b57cec5SDimitry Andric assert((isUnknownLocation() || isRegisterLocation()) && 450b57cec5SDimitry Andric "location description already locked down"); 460b57cec5SDimitry Andric LocationKind = Register; 470b57cec5SDimitry Andric if (DwarfReg < 32) { 480b57cec5SDimitry Andric emitOp(dwarf::DW_OP_reg0 + DwarfReg, Comment); 490b57cec5SDimitry Andric } else { 500b57cec5SDimitry Andric emitOp(dwarf::DW_OP_regx, Comment); 510b57cec5SDimitry Andric emitUnsigned(DwarfReg); 520b57cec5SDimitry Andric } 530b57cec5SDimitry Andric } 540b57cec5SDimitry Andric 550b57cec5SDimitry Andric void DwarfExpression::addBReg(int DwarfReg, int Offset) { 560b57cec5SDimitry Andric assert(DwarfReg >= 0 && "invalid negative dwarf register number"); 570b57cec5SDimitry Andric assert(!isRegisterLocation() && "location description already locked down"); 580b57cec5SDimitry Andric if (DwarfReg < 32) { 590b57cec5SDimitry Andric emitOp(dwarf::DW_OP_breg0 + DwarfReg); 600b57cec5SDimitry Andric } else { 610b57cec5SDimitry Andric emitOp(dwarf::DW_OP_bregx); 620b57cec5SDimitry Andric emitUnsigned(DwarfReg); 630b57cec5SDimitry Andric } 640b57cec5SDimitry Andric emitSigned(Offset); 650b57cec5SDimitry Andric } 660b57cec5SDimitry Andric 670b57cec5SDimitry Andric void DwarfExpression::addFBReg(int Offset) { 680b57cec5SDimitry Andric emitOp(dwarf::DW_OP_fbreg); 690b57cec5SDimitry Andric emitSigned(Offset); 700b57cec5SDimitry Andric } 710b57cec5SDimitry Andric 720b57cec5SDimitry Andric void DwarfExpression::addOpPiece(unsigned SizeInBits, unsigned OffsetInBits) { 730b57cec5SDimitry Andric if (!SizeInBits) 740b57cec5SDimitry Andric return; 750b57cec5SDimitry Andric 760b57cec5SDimitry Andric const unsigned SizeOfByte = 8; 770b57cec5SDimitry Andric if (OffsetInBits > 0 || SizeInBits % SizeOfByte) { 780b57cec5SDimitry Andric emitOp(dwarf::DW_OP_bit_piece); 790b57cec5SDimitry Andric emitUnsigned(SizeInBits); 800b57cec5SDimitry Andric emitUnsigned(OffsetInBits); 810b57cec5SDimitry Andric } else { 820b57cec5SDimitry Andric emitOp(dwarf::DW_OP_piece); 830b57cec5SDimitry Andric unsigned ByteSize = SizeInBits / SizeOfByte; 840b57cec5SDimitry Andric emitUnsigned(ByteSize); 850b57cec5SDimitry Andric } 860b57cec5SDimitry Andric this->OffsetInBits += SizeInBits; 870b57cec5SDimitry Andric } 880b57cec5SDimitry Andric 890b57cec5SDimitry Andric void DwarfExpression::addShr(unsigned ShiftBy) { 900b57cec5SDimitry Andric emitConstu(ShiftBy); 910b57cec5SDimitry Andric emitOp(dwarf::DW_OP_shr); 920b57cec5SDimitry Andric } 930b57cec5SDimitry Andric 940b57cec5SDimitry Andric void DwarfExpression::addAnd(unsigned Mask) { 950b57cec5SDimitry Andric emitConstu(Mask); 960b57cec5SDimitry Andric emitOp(dwarf::DW_OP_and); 970b57cec5SDimitry Andric } 980b57cec5SDimitry Andric 990b57cec5SDimitry Andric bool DwarfExpression::addMachineReg(const TargetRegisterInfo &TRI, 100e8d8bef9SDimitry Andric llvm::Register MachineReg, 101e8d8bef9SDimitry Andric unsigned MaxSize) { 1028bcb0991SDimitry Andric if (!llvm::Register::isPhysicalRegister(MachineReg)) { 1030b57cec5SDimitry Andric if (isFrameRegister(TRI, MachineReg)) { 1045ffd83dbSDimitry Andric DwarfRegs.push_back(Register::createRegister(-1, nullptr)); 1050b57cec5SDimitry Andric return true; 1060b57cec5SDimitry Andric } 1070b57cec5SDimitry Andric return false; 1080b57cec5SDimitry Andric } 1090b57cec5SDimitry Andric 1100b57cec5SDimitry Andric int Reg = TRI.getDwarfRegNum(MachineReg, false); 1110b57cec5SDimitry Andric 1120b57cec5SDimitry Andric // If this is a valid register number, emit it. 1130b57cec5SDimitry Andric if (Reg >= 0) { 1145ffd83dbSDimitry Andric DwarfRegs.push_back(Register::createRegister(Reg, nullptr)); 1150b57cec5SDimitry Andric return true; 1160b57cec5SDimitry Andric } 1170b57cec5SDimitry Andric 1180b57cec5SDimitry Andric // Walk up the super-register chain until we find a valid number. 1190b57cec5SDimitry Andric // For example, EAX on x86_64 is a 32-bit fragment of RAX with offset 0. 1200b57cec5SDimitry Andric for (MCSuperRegIterator SR(MachineReg, &TRI); SR.isValid(); ++SR) { 1210b57cec5SDimitry Andric Reg = TRI.getDwarfRegNum(*SR, false); 1220b57cec5SDimitry Andric if (Reg >= 0) { 1230b57cec5SDimitry Andric unsigned Idx = TRI.getSubRegIndex(*SR, MachineReg); 1240b57cec5SDimitry Andric unsigned Size = TRI.getSubRegIdxSize(Idx); 1250b57cec5SDimitry Andric unsigned RegOffset = TRI.getSubRegIdxOffset(Idx); 1265ffd83dbSDimitry Andric DwarfRegs.push_back(Register::createRegister(Reg, "super-register")); 1270b57cec5SDimitry Andric // Use a DW_OP_bit_piece to describe the sub-register. 1280b57cec5SDimitry Andric setSubRegisterPiece(Size, RegOffset); 1290b57cec5SDimitry Andric return true; 1300b57cec5SDimitry Andric } 1310b57cec5SDimitry Andric } 1320b57cec5SDimitry Andric 1330b57cec5SDimitry Andric // Otherwise, attempt to find a covering set of sub-register numbers. 1340b57cec5SDimitry Andric // For example, Q0 on ARM is a composition of D0+D1. 1350b57cec5SDimitry Andric unsigned CurPos = 0; 1360b57cec5SDimitry Andric // The size of the register in bits. 1370b57cec5SDimitry Andric const TargetRegisterClass *RC = TRI.getMinimalPhysRegClass(MachineReg); 1380b57cec5SDimitry Andric unsigned RegSize = TRI.getRegSizeInBits(*RC); 1390b57cec5SDimitry Andric // Keep track of the bits in the register we already emitted, so we 1400b57cec5SDimitry Andric // can avoid emitting redundant aliasing subregs. Because this is 1410b57cec5SDimitry Andric // just doing a greedy scan of all subregisters, it is possible that 1420b57cec5SDimitry Andric // this doesn't find a combination of subregisters that fully cover 1430b57cec5SDimitry Andric // the register (even though one may exist). 1440b57cec5SDimitry Andric SmallBitVector Coverage(RegSize, false); 1450b57cec5SDimitry Andric for (MCSubRegIterator SR(MachineReg, &TRI); SR.isValid(); ++SR) { 1460b57cec5SDimitry Andric unsigned Idx = TRI.getSubRegIndex(MachineReg, *SR); 1470b57cec5SDimitry Andric unsigned Size = TRI.getSubRegIdxSize(Idx); 1480b57cec5SDimitry Andric unsigned Offset = TRI.getSubRegIdxOffset(Idx); 1490b57cec5SDimitry Andric Reg = TRI.getDwarfRegNum(*SR, false); 1500b57cec5SDimitry Andric if (Reg < 0) 1510b57cec5SDimitry Andric continue; 1520b57cec5SDimitry Andric 1535ffd83dbSDimitry Andric // Used to build the intersection between the bits we already 1545ffd83dbSDimitry Andric // emitted and the bits covered by this subregister. 1550b57cec5SDimitry Andric SmallBitVector CurSubReg(RegSize, false); 1560b57cec5SDimitry Andric CurSubReg.set(Offset, Offset + Size); 1570b57cec5SDimitry Andric 1580b57cec5SDimitry Andric // If this sub-register has a DWARF number and we haven't covered 159480093f4SDimitry Andric // its range, and its range covers the value, emit a DWARF piece for it. 160480093f4SDimitry Andric if (Offset < MaxSize && CurSubReg.test(Coverage)) { 1610b57cec5SDimitry Andric // Emit a piece for any gap in the coverage. 1620b57cec5SDimitry Andric if (Offset > CurPos) 1635ffd83dbSDimitry Andric DwarfRegs.push_back(Register::createSubRegister( 1645ffd83dbSDimitry Andric -1, Offset - CurPos, "no DWARF register encoding")); 1655ffd83dbSDimitry Andric if (Offset == 0 && Size >= MaxSize) 1665ffd83dbSDimitry Andric DwarfRegs.push_back(Register::createRegister(Reg, "sub-register")); 1675ffd83dbSDimitry Andric else 1685ffd83dbSDimitry Andric DwarfRegs.push_back(Register::createSubRegister( 1695ffd83dbSDimitry Andric Reg, std::min<unsigned>(Size, MaxSize - Offset), "sub-register")); 170480093f4SDimitry Andric } 1710b57cec5SDimitry Andric // Mark it as emitted. 1720b57cec5SDimitry Andric Coverage.set(Offset, Offset + Size); 1730b57cec5SDimitry Andric CurPos = Offset + Size; 1740b57cec5SDimitry Andric } 1750b57cec5SDimitry Andric // Failed to find any DWARF encoding. 1760b57cec5SDimitry Andric if (CurPos == 0) 1770b57cec5SDimitry Andric return false; 1780b57cec5SDimitry Andric // Found a partial or complete DWARF encoding. 1790b57cec5SDimitry Andric if (CurPos < RegSize) 1805ffd83dbSDimitry Andric DwarfRegs.push_back(Register::createSubRegister( 1815ffd83dbSDimitry Andric -1, RegSize - CurPos, "no DWARF register encoding")); 1820b57cec5SDimitry Andric return true; 1830b57cec5SDimitry Andric } 1840b57cec5SDimitry Andric 1850b57cec5SDimitry Andric void DwarfExpression::addStackValue() { 1860b57cec5SDimitry Andric if (DwarfVersion >= 4) 1870b57cec5SDimitry Andric emitOp(dwarf::DW_OP_stack_value); 1880b57cec5SDimitry Andric } 1890b57cec5SDimitry Andric 1900b57cec5SDimitry Andric void DwarfExpression::addSignedConstant(int64_t Value) { 1910b57cec5SDimitry Andric assert(isImplicitLocation() || isUnknownLocation()); 1920b57cec5SDimitry Andric LocationKind = Implicit; 1930b57cec5SDimitry Andric emitOp(dwarf::DW_OP_consts); 1940b57cec5SDimitry Andric emitSigned(Value); 1950b57cec5SDimitry Andric } 1960b57cec5SDimitry Andric 1970b57cec5SDimitry Andric void DwarfExpression::addUnsignedConstant(uint64_t Value) { 1980b57cec5SDimitry Andric assert(isImplicitLocation() || isUnknownLocation()); 1990b57cec5SDimitry Andric LocationKind = Implicit; 2000b57cec5SDimitry Andric emitConstu(Value); 2010b57cec5SDimitry Andric } 2020b57cec5SDimitry Andric 2030b57cec5SDimitry Andric void DwarfExpression::addUnsignedConstant(const APInt &Value) { 2040b57cec5SDimitry Andric assert(isImplicitLocation() || isUnknownLocation()); 2050b57cec5SDimitry Andric LocationKind = Implicit; 2060b57cec5SDimitry Andric 2070b57cec5SDimitry Andric unsigned Size = Value.getBitWidth(); 2080b57cec5SDimitry Andric const uint64_t *Data = Value.getRawData(); 2090b57cec5SDimitry Andric 2100b57cec5SDimitry Andric // Chop it up into 64-bit pieces, because that's the maximum that 2110b57cec5SDimitry Andric // addUnsignedConstant takes. 2120b57cec5SDimitry Andric unsigned Offset = 0; 2130b57cec5SDimitry Andric while (Offset < Size) { 2140b57cec5SDimitry Andric addUnsignedConstant(*Data++); 2150b57cec5SDimitry Andric if (Offset == 0 && Size <= 64) 2160b57cec5SDimitry Andric break; 2170b57cec5SDimitry Andric addStackValue(); 2180b57cec5SDimitry Andric addOpPiece(std::min(Size - Offset, 64u), Offset); 2190b57cec5SDimitry Andric Offset += 64; 2200b57cec5SDimitry Andric } 2210b57cec5SDimitry Andric } 2220b57cec5SDimitry Andric 223e8d8bef9SDimitry Andric void DwarfExpression::addConstantFP(const APFloat &APF, const AsmPrinter &AP) { 224e8d8bef9SDimitry Andric assert(isImplicitLocation() || isUnknownLocation()); 225e8d8bef9SDimitry Andric APInt API = APF.bitcastToAPInt(); 226e8d8bef9SDimitry Andric int NumBytes = API.getBitWidth() / 8; 227e8d8bef9SDimitry Andric if (NumBytes == 4 /*float*/ || NumBytes == 8 /*double*/) { 228e8d8bef9SDimitry Andric // FIXME: Add support for `long double`. 229e8d8bef9SDimitry Andric emitOp(dwarf::DW_OP_implicit_value); 230e8d8bef9SDimitry Andric emitUnsigned(NumBytes /*Size of the block in bytes*/); 231e8d8bef9SDimitry Andric 232e8d8bef9SDimitry Andric // The loop below is emitting the value starting at least significant byte, 233e8d8bef9SDimitry Andric // so we need to perform a byte-swap to get the byte order correct in case 234e8d8bef9SDimitry Andric // of a big-endian target. 235e8d8bef9SDimitry Andric if (AP.getDataLayout().isBigEndian()) 236e8d8bef9SDimitry Andric API = API.byteSwap(); 237e8d8bef9SDimitry Andric 238e8d8bef9SDimitry Andric for (int i = 0; i < NumBytes; ++i) { 239e8d8bef9SDimitry Andric emitData1(API.getZExtValue() & 0xFF); 240e8d8bef9SDimitry Andric API = API.lshr(8); 241e8d8bef9SDimitry Andric } 242e8d8bef9SDimitry Andric 243e8d8bef9SDimitry Andric return; 244e8d8bef9SDimitry Andric } 245e8d8bef9SDimitry Andric LLVM_DEBUG( 246e8d8bef9SDimitry Andric dbgs() << "Skipped DW_OP_implicit_value creation for ConstantFP of size: " 247e8d8bef9SDimitry Andric << API.getBitWidth() << " bits\n"); 248e8d8bef9SDimitry Andric } 249e8d8bef9SDimitry Andric 2500b57cec5SDimitry Andric bool DwarfExpression::addMachineRegExpression(const TargetRegisterInfo &TRI, 2510b57cec5SDimitry Andric DIExpressionCursor &ExprCursor, 252e8d8bef9SDimitry Andric llvm::Register MachineReg, 2530b57cec5SDimitry Andric unsigned FragmentOffsetInBits) { 2540b57cec5SDimitry Andric auto Fragment = ExprCursor.getFragmentInfo(); 2550b57cec5SDimitry Andric if (!addMachineReg(TRI, MachineReg, Fragment ? Fragment->SizeInBits : ~1U)) { 2560b57cec5SDimitry Andric LocationKind = Unknown; 2570b57cec5SDimitry Andric return false; 2580b57cec5SDimitry Andric } 2590b57cec5SDimitry Andric 2600b57cec5SDimitry Andric bool HasComplexExpression = false; 2610b57cec5SDimitry Andric auto Op = ExprCursor.peek(); 2620b57cec5SDimitry Andric if (Op && Op->getOp() != dwarf::DW_OP_LLVM_fragment) 2630b57cec5SDimitry Andric HasComplexExpression = true; 2640b57cec5SDimitry Andric 2650b57cec5SDimitry Andric // If the register can only be described by a complex expression (i.e., 2660b57cec5SDimitry Andric // multiple subregisters) it doesn't safely compose with another complex 2670b57cec5SDimitry Andric // expression. For example, it is not possible to apply a DW_OP_deref 2685ffd83dbSDimitry Andric // operation to multiple DW_OP_pieces, since composite location descriptions 2695ffd83dbSDimitry Andric // do not push anything on the DWARF stack. 2705ffd83dbSDimitry Andric // 2715ffd83dbSDimitry Andric // DW_OP_entry_value operations can only hold a DWARF expression or a 2725ffd83dbSDimitry Andric // register location description, so we can't emit a single entry value 2735ffd83dbSDimitry Andric // covering a composite location description. In the future we may want to 2745ffd83dbSDimitry Andric // emit entry value operations for each register location in the composite 2755ffd83dbSDimitry Andric // location, but until that is supported do not emit anything. 2765ffd83dbSDimitry Andric if ((HasComplexExpression || IsEmittingEntryValue) && DwarfRegs.size() > 1) { 2775ffd83dbSDimitry Andric if (IsEmittingEntryValue) 2785ffd83dbSDimitry Andric cancelEntryValue(); 2790b57cec5SDimitry Andric DwarfRegs.clear(); 2800b57cec5SDimitry Andric LocationKind = Unknown; 2810b57cec5SDimitry Andric return false; 2820b57cec5SDimitry Andric } 2830b57cec5SDimitry Andric 2848bcb0991SDimitry Andric // Handle simple register locations. If we are supposed to emit 2858bcb0991SDimitry Andric // a call site parameter expression and if that expression is just a register 2868bcb0991SDimitry Andric // location, emit it with addBReg and offset 0, because we should emit a DWARF 2878bcb0991SDimitry Andric // expression representing a value, rather than a location. 288*fe6060f1SDimitry Andric if ((!isParameterValue() && !isMemoryLocation() && !HasComplexExpression) || 289*fe6060f1SDimitry Andric isEntryValue()) { 2900b57cec5SDimitry Andric for (auto &Reg : DwarfRegs) { 2910b57cec5SDimitry Andric if (Reg.DwarfRegNo >= 0) 2920b57cec5SDimitry Andric addReg(Reg.DwarfRegNo, Reg.Comment); 2935ffd83dbSDimitry Andric addOpPiece(Reg.SubRegSize); 2940b57cec5SDimitry Andric } 2950b57cec5SDimitry Andric 296*fe6060f1SDimitry Andric if (isEntryValue()) { 2978bcb0991SDimitry Andric finalizeEntryValue(); 2988bcb0991SDimitry Andric 299*fe6060f1SDimitry Andric if (!isIndirect() && !isParameterValue() && !HasComplexExpression && 3005ffd83dbSDimitry Andric DwarfVersion >= 4) 3010b57cec5SDimitry Andric emitOp(dwarf::DW_OP_stack_value); 302*fe6060f1SDimitry Andric } 3030b57cec5SDimitry Andric 3040b57cec5SDimitry Andric DwarfRegs.clear(); 305*fe6060f1SDimitry Andric // If we need to mask out a subregister, do it now, unless the next 306*fe6060f1SDimitry Andric // operation would emit an OpPiece anyway. 307*fe6060f1SDimitry Andric auto NextOp = ExprCursor.peek(); 308*fe6060f1SDimitry Andric if (SubRegisterSizeInBits && NextOp && 309*fe6060f1SDimitry Andric (NextOp->getOp() != dwarf::DW_OP_LLVM_fragment)) 310*fe6060f1SDimitry Andric maskSubRegister(); 3110b57cec5SDimitry Andric return true; 3120b57cec5SDimitry Andric } 3130b57cec5SDimitry Andric 3140b57cec5SDimitry Andric // Don't emit locations that cannot be expressed without DW_OP_stack_value. 3150b57cec5SDimitry Andric if (DwarfVersion < 4) 3160b57cec5SDimitry Andric if (any_of(ExprCursor, [](DIExpression::ExprOperand Op) -> bool { 3170b57cec5SDimitry Andric return Op.getOp() == dwarf::DW_OP_stack_value; 3180b57cec5SDimitry Andric })) { 3190b57cec5SDimitry Andric DwarfRegs.clear(); 3200b57cec5SDimitry Andric LocationKind = Unknown; 3210b57cec5SDimitry Andric return false; 3220b57cec5SDimitry Andric } 3230b57cec5SDimitry Andric 3240b57cec5SDimitry Andric assert(DwarfRegs.size() == 1); 3250b57cec5SDimitry Andric auto Reg = DwarfRegs[0]; 3260b57cec5SDimitry Andric bool FBReg = isFrameRegister(TRI, MachineReg); 3270b57cec5SDimitry Andric int SignedOffset = 0; 3285ffd83dbSDimitry Andric assert(!Reg.isSubRegister() && "full register expected"); 3290b57cec5SDimitry Andric 3300b57cec5SDimitry Andric // Pattern-match combinations for which more efficient representations exist. 3310b57cec5SDimitry Andric // [Reg, DW_OP_plus_uconst, Offset] --> [DW_OP_breg, Offset]. 3320b57cec5SDimitry Andric if (Op && (Op->getOp() == dwarf::DW_OP_plus_uconst)) { 3338bcb0991SDimitry Andric uint64_t Offset = Op->getArg(0); 3348bcb0991SDimitry Andric uint64_t IntMax = static_cast<uint64_t>(std::numeric_limits<int>::max()); 3358bcb0991SDimitry Andric if (Offset <= IntMax) { 3368bcb0991SDimitry Andric SignedOffset = Offset; 3370b57cec5SDimitry Andric ExprCursor.take(); 3380b57cec5SDimitry Andric } 3398bcb0991SDimitry Andric } 3400b57cec5SDimitry Andric 3410b57cec5SDimitry Andric // [Reg, DW_OP_constu, Offset, DW_OP_plus] --> [DW_OP_breg, Offset] 3420b57cec5SDimitry Andric // [Reg, DW_OP_constu, Offset, DW_OP_minus] --> [DW_OP_breg,-Offset] 3430b57cec5SDimitry Andric // If Reg is a subregister we need to mask it out before subtracting. 3440b57cec5SDimitry Andric if (Op && Op->getOp() == dwarf::DW_OP_constu) { 3458bcb0991SDimitry Andric uint64_t Offset = Op->getArg(0); 3468bcb0991SDimitry Andric uint64_t IntMax = static_cast<uint64_t>(std::numeric_limits<int>::max()); 3470b57cec5SDimitry Andric auto N = ExprCursor.peekNext(); 3488bcb0991SDimitry Andric if (N && N->getOp() == dwarf::DW_OP_plus && Offset <= IntMax) { 3498bcb0991SDimitry Andric SignedOffset = Offset; 3508bcb0991SDimitry Andric ExprCursor.consume(2); 3518bcb0991SDimitry Andric } else if (N && N->getOp() == dwarf::DW_OP_minus && 3528bcb0991SDimitry Andric !SubRegisterSizeInBits && Offset <= IntMax + 1) { 3538bcb0991SDimitry Andric SignedOffset = -static_cast<int64_t>(Offset); 3540b57cec5SDimitry Andric ExprCursor.consume(2); 3550b57cec5SDimitry Andric } 3560b57cec5SDimitry Andric } 3570b57cec5SDimitry Andric 3580b57cec5SDimitry Andric if (FBReg) 3590b57cec5SDimitry Andric addFBReg(SignedOffset); 3600b57cec5SDimitry Andric else 3610b57cec5SDimitry Andric addBReg(Reg.DwarfRegNo, SignedOffset); 3620b57cec5SDimitry Andric DwarfRegs.clear(); 363*fe6060f1SDimitry Andric 364*fe6060f1SDimitry Andric // If we need to mask out a subregister, do it now, unless the next 365*fe6060f1SDimitry Andric // operation would emit an OpPiece anyway. 366*fe6060f1SDimitry Andric auto NextOp = ExprCursor.peek(); 367*fe6060f1SDimitry Andric if (SubRegisterSizeInBits && NextOp && 368*fe6060f1SDimitry Andric (NextOp->getOp() != dwarf::DW_OP_LLVM_fragment)) 369*fe6060f1SDimitry Andric maskSubRegister(); 370*fe6060f1SDimitry Andric 3710b57cec5SDimitry Andric return true; 3720b57cec5SDimitry Andric } 3730b57cec5SDimitry Andric 3745ffd83dbSDimitry Andric void DwarfExpression::setEntryValueFlags(const MachineLocation &Loc) { 3755ffd83dbSDimitry Andric LocationFlags |= EntryValue; 3765ffd83dbSDimitry Andric if (Loc.isIndirect()) 3775ffd83dbSDimitry Andric LocationFlags |= Indirect; 3785ffd83dbSDimitry Andric } 3795ffd83dbSDimitry Andric 3805ffd83dbSDimitry Andric void DwarfExpression::setLocation(const MachineLocation &Loc, 3815ffd83dbSDimitry Andric const DIExpression *DIExpr) { 3825ffd83dbSDimitry Andric if (Loc.isIndirect()) 3835ffd83dbSDimitry Andric setMemoryLocationKind(); 3845ffd83dbSDimitry Andric 3855ffd83dbSDimitry Andric if (DIExpr->isEntryValue()) 3865ffd83dbSDimitry Andric setEntryValueFlags(Loc); 3875ffd83dbSDimitry Andric } 3885ffd83dbSDimitry Andric 3898bcb0991SDimitry Andric void DwarfExpression::beginEntryValueExpression( 3908bcb0991SDimitry Andric DIExpressionCursor &ExprCursor) { 3910b57cec5SDimitry Andric auto Op = ExprCursor.take(); 3928bcb0991SDimitry Andric (void)Op; 3938bcb0991SDimitry Andric assert(Op && Op->getOp() == dwarf::DW_OP_LLVM_entry_value); 3948bcb0991SDimitry Andric assert(!IsEmittingEntryValue && "Already emitting entry value?"); 3958bcb0991SDimitry Andric assert(Op->getArg(0) == 1 && 3968bcb0991SDimitry Andric "Can currently only emit entry values covering a single operation"); 3970b57cec5SDimitry Andric 398*fe6060f1SDimitry Andric SavedLocationKind = LocationKind; 399*fe6060f1SDimitry Andric LocationKind = Register; 4008bcb0991SDimitry Andric IsEmittingEntryValue = true; 4018bcb0991SDimitry Andric enableTemporaryBuffer(); 4028bcb0991SDimitry Andric } 4038bcb0991SDimitry Andric 4048bcb0991SDimitry Andric void DwarfExpression::finalizeEntryValue() { 4058bcb0991SDimitry Andric assert(IsEmittingEntryValue && "Entry value not open?"); 4068bcb0991SDimitry Andric disableTemporaryBuffer(); 4078bcb0991SDimitry Andric 4085ffd83dbSDimitry Andric emitOp(CU.getDwarf5OrGNULocationAtom(dwarf::DW_OP_entry_value)); 4095ffd83dbSDimitry Andric 4108bcb0991SDimitry Andric // Emit the entry value's size operand. 4118bcb0991SDimitry Andric unsigned Size = getTemporaryBufferSize(); 4128bcb0991SDimitry Andric emitUnsigned(Size); 4138bcb0991SDimitry Andric 4148bcb0991SDimitry Andric // Emit the entry value's DWARF block operand. 4158bcb0991SDimitry Andric commitTemporaryBuffer(); 4168bcb0991SDimitry Andric 417*fe6060f1SDimitry Andric LocationFlags &= ~EntryValue; 418*fe6060f1SDimitry Andric LocationKind = SavedLocationKind; 4198bcb0991SDimitry Andric IsEmittingEntryValue = false; 4200b57cec5SDimitry Andric } 4210b57cec5SDimitry Andric 4225ffd83dbSDimitry Andric void DwarfExpression::cancelEntryValue() { 4235ffd83dbSDimitry Andric assert(IsEmittingEntryValue && "Entry value not open?"); 4245ffd83dbSDimitry Andric disableTemporaryBuffer(); 4255ffd83dbSDimitry Andric 4265ffd83dbSDimitry Andric // The temporary buffer can't be emptied, so for now just assert that nothing 4275ffd83dbSDimitry Andric // has been emitted to it. 4285ffd83dbSDimitry Andric assert(getTemporaryBufferSize() == 0 && 4295ffd83dbSDimitry Andric "Began emitting entry value block before cancelling entry value"); 4305ffd83dbSDimitry Andric 431*fe6060f1SDimitry Andric LocationKind = SavedLocationKind; 4325ffd83dbSDimitry Andric IsEmittingEntryValue = false; 4335ffd83dbSDimitry Andric } 4345ffd83dbSDimitry Andric 4355ffd83dbSDimitry Andric unsigned DwarfExpression::getOrCreateBaseType(unsigned BitSize, 4365ffd83dbSDimitry Andric dwarf::TypeKind Encoding) { 4375ffd83dbSDimitry Andric // Reuse the base_type if we already have one in this CU otherwise we 4385ffd83dbSDimitry Andric // create a new one. 4395ffd83dbSDimitry Andric unsigned I = 0, E = CU.ExprRefedBaseTypes.size(); 4405ffd83dbSDimitry Andric for (; I != E; ++I) 4415ffd83dbSDimitry Andric if (CU.ExprRefedBaseTypes[I].BitSize == BitSize && 4425ffd83dbSDimitry Andric CU.ExprRefedBaseTypes[I].Encoding == Encoding) 4435ffd83dbSDimitry Andric break; 4445ffd83dbSDimitry Andric 4455ffd83dbSDimitry Andric if (I == E) 4465ffd83dbSDimitry Andric CU.ExprRefedBaseTypes.emplace_back(BitSize, Encoding); 4475ffd83dbSDimitry Andric return I; 4485ffd83dbSDimitry Andric } 4495ffd83dbSDimitry Andric 4505ffd83dbSDimitry Andric /// Assuming a well-formed expression, match "DW_OP_deref* 4515ffd83dbSDimitry Andric /// DW_OP_LLVM_fragment?". 4520b57cec5SDimitry Andric static bool isMemoryLocation(DIExpressionCursor ExprCursor) { 4530b57cec5SDimitry Andric while (ExprCursor) { 4540b57cec5SDimitry Andric auto Op = ExprCursor.take(); 4550b57cec5SDimitry Andric switch (Op->getOp()) { 4560b57cec5SDimitry Andric case dwarf::DW_OP_deref: 4570b57cec5SDimitry Andric case dwarf::DW_OP_LLVM_fragment: 4580b57cec5SDimitry Andric break; 4590b57cec5SDimitry Andric default: 4600b57cec5SDimitry Andric return false; 4610b57cec5SDimitry Andric } 4620b57cec5SDimitry Andric } 4630b57cec5SDimitry Andric return true; 4640b57cec5SDimitry Andric } 4650b57cec5SDimitry Andric 4660b57cec5SDimitry Andric void DwarfExpression::addExpression(DIExpressionCursor &&ExprCursor, 4670b57cec5SDimitry Andric unsigned FragmentOffsetInBits) { 468*fe6060f1SDimitry Andric addExpression(std::move(ExprCursor), 469*fe6060f1SDimitry Andric [](unsigned Idx, DIExpressionCursor &Cursor) -> bool { 470*fe6060f1SDimitry Andric llvm_unreachable("unhandled opcode found in expression"); 471*fe6060f1SDimitry Andric }); 472*fe6060f1SDimitry Andric } 473*fe6060f1SDimitry Andric 474*fe6060f1SDimitry Andric void DwarfExpression::addExpression( 475*fe6060f1SDimitry Andric DIExpressionCursor &&ExprCursor, 476*fe6060f1SDimitry Andric llvm::function_ref<bool(unsigned, DIExpressionCursor &)> InsertArg) { 4775ffd83dbSDimitry Andric // Entry values can currently only cover the initial register location, 4785ffd83dbSDimitry Andric // and not any other parts of the following DWARF expression. 4795ffd83dbSDimitry Andric assert(!IsEmittingEntryValue && "Can't emit entry value around expression"); 4805ffd83dbSDimitry Andric 4810b57cec5SDimitry Andric Optional<DIExpression::ExprOperand> PrevConvertOp = None; 4820b57cec5SDimitry Andric 4830b57cec5SDimitry Andric while (ExprCursor) { 4840b57cec5SDimitry Andric auto Op = ExprCursor.take(); 4858bcb0991SDimitry Andric uint64_t OpNum = Op->getOp(); 4868bcb0991SDimitry Andric 4878bcb0991SDimitry Andric if (OpNum >= dwarf::DW_OP_reg0 && OpNum <= dwarf::DW_OP_reg31) { 4888bcb0991SDimitry Andric emitOp(OpNum); 4898bcb0991SDimitry Andric continue; 4908bcb0991SDimitry Andric } else if (OpNum >= dwarf::DW_OP_breg0 && OpNum <= dwarf::DW_OP_breg31) { 4918bcb0991SDimitry Andric addBReg(OpNum - dwarf::DW_OP_breg0, Op->getArg(0)); 4928bcb0991SDimitry Andric continue; 4938bcb0991SDimitry Andric } 4948bcb0991SDimitry Andric 4958bcb0991SDimitry Andric switch (OpNum) { 496*fe6060f1SDimitry Andric case dwarf::DW_OP_LLVM_arg: 497*fe6060f1SDimitry Andric if (!InsertArg(Op->getArg(0), ExprCursor)) { 498*fe6060f1SDimitry Andric LocationKind = Unknown; 499*fe6060f1SDimitry Andric return; 500*fe6060f1SDimitry Andric } 501*fe6060f1SDimitry Andric break; 5020b57cec5SDimitry Andric case dwarf::DW_OP_LLVM_fragment: { 5030b57cec5SDimitry Andric unsigned SizeInBits = Op->getArg(1); 5040b57cec5SDimitry Andric unsigned FragmentOffset = Op->getArg(0); 5050b57cec5SDimitry Andric // The fragment offset must have already been adjusted by emitting an 5060b57cec5SDimitry Andric // empty DW_OP_piece / DW_OP_bit_piece before we emitted the base 5070b57cec5SDimitry Andric // location. 5080b57cec5SDimitry Andric assert(OffsetInBits >= FragmentOffset && "fragment offset not added?"); 509480093f4SDimitry Andric assert(SizeInBits >= OffsetInBits - FragmentOffset && "size underflow"); 5100b57cec5SDimitry Andric 5110b57cec5SDimitry Andric // If addMachineReg already emitted DW_OP_piece operations to represent 5120b57cec5SDimitry Andric // a super-register by splicing together sub-registers, subtract the size 5130b57cec5SDimitry Andric // of the pieces that was already emitted. 5140b57cec5SDimitry Andric SizeInBits -= OffsetInBits - FragmentOffset; 5150b57cec5SDimitry Andric 5160b57cec5SDimitry Andric // If addMachineReg requested a DW_OP_bit_piece to stencil out a 5170b57cec5SDimitry Andric // sub-register that is smaller than the current fragment's size, use it. 5180b57cec5SDimitry Andric if (SubRegisterSizeInBits) 5190b57cec5SDimitry Andric SizeInBits = std::min<unsigned>(SizeInBits, SubRegisterSizeInBits); 5200b57cec5SDimitry Andric 5210b57cec5SDimitry Andric // Emit a DW_OP_stack_value for implicit location descriptions. 5220b57cec5SDimitry Andric if (isImplicitLocation()) 5230b57cec5SDimitry Andric addStackValue(); 5240b57cec5SDimitry Andric 5250b57cec5SDimitry Andric // Emit the DW_OP_piece. 5260b57cec5SDimitry Andric addOpPiece(SizeInBits, SubRegisterOffsetInBits); 5270b57cec5SDimitry Andric setSubRegisterPiece(0, 0); 5280b57cec5SDimitry Andric // Reset the location description kind. 5290b57cec5SDimitry Andric LocationKind = Unknown; 5300b57cec5SDimitry Andric return; 5310b57cec5SDimitry Andric } 5320b57cec5SDimitry Andric case dwarf::DW_OP_plus_uconst: 5330b57cec5SDimitry Andric assert(!isRegisterLocation()); 5340b57cec5SDimitry Andric emitOp(dwarf::DW_OP_plus_uconst); 5350b57cec5SDimitry Andric emitUnsigned(Op->getArg(0)); 5360b57cec5SDimitry Andric break; 5370b57cec5SDimitry Andric case dwarf::DW_OP_plus: 5380b57cec5SDimitry Andric case dwarf::DW_OP_minus: 5390b57cec5SDimitry Andric case dwarf::DW_OP_mul: 5400b57cec5SDimitry Andric case dwarf::DW_OP_div: 5410b57cec5SDimitry Andric case dwarf::DW_OP_mod: 5420b57cec5SDimitry Andric case dwarf::DW_OP_or: 5430b57cec5SDimitry Andric case dwarf::DW_OP_and: 5440b57cec5SDimitry Andric case dwarf::DW_OP_xor: 5450b57cec5SDimitry Andric case dwarf::DW_OP_shl: 5460b57cec5SDimitry Andric case dwarf::DW_OP_shr: 5470b57cec5SDimitry Andric case dwarf::DW_OP_shra: 5480b57cec5SDimitry Andric case dwarf::DW_OP_lit0: 5490b57cec5SDimitry Andric case dwarf::DW_OP_not: 5500b57cec5SDimitry Andric case dwarf::DW_OP_dup: 5515ffd83dbSDimitry Andric case dwarf::DW_OP_push_object_address: 552e8d8bef9SDimitry Andric case dwarf::DW_OP_over: 5538bcb0991SDimitry Andric emitOp(OpNum); 5540b57cec5SDimitry Andric break; 5550b57cec5SDimitry Andric case dwarf::DW_OP_deref: 5560b57cec5SDimitry Andric assert(!isRegisterLocation()); 5570b57cec5SDimitry Andric if (!isMemoryLocation() && ::isMemoryLocation(ExprCursor)) 5580b57cec5SDimitry Andric // Turning this into a memory location description makes the deref 5590b57cec5SDimitry Andric // implicit. 5600b57cec5SDimitry Andric LocationKind = Memory; 5610b57cec5SDimitry Andric else 5620b57cec5SDimitry Andric emitOp(dwarf::DW_OP_deref); 5630b57cec5SDimitry Andric break; 5640b57cec5SDimitry Andric case dwarf::DW_OP_constu: 5650b57cec5SDimitry Andric assert(!isRegisterLocation()); 5660b57cec5SDimitry Andric emitConstu(Op->getArg(0)); 5670b57cec5SDimitry Andric break; 568e8d8bef9SDimitry Andric case dwarf::DW_OP_consts: 569e8d8bef9SDimitry Andric assert(!isRegisterLocation()); 570e8d8bef9SDimitry Andric emitOp(dwarf::DW_OP_consts); 571e8d8bef9SDimitry Andric emitSigned(Op->getArg(0)); 572e8d8bef9SDimitry Andric break; 5730b57cec5SDimitry Andric case dwarf::DW_OP_LLVM_convert: { 5740b57cec5SDimitry Andric unsigned BitSize = Op->getArg(0); 5750b57cec5SDimitry Andric dwarf::TypeKind Encoding = static_cast<dwarf::TypeKind>(Op->getArg(1)); 576e8d8bef9SDimitry Andric if (DwarfVersion >= 5 && CU.getDwarfDebug().useOpConvert()) { 5770b57cec5SDimitry Andric emitOp(dwarf::DW_OP_convert); 5780b57cec5SDimitry Andric // If targeting a location-list; simply emit the index into the raw 5790b57cec5SDimitry Andric // byte stream as ULEB128, DwarfDebug::emitDebugLocEntry has been 5800b57cec5SDimitry Andric // fitted with means to extract it later. 5810b57cec5SDimitry Andric // If targeting a inlined DW_AT_location; insert a DIEBaseTypeRef 5820b57cec5SDimitry Andric // (containing the index and a resolve mechanism during emit) into the 5830b57cec5SDimitry Andric // DIE value list. 5845ffd83dbSDimitry Andric emitBaseTypeRef(getOrCreateBaseType(BitSize, Encoding)); 5850b57cec5SDimitry Andric } else { 5860b57cec5SDimitry Andric if (PrevConvertOp && PrevConvertOp->getArg(0) < BitSize) { 5870b57cec5SDimitry Andric if (Encoding == dwarf::DW_ATE_signed) 5880b57cec5SDimitry Andric emitLegacySExt(PrevConvertOp->getArg(0)); 5890b57cec5SDimitry Andric else if (Encoding == dwarf::DW_ATE_unsigned) 5900b57cec5SDimitry Andric emitLegacyZExt(PrevConvertOp->getArg(0)); 5910b57cec5SDimitry Andric PrevConvertOp = None; 5920b57cec5SDimitry Andric } else { 5930b57cec5SDimitry Andric PrevConvertOp = Op; 5940b57cec5SDimitry Andric } 5950b57cec5SDimitry Andric } 5960b57cec5SDimitry Andric break; 5970b57cec5SDimitry Andric } 5980b57cec5SDimitry Andric case dwarf::DW_OP_stack_value: 5990b57cec5SDimitry Andric LocationKind = Implicit; 6000b57cec5SDimitry Andric break; 6010b57cec5SDimitry Andric case dwarf::DW_OP_swap: 6020b57cec5SDimitry Andric assert(!isRegisterLocation()); 6030b57cec5SDimitry Andric emitOp(dwarf::DW_OP_swap); 6040b57cec5SDimitry Andric break; 6050b57cec5SDimitry Andric case dwarf::DW_OP_xderef: 6060b57cec5SDimitry Andric assert(!isRegisterLocation()); 6070b57cec5SDimitry Andric emitOp(dwarf::DW_OP_xderef); 6080b57cec5SDimitry Andric break; 6090b57cec5SDimitry Andric case dwarf::DW_OP_deref_size: 6100b57cec5SDimitry Andric emitOp(dwarf::DW_OP_deref_size); 6110b57cec5SDimitry Andric emitData1(Op->getArg(0)); 6120b57cec5SDimitry Andric break; 6130b57cec5SDimitry Andric case dwarf::DW_OP_LLVM_tag_offset: 6140b57cec5SDimitry Andric TagOffset = Op->getArg(0); 6150b57cec5SDimitry Andric break; 6168bcb0991SDimitry Andric case dwarf::DW_OP_regx: 6178bcb0991SDimitry Andric emitOp(dwarf::DW_OP_regx); 6188bcb0991SDimitry Andric emitUnsigned(Op->getArg(0)); 6198bcb0991SDimitry Andric break; 6208bcb0991SDimitry Andric case dwarf::DW_OP_bregx: 6218bcb0991SDimitry Andric emitOp(dwarf::DW_OP_bregx); 6228bcb0991SDimitry Andric emitUnsigned(Op->getArg(0)); 6238bcb0991SDimitry Andric emitSigned(Op->getArg(1)); 6248bcb0991SDimitry Andric break; 6250b57cec5SDimitry Andric default: 6260b57cec5SDimitry Andric llvm_unreachable("unhandled opcode found in expression"); 6270b57cec5SDimitry Andric } 6280b57cec5SDimitry Andric } 6290b57cec5SDimitry Andric 6308bcb0991SDimitry Andric if (isImplicitLocation() && !isParameterValue()) 6310b57cec5SDimitry Andric // Turn this into an implicit location description. 6320b57cec5SDimitry Andric addStackValue(); 6330b57cec5SDimitry Andric } 6340b57cec5SDimitry Andric 6350b57cec5SDimitry Andric /// add masking operations to stencil out a subregister. 6360b57cec5SDimitry Andric void DwarfExpression::maskSubRegister() { 6370b57cec5SDimitry Andric assert(SubRegisterSizeInBits && "no subregister was registered"); 6380b57cec5SDimitry Andric if (SubRegisterOffsetInBits > 0) 6390b57cec5SDimitry Andric addShr(SubRegisterOffsetInBits); 6400b57cec5SDimitry Andric uint64_t Mask = (1ULL << (uint64_t)SubRegisterSizeInBits) - 1ULL; 6410b57cec5SDimitry Andric addAnd(Mask); 6420b57cec5SDimitry Andric } 6430b57cec5SDimitry Andric 6440b57cec5SDimitry Andric void DwarfExpression::finalize() { 6450b57cec5SDimitry Andric assert(DwarfRegs.size() == 0 && "dwarf registers not emitted"); 6460b57cec5SDimitry Andric // Emit any outstanding DW_OP_piece operations to mask out subregisters. 6470b57cec5SDimitry Andric if (SubRegisterSizeInBits == 0) 6480b57cec5SDimitry Andric return; 6490b57cec5SDimitry Andric // Don't emit a DW_OP_piece for a subregister at offset 0. 6500b57cec5SDimitry Andric if (SubRegisterOffsetInBits == 0) 6510b57cec5SDimitry Andric return; 6520b57cec5SDimitry Andric addOpPiece(SubRegisterSizeInBits, SubRegisterOffsetInBits); 6530b57cec5SDimitry Andric } 6540b57cec5SDimitry Andric 6550b57cec5SDimitry Andric void DwarfExpression::addFragmentOffset(const DIExpression *Expr) { 6560b57cec5SDimitry Andric if (!Expr || !Expr->isFragment()) 6570b57cec5SDimitry Andric return; 6580b57cec5SDimitry Andric 6590b57cec5SDimitry Andric uint64_t FragmentOffset = Expr->getFragmentInfo()->OffsetInBits; 6600b57cec5SDimitry Andric assert(FragmentOffset >= OffsetInBits && 6610b57cec5SDimitry Andric "overlapping or duplicate fragments"); 6620b57cec5SDimitry Andric if (FragmentOffset > OffsetInBits) 6630b57cec5SDimitry Andric addOpPiece(FragmentOffset - OffsetInBits); 6640b57cec5SDimitry Andric OffsetInBits = FragmentOffset; 6650b57cec5SDimitry Andric } 6660b57cec5SDimitry Andric 6670b57cec5SDimitry Andric void DwarfExpression::emitLegacySExt(unsigned FromBits) { 6680b57cec5SDimitry Andric // (((X >> (FromBits - 1)) * (~0)) << FromBits) | X 6690b57cec5SDimitry Andric emitOp(dwarf::DW_OP_dup); 6700b57cec5SDimitry Andric emitOp(dwarf::DW_OP_constu); 6710b57cec5SDimitry Andric emitUnsigned(FromBits - 1); 6720b57cec5SDimitry Andric emitOp(dwarf::DW_OP_shr); 6730b57cec5SDimitry Andric emitOp(dwarf::DW_OP_lit0); 6740b57cec5SDimitry Andric emitOp(dwarf::DW_OP_not); 6750b57cec5SDimitry Andric emitOp(dwarf::DW_OP_mul); 6760b57cec5SDimitry Andric emitOp(dwarf::DW_OP_constu); 6770b57cec5SDimitry Andric emitUnsigned(FromBits); 6780b57cec5SDimitry Andric emitOp(dwarf::DW_OP_shl); 6790b57cec5SDimitry Andric emitOp(dwarf::DW_OP_or); 6800b57cec5SDimitry Andric } 6810b57cec5SDimitry Andric 6820b57cec5SDimitry Andric void DwarfExpression::emitLegacyZExt(unsigned FromBits) { 6830b57cec5SDimitry Andric // (X & (1 << FromBits - 1)) 6840b57cec5SDimitry Andric emitOp(dwarf::DW_OP_constu); 6850b57cec5SDimitry Andric emitUnsigned((1ULL << FromBits) - 1); 6860b57cec5SDimitry Andric emitOp(dwarf::DW_OP_and); 6870b57cec5SDimitry Andric } 688480093f4SDimitry Andric 6895ffd83dbSDimitry Andric void DwarfExpression::addWasmLocation(unsigned Index, uint64_t Offset) { 690*fe6060f1SDimitry Andric emitOp(dwarf::DW_OP_WASM_location); 691*fe6060f1SDimitry Andric emitUnsigned(Index == 4/*TI_LOCAL_INDIRECT*/ ? 0/*TI_LOCAL*/ : Index); 692*fe6060f1SDimitry Andric emitUnsigned(Offset); 693*fe6060f1SDimitry Andric if (Index == 4 /*TI_LOCAL_INDIRECT*/) { 694*fe6060f1SDimitry Andric assert(LocationKind == Unknown); 695*fe6060f1SDimitry Andric LocationKind = Memory; 696*fe6060f1SDimitry Andric } else { 697480093f4SDimitry Andric assert(LocationKind == Implicit || LocationKind == Unknown); 698480093f4SDimitry Andric LocationKind = Implicit; 699*fe6060f1SDimitry Andric } 700480093f4SDimitry Andric } 701