1 //===-- SparcMCInstLower.cpp - Convert Sparc MachineInstr to MCInst -------===//
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 // This file contains code to lower Sparc MachineInstrs to their corresponding
10 // MCInst records.
11 //
12 //===----------------------------------------------------------------------===//
13 
14 #include "MCTargetDesc/SparcMCExpr.h"
15 #include "Sparc.h"
16 #include "llvm/CodeGen/AsmPrinter.h"
17 #include "llvm/CodeGen/MachineFunction.h"
18 #include "llvm/CodeGen/MachineInstr.h"
19 #include "llvm/CodeGen/MachineOperand.h"
20 #include "llvm/IR/Mangler.h"
21 #include "llvm/MC/MCAsmInfo.h"
22 #include "llvm/MC/MCContext.h"
23 #include "llvm/MC/MCExpr.h"
24 #include "llvm/MC/MCInst.h"
25 
26 using namespace llvm;
27 
28 
LowerSymbolOperand(const MachineInstr * MI,const MachineOperand & MO,AsmPrinter & AP)29 static MCOperand LowerSymbolOperand(const MachineInstr *MI,
30                                     const MachineOperand &MO,
31                                     AsmPrinter &AP) {
32 
33   SparcMCExpr::VariantKind Kind =
34     (SparcMCExpr::VariantKind)MO.getTargetFlags();
35   const MCSymbol *Symbol = nullptr;
36 
37   switch(MO.getType()) {
38   default: llvm_unreachable("Unknown type in LowerSymbolOperand");
39   case MachineOperand::MO_MachineBasicBlock:
40     Symbol = MO.getMBB()->getSymbol();
41     break;
42 
43   case MachineOperand::MO_GlobalAddress:
44     Symbol = AP.getSymbol(MO.getGlobal());
45     break;
46 
47   case MachineOperand::MO_BlockAddress:
48     Symbol = AP.GetBlockAddressSymbol(MO.getBlockAddress());
49     break;
50 
51   case MachineOperand::MO_ExternalSymbol:
52     Symbol = AP.GetExternalSymbolSymbol(MO.getSymbolName());
53     break;
54 
55   case MachineOperand::MO_ConstantPoolIndex:
56     Symbol = AP.GetCPISymbol(MO.getIndex());
57     break;
58   }
59 
60   const MCSymbolRefExpr *MCSym = MCSymbolRefExpr::create(Symbol,
61                                                          AP.OutContext);
62   const SparcMCExpr *expr = SparcMCExpr::create(Kind, MCSym,
63                                                 AP.OutContext);
64   return MCOperand::createExpr(expr);
65 }
66 
LowerOperand(const MachineInstr * MI,const MachineOperand & MO,AsmPrinter & AP)67 static MCOperand LowerOperand(const MachineInstr *MI,
68                               const MachineOperand &MO,
69                               AsmPrinter &AP) {
70   switch(MO.getType()) {
71   default: llvm_unreachable("unknown operand type"); break;
72   case MachineOperand::MO_Register:
73     if (MO.isImplicit())
74       break;
75     return MCOperand::createReg(MO.getReg());
76 
77   case MachineOperand::MO_Immediate:
78     return MCOperand::createImm(MO.getImm());
79 
80   case MachineOperand::MO_MachineBasicBlock:
81   case MachineOperand::MO_GlobalAddress:
82   case MachineOperand::MO_BlockAddress:
83   case MachineOperand::MO_ExternalSymbol:
84   case MachineOperand::MO_ConstantPoolIndex:
85     return LowerSymbolOperand(MI, MO, AP);
86 
87   case MachineOperand::MO_RegisterMask:   break;
88 
89   }
90   return MCOperand();
91 }
92 
LowerSparcMachineInstrToMCInst(const MachineInstr * MI,MCInst & OutMI,AsmPrinter & AP)93 void llvm::LowerSparcMachineInstrToMCInst(const MachineInstr *MI,
94                                           MCInst &OutMI,
95                                           AsmPrinter &AP)
96 {
97 
98   OutMI.setOpcode(MI->getOpcode());
99 
100   for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
101     const MachineOperand &MO = MI->getOperand(i);
102     MCOperand MCOp = LowerOperand(MI, MO, AP);
103 
104     if (MCOp.isValid())
105       OutMI.addOperand(MCOp);
106   }
107 }
108