119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//===-- AlphaAsmPrinter.cpp - Alpha LLVM assembly writer ------------------===//
219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//
319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//                     The LLVM Compiler Infrastructure
419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//
519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman// This file is distributed under the University of Illinois Open Source
619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman// License. See LICENSE.TXT for details.
719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//
819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//===----------------------------------------------------------------------===//
919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//
1019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman// This file contains a printer that converts from our internal representation
1119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman// of machine-dependent LLVM code to GAS-format Alpha assembly language.
1219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//
1319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman//===----------------------------------------------------------------------===//
1419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
1519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#define DEBUG_TYPE "asm-printer"
1619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "Alpha.h"
1719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "AlphaInstrInfo.h"
1819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "AlphaTargetMachine.h"
1919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Module.h"
2019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Type.h"
2119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Assembly/Writer.h"
2219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/CodeGen/AsmPrinter.h"
2319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/MC/MCStreamer.h"
2419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/MC/MCAsmInfo.h"
2519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/MC/MCSymbol.h"
2619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Target/Mangler.h"
2719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Target/TargetLoweringObjectFile.h"
2819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Target/TargetMachine.h"
2919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/ADT/SmallString.h"
3019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Support/TargetRegistry.h"
3119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "llvm/Support/raw_ostream.h"
3219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanusing namespace llvm;
3319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
3419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumannamespace {
3519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  struct AlphaAsmPrinter : public AsmPrinter {
3619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    /// Unique incrementer for label values for referencing Global values.
3719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    ///
3819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
3919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    explicit AlphaAsmPrinter(TargetMachine &tm, MCStreamer &Streamer)
4019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      : AsmPrinter(tm, Streamer) {}
4119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
4219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    virtual const char *getPassName() const {
4319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      return "Alpha Assembly Printer";
4419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    }
4519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    void printInstruction(const MachineInstr *MI, raw_ostream &O);
4619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    void EmitInstruction(const MachineInstr *MI) {
4719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      SmallString<128> Str;
4819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      raw_svector_ostream OS(Str);
4919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      printInstruction(MI, OS);
5019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      OutStreamer.EmitRawText(OS.str());
5119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    }
5219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    static const char *getRegisterName(unsigned RegNo);
5319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
5419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    void printOp(const MachineOperand &MO, raw_ostream &O);
5519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    void printOperand(const MachineInstr *MI, int opNum, raw_ostream &O);
5619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    virtual void EmitFunctionBodyStart();
5719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    virtual void EmitFunctionBodyEnd();
5819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    void EmitStartOfAsmFile(Module &M);
5919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
6019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    bool PrintAsmOperand(const MachineInstr *MI, unsigned OpNo,
6119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                         unsigned AsmVariant, const char *ExtraCode,
6219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                         raw_ostream &O);
6319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    bool PrintAsmMemoryOperand(const MachineInstr *MI,
6419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                               unsigned OpNo, unsigned AsmVariant,
6519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                               const char *ExtraCode, raw_ostream &O);
6619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  };
6719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman} // end of anonymous namespace
6819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
6919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman#include "AlphaGenAsmWriter.inc"
7019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
7119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanvoid AlphaAsmPrinter::printOperand(const MachineInstr *MI, int opNum,
7219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                                   raw_ostream &O) {
7319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  const MachineOperand &MO = MI->getOperand(opNum);
7419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  if (MO.isReg()) {
7519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    assert(TargetRegisterInfo::isPhysicalRegister(MO.getReg()) &&
7619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman           "Not physreg??");
7719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << getRegisterName(MO.getReg());
7819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  } else if (MO.isImm()) {
7919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << MO.getImm();
8019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    assert(MO.getImm() < (1 << 30));
8119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  } else {
8219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    printOp(MO, O);
8319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  }
8419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
8519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
8619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
8719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanvoid AlphaAsmPrinter::printOp(const MachineOperand &MO, raw_ostream &O) {
8819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  switch (MO.getType()) {
8919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  case MachineOperand::MO_Register:
9019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << getRegisterName(MO.getReg());
9119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
9219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
9319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  case MachineOperand::MO_Immediate:
9419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    assert(0 && "printOp() does not handle immediate values");
9519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
9619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
9719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  case MachineOperand::MO_MachineBasicBlock:
9819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << *MO.getMBB()->getSymbol();
9919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
10019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
10119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  case MachineOperand::MO_ConstantPoolIndex:
10219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << MAI->getPrivateGlobalPrefix() << "CPI" << getFunctionNumber() << "_"
10319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      << MO.getIndex();
10419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
10519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
10619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  case MachineOperand::MO_ExternalSymbol:
10719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << MO.getSymbolName();
10819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
10919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
11019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  case MachineOperand::MO_GlobalAddress:
11119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << *Mang->getSymbol(MO.getGlobal());
11219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
11319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
11419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  case MachineOperand::MO_JumpTableIndex:
11519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << MAI->getPrivateGlobalPrefix() << "JTI" << getFunctionNumber()
11619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman      << '_' << MO.getIndex();
11719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
11819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
11919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  default:
12019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    O << "<unknown operand type: " << MO.getType() << ">";
12119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return;
12219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  }
12319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
12419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
12519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman/// EmitFunctionBodyStart - Targets can override this to emit stuff before
12619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman/// the first basic block in the function.
12719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanvoid AlphaAsmPrinter::EmitFunctionBodyStart() {
12819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  OutStreamer.EmitRawText("\t.ent " + Twine(CurrentFnSym->getName()));
12919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
13019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
13119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman/// EmitFunctionBodyEnd - Targets can override this to emit stuff after
13219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman/// the last basic block in the function.
13319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanvoid AlphaAsmPrinter::EmitFunctionBodyEnd() {
13419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  OutStreamer.EmitRawText("\t.end " + Twine(CurrentFnSym->getName()));
13519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
13619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
13719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanvoid AlphaAsmPrinter::EmitStartOfAsmFile(Module &M) {
13819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  OutStreamer.EmitRawText(StringRef("\t.arch ev6"));
13919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  OutStreamer.EmitRawText(StringRef("\t.set noat"));
14019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
14119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
14219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman/// PrintAsmOperand - Print out an operand for an inline asm expression.
14319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman///
14419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanbool AlphaAsmPrinter::PrintAsmOperand(const MachineInstr *MI, unsigned OpNo,
14519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                                      unsigned AsmVariant,
14619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                                      const char *ExtraCode, raw_ostream &O) {
14719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  printOperand(MI, OpNo, O);
14819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  return false;
14919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
15019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
15119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanbool AlphaAsmPrinter::PrintAsmMemoryOperand(const MachineInstr *MI,
15219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                                            unsigned OpNo, unsigned AsmVariant,
15319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                                            const char *ExtraCode,
15419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman                                            raw_ostream &O) {
15519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  if (ExtraCode && ExtraCode[0])
15619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman    return true; // Unknown modifier.
15719bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  O << "0(";
15819bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  printOperand(MI, OpNo, O);
15919bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  O << ")";
16019bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  return false;
16119bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
16219bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman
16319bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman// Force static initialization.
16419bac1e08be200c31efd26f0f5fd144c9b3eefd3John Baumanextern "C" void LLVMInitializeAlphaAsmPrinter() {
16519bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman  RegisterAsmPrinter<AlphaAsmPrinter> X(TheAlphaTarget);
16619bac1e08be200c31efd26f0f5fd144c9b3eefd3John Bauman}
167