LLVM  10.0.0svn
WebAssemblyUtilities.cpp
Go to the documentation of this file.
1 //===-- WebAssemblyUtilities.cpp - WebAssembly Utility Functions ----------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 ///
9 /// \file
10 /// This file implements several utility functions for WebAssembly.
11 ///
12 //===----------------------------------------------------------------------===//
13 
14 #include "WebAssemblyUtilities.h"
18 using namespace llvm;
19 
20 const char *const WebAssembly::ClangCallTerminateFn = "__clang_call_terminate";
21 const char *const WebAssembly::CxaBeginCatchFn = "__cxa_begin_catch";
22 const char *const WebAssembly::CxaRethrowFn = "__cxa_rethrow";
23 const char *const WebAssembly::StdTerminateFn = "_ZSt9terminatev";
25  "_Unwind_Wasm_CallPersonality";
26 
27 /// Test whether MI is a child of some other node in an expression tree.
29  const WebAssemblyFunctionInfo &MFI) {
30  if (MI.getNumOperands() == 0)
31  return false;
32  const MachineOperand &MO = MI.getOperand(0);
33  if (!MO.isReg() || MO.isImplicit() || !MO.isDef())
34  return false;
35  Register Reg = MO.getReg();
36  return Register::isVirtualRegister(Reg) && MFI.isVRegStackified(Reg);
37 }
38 
40  switch (MI.getOpcode()) {
41  case WebAssembly::THROW:
42  case WebAssembly::THROW_S:
43  case WebAssembly::RETHROW:
44  case WebAssembly::RETHROW_S:
45  return true;
46  }
47  if (isCallIndirect(MI.getOpcode()))
48  return true;
49  if (!MI.isCall())
50  return false;
51 
52  const MachineOperand &MO = MI.getOperand(getCalleeOpNo(MI.getOpcode()));
53  assert(MO.isGlobal() || MO.isSymbol());
54 
55  if (MO.isSymbol()) {
56  // Some intrinsics are lowered to calls to external symbols, which are then
57  // lowered to calls to library functions. Most of libcalls don't throw, but
58  // we only list some of them here now.
59  // TODO Consider adding 'nounwind' info in TargetLowering::CallLoweringInfo
60  // instead for more accurate info.
61  const char *Name = MO.getSymbolName();
62  if (strcmp(Name, "memcpy") == 0 || strcmp(Name, "memmove") == 0 ||
63  strcmp(Name, "memset") == 0)
64  return false;
65  return true;
66  }
67 
68  const auto *F = dyn_cast<Function>(MO.getGlobal());
69  if (!F)
70  return true;
71  if (F->doesNotThrow())
72  return false;
73  // These functions never throw
74  if (F->getName() == CxaBeginCatchFn || F->getName() == PersonalityWrapperFn ||
75  F->getName() == ClangCallTerminateFn || F->getName() == StdTerminateFn)
76  return false;
77 
78  // TODO Can we exclude call instructions that are marked as 'nounwind' in the
79  // original LLVm IR? (Even when the callee may throw)
80  return true;
81 }
bool isCall(QueryType Type=AnyInBundle) const
Definition: MachineInstr.h:656
This class represents lattice values for constants.
Definition: AllocatorList.h:23
amdgpu Simplify well known AMD library false FunctionCallee Value const Twine & Name
bool mayThrow(const MachineInstr &MI)
unsigned Reg
F(f)
unsigned getNumOperands() const
Retuns the total number of operands.
Definition: MachineInstr.h:413
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
Definition: MachineInstr.h:410
const char *const CxaBeginCatchFn
const char * getSymbolName() const
unsigned getCalleeOpNo(unsigned Opc)
Returns the operand number of a callee, assuming the argument is a call instruction.
const char *const StdTerminateFn
This file contains the declaration of the WebAssembly-specific utility functions. ...
const GlobalValue * getGlobal() const
const char *const CxaRethrowFn
bool isGlobal() const
isGlobal - Tests if this is a MO_GlobalAddress operand.
const char *const ClangCallTerminateFn
MachineOperand class - Representation of each machine instruction operand.
const char *const PersonalityWrapperFn
Representation of each machine instruction.
Definition: MachineInstr.h:63
This class is derived from MachineFunctionInfo and contains private WebAssembly-specific information ...
bool isCallIndirect(unsigned Opc)
This file declares WebAssembly-specific per-machine-function information.
LLVM_NODISCARD std::enable_if<!is_simple_type< Y >::value, typename cast_retty< X, const Y >::ret_type >::type dyn_cast(const Y &Val)
Definition: Casting.h:332
bool isSymbol() const
isSymbol - Tests if this is a MO_ExternalSymbol operand.
bool isReg() const
isReg - Tests if this is a MO_Register operand.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static bool isVirtualRegister(unsigned Reg)
Return true if the specified register number is in the virtual register namespace.
Definition: Register.h:69
IRTranslator LLVM IR MI
Register getReg() const
getReg - Returns the register number.
bool isChild(const MachineInstr &MI, const WebAssemblyFunctionInfo &MFI)
Test whether MI is a child of some other node in an expression tree.
const MachineOperand & getOperand(unsigned i) const
Definition: MachineInstr.h:415
Wrapper class representing virtual and physical registers.
Definition: Register.h:19
bool isImplicit() const