blob: 0ef2ad89d6b3d65baa2d25473333fe0036d24c12 [file] [log] [blame]
Shih-wei Liao462aefd2010-06-04 15:32:04 -07001#include "slang_rs_context.hpp"
2#include "slang_rs_pragma_handler.hpp"
3
4#include "clang/Lex/Preprocessor.h" /* for class Preprocessor */
5#include "clang/Lex/Token.h" /* for class Token */
6#include "clang/Basic/TokenKinds.h" /* for class Token */
7
8#include "clang/Basic/IdentifierTable.h" /* for class IdentifierInfo */
9
10namespace {
11
12using namespace clang;
13using namespace slang;
14
15class RSExportVarPragmaHandler : public RSPragmaHandler {
16private:
17 void handleItem(const std::string& Item) {
18 mContext->addExportVar(Item);
19 }
20
21public:
22 RSExportVarPragmaHandler(IdentifierInfo* II, RSContext* Context) : RSPragmaHandler(II, Context) { return; }
23
24 void HandlePragma(Preprocessor& PP, Token& FirstToken) {
25 this->handleItemListPragma(PP, FirstToken);
26 }
27};
28
29class RSExportFuncPragmaHandler : public RSPragmaHandler {
30private:
31 void handleItem(const std::string& Item) {
32 mContext->addExportFunc(Item);
33 }
34
35public:
36 RSExportFuncPragmaHandler(IdentifierInfo* II, RSContext* Context) : RSPragmaHandler(II, Context) { return; }
37
38 void HandlePragma(Preprocessor& PP, Token& FirstToken) {
39 this->handleItemListPragma(PP, FirstToken);
40 }
41};
42
43class RSExportTypePragmaHandler : public RSPragmaHandler {
44private:
45 void handleItem(const std::string& Item) {
46 mContext->addExportType(Item);
47 }
48
49public:
50 RSExportTypePragmaHandler(IdentifierInfo* II, RSContext* Context) : RSPragmaHandler(II, Context) { return; }
51
52 void HandlePragma(Preprocessor& PP, Token& FirstToken) {
53 this->handleItemListPragma(PP, FirstToken);
54 }
55};
56
57} /* anonymous namespace */
58
59namespace slang {
60
61RSPragmaHandler* RSPragmaHandler::CreatePragmaExportVarHandler(RSContext* Context) {
62 IdentifierInfo* II = Context->getPreprocessor()->getIdentifierInfo("export_var");
63 if(II != NULL)
64 return new RSExportVarPragmaHandler(II, Context);
65 else
66 return NULL;
67}
68
69RSPragmaHandler* RSPragmaHandler::CreatePragmaExportFuncHandler(RSContext* Context) {
70 IdentifierInfo* II = Context->getPreprocessor()->getIdentifierInfo("export_func");
71 if(II != NULL)
72 return new RSExportFuncPragmaHandler(II, Context);
73 else
74 return NULL;
75}
76
77RSPragmaHandler* RSPragmaHandler::CreatePragmaExportTypeHandler(RSContext* Context) {
78 IdentifierInfo* II = Context->getPreprocessor()->getIdentifierInfo("export_type");
79 if(II != NULL)
80 return new RSExportTypePragmaHandler(II, Context);
81 else
82 return NULL;
83}
84
85void RSPragmaHandler::handleItemListPragma(Preprocessor& PP, Token& FirstToken) {
86 Token& PragmaToken = FirstToken;
87
88 /* Skip first token, like "export_var" */
89 PP.LexUnexpandedToken(PragmaToken);
90
91 /* Now, the current token must be tok::lpara */
92 if(PragmaToken.isNot(tok::l_paren))
93 return;
94
95 while(PragmaToken.isNot(tok::eom)) {
96 /* Lex variable name */
97 PP.LexUnexpandedToken(PragmaToken);
98 if(PragmaToken.is(tok::identifier))
99 this->handleItem( PP.getSpelling(PragmaToken) );
100 else
101 break;
102
103 assert(PragmaToken.isNot(tok::eom));
104
105 PP.LexUnexpandedToken(PragmaToken);
106
107 if(PragmaToken.isNot(tok::comma))
108 break;
109 }
110 return;
111}
112
113} /* namespace slang */
114