blob: e3dbdef8e8d0c9ca01bab0e384103252b97689dd [file] [log] [blame]
Zonr Changc383a502010-10-12 01:52:08 +08001/*
2 * Copyright 2010, The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
Stephen Hinese639eb52010-11-08 19:27:20 -080017#ifndef _FRAMEWORKS_COMPILE_SLANG_SLANG_BACKEND_H_ // NOLINT
18#define _FRAMEWORKS_COMPILE_SLANG_SLANG_BACKEND_H_
19
20#include "clang/AST/ASTConsumer.h"
Shih-wei Liao462aefd2010-06-04 15:32:04 -070021
Stephen Hinesc7069072015-03-18 14:53:14 -070022#include "llvm/IR/LegacyPassManager.h"
Shih-wei Liao462aefd2010-06-04 15:32:04 -070023
Pirama Arumuga Nainar2444eaa2015-05-06 11:17:16 -070024#include "llvm/Support/raw_ostream.h"
Shih-wei Liao462aefd2010-06-04 15:32:04 -070025
Zonr Chang3a9ca1f2010-10-06 17:52:56 +080026#include "slang.h"
zonr6315f762010-10-05 15:35:14 +080027#include "slang_pragma_recorder.h"
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -070028#include "slang_rs_check_ast.h"
29#include "slang_rs_object_ref_count.h"
Stephen Hines4cc499d2011-08-24 19:06:17 -070030#include "slang_version.h"
zonr6315f762010-10-05 15:35:14 +080031
Shih-wei Liao462aefd2010-06-04 15:32:04 -070032namespace llvm {
Pirama Arumuga Nainar2444eaa2015-05-06 11:17:16 -070033 class buffer_ostream;
zonr6315f762010-10-05 15:35:14 +080034 class LLVMContext;
35 class NamedMDNode;
zonr6315f762010-10-05 15:35:14 +080036 class Module;
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070037}
Shih-wei Liao462aefd2010-06-04 15:32:04 -070038
39namespace clang {
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -070040 class ASTConsumer;
41 class ASTContext;
Zonr Chang3a9ca1f2010-10-06 17:52:56 +080042 class CodeGenOptions;
zonr6315f762010-10-05 15:35:14 +080043 class CodeGenerator;
zonr6315f762010-10-05 15:35:14 +080044 class DeclGroupRef;
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -070045 class DiagnosticsEngine;
46 class FunctionDecl;
zonr6315f762010-10-05 15:35:14 +080047 class TagDecl;
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -070048 class TargetOptions;
zonr6315f762010-10-05 15:35:14 +080049 class VarDecl;
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070050}
Shih-wei Liao462aefd2010-06-04 15:32:04 -070051
52namespace slang {
53
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -070054class RSContext;
55
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070056class Backend : public clang::ASTConsumer {
57 private:
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070058 const clang::TargetOptions &mTargetOpts;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070059
Zonr Chang68fc02c2010-10-13 19:09:19 +080060 llvm::Module *mpModule;
61
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070062 // Output stream
63 llvm::raw_ostream *mpOS;
Zonr Chang3a9ca1f2010-10-06 17:52:56 +080064 Slang::OutputType mOT;
Kirk Stewart6b226742010-06-11 10:51:12 -070065
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070066 // This helps us translate Clang AST using into LLVM IR
67 clang::CodeGenerator *mGen;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070068
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070069 // Passes
Shih-wei Liao462aefd2010-06-04 15:32:04 -070070
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070071 // Passes apply on function scope in a translation unit
Stephen Hinesc7069072015-03-18 14:53:14 -070072 llvm::legacy::FunctionPassManager *mPerFunctionPasses;
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070073 // Passes apply on module scope
Stephen Hinesc7069072015-03-18 14:53:14 -070074 llvm::legacy::PassManager *mPerModulePasses;
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070075 // Passes for code emission
Stephen Hinesc7069072015-03-18 14:53:14 -070076 llvm::legacy::FunctionPassManager *mCodeGenPasses;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070077
Pirama Arumuga Nainar2444eaa2015-05-06 11:17:16 -070078 llvm::buffer_ostream mBufferOutStream;
Shih-wei Liao462aefd2010-06-04 15:32:04 -070079
Zonr Chang3a9ca1f2010-10-06 17:52:56 +080080 void CreateFunctionPasses();
81 void CreateModulePasses();
Shih-wei Liao9ef2f782010-10-01 12:31:37 -070082 bool CreateCodeGenPasses();
Shih-wei Liao462aefd2010-06-04 15:32:04 -070083
Stephen Hines5e6d0d52011-11-22 19:42:41 -080084 void WrapBitcode(llvm::raw_string_ostream &Bitcode);
85
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -070086 RSContext *mContext;
87
88 clang::SourceManager &mSourceMgr;
89
90 bool mAllowRSPrefix;
91
92 bool mIsFilterscript;
93
94 llvm::NamedMDNode *mExportVarMetadata;
95 llvm::NamedMDNode *mExportFuncMetadata;
96 llvm::NamedMDNode *mExportForEachNameMetadata;
97 llvm::NamedMDNode *mExportForEachSignatureMetadata;
98 llvm::NamedMDNode *mExportTypeMetadata;
99 llvm::NamedMDNode *mRSObjectSlotsMetadata;
100
101 RSObjectRefCount mRefCount;
102
103 RSCheckAST mASTChecker;
104
105 void AnnotateFunction(clang::FunctionDecl *FD);
106
107 void dumpExportVarInfo(llvm::Module *M);
108 void dumpExportFunctionInfo(llvm::Module *M);
109 void dumpExportForEachInfo(llvm::Module *M);
110 void dumpExportTypeInfo(llvm::Module *M);
111
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700112 protected:
113 llvm::LLVMContext &mLLVMContext;
Logan Chien9207a2e2011-10-21 15:39:28 +0800114 clang::DiagnosticsEngine &mDiagEngine;
mkopec1c460b372012-01-09 11:21:50 -0500115 const clang::CodeGenOptions &mCodeGenOpts;
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700116
Stephen Hines3fd0a942011-01-18 12:27:39 -0800117 PragmaList *mPragmas;
Shih-wei Liaocecd11d2010-09-21 08:07:58 -0700118
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700119 unsigned int getTargetAPI() const { return mContext->getTargetAPI(); }
120
121 // TODO These are no longer virtual from base. Look into merging into caller.
Stephen Hines4cc499d2011-08-24 19:06:17 -0700122
Zonr Chang8785d052010-10-13 22:42:43 +0800123 // This handler will be invoked before Clang translates @Ctx to LLVM IR. This
Zonr Chang68fc02c2010-10-13 19:09:19 +0800124 // give you an opportunity to modified the IR in AST level (scope information,
125 // unoptimized IR, etc.). After the return from this method, slang will start
126 // translate @Ctx into LLVM IR. One should not operate on @Ctx afterwards
127 // since the changes applied on that never reflects to the LLVM module used
128 // in the final codegen.
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700129 void HandleTranslationUnitPre(clang::ASTContext &Ctx);
Zonr Chang68fc02c2010-10-13 19:09:19 +0800130
131 // This handler will be invoked when Clang have converted AST tree to LLVM IR.
132 // The @M contains the resulting LLVM IR tree. After the return from this
133 // method, slang will start doing optimization and code generation for @M.
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700134 void HandleTranslationUnitPost(llvm::Module *M);
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700135
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700136 public:
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700137 Backend(RSContext *Context,
138 clang::DiagnosticsEngine *DiagEngine,
139 const clang::CodeGenOptions &CodeGenOpts,
140 const clang::TargetOptions &TargetOpts,
141 PragmaList *Pragmas,
142 llvm::raw_ostream *OS,
143 Slang::OutputType OT,
144 clang::SourceManager &SourceMgr,
145 bool AllowRSPrefix,
146 bool IsFilterscript);
147
148 virtual ~Backend();
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700149
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700150 // Initialize - This is called to initialize the consumer, providing the
151 // ASTContext.
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700152 void Initialize(clang::ASTContext &Ctx) override;
153
154 // TODO Clean up what should be private, protected
155 // TODO Also clean up the include files
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700156
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700157 // HandleTopLevelDecl - Handle the specified top-level declaration. This is
158 // called by the parser to process every top-level Decl*. Note that D can be
159 // the head of a chain of Decls (e.g. for `int a, b` the chain will have two
160 // elements). Use Decl::getNextDeclarator() to walk the chain.
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700161 bool HandleTopLevelDecl(clang::DeclGroupRef D) override;
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700162
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700163 // HandleTranslationUnit - This method is called when the ASTs for entire
164 // translation unit have been parsed.
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700165 void HandleTranslationUnit(clang::ASTContext &Ctx) override;
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700166
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700167 // HandleTagDeclDefinition - This callback is invoked each time a TagDecl
168 // (e.g. struct, union, enum, class) is completed. This allows the client to
169 // hack on the type, which can occur at any point in the file (because these
170 // can be defined in declspecs).
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700171 void HandleTagDeclDefinition(clang::TagDecl *D) override;
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700172
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700173 // CompleteTentativeDefinition - Callback invoked at the end of a translation
174 // unit to notify the consumer that the given tentative definition should be
175 // completed.
Jean-Luc Brouilletc10bc752015-05-04 23:02:25 -0700176 void CompleteTentativeDefinition(clang::VarDecl *D) override;
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700177};
178
Shih-wei Liao9ef2f782010-10-01 12:31:37 -0700179} // namespace slang
Shih-wei Liao462aefd2010-06-04 15:32:04 -0700180
Stephen Hinese639eb52010-11-08 19:27:20 -0800181#endif // _FRAMEWORKS_COMPILE_SLANG_SLANG_BACKEND_H_ NOLINT