1 //===--- Action.h - Abstract compilation steps ------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #ifndef LLVM_CLANG_DRIVER_ACTION_H
11 #define LLVM_CLANG_DRIVER_ACTION_H
12 
13 #include "clang/Driver/Types.h"
14 #include "clang/Driver/Util.h"
15 #include "llvm/ADT/SmallVector.h"
16 
17 namespace llvm {
18 namespace opt {
19   class Arg;
20 }
21 }
22 
23 namespace clang {
24 namespace driver {
25 
26 /// Action - Represent an abstract compilation step to perform.
27 ///
28 /// An action represents an edge in the compilation graph; typically
29 /// it is a job to transform an input using some tool.
30 ///
31 /// The current driver is hard wired to expect actions which produce a
32 /// single primary output, at least in terms of controlling the
33 /// compilation. Actions can produce auxiliary files, but can only
34 /// produce a single output to feed into subsequent actions.
35 class Action {
36 public:
37   typedef ActionList::size_type size_type;
38   typedef ActionList::iterator iterator;
39   typedef ActionList::const_iterator const_iterator;
40 
41   enum ActionClass {
42     InputClass = 0,
43     BindArchClass,
44     PreprocessJobClass,
45     PrecompileJobClass,
46     AnalyzeJobClass,
47     MigrateJobClass,
48     CompileJobClass,
49     BackendJobClass,
50     AssembleJobClass,
51     LinkJobClass,
52     LipoJobClass,
53     DsymutilJobClass,
54     VerifyDebugInfoJobClass,
55     VerifyPCHJobClass,
56 
57     JobClassFirst=PreprocessJobClass,
58     JobClassLast=VerifyPCHJobClass
59   };
60 
61   static const char *getClassName(ActionClass AC);
62 
63 private:
64   ActionClass Kind;
65 
66   /// The output type of this action.
67   types::ID Type;
68 
69   ActionList Inputs;
70 
71   unsigned OwnsInputs : 1;
72 
73 protected:
Action(ActionClass _Kind,types::ID _Type)74   Action(ActionClass _Kind, types::ID _Type)
75     : Kind(_Kind), Type(_Type), OwnsInputs(true)  {}
Action(ActionClass _Kind,std::unique_ptr<Action> Input,types::ID _Type)76   Action(ActionClass _Kind, std::unique_ptr<Action> Input, types::ID _Type)
77       : Kind(_Kind), Type(_Type), Inputs(1, Input.release()), OwnsInputs(true) {
78   }
Action(ActionClass _Kind,std::unique_ptr<Action> Input)79   Action(ActionClass _Kind, std::unique_ptr<Action> Input)
80       : Kind(_Kind), Type(Input->getType()), Inputs(1, Input.release()),
81         OwnsInputs(true) {}
Action(ActionClass _Kind,const ActionList & _Inputs,types::ID _Type)82   Action(ActionClass _Kind, const ActionList &_Inputs, types::ID _Type)
83     : Kind(_Kind), Type(_Type), Inputs(_Inputs), OwnsInputs(true) {}
84 public:
85   virtual ~Action();
86 
getClassName()87   const char *getClassName() const { return Action::getClassName(getKind()); }
88 
getOwnsInputs()89   bool getOwnsInputs() { return OwnsInputs; }
setOwnsInputs(bool Value)90   void setOwnsInputs(bool Value) { OwnsInputs = Value; }
91 
getKind()92   ActionClass getKind() const { return Kind; }
getType()93   types::ID getType() const { return Type; }
94 
getInputs()95   ActionList &getInputs() { return Inputs; }
getInputs()96   const ActionList &getInputs() const { return Inputs; }
97 
size()98   size_type size() const { return Inputs.size(); }
99 
begin()100   iterator begin() { return Inputs.begin(); }
end()101   iterator end() { return Inputs.end(); }
begin()102   const_iterator begin() const { return Inputs.begin(); }
end()103   const_iterator end() const { return Inputs.end(); }
104 };
105 
106 class InputAction : public Action {
107   virtual void anchor();
108   const llvm::opt::Arg &Input;
109 
110 public:
111   InputAction(const llvm::opt::Arg &_Input, types::ID _Type);
112 
getInputArg()113   const llvm::opt::Arg &getInputArg() const { return Input; }
114 
classof(const Action * A)115   static bool classof(const Action *A) {
116     return A->getKind() == InputClass;
117   }
118 };
119 
120 class BindArchAction : public Action {
121   virtual void anchor();
122   /// The architecture to bind, or 0 if the default architecture
123   /// should be bound.
124   const char *ArchName;
125 
126 public:
127   BindArchAction(std::unique_ptr<Action> Input, const char *_ArchName);
128 
getArchName()129   const char *getArchName() const { return ArchName; }
130 
classof(const Action * A)131   static bool classof(const Action *A) {
132     return A->getKind() == BindArchClass;
133   }
134 };
135 
136 class JobAction : public Action {
137   virtual void anchor();
138 protected:
139   JobAction(ActionClass Kind, std::unique_ptr<Action> Input, types::ID Type);
140   JobAction(ActionClass Kind, const ActionList &Inputs, types::ID Type);
141 
142 public:
classof(const Action * A)143   static bool classof(const Action *A) {
144     return (A->getKind() >= JobClassFirst &&
145             A->getKind() <= JobClassLast);
146   }
147 };
148 
149 class PreprocessJobAction : public JobAction {
150   void anchor() override;
151 public:
152   PreprocessJobAction(std::unique_ptr<Action> Input, types::ID OutputType);
153 
classof(const Action * A)154   static bool classof(const Action *A) {
155     return A->getKind() == PreprocessJobClass;
156   }
157 };
158 
159 class PrecompileJobAction : public JobAction {
160   void anchor() override;
161 public:
162   PrecompileJobAction(std::unique_ptr<Action> Input, types::ID OutputType);
163 
classof(const Action * A)164   static bool classof(const Action *A) {
165     return A->getKind() == PrecompileJobClass;
166   }
167 };
168 
169 class AnalyzeJobAction : public JobAction {
170   void anchor() override;
171 public:
172   AnalyzeJobAction(std::unique_ptr<Action> Input, types::ID OutputType);
173 
classof(const Action * A)174   static bool classof(const Action *A) {
175     return A->getKind() == AnalyzeJobClass;
176   }
177 };
178 
179 class MigrateJobAction : public JobAction {
180   void anchor() override;
181 public:
182   MigrateJobAction(std::unique_ptr<Action> Input, types::ID OutputType);
183 
classof(const Action * A)184   static bool classof(const Action *A) {
185     return A->getKind() == MigrateJobClass;
186   }
187 };
188 
189 class CompileJobAction : public JobAction {
190   void anchor() override;
191 public:
192   CompileJobAction(std::unique_ptr<Action> Input, types::ID OutputType);
193 
classof(const Action * A)194   static bool classof(const Action *A) {
195     return A->getKind() == CompileJobClass;
196   }
197 };
198 
199 class BackendJobAction : public JobAction {
200   void anchor() override;
201 public:
202   BackendJobAction(std::unique_ptr<Action> Input, types::ID OutputType);
203 
classof(const Action * A)204   static bool classof(const Action *A) {
205     return A->getKind() == BackendJobClass;
206   }
207 };
208 
209 class AssembleJobAction : public JobAction {
210   void anchor() override;
211 public:
212   AssembleJobAction(std::unique_ptr<Action> Input, types::ID OutputType);
213 
classof(const Action * A)214   static bool classof(const Action *A) {
215     return A->getKind() == AssembleJobClass;
216   }
217 };
218 
219 class LinkJobAction : public JobAction {
220   void anchor() override;
221 public:
222   LinkJobAction(ActionList &Inputs, types::ID Type);
223 
classof(const Action * A)224   static bool classof(const Action *A) {
225     return A->getKind() == LinkJobClass;
226   }
227 };
228 
229 class LipoJobAction : public JobAction {
230   void anchor() override;
231 public:
232   LipoJobAction(ActionList &Inputs, types::ID Type);
233 
classof(const Action * A)234   static bool classof(const Action *A) {
235     return A->getKind() == LipoJobClass;
236   }
237 };
238 
239 class DsymutilJobAction : public JobAction {
240   void anchor() override;
241 public:
242   DsymutilJobAction(ActionList &Inputs, types::ID Type);
243 
classof(const Action * A)244   static bool classof(const Action *A) {
245     return A->getKind() == DsymutilJobClass;
246   }
247 };
248 
249 class VerifyJobAction : public JobAction {
250   void anchor() override;
251 public:
252   VerifyJobAction(ActionClass Kind, std::unique_ptr<Action> Input,
253                   types::ID Type);
254   VerifyJobAction(ActionClass Kind, ActionList &Inputs, types::ID Type);
classof(const Action * A)255   static bool classof(const Action *A) {
256     return A->getKind() == VerifyDebugInfoJobClass ||
257            A->getKind() == VerifyPCHJobClass;
258   }
259 };
260 
261 class VerifyDebugInfoJobAction : public VerifyJobAction {
262   void anchor() override;
263 public:
264   VerifyDebugInfoJobAction(std::unique_ptr<Action> Input, types::ID Type);
classof(const Action * A)265   static bool classof(const Action *A) {
266     return A->getKind() == VerifyDebugInfoJobClass;
267   }
268 };
269 
270 class VerifyPCHJobAction : public VerifyJobAction {
271   void anchor() override;
272 public:
273   VerifyPCHJobAction(std::unique_ptr<Action> Input, types::ID Type);
classof(const Action * A)274   static bool classof(const Action *A) {
275     return A->getKind() == VerifyPCHJobClass;
276   }
277 };
278 
279 } // end namespace driver
280 } // end namespace clang
281 
282 #endif
283