OSDN Git Service

Initial support for the cfi directives. This is just enough to get
[android-x86/external-llvm.git] / include / llvm / Target / TargetRegistry.h
1 //===-- Target/TargetRegistry.h - Target Registration -----------*- 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 // This file exposes the TargetRegistry interface, which tools can use to access
11 // the appropriate target specific classes (TargetMachine, AsmPrinter, etc.)
12 // which have been registered.
13 //
14 // Target specific class implementations should register themselves using the
15 // appropriate TargetRegistry interfaces.
16 //
17 //===----------------------------------------------------------------------===//
18
19 #ifndef LLVM_TARGET_TARGETREGISTRY_H
20 #define LLVM_TARGET_TARGETREGISTRY_H
21
22 #include "llvm/ADT/Triple.h"
23 #include <string>
24 #include <cassert>
25
26 namespace llvm {
27   class AsmPrinter;
28   class Module;
29   class MCAssembler;
30   class MCAsmInfo;
31   class MCAsmParser;
32   class MCCodeEmitter;
33   class MCContext;
34   class MCDisassembler;
35   class MCInstPrinter;
36   class MCStreamer;
37   class TargetAsmBackend;
38   class TargetAsmLexer;
39   class TargetAsmParser;
40   class TargetMachine;
41   class raw_ostream;
42   class formatted_raw_ostream;
43
44   MCStreamer *createAsmStreamer(MCContext &Ctx, formatted_raw_ostream &OS,
45                                 bool isVerboseAsm,
46                                 bool useLoc,
47                                 MCInstPrinter *InstPrint,
48                                 MCCodeEmitter *CE,
49                                 bool ShowInst);
50
51   /// Target - Wrapper for Target specific information.
52   ///
53   /// For registration purposes, this is a POD type so that targets can be
54   /// registered without the use of static constructors.
55   ///
56   /// Targets should implement a single global instance of this class (which
57   /// will be zero initialized), and pass that instance to the TargetRegistry as
58   /// part of their initialization.
59   class Target {
60   public:
61     friend struct TargetRegistry;
62
63     typedef unsigned (*TripleMatchQualityFnTy)(const std::string &TT);
64
65     typedef MCAsmInfo *(*AsmInfoCtorFnTy)(const Target &T,
66                                                 StringRef TT);
67     typedef TargetMachine *(*TargetMachineCtorTy)(const Target &T,
68                                                   const std::string &TT,
69                                                   const std::string &Features);
70     typedef AsmPrinter *(*AsmPrinterCtorTy)(TargetMachine &TM,
71                                             MCStreamer &Streamer);
72     typedef TargetAsmBackend *(*AsmBackendCtorTy)(const Target &T,
73                                                   const std::string &TT);
74     typedef TargetAsmLexer *(*AsmLexerCtorTy)(const Target &T,
75                                               const MCAsmInfo &MAI);
76     typedef TargetAsmParser *(*AsmParserCtorTy)(const Target &T,MCAsmParser &P,
77                                                 TargetMachine &TM);
78     typedef MCDisassembler *(*MCDisassemblerCtorTy)(const Target &T);
79     typedef MCInstPrinter *(*MCInstPrinterCtorTy)(const Target &T,
80                                                   unsigned SyntaxVariant,
81                                                   const MCAsmInfo &MAI);
82     typedef MCCodeEmitter *(*CodeEmitterCtorTy)(const Target &T,
83                                                 TargetMachine &TM,
84                                                 MCContext &Ctx);
85     typedef MCStreamer *(*ObjectStreamerCtorTy)(const Target &T,
86                                                 const std::string &TT,
87                                                 MCContext &Ctx,
88                                                 TargetAsmBackend &TAB,
89                                                 raw_ostream &_OS,
90                                                 MCCodeEmitter *_Emitter,
91                                                 bool RelaxAll);
92     typedef MCStreamer *(*AsmStreamerCtorTy)(MCContext &Ctx,
93                                              formatted_raw_ostream &OS,
94                                              bool isVerboseAsm,
95                                              bool useLoc,
96                                              MCInstPrinter *InstPrint,
97                                              MCCodeEmitter *CE,
98                                              bool ShowInst);
99
100   private:
101     /// Next - The next registered target in the linked list, maintained by the
102     /// TargetRegistry.
103     Target *Next;
104
105     /// TripleMatchQualityFn - The target function for rating the match quality
106     /// of a triple.
107     TripleMatchQualityFnTy TripleMatchQualityFn;
108
109     /// Name - The target name.
110     const char *Name;
111
112     /// ShortDesc - A short description of the target.
113     const char *ShortDesc;
114
115     /// HasJIT - Whether this target supports the JIT.
116     bool HasJIT;
117
118     AsmInfoCtorFnTy AsmInfoCtorFn;
119
120     /// TargetMachineCtorFn - Construction function for this target's
121     /// TargetMachine, if registered.
122     TargetMachineCtorTy TargetMachineCtorFn;
123
124     /// AsmBackendCtorFn - Construction function for this target's
125     /// TargetAsmBackend, if registered.
126     AsmBackendCtorTy AsmBackendCtorFn;
127
128     /// AsmLexerCtorFn - Construction function for this target's TargetAsmLexer,
129     /// if registered.
130     AsmLexerCtorTy AsmLexerCtorFn;
131
132     /// AsmParserCtorFn - Construction function for this target's
133     /// TargetAsmParser, if registered.
134     AsmParserCtorTy AsmParserCtorFn;
135
136     /// AsmPrinterCtorFn - Construction function for this target's AsmPrinter,
137     /// if registered.
138     AsmPrinterCtorTy AsmPrinterCtorFn;
139
140     /// MCDisassemblerCtorFn - Construction function for this target's
141     /// MCDisassembler, if registered.
142     MCDisassemblerCtorTy MCDisassemblerCtorFn;
143
144     /// MCInstPrinterCtorFn - Construction function for this target's
145     /// MCInstPrinter, if registered.
146     MCInstPrinterCtorTy MCInstPrinterCtorFn;
147
148     /// CodeEmitterCtorFn - Construction function for this target's CodeEmitter,
149     /// if registered.
150     CodeEmitterCtorTy CodeEmitterCtorFn;
151
152     /// ObjectStreamerCtorFn - Construction function for this target's
153     /// ObjectStreamer, if registered.
154     ObjectStreamerCtorTy ObjectStreamerCtorFn;
155
156     /// AsmStreamerCtorFn - Construction function for this target's
157     /// AsmStreamer, if registered (default = llvm::createAsmStreamer).
158     AsmStreamerCtorTy AsmStreamerCtorFn;
159
160   public:
161     Target() : AsmStreamerCtorFn(llvm::createAsmStreamer) {}
162
163     /// @name Target Information
164     /// @{
165
166     // getNext - Return the next registered target.
167     const Target *getNext() const { return Next; }
168
169     /// getName - Get the target name.
170     const char *getName() const { return Name; }
171
172     /// getShortDescription - Get a short description of the target.
173     const char *getShortDescription() const { return ShortDesc; }
174
175     /// @}
176     /// @name Feature Predicates
177     /// @{
178
179     /// hasJIT - Check if this targets supports the just-in-time compilation.
180     bool hasJIT() const { return HasJIT; }
181
182     /// hasTargetMachine - Check if this target supports code generation.
183     bool hasTargetMachine() const { return TargetMachineCtorFn != 0; }
184
185     /// hasAsmBackend - Check if this target supports .o generation.
186     bool hasAsmBackend() const { return AsmBackendCtorFn != 0; }
187
188     /// hasAsmLexer - Check if this target supports .s lexing.
189     bool hasAsmLexer() const { return AsmLexerCtorFn != 0; }
190
191     /// hasAsmParser - Check if this target supports .s parsing.
192     bool hasAsmParser() const { return AsmParserCtorFn != 0; }
193
194     /// hasAsmPrinter - Check if this target supports .s printing.
195     bool hasAsmPrinter() const { return AsmPrinterCtorFn != 0; }
196
197     /// hasMCDisassembler - Check if this target has a disassembler.
198     bool hasMCDisassembler() const { return MCDisassemblerCtorFn != 0; }
199
200     /// hasMCInstPrinter - Check if this target has an instruction printer.
201     bool hasMCInstPrinter() const { return MCInstPrinterCtorFn != 0; }
202
203     /// hasCodeEmitter - Check if this target supports instruction encoding.
204     bool hasCodeEmitter() const { return CodeEmitterCtorFn != 0; }
205
206     /// hasObjectStreamer - Check if this target supports streaming to files.
207     bool hasObjectStreamer() const { return ObjectStreamerCtorFn != 0; }
208
209     /// hasAsmStreamer - Check if this target supports streaming to files.
210     bool hasAsmStreamer() const { return AsmStreamerCtorFn != 0; }
211
212     /// @}
213     /// @name Feature Constructors
214     /// @{
215
216     /// createAsmInfo - Create a MCAsmInfo implementation for the specified
217     /// target triple.
218     ///
219     /// \arg Triple - This argument is used to determine the target machine
220     /// feature set; it should always be provided. Generally this should be
221     /// either the target triple from the module, or the target triple of the
222     /// host if that does not exist.
223     MCAsmInfo *createAsmInfo(StringRef Triple) const {
224       if (!AsmInfoCtorFn)
225         return 0;
226       return AsmInfoCtorFn(*this, Triple);
227     }
228
229     /// createTargetMachine - Create a target specific machine implementation
230     /// for the specified \arg Triple.
231     ///
232     /// \arg Triple - This argument is used to determine the target machine
233     /// feature set; it should always be provided. Generally this should be
234     /// either the target triple from the module, or the target triple of the
235     /// host if that does not exist.
236     TargetMachine *createTargetMachine(const std::string &Triple,
237                                        const std::string &Features) const {
238       if (!TargetMachineCtorFn)
239         return 0;
240       return TargetMachineCtorFn(*this, Triple, Features);
241     }
242
243     /// createAsmBackend - Create a target specific assembly parser.
244     ///
245     /// \arg Triple - The target triple string.
246     /// \arg Backend - The target independent assembler object.
247     TargetAsmBackend *createAsmBackend(const std::string &Triple) const {
248       if (!AsmBackendCtorFn)
249         return 0;
250       return AsmBackendCtorFn(*this, Triple);
251     }
252
253     /// createAsmLexer - Create a target specific assembly lexer.
254     ///
255     TargetAsmLexer *createAsmLexer(const MCAsmInfo &MAI) const {
256       if (!AsmLexerCtorFn)
257         return 0;
258       return AsmLexerCtorFn(*this, MAI);
259     }
260
261     /// createAsmParser - Create a target specific assembly parser.
262     ///
263     /// \arg Parser - The target independent parser implementation to use for
264     /// parsing and lexing.
265     TargetAsmParser *createAsmParser(MCAsmParser &Parser,
266                                      TargetMachine &TM) const {
267       if (!AsmParserCtorFn)
268         return 0;
269       return AsmParserCtorFn(*this, Parser, TM);
270     }
271
272     /// createAsmPrinter - Create a target specific assembly printer pass.  This
273     /// takes ownership of the MCStreamer object.
274     AsmPrinter *createAsmPrinter(TargetMachine &TM, MCStreamer &Streamer) const{
275       if (!AsmPrinterCtorFn)
276         return 0;
277       return AsmPrinterCtorFn(TM, Streamer);
278     }
279
280     MCDisassembler *createMCDisassembler() const {
281       if (!MCDisassemblerCtorFn)
282         return 0;
283       return MCDisassemblerCtorFn(*this);
284     }
285
286     MCInstPrinter *createMCInstPrinter(unsigned SyntaxVariant,
287                                        const MCAsmInfo &MAI) const {
288       if (!MCInstPrinterCtorFn)
289         return 0;
290       return MCInstPrinterCtorFn(*this, SyntaxVariant, MAI);
291     }
292
293
294     /// createCodeEmitter - Create a target specific code emitter.
295     MCCodeEmitter *createCodeEmitter(TargetMachine &TM, MCContext &Ctx) const {
296       if (!CodeEmitterCtorFn)
297         return 0;
298       return CodeEmitterCtorFn(*this, TM, Ctx);
299     }
300
301     /// createObjectStreamer - Create a target specific MCStreamer.
302     ///
303     /// \arg TT - The target triple.
304     /// \arg Ctx - The target context.
305     /// \arg TAB - The target assembler backend object. Takes ownership.
306     /// \arg _OS - The stream object.
307     /// \arg _Emitter - The target independent assembler object.Takes ownership.
308     /// \arg RelaxAll - Relax all fixups?
309     MCStreamer *createObjectStreamer(const std::string &TT, MCContext &Ctx,
310                                      TargetAsmBackend &TAB,
311                                      raw_ostream &_OS,
312                                      MCCodeEmitter *_Emitter,
313                                      bool RelaxAll) const {
314       if (!ObjectStreamerCtorFn)
315         return 0;
316       return ObjectStreamerCtorFn(*this, TT, Ctx, TAB, _OS, _Emitter, RelaxAll);
317     }
318
319     /// createAsmStreamer - Create a target specific MCStreamer.
320     MCStreamer *createAsmStreamer(MCContext &Ctx,
321                                   formatted_raw_ostream &OS,
322                                   bool isVerboseAsm,
323                                   bool useLoc,
324                                   MCInstPrinter *InstPrint,
325                                   MCCodeEmitter *CE,
326                                   bool ShowInst) const {
327       // AsmStreamerCtorFn is default to llvm::createAsmStreamer
328       return AsmStreamerCtorFn(Ctx, OS, isVerboseAsm, useLoc,
329                                InstPrint, CE, ShowInst);
330     }
331
332     /// @}
333   };
334
335   /// TargetRegistry - Generic interface to target specific features.
336   struct TargetRegistry {
337     class iterator {
338       const Target *Current;
339       explicit iterator(Target *T) : Current(T) {}
340       friend struct TargetRegistry;
341     public:
342       iterator(const iterator &I) : Current(I.Current) {}
343       iterator() : Current(0) {}
344
345       bool operator==(const iterator &x) const {
346         return Current == x.Current;
347       }
348       bool operator!=(const iterator &x) const {
349         return !operator==(x);
350       }
351
352       // Iterator traversal: forward iteration only
353       iterator &operator++() {          // Preincrement
354         assert(Current && "Cannot increment end iterator!");
355         Current = Current->getNext();
356         return *this;
357       }
358       iterator operator++(int) {        // Postincrement
359         iterator tmp = *this;
360         ++*this;
361         return tmp;
362       }
363
364       const Target &operator*() const {
365         assert(Current && "Cannot dereference end iterator!");
366         return *Current;
367       }
368
369       const Target *operator->() const {
370         return &operator*();
371       }
372     };
373
374     /// @name Registry Access
375     /// @{
376
377     static iterator begin();
378
379     static iterator end() { return iterator(); }
380
381     /// lookupTarget - Lookup a target based on a target triple.
382     ///
383     /// \param Triple - The triple to use for finding a target.
384     /// \param Error - On failure, an error string describing why no target was
385     /// found.
386     static const Target *lookupTarget(const std::string &Triple,
387                                       std::string &Error);
388
389     /// getClosestTargetForJIT - Pick the best target that is compatible with
390     /// the current host.  If no close target can be found, this returns null
391     /// and sets the Error string to a reason.
392     ///
393     /// Maintained for compatibility through 2.6.
394     static const Target *getClosestTargetForJIT(std::string &Error);
395
396     /// @}
397     /// @name Target Registration
398     /// @{
399
400     /// RegisterTarget - Register the given target. Attempts to register a
401     /// target which has already been registered will be ignored.
402     ///
403     /// Clients are responsible for ensuring that registration doesn't occur
404     /// while another thread is attempting to access the registry. Typically
405     /// this is done by initializing all targets at program startup.
406     ///
407     /// @param T - The target being registered.
408     /// @param Name - The target name. This should be a static string.
409     /// @param ShortDesc - A short target description. This should be a static
410     /// string.
411     /// @param TQualityFn - The triple match quality computation function for
412     /// this target.
413     /// @param HasJIT - Whether the target supports JIT code
414     /// generation.
415     static void RegisterTarget(Target &T,
416                                const char *Name,
417                                const char *ShortDesc,
418                                Target::TripleMatchQualityFnTy TQualityFn,
419                                bool HasJIT = false);
420
421     /// RegisterAsmInfo - Register a MCAsmInfo implementation for the
422     /// given target.
423     ///
424     /// Clients are responsible for ensuring that registration doesn't occur
425     /// while another thread is attempting to access the registry. Typically
426     /// this is done by initializing all targets at program startup.
427     ///
428     /// @param T - The target being registered.
429     /// @param Fn - A function to construct a MCAsmInfo for the target.
430     static void RegisterAsmInfo(Target &T, Target::AsmInfoCtorFnTy Fn) {
431       // Ignore duplicate registration.
432       if (!T.AsmInfoCtorFn)
433         T.AsmInfoCtorFn = Fn;
434     }
435
436     /// RegisterTargetMachine - Register a TargetMachine implementation for the
437     /// given target.
438     ///
439     /// Clients are responsible for ensuring that registration doesn't occur
440     /// while another thread is attempting to access the registry. Typically
441     /// this is done by initializing all targets at program startup.
442     ///
443     /// @param T - The target being registered.
444     /// @param Fn - A function to construct a TargetMachine for the target.
445     static void RegisterTargetMachine(Target &T,
446                                       Target::TargetMachineCtorTy Fn) {
447       // Ignore duplicate registration.
448       if (!T.TargetMachineCtorFn)
449         T.TargetMachineCtorFn = Fn;
450     }
451
452     /// RegisterAsmBackend - Register a TargetAsmBackend implementation for the
453     /// given target.
454     ///
455     /// Clients are responsible for ensuring that registration doesn't occur
456     /// while another thread is attempting to access the registry. Typically
457     /// this is done by initializing all targets at program startup.
458     ///
459     /// @param T - The target being registered.
460     /// @param Fn - A function to construct an AsmBackend for the target.
461     static void RegisterAsmBackend(Target &T, Target::AsmBackendCtorTy Fn) {
462       if (!T.AsmBackendCtorFn)
463         T.AsmBackendCtorFn = Fn;
464     }
465
466     /// RegisterAsmLexer - Register a TargetAsmLexer implementation for the
467     /// given target.
468     ///
469     /// Clients are responsible for ensuring that registration doesn't occur
470     /// while another thread is attempting to access the registry. Typically
471     /// this is done by initializing all targets at program startup.
472     ///
473     /// @param T - The target being registered.
474     /// @param Fn - A function to construct an AsmLexer for the target.
475     static void RegisterAsmLexer(Target &T, Target::AsmLexerCtorTy Fn) {
476       if (!T.AsmLexerCtorFn)
477         T.AsmLexerCtorFn = Fn;
478     }
479
480     /// RegisterAsmParser - Register a TargetAsmParser implementation for the
481     /// given target.
482     ///
483     /// Clients are responsible for ensuring that registration doesn't occur
484     /// while another thread is attempting to access the registry. Typically
485     /// this is done by initializing all targets at program startup.
486     ///
487     /// @param T - The target being registered.
488     /// @param Fn - A function to construct an AsmParser for the target.
489     static void RegisterAsmParser(Target &T, Target::AsmParserCtorTy Fn) {
490       if (!T.AsmParserCtorFn)
491         T.AsmParserCtorFn = Fn;
492     }
493
494     /// RegisterAsmPrinter - Register an AsmPrinter implementation for the given
495     /// target.
496     ///
497     /// Clients are responsible for ensuring that registration doesn't occur
498     /// while another thread is attempting to access the registry. Typically
499     /// this is done by initializing all targets at program startup.
500     ///
501     /// @param T - The target being registered.
502     /// @param Fn - A function to construct an AsmPrinter for the target.
503     static void RegisterAsmPrinter(Target &T, Target::AsmPrinterCtorTy Fn) {
504       // Ignore duplicate registration.
505       if (!T.AsmPrinterCtorFn)
506         T.AsmPrinterCtorFn = Fn;
507     }
508
509     /// RegisterMCDisassembler - Register a MCDisassembler implementation for
510     /// the given target.
511     ///
512     /// Clients are responsible for ensuring that registration doesn't occur
513     /// while another thread is attempting to access the registry. Typically
514     /// this is done by initializing all targets at program startup.
515     ///
516     /// @param T - The target being registered.
517     /// @param Fn - A function to construct an MCDisassembler for the target.
518     static void RegisterMCDisassembler(Target &T,
519                                        Target::MCDisassemblerCtorTy Fn) {
520       if (!T.MCDisassemblerCtorFn)
521         T.MCDisassemblerCtorFn = Fn;
522     }
523
524     /// RegisterMCInstPrinter - Register a MCInstPrinter implementation for the
525     /// given target.
526     ///
527     /// Clients are responsible for ensuring that registration doesn't occur
528     /// while another thread is attempting to access the registry. Typically
529     /// this is done by initializing all targets at program startup.
530     ///
531     /// @param T - The target being registered.
532     /// @param Fn - A function to construct an MCInstPrinter for the target.
533     static void RegisterMCInstPrinter(Target &T,
534                                       Target::MCInstPrinterCtorTy Fn) {
535       if (!T.MCInstPrinterCtorFn)
536         T.MCInstPrinterCtorFn = Fn;
537     }
538
539     /// RegisterCodeEmitter - Register a MCCodeEmitter implementation for the
540     /// given target.
541     ///
542     /// Clients are responsible for ensuring that registration doesn't occur
543     /// while another thread is attempting to access the registry. Typically
544     /// this is done by initializing all targets at program startup.
545     ///
546     /// @param T - The target being registered.
547     /// @param Fn - A function to construct an MCCodeEmitter for the target.
548     static void RegisterCodeEmitter(Target &T, Target::CodeEmitterCtorTy Fn) {
549       if (!T.CodeEmitterCtorFn)
550         T.CodeEmitterCtorFn = Fn;
551     }
552
553     /// RegisterObjectStreamer - Register a object code MCStreamer implementation
554     /// for the given target.
555     ///
556     /// Clients are responsible for ensuring that registration doesn't occur
557     /// while another thread is attempting to access the registry. Typically
558     /// this is done by initializing all targets at program startup.
559     ///
560     /// @param T - The target being registered.
561     /// @param Fn - A function to construct an MCStreamer for the target.
562     static void RegisterObjectStreamer(Target &T, Target::ObjectStreamerCtorTy Fn) {
563       if (!T.ObjectStreamerCtorFn)
564         T.ObjectStreamerCtorFn = Fn;
565     }
566
567     /// RegisterAsmStreamer - Register an assembly MCStreamer implementation
568     /// for the given target.
569     ///
570     /// Clients are responsible for ensuring that registration doesn't occur
571     /// while another thread is attempting to access the registry. Typically
572     /// this is done by initializing all targets at program startup.
573     ///
574     /// @param T - The target being registered.
575     /// @param Fn - A function to construct an MCStreamer for the target.
576     static void RegisterAsmStreamer(Target &T, Target::AsmStreamerCtorTy Fn) {
577       if (T.AsmStreamerCtorFn == createAsmStreamer)
578         T.AsmStreamerCtorFn = Fn;
579     }
580
581     /// @}
582   };
583
584
585   //===--------------------------------------------------------------------===//
586
587   /// RegisterTarget - Helper template for registering a target, for use in the
588   /// target's initialization function. Usage:
589   ///
590   ///
591   /// Target TheFooTarget; // The global target instance.
592   ///
593   /// extern "C" void LLVMInitializeFooTargetInfo() {
594   ///   RegisterTarget<Triple::foo> X(TheFooTarget, "foo", "Foo description");
595   /// }
596   template<Triple::ArchType TargetArchType = Triple::InvalidArch,
597            bool HasJIT = false>
598   struct RegisterTarget {
599     RegisterTarget(Target &T, const char *Name, const char *Desc) {
600       TargetRegistry::RegisterTarget(T, Name, Desc,
601                                      &getTripleMatchQuality,
602                                      HasJIT);
603     }
604
605     static unsigned getTripleMatchQuality(const std::string &TT) {
606       if (Triple(TT).getArch() == TargetArchType)
607         return 20;
608       return 0;
609     }
610   };
611
612   /// RegisterAsmInfo - Helper template for registering a target assembly info
613   /// implementation.  This invokes the static "Create" method on the class to
614   /// actually do the construction.  Usage:
615   ///
616   /// extern "C" void LLVMInitializeFooTarget() {
617   ///   extern Target TheFooTarget;
618   ///   RegisterAsmInfo<FooMCAsmInfo> X(TheFooTarget);
619   /// }
620   template<class MCAsmInfoImpl>
621   struct RegisterAsmInfo {
622     RegisterAsmInfo(Target &T) {
623       TargetRegistry::RegisterAsmInfo(T, &Allocator);
624     }
625   private:
626     static MCAsmInfo *Allocator(const Target &T, StringRef TT) {
627       return new MCAsmInfoImpl(T, TT);
628     }
629
630   };
631
632   /// RegisterAsmInfoFn - Helper template for registering a target assembly info
633   /// implementation.  This invokes the specified function to do the
634   /// construction.  Usage:
635   ///
636   /// extern "C" void LLVMInitializeFooTarget() {
637   ///   extern Target TheFooTarget;
638   ///   RegisterAsmInfoFn X(TheFooTarget, TheFunction);
639   /// }
640   struct RegisterAsmInfoFn {
641     RegisterAsmInfoFn(Target &T, Target::AsmInfoCtorFnTy Fn) {
642       TargetRegistry::RegisterAsmInfo(T, Fn);
643     }
644   };
645
646
647   /// RegisterTargetMachine - Helper template for registering a target machine
648   /// implementation, for use in the target machine initialization
649   /// function. Usage:
650   ///
651   /// extern "C" void LLVMInitializeFooTarget() {
652   ///   extern Target TheFooTarget;
653   ///   RegisterTargetMachine<FooTargetMachine> X(TheFooTarget);
654   /// }
655   template<class TargetMachineImpl>
656   struct RegisterTargetMachine {
657     RegisterTargetMachine(Target &T) {
658       TargetRegistry::RegisterTargetMachine(T, &Allocator);
659     }
660
661   private:
662     static TargetMachine *Allocator(const Target &T, const std::string &TT,
663                                     const std::string &FS) {
664       return new TargetMachineImpl(T, TT, FS);
665     }
666   };
667
668   /// RegisterAsmBackend - Helper template for registering a target specific
669   /// assembler backend. Usage:
670   ///
671   /// extern "C" void LLVMInitializeFooAsmBackend() {
672   ///   extern Target TheFooTarget;
673   ///   RegisterAsmBackend<FooAsmLexer> X(TheFooTarget);
674   /// }
675   template<class AsmBackendImpl>
676   struct RegisterAsmBackend {
677     RegisterAsmBackend(Target &T) {
678       TargetRegistry::RegisterAsmBackend(T, &Allocator);
679     }
680
681   private:
682     static TargetAsmBackend *Allocator(const Target &T,
683                                        const std::string &Triple) {
684       return new AsmBackendImpl(T, Triple);
685     }
686   };
687
688   /// RegisterAsmLexer - Helper template for registering a target specific
689   /// assembly lexer, for use in the target machine initialization
690   /// function. Usage:
691   ///
692   /// extern "C" void LLVMInitializeFooAsmLexer() {
693   ///   extern Target TheFooTarget;
694   ///   RegisterAsmLexer<FooAsmLexer> X(TheFooTarget);
695   /// }
696   template<class AsmLexerImpl>
697   struct RegisterAsmLexer {
698     RegisterAsmLexer(Target &T) {
699       TargetRegistry::RegisterAsmLexer(T, &Allocator);
700     }
701
702   private:
703     static TargetAsmLexer *Allocator(const Target &T, const MCAsmInfo &MAI) {
704       return new AsmLexerImpl(T, MAI);
705     }
706   };
707
708   /// RegisterAsmParser - Helper template for registering a target specific
709   /// assembly parser, for use in the target machine initialization
710   /// function. Usage:
711   ///
712   /// extern "C" void LLVMInitializeFooAsmParser() {
713   ///   extern Target TheFooTarget;
714   ///   RegisterAsmParser<FooAsmParser> X(TheFooTarget);
715   /// }
716   template<class AsmParserImpl>
717   struct RegisterAsmParser {
718     RegisterAsmParser(Target &T) {
719       TargetRegistry::RegisterAsmParser(T, &Allocator);
720     }
721
722   private:
723     static TargetAsmParser *Allocator(const Target &T, MCAsmParser &P,
724                                       TargetMachine &TM) {
725       return new AsmParserImpl(T, P, TM);
726     }
727   };
728
729   /// RegisterAsmPrinter - Helper template for registering a target specific
730   /// assembly printer, for use in the target machine initialization
731   /// function. Usage:
732   ///
733   /// extern "C" void LLVMInitializeFooAsmPrinter() {
734   ///   extern Target TheFooTarget;
735   ///   RegisterAsmPrinter<FooAsmPrinter> X(TheFooTarget);
736   /// }
737   template<class AsmPrinterImpl>
738   struct RegisterAsmPrinter {
739     RegisterAsmPrinter(Target &T) {
740       TargetRegistry::RegisterAsmPrinter(T, &Allocator);
741     }
742
743   private:
744     static AsmPrinter *Allocator(TargetMachine &TM, MCStreamer &Streamer) {
745       return new AsmPrinterImpl(TM, Streamer);
746     }
747   };
748
749   /// RegisterCodeEmitter - Helper template for registering a target specific
750   /// machine code emitter, for use in the target initialization
751   /// function. Usage:
752   ///
753   /// extern "C" void LLVMInitializeFooCodeEmitter() {
754   ///   extern Target TheFooTarget;
755   ///   RegisterCodeEmitter<FooCodeEmitter> X(TheFooTarget);
756   /// }
757   template<class CodeEmitterImpl>
758   struct RegisterCodeEmitter {
759     RegisterCodeEmitter(Target &T) {
760       TargetRegistry::RegisterCodeEmitter(T, &Allocator);
761     }
762
763   private:
764     static MCCodeEmitter *Allocator(const Target &T, TargetMachine &TM,
765                                     MCContext &Ctx) {
766       return new CodeEmitterImpl(T, TM, Ctx);
767     }
768   };
769
770 }
771
772 #endif