OLD | NEW |
---|---|
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 11 matching lines...) Expand all Loading... | |
22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, | 22 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY | 23 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | 24 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | 25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
27 | 27 |
28 #include "v8.h" | 28 #include "v8.h" |
29 | 29 |
30 #include "ast.h" | 30 #include "ast.h" |
31 #include "scopes.h" | 31 #include "scopes.h" |
32 #include "string-stream.h" | |
32 | 33 |
33 namespace v8 { namespace internal { | 34 namespace v8 { namespace internal { |
34 | 35 |
35 | 36 |
36 VariableProxySentinel VariableProxySentinel::this_proxy_(true); | 37 VariableProxySentinel VariableProxySentinel::this_proxy_(true); |
37 VariableProxySentinel VariableProxySentinel::identifier_proxy_(false); | 38 VariableProxySentinel VariableProxySentinel::identifier_proxy_(false); |
38 ValidLeftHandSideSentinel ValidLeftHandSideSentinel::instance_; | 39 ValidLeftHandSideSentinel ValidLeftHandSideSentinel::instance_; |
39 Property Property::this_property_(VariableProxySentinel::this_proxy(), NULL, 0); | 40 Property Property::this_property_(VariableProxySentinel::this_proxy(), NULL, 0); |
40 Call Call::sentinel_(NULL, NULL, false, 0); | 41 Call Call::sentinel_(NULL, NULL, false, 0); |
41 | 42 |
(...skipping 130 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
172 // The variable statement visiting code may pass NULL expressions | 173 // The variable statement visiting code may pass NULL expressions |
173 // to this code. Maybe this should be handled by introducing an | 174 // to this code. Maybe this should be handled by introducing an |
174 // undefined expression or literal? Revisit this code if this | 175 // undefined expression or literal? Revisit this code if this |
175 // changes | 176 // changes |
176 Expression* expression = expressions->at(i); | 177 Expression* expression = expressions->at(i); |
177 if (expression != NULL) Visit(expression); | 178 if (expression != NULL) Visit(expression); |
178 } | 179 } |
179 } | 180 } |
180 | 181 |
181 | 182 |
183 // ---------------------------------------------------------------------------- | |
184 // Regular expressions | |
185 | |
186 #define MAKE_ACCEPT(Name) \ | |
187 void* RegExp##Name::Accept(RegExpVisitor* visitor, void* data) { \ | |
188 return visitor->Visit##Name(this, data); \ | |
189 } | |
190 FOR_EACH_REG_EXP_TREE_TYPE(MAKE_ACCEPT) | |
191 #undef MAKE_ACCEPT | |
192 | |
193 #define MAKE_TYPE_CASE(Name) \ | |
194 RegExp##Name* RegExpTree::As##Name() { \ | |
195 return NULL; \ | |
196 } \ | |
197 bool RegExpTree::Is##Name() { return false; } | |
198 FOR_EACH_REG_EXP_TREE_TYPE(MAKE_TYPE_CASE) | |
Mads Ager (chromium)
2008/11/25 21:09:41
Do not indent this line.
Erik Corry
2008/11/26 12:18:36
Fixed.
| |
199 #undef MAKE_TYPE_CASE | |
200 | |
201 #define MAKE_TYPE_CASE(Name) \ | |
202 RegExp##Name* RegExp##Name::As##Name() { \ | |
203 return this; \ | |
204 } \ | |
205 bool RegExp##Name::Is##Name() { return true; } | |
206 FOR_EACH_REG_EXP_TREE_TYPE(MAKE_TYPE_CASE) | |
207 #undef MAKE_TYPE_CASE | |
208 | |
209 RegExpEmpty RegExpEmpty::kInstance; | |
210 | |
211 | |
212 // Convert regular expression trees to a simple sexp representation. | |
213 // This representation should be different from the input grammar | |
214 // in as many cases as possible, to make it more difficult for incorrect | |
215 // parses to look as correct ones which is likely if the input and | |
216 // output formats are alike. | |
217 class RegExpUnparser: public RegExpVisitor { | |
218 public: | |
219 RegExpUnparser(); | |
220 void VisitCharacterRange(CharacterRange that); | |
221 SmartPointer<const char> ToString() { return stream_.ToCString(); } | |
222 #define MAKE_CASE(Name) virtual void* Visit##Name(RegExp##Name*, void* data); | |
223 FOR_EACH_REG_EXP_TREE_TYPE(MAKE_CASE) | |
224 #undef MAKE_CASE | |
225 private: | |
226 StringStream* stream() { return &stream_; } | |
227 HeapStringAllocator alloc_; | |
228 StringStream stream_; | |
229 }; | |
230 | |
231 | |
232 RegExpUnparser::RegExpUnparser() : stream_(&alloc_) { | |
233 } | |
234 | |
235 | |
236 void* RegExpUnparser::VisitDisjunction(RegExpDisjunction* that, void* data) { | |
237 stream()->Add("(|"); | |
238 for (int i = 0; i < that->alternatives()->length(); i++) { | |
239 stream()->Add(" "); | |
240 that->alternatives()->at(i)->Accept(this, data); | |
241 } | |
242 stream()->Add(")"); | |
243 return NULL; | |
244 } | |
245 | |
246 | |
247 void* RegExpUnparser::VisitAlternative(RegExpAlternative* that, void* data) { | |
248 stream()->Add("(:"); | |
249 for (int i = 0; i < that->nodes()->length(); i++) { | |
250 stream()->Add(" "); | |
251 that->nodes()->at(i)->Accept(this, data); | |
252 } | |
253 stream()->Add(")"); | |
254 return NULL; | |
255 } | |
256 | |
257 | |
258 void RegExpUnparser::VisitCharacterRange(CharacterRange that) { | |
259 stream()->Add("%k", that.from()); | |
260 if (!that.IsSingleton()) { | |
261 stream()->Add("-%k", that.to()); | |
262 } | |
263 } | |
264 | |
265 | |
266 | |
267 void* RegExpUnparser::VisitCharacterClass(RegExpCharacterClass* that, | |
268 void* data) { | |
269 if (that->is_negated()) | |
270 stream()->Add("^"); | |
271 stream()->Add("["); | |
272 for (int i = 0; i < that->ranges()->length(); i++) { | |
273 if (i > 0) stream()->Add(" "); | |
274 VisitCharacterRange(that->ranges()->at(i)); | |
275 } | |
276 stream()->Add("]"); | |
277 return NULL; | |
278 } | |
279 | |
280 | |
281 void* RegExpUnparser::VisitAssertion(RegExpAssertion* that, void* data) { | |
282 switch (that->type()) { | |
283 case RegExpAssertion::START_OF_INPUT: | |
284 stream()->Add("@^i"); | |
285 break; | |
286 case RegExpAssertion::END_OF_INPUT: | |
287 stream()->Add("@$i"); | |
288 break; | |
289 case RegExpAssertion::START_OF_LINE: | |
290 stream()->Add("@^l"); | |
291 break; | |
292 case RegExpAssertion::END_OF_LINE: | |
293 stream()->Add("@$l"); | |
294 break; | |
295 case RegExpAssertion::BOUNDARY: | |
296 stream()->Add("@b"); | |
297 break; | |
298 case RegExpAssertion::NON_BOUNDARY: | |
299 stream()->Add("@B"); | |
300 break; | |
301 } | |
302 return NULL; | |
303 } | |
304 | |
305 | |
306 void* RegExpUnparser::VisitAtom(RegExpAtom* that, void* data) { | |
307 stream()->Add("'"); | |
308 Vector<const uc16> chardata = that->data(); | |
309 for (int i = 0; i < chardata.length(); i++) { | |
310 stream()->Add("%k", chardata[i]); | |
311 } | |
312 stream()->Add("'"); | |
313 return NULL; | |
314 } | |
315 | |
316 | |
317 void* RegExpUnparser::VisitText(RegExpText* that, void* data) { | |
318 if (that->elements()->length() == 1) { | |
319 that->elements()->at(0).data.u_atom->Accept(this, data); | |
320 } else { | |
321 stream()->Add("(!"); | |
322 for (int i = 0; i < that->elements()->length(); i++) { | |
323 stream()->Add(" "); | |
324 that->elements()->at(i).data.u_atom->Accept(this, data); | |
325 } | |
326 stream()->Add(")"); | |
327 } | |
328 return NULL; | |
329 } | |
330 | |
331 | |
332 void* RegExpUnparser::VisitQuantifier(RegExpQuantifier* that, void* data) { | |
333 stream()->Add("(# %i ", that->min()); | |
334 if (that->max() == RegExpQuantifier::kInfinity) { | |
335 stream()->Add("- "); | |
336 } else { | |
337 stream()->Add("%i ", that->max()); | |
338 } | |
339 stream()->Add(that->is_greedy() ? "g " : "n "); | |
340 that->body()->Accept(this, data); | |
341 stream()->Add(")"); | |
342 return NULL; | |
343 } | |
344 | |
345 | |
346 void* RegExpUnparser::VisitCapture(RegExpCapture* that, void* data) { | |
347 stream()->Add("(^ "); | |
348 that->body()->Accept(this, data); | |
349 stream()->Add(")"); | |
350 return NULL; | |
351 } | |
352 | |
353 | |
354 void* RegExpUnparser::VisitLookahead(RegExpLookahead* that, void* data) { | |
355 stream()->Add("(-> "); | |
356 stream()->Add(that->is_positive() ? "+ " : "- "); | |
357 that->body()->Accept(this, data); | |
358 stream()->Add(")"); | |
359 return NULL; | |
360 } | |
361 | |
362 | |
363 void* RegExpUnparser::VisitBackReference(RegExpBackReference* that, | |
364 void* data) { | |
365 stream()->Add("(<- %i)", that->index()); | |
366 return NULL; | |
367 } | |
368 | |
369 | |
370 void* RegExpUnparser::VisitEmpty(RegExpEmpty* that, void* data) { | |
371 stream()->Put('%'); | |
372 return NULL; | |
373 } | |
374 | |
375 | |
376 SmartPointer<const char> RegExpTree::ToString() { | |
377 RegExpUnparser unparser; | |
378 Accept(&unparser, NULL); | |
379 return unparser.ToString(); | |
380 } | |
381 | |
382 | |
182 } } // namespace v8::internal | 383 } } // namespace v8::internal |
OLD | NEW |