fix assignment in conjunction of conditionals
[hiphop-php.git] / hphp / compiler / code_generator.h
blob5ef7d80987ac226a99c0165be65b322341028bdf
1 /*
2 +----------------------------------------------------------------------+
3 | HipHop for PHP |
4 +----------------------------------------------------------------------+
5 | Copyright (c) 2010-present Facebook, Inc. (http://www.facebook.com) |
6 +----------------------------------------------------------------------+
7 | This source file is subject to version 3.01 of the PHP license, |
8 | that is bundled with this package in the file LICENSE, and is |
9 | available through the world-wide-web at the following url: |
10 | http://www.php.net/license/3_01.txt |
11 | If you did not receive a copy of the PHP license and are unable to |
12 | obtain it through the world-wide-web, please send a note to |
13 | license@php.net so we can mail you a copy immediately. |
14 +----------------------------------------------------------------------+
17 #ifndef incl_HPHP_CODE_GENERATOR_H_
18 #define incl_HPHP_CODE_GENERATOR_H_
20 #include <deque>
21 #include <map>
22 #include <ostream>
23 #include <set>
24 #include <utility>
25 #include <vector>
27 #include "hphp/util/deprecated/declare-boost-types.h"
29 #include "hphp/compiler/hphp.h"
31 namespace HPHP {
32 ///////////////////////////////////////////////////////////////////////////////
34 DECLARE_BOOST_TYPES(AnalysisResult);
35 DECLARE_BOOST_TYPES(Statement);
36 DECLARE_BOOST_TYPES(Construct);
37 DECLARE_BOOST_TYPES(BlockScope);
38 DECLARE_EXTENDED_BOOST_TYPES(ClassScope);
39 DECLARE_BOOST_TYPES(FunctionScope);
40 DECLARE_BOOST_TYPES(FileScope);
41 DECLARE_BOOST_TYPES(LoopStatement);
43 struct CodeGenerator {
44 enum Output {
45 InvalidOutput,
47 PickledPHP, // stripped comments, etc. but 1 to 1 file to file
48 InlinedPHP, // all includes are inlined
49 TrimmedPHP, // unreferenced functions and classes are removed
50 TextHHBC, // HHBC dump in human-readable format
53 enum Stream {
54 NullStream = -1, // suppress output
55 PrimaryStream, // main output
57 StreamCount
60 enum Context {
61 NoContext,
63 PhpDeclaration,
64 PhpImplementation,
67 public:
68 CodeGenerator() {} // only for creating a dummy code generator
69 explicit CodeGenerator(std::ostream *primary, Output output = PickledPHP,
70 const std::string *filename = nullptr);
72 /**
73 * ...if it was passed in from constructor.
75 const std::string& getFileName() const { return m_filename;}
77 /**
78 * What kind of program are we generating?
80 Output getOutput() const { return m_output;}
82 /**
83 * Stream functions.
85 void useStream(Stream stream);
86 bool usingStream(Stream stream);
87 std::ostream *getStream() const { return m_out;}
88 void setStream(Stream stream, std::ostream *out);
90 /**
91 * Output strings.
93 void printf(ATTRIBUTE_PRINTF_STRING const char *fmt, ...)
94 ATTRIBUTE_PRINTF(2,3);
95 void indentBegin(ATTRIBUTE_PRINTF_STRING const char *fmt, ...)
96 ATTRIBUTE_PRINTF(2,3);
97 void indentEnd(ATTRIBUTE_PRINTF_STRING const char *fmt, ...)
98 ATTRIBUTE_PRINTF(2,3);
99 void indentEnd();
100 void printRaw(const char *msg) { print(msg, false);}
102 * Pre-formatted outputs.
104 void printSeparator();
105 void namespaceBegin();
106 void namespaceEnd();
109 * Make sure PHP variables, functions and typenames are unique and
110 * different from C's built-in keywords and HPHP's.
112 int createNewId(const std::string &key);
113 static std::string GetNewLambda(); // for create_function()
116 * Contexts allow one construct generates more than one kind of source.
117 * For example, a ClassStatement generates different source code, depending
118 * on whether we are generating a header file or an implementation file.
120 void setContext(Context context) { m_context = context;}
121 Context getContext() const { return m_context;}
123 bool translatePredefined() { return m_translatePredefined; }
124 void translatePredefined(bool flag) { m_translatePredefined = flag; }
126 private:
127 std::string m_filename;
128 Stream m_curStream;
129 std::ostream *m_streams[StreamCount];
130 std::ostream *m_out;
131 Output m_output;
133 int m_indentation[StreamCount];
134 bool m_indentPending[StreamCount];
135 int m_lineNo[StreamCount];
136 int m_inComments[StreamCount];
137 bool m_wrappedExpression[StreamCount];
138 bool m_inExpression[StreamCount];
139 bool m_inFileOrClassHeader;
140 bool m_inNamespace;
142 static int s_idLambda;
143 std::map<std::string, int> m_idCounters;
144 Context m_context;
145 std::vector<int> m_breakScopes;
146 std::set<int> m_breakLabelIds; // break labels referenced
147 std::set<int> m_contLabelIds; // continue labels referenced
148 std::deque<int> m_callInfos;
149 LoopStatementPtr m_loopStatement;
150 StringToClassScopePtrVecMap m_classes;
151 std::set<const FunctionScope*> m_declaredClosures;
152 FileScopeRawPtr m_literalScope;
154 bool m_translatePredefined; // translate predefined constants in PHP output
155 bool m_scalarVariant;
156 bool m_initListFirstElem;
158 public: void print(const char *msg, bool indent = true);
160 private:
161 void print(ATTRIBUTE_PRINTF_STRING const char *fmt, va_list ap)
162 ATTRIBUTE_PRINTF(2,0);
163 void printSubstring(const char *start, int length);
164 void printIndent();
167 #define cg_printf cg.printf
168 #define cg_print cg.print
169 #define cg_indentBegin cg.indentBegin
170 #define cg_indentEnd cg.indentEnd
171 #define cg_printInclude cg.printInclude
172 #define cg_printString cg.printString
174 ///////////////////////////////////////////////////////////////////////////////
176 #endif // incl_HPHP_CODE_GENERATOR_H_