1336815Sdim//===--- RISCV.h - Declare RISCV target feature support ---------*- C++ -*-===//
2336815Sdim//
3353358Sdim// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4353358Sdim// See https://llvm.org/LICENSE.txt for license information.
5353358Sdim// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6336815Sdim//
7336815Sdim//===----------------------------------------------------------------------===//
8336815Sdim//
9336815Sdim// This file declares RISCV TargetInfo objects.
10336815Sdim//
11336815Sdim//===----------------------------------------------------------------------===//
12336815Sdim
13336815Sdim#ifndef LLVM_CLANG_LIB_BASIC_TARGETS_RISCV_H
14336815Sdim#define LLVM_CLANG_LIB_BASIC_TARGETS_RISCV_H
15336815Sdim
16336815Sdim#include "clang/Basic/TargetInfo.h"
17336815Sdim#include "clang/Basic/TargetOptions.h"
18336815Sdim#include "llvm/ADT/Triple.h"
19336815Sdim#include "llvm/Support/Compiler.h"
20336815Sdim
21336815Sdimnamespace clang {
22336815Sdimnamespace targets {
23336815Sdim
24336815Sdim// RISC-V Target
25336815Sdimclass RISCVTargetInfo : public TargetInfo {
26336815Sdimprotected:
27336815Sdim  std::string ABI;
28336815Sdim  bool HasM;
29336815Sdim  bool HasA;
30336815Sdim  bool HasF;
31336815Sdim  bool HasD;
32336815Sdim  bool HasC;
33336815Sdim
34336815Sdimpublic:
35336815Sdim  RISCVTargetInfo(const llvm::Triple &Triple, const TargetOptions &)
36336815Sdim      : TargetInfo(Triple), HasM(false), HasA(false), HasF(false),
37336815Sdim        HasD(false), HasC(false) {
38336815Sdim    LongDoubleWidth = 128;
39336815Sdim    LongDoubleAlign = 128;
40336815Sdim    LongDoubleFormat = &llvm::APFloat::IEEEquad();
41336815Sdim    SuitableAlign = 128;
42336815Sdim    WCharType = SignedInt;
43336815Sdim    WIntType = UnsignedInt;
44336815Sdim  }
45336815Sdim
46336815Sdim  StringRef getABI() const override { return ABI; }
47336815Sdim  void getTargetDefines(const LangOptions &Opts,
48336815Sdim                        MacroBuilder &Builder) const override;
49336815Sdim
50336815Sdim  ArrayRef<Builtin::Info> getTargetBuiltins() const override { return None; }
51336815Sdim
52336815Sdim  BuiltinVaListKind getBuiltinVaListKind() const override {
53336815Sdim    return TargetInfo::VoidPtrBuiltinVaList;
54336815Sdim  }
55336815Sdim
56336815Sdim  const char *getClobbers() const override { return ""; }
57336815Sdim
58336815Sdim  ArrayRef<const char *> getGCCRegNames() const override;
59336815Sdim
60353358Sdim  int getEHDataRegisterNumber(unsigned RegNo) const override {
61353358Sdim    if (RegNo == 0)
62353358Sdim      return 10;
63353358Sdim    else if (RegNo == 1)
64353358Sdim      return 11;
65353358Sdim    else
66353358Sdim      return -1;
67353358Sdim  }
68353358Sdim
69336815Sdim  ArrayRef<TargetInfo::GCCRegAlias> getGCCRegAliases() const override;
70336815Sdim
71336815Sdim  bool validateAsmConstraint(const char *&Name,
72353358Sdim                             TargetInfo::ConstraintInfo &Info) const override;
73336815Sdim
74336815Sdim  bool hasFeature(StringRef Feature) const override;
75336815Sdim
76336815Sdim  bool handleTargetFeatures(std::vector<std::string> &Features,
77336815Sdim                            DiagnosticsEngine &Diags) override;
78336815Sdim};
79336815Sdimclass LLVM_LIBRARY_VISIBILITY RISCV32TargetInfo : public RISCVTargetInfo {
80336815Sdimpublic:
81336815Sdim  RISCV32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
82336815Sdim      : RISCVTargetInfo(Triple, Opts) {
83336815Sdim    IntPtrType = SignedInt;
84336815Sdim    PtrDiffType = SignedInt;
85336815Sdim    SizeType = UnsignedInt;
86336815Sdim    resetDataLayout("e-m:e-p:32:32-i64:64-n32-S128");
87336815Sdim  }
88336815Sdim
89336815Sdim  bool setABI(const std::string &Name) override {
90353358Sdim    if (Name == "ilp32" || Name == "ilp32f" || Name == "ilp32d") {
91336815Sdim      ABI = Name;
92336815Sdim      return true;
93336815Sdim    }
94336815Sdim    return false;
95336815Sdim  }
96353358Sdim
97353358Sdim  void setMaxAtomicWidth() override {
98353358Sdim    MaxAtomicPromoteWidth = 128;
99353358Sdim
100353358Sdim    if (HasA)
101353358Sdim      MaxAtomicInlineWidth = 32;
102353358Sdim  }
103336815Sdim};
104336815Sdimclass LLVM_LIBRARY_VISIBILITY RISCV64TargetInfo : public RISCVTargetInfo {
105336815Sdimpublic:
106336815Sdim  RISCV64TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts)
107336815Sdim      : RISCVTargetInfo(Triple, Opts) {
108336815Sdim    LongWidth = LongAlign = PointerWidth = PointerAlign = 64;
109336815Sdim    IntMaxType = Int64Type = SignedLong;
110336815Sdim    resetDataLayout("e-m:e-p:64:64-i64:64-i128:128-n64-S128");
111336815Sdim  }
112336815Sdim
113336815Sdim  bool setABI(const std::string &Name) override {
114353358Sdim    if (Name == "lp64" || Name == "lp64f" || Name == "lp64d") {
115336815Sdim      ABI = Name;
116336815Sdim      return true;
117336815Sdim    }
118336815Sdim    return false;
119336815Sdim  }
120353358Sdim
121353358Sdim  void setMaxAtomicWidth() override {
122353358Sdim    MaxAtomicPromoteWidth = 128;
123353358Sdim
124353358Sdim    if (HasA)
125353358Sdim      MaxAtomicInlineWidth = 64;
126353358Sdim  }
127336815Sdim};
128336815Sdim} // namespace targets
129336815Sdim} // namespace clang
130336815Sdim
131336815Sdim#endif // LLVM_CLANG_LIB_BASIC_TARGETS_RISCV_H
132