source: webkit/trunk/JavaScriptCore/kjs/nodes2string.cpp@ 5356

Last change on this file since 5356 was 3373, checked in by darin, 22 years ago

More copyright fixes.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 11.7 KB
Line 
1// -*- c-basic-offset: 2 -*-
2/*
3 * This file is part of the KDE libraries
4 * Copyright (C) 2002 Harri Porten ([email protected])
5 * Copyright (C) 2003 Apple Computer, Inc.
6 *
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Library General Public
9 * License as published by the Free Software Foundation; either
10 * version 2 of the License, or (at your option) any later version.
11 *
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Library General Public License for more details.
16 *
17 * You should have received a copy of the GNU Library General Public License
18 * along with this library; see the file COPYING.LIB. If not, write to
19 * the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
20 * Boston, MA 02111-1307, USA.
21 *
22 */
23
24#include "nodes.h"
25
26namespace KJS {
27 /**
28 * A simple text streaming class that helps with code indentation.
29 */
30 class SourceStream {
31 public:
32 enum Format {
33 Endl, Indent, Unindent
34 };
35
36 UString toString() const { return str; }
37 SourceStream& operator<<(const Identifier &);
38 SourceStream& operator<<(const UString &);
39 SourceStream& operator<<(const char *);
40 SourceStream& operator<<(char);
41 SourceStream& operator<<(Format f);
42 SourceStream& operator<<(const Node *);
43 private:
44 UString str; /* TODO: buffer */
45 UString ind;
46 };
47};
48
49using namespace KJS;
50
51SourceStream& SourceStream::operator<<(char c)
52{
53 str += UString(c);
54 return *this;
55}
56
57SourceStream& SourceStream::operator<<(const char *s)
58{
59 str += UString(s);
60 return *this;
61}
62
63SourceStream& SourceStream::operator<<(const UString &s)
64{
65 str += s;
66 return *this;
67}
68
69SourceStream& SourceStream::operator<<(const Identifier &s)
70{
71 str += s.ustring();
72 return *this;
73}
74
75SourceStream& SourceStream::operator<<(const Node *n)
76{
77 if (n)
78 n->streamTo(*this);
79 return *this;
80}
81
82SourceStream& SourceStream::operator<<(Format f)
83{
84 switch (f) {
85 case Endl:
86 str += "\n" + ind;
87 break;
88 case Indent:
89 ind += " ";
90 break;
91 case Unindent:
92 ind = ind.substr(0, ind.size() - 2);
93 break;
94 }
95
96 return *this;
97}
98
99UString Node::toString() const
100{
101 SourceStream str;
102 streamTo(str);
103
104 return str.toString();
105}
106
107void NullNode::streamTo(SourceStream &s) const { s << "null"; }
108
109void BooleanNode::streamTo(SourceStream &s) const
110{
111 s << (value ? "true" : "false");
112}
113
114void NumberNode::streamTo(SourceStream &s) const { s << UString::from(value); }
115
116void StringNode::streamTo(SourceStream &s) const
117{
118 s << '"' << value << '"';
119}
120
121void RegExpNode::streamTo(SourceStream &s) const { s << pattern; }
122
123void ThisNode::streamTo(SourceStream &s) const { s << "this"; }
124
125void ResolveNode::streamTo(SourceStream &s) const { s << ident; }
126
127void ElementNode::streamTo(SourceStream &s) const
128{
129 for (const ElementNode *n = this; n; n = n->list) {
130 for (int i = 0; i < n->elision; i++)
131 s << ",";
132 s << n->node;
133 }
134}
135
136void ArrayNode::streamTo(SourceStream &s) const
137{
138 s << "[" << element;
139 for (int i = 0; i < elision; i++)
140 s << ",";
141 s << "]";
142}
143
144void ObjectLiteralNode::streamTo(SourceStream &s) const
145{
146 if (list)
147 s << "{ " << list << " }";
148 else
149 s << "{ }";
150}
151
152void PropertyValueNode::streamTo(SourceStream &s) const
153{
154 for (const PropertyValueNode *n = this; n; n = n->list)
155 s << n->name << ": " << n->assign;
156}
157
158void PropertyNode::streamTo(SourceStream &s) const
159{
160 if (str.isNull())
161 s << UString::from(numeric);
162 else
163 s << str;
164}
165
166void AccessorNode1::streamTo(SourceStream &s) const
167{
168 s << expr1 << "[" << expr2 << "]";
169}
170
171void AccessorNode2::streamTo(SourceStream &s) const
172{
173 s << expr << "." << ident;
174}
175
176void ArgumentListNode::streamTo(SourceStream &s) const
177{
178 s << expr;
179 for (ArgumentListNode *n = list; n; n = n->list)
180 s << ", " << n->expr;
181}
182
183void ArgumentsNode::streamTo(SourceStream &s) const
184{
185 s << "(" << list << ")";
186}
187
188void NewExprNode::streamTo(SourceStream &s) const
189{
190 s << "new " << expr << args;
191}
192
193void FunctionCallNode::streamTo(SourceStream &s) const
194{
195 s << expr << args;
196}
197
198void PostfixNode::streamTo(SourceStream &s) const
199{
200 s << expr;
201 if (oper == OpPlusPlus)
202 s << "++";
203 else
204 s << "--";
205}
206
207void DeleteNode::streamTo(SourceStream &s) const
208{
209 s << "delete " << expr;
210}
211
212void VoidNode::streamTo(SourceStream &s) const
213{
214 s << "void " << expr;
215}
216
217void TypeOfNode::streamTo(SourceStream &s) const
218{
219 s << "typeof " << expr;
220}
221
222void PrefixNode::streamTo(SourceStream &s) const
223{
224 s << expr << (oper == OpPlusPlus ? "++" : "--");
225}
226
227void UnaryPlusNode::streamTo(SourceStream &s) const
228{
229 s << "+" << expr;
230}
231
232void NegateNode::streamTo(SourceStream &s) const
233{
234 s << "-" << expr;
235}
236
237void BitwiseNotNode::streamTo(SourceStream &s) const
238{
239 s << "~" << expr;
240}
241
242void LogicalNotNode::streamTo(SourceStream &s) const
243{
244 s << "!" << expr;
245}
246
247void MultNode::streamTo(SourceStream &s) const
248{
249 s << term1 << oper << term2;
250}
251
252void AddNode::streamTo(SourceStream &s) const
253{
254 s << term1 << oper << term2;
255}
256
257void ShiftNode::streamTo(SourceStream &s) const
258{
259 s << term1;
260 if (oper == OpLShift)
261 s << "<<";
262 else if (oper == OpRShift)
263 s << ">>";
264 else
265 s << ">>>";
266 s << term2;
267}
268
269void RelationalNode::streamTo(SourceStream &s) const
270{
271 s << expr1;
272 switch (oper) {
273 case OpLess:
274 s << " < ";
275 break;
276 case OpGreater:
277 s << " > ";
278 break;
279 case OpLessEq:
280 s << " <= ";
281 break;
282 case OpGreaterEq:
283 s << " >= ";
284 break;
285 case OpInstanceOf:
286 s << " instanceof ";
287 break;
288 case OpIn:
289 s << " in ";
290 break;
291 default:
292 ;
293 }
294 s << expr2;
295}
296
297void EqualNode::streamTo(SourceStream &s) const
298{
299 s << expr1;
300 switch (oper) {
301 case OpEqEq:
302 s << " == ";
303 break;
304 case OpNotEq:
305 s << " != ";
306 break;
307 case OpStrEq:
308 s << " === ";
309 break;
310 case OpStrNEq:
311 s << " !== ";
312 break;
313 default:
314 ;
315 }
316 s << expr2;
317}
318
319void BitOperNode::streamTo(SourceStream &s) const
320{
321 s << expr1;
322 if (oper == OpBitAnd)
323 s << " & ";
324 else if (oper == OpBitXOr)
325 s << " ^ ";
326 else
327 s << " | ";
328 s << expr2;
329}
330
331void BinaryLogicalNode::streamTo(SourceStream &s) const
332{
333 s << expr1 << (oper == OpAnd ? " && " : " || ") << expr2;
334}
335
336void ConditionalNode::streamTo(SourceStream &s) const
337{
338 s << logical << " ? " << expr1 << " : " << expr2;
339}
340
341void AssignNode::streamTo(SourceStream &s) const
342{
343 s << left;
344 const char *opStr;
345 switch (oper) {
346 case OpEqual:
347 opStr = " = ";
348 break;
349 case OpMultEq:
350 opStr = " *= ";
351 break;
352 case OpDivEq:
353 opStr = " /= ";
354 break;
355 case OpPlusEq:
356 opStr = " += ";
357 break;
358 case OpMinusEq:
359 opStr = " -= ";
360 break;
361 case OpLShift:
362 opStr = " <<= ";
363 break;
364 case OpRShift:
365 opStr = " >>= ";
366 break;
367 case OpURShift:
368 opStr = " >>= ";
369 break;
370 case OpAndEq:
371 opStr = " &= ";
372 break;
373 case OpXOrEq:
374 opStr = " ^= ";
375 break;
376 case OpOrEq:
377 opStr = " |= ";
378 break;
379 case OpModEq:
380 opStr = " %= ";
381 break;
382 default:
383 opStr = " ?= ";
384 }
385 s << opStr << expr;
386}
387
388void CommaNode::streamTo(SourceStream &s) const
389{
390 s << expr1 << ", " << expr2;
391}
392
393void StatListNode::streamTo(SourceStream &s) const
394{
395 for (const StatListNode *n = this; n; n = n->list)
396 s << n->statement;
397}
398
399void AssignExprNode::streamTo(SourceStream &s) const
400{
401 s << " = " << expr;
402}
403
404void VarDeclNode::streamTo(SourceStream &s) const
405{
406 s << ident << init;
407}
408
409void VarDeclListNode::streamTo(SourceStream &s) const
410{
411 s << var;
412 for (VarDeclListNode *n = list; n; n = n->list)
413 s << ", " << n->var;
414}
415
416void VarStatementNode::streamTo(SourceStream &s) const
417{
418 s << SourceStream::Endl << "var " << list << ";";
419}
420
421void BlockNode::streamTo(SourceStream &s) const
422{
423 s << SourceStream::Endl << "{" << SourceStream::Indent
424 << source << SourceStream::Unindent << SourceStream::Endl << "}";
425}
426
427void EmptyStatementNode::streamTo(SourceStream &s) const
428{
429 s << SourceStream::Endl << ";";
430}
431
432void ExprStatementNode::streamTo(SourceStream &s) const
433{
434 s << SourceStream::Endl << expr << ";";
435}
436
437void IfNode::streamTo(SourceStream &s) const
438{
439 s << SourceStream::Endl << "if (" << expr << ")" << SourceStream::Indent
440 << statement1 << SourceStream::Unindent;
441 if (statement2)
442 s << SourceStream::Endl << "else" << SourceStream::Indent
443 << statement2 << SourceStream::Unindent;
444}
445
446void DoWhileNode::streamTo(SourceStream &s) const
447{
448 s << SourceStream::Endl << "do " << SourceStream::Indent
449 << statement << SourceStream::Unindent << SourceStream::Endl
450 << "while (" << expr << ");";
451}
452
453void WhileNode::streamTo(SourceStream &s) const
454{
455 s << SourceStream::Endl << "while (" << expr << ")" << SourceStream::Indent
456 << statement << SourceStream::Unindent;
457}
458
459void ForNode::streamTo(SourceStream &s) const
460{
461 s << SourceStream::Endl << "for ("
462 << expr1 // TODO: doesn't properly do "var i = 0"
463 << "; " << expr2
464 << "; " << expr3
465 << ")" << SourceStream::Indent << statement << SourceStream::Unindent;
466}
467
468void ForInNode::streamTo(SourceStream &s) const
469{
470 s << SourceStream::Endl << "for (";
471 if (varDecl)
472 s << "var " << varDecl;
473 if (init)
474 s << " = " << init;
475 s << " in " << expr << ")" << SourceStream::Indent
476 << statement << SourceStream::Unindent;
477}
478
479void ContinueNode::streamTo(SourceStream &s) const
480{
481 s << SourceStream::Endl << "continue";
482 if (!ident.isNull())
483 s << " " << ident;
484 s << ";";
485}
486
487void BreakNode::streamTo(SourceStream &s) const
488{
489 s << SourceStream::Endl << "break";
490 if (!ident.isNull())
491 s << " " << ident;
492 s << ";";
493}
494
495void ReturnNode::streamTo(SourceStream &s) const
496{
497 s << SourceStream::Endl << "return";
498 if (value)
499 s << " " << value;
500 s << ";";
501}
502
503void WithNode::streamTo(SourceStream &s) const
504{
505 s << SourceStream::Endl << "with (" << expr << ") "
506 << statement;
507}
508
509void CaseClauseNode::streamTo(SourceStream &s) const
510{
511 s << SourceStream::Endl;
512 if (expr)
513 s << "case " << expr;
514 else
515 s << "default";
516 s << ":" << SourceStream::Indent;
517 if (list)
518 s << list;
519 s << SourceStream::Unindent;
520}
521
522void ClauseListNode::streamTo(SourceStream &s) const
523{
524 for (const ClauseListNode *n = this; n; n = n->next())
525 s << n->clause();
526}
527
528void CaseBlockNode::streamTo(SourceStream &s) const
529{
530 for (const ClauseListNode *n = list1; n; n = n->next())
531 s << n->clause();
532 if (def)
533 s << def;
534 for (const ClauseListNode *n = list2; n; n = n->next())
535 s << n->clause();
536}
537
538void SwitchNode::streamTo(SourceStream &s) const
539{
540 s << SourceStream::Endl << "switch (" << expr << ") {"
541 << SourceStream::Indent << block << SourceStream::Unindent
542 << SourceStream::Endl << "}";
543}
544
545void LabelNode::streamTo(SourceStream &s) const
546{
547 s << SourceStream::Endl << label << ":" << SourceStream::Indent
548 << statement << SourceStream::Unindent;
549}
550
551void ThrowNode::streamTo(SourceStream &s) const
552{
553 s << SourceStream::Endl << "throw " << expr << ";";
554}
555
556void CatchNode::streamTo(SourceStream &s) const
557{
558 s << SourceStream::Endl << "catch (" << ident << ")" << block;
559}
560
561void FinallyNode::streamTo(SourceStream &s) const
562{
563 s << SourceStream::Endl << "finally " << block;
564}
565
566void TryNode::streamTo(SourceStream &s) const
567{
568 s << "try " << block
569 << _catch
570 << _final;
571}
572
573void ParameterNode::streamTo(SourceStream &s) const
574{
575 s << id;
576 for (ParameterNode *n = next; n; n = n->next)
577 s << ", " << n->id;
578}
579
580void FuncDeclNode::streamTo(SourceStream &s) const {
581 s << "function " << ident << "(";
582 if (param)
583 s << param;
584 s << ")" << body;
585}
586
587void FuncExprNode::streamTo(SourceStream &s) const
588{
589 s << "function " << "("
590 << param
591 << ")" << body;
592}
593
594void SourceElementsNode::streamTo(SourceStream &s) const
595{
596 for (const SourceElementsNode *n = this; n; n = n->elements)
597 s << n->element;
598}
599
Note: See TracBrowser for help on using the repository browser.