tools/porting/src/rpp.h
changeset 0 1918ee327afb
child 4 3b1da2848fc7
equal deleted inserted replaced
-1:000000000000 0:1918ee327afb
       
     1 /****************************************************************************
       
     2 **
       
     3 ** Copyright (C) 2001-2004 Roberto Raggi
       
     4 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
       
     5 ** All rights reserved.
       
     6 ** Contact: Nokia Corporation (qt-info@nokia.com)
       
     7 **
       
     8 ** This file is part of the qt3to4 porting application of the Qt Toolkit.
       
     9 **
       
    10 ** $QT_BEGIN_LICENSE:LGPL$
       
    11 ** No Commercial Usage
       
    12 ** This file contains pre-release code and may not be distributed.
       
    13 ** You may use this file in accordance with the terms and conditions
       
    14 ** contained in the Technology Preview License Agreement accompanying
       
    15 ** this package.
       
    16 **
       
    17 ** GNU Lesser General Public License Usage
       
    18 ** Alternatively, this file may be used under the terms of the GNU Lesser
       
    19 ** General Public License version 2.1 as published by the Free Software
       
    20 ** Foundation and appearing in the file LICENSE.LGPL included in the
       
    21 ** packaging of this file.  Please review the following information to
       
    22 ** ensure the GNU Lesser General Public License version 2.1 requirements
       
    23 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
       
    24 **
       
    25 ** In addition, as a special exception, Nokia gives you certain additional
       
    26 ** rights.  These rights are described in the Nokia Qt LGPL Exception
       
    27 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
       
    28 **
       
    29 ** If you have questions regarding the use of this file, please contact
       
    30 ** Nokia at qt-info@nokia.com.
       
    31 **
       
    32 **
       
    33 **
       
    34 **
       
    35 **
       
    36 **
       
    37 **
       
    38 **
       
    39 ** $QT_END_LICENSE$
       
    40 **
       
    41 ****************************************************************************/
       
    42 
       
    43 #ifndef RPP_H
       
    44 #define RPP_H
       
    45 
       
    46 #include "tokenengine.h"
       
    47 #include "rpplexer.h"
       
    48 #include "tokens.h"
       
    49 #include "smallobject.h"
       
    50 #include <QHash>
       
    51 #include <QStringList>
       
    52 #include <QFile>
       
    53 #include <QByteArray>
       
    54 #include <QDir>
       
    55 #include <QMultiMap>
       
    56 #include <ctype.h>
       
    57 
       
    58 QT_BEGIN_NAMESPACE
       
    59 
       
    60 namespace Rpp
       
    61 {
       
    62 
       
    63 struct Item;
       
    64 struct ItemComposite;
       
    65 
       
    66 struct Source;
       
    67 
       
    68 struct Directive;
       
    69 struct EmptyDirective;
       
    70 struct ErrorDirective;
       
    71 struct PragmaDirective;
       
    72 struct IncludeDirective;
       
    73 struct ConditionalDirective;
       
    74 struct DefineDirective;
       
    75 struct UndefDirective;
       
    76 struct LineDirective;
       
    77 struct NonDirective;
       
    78 
       
    79 struct IfSection;
       
    80 struct IfLikeDirective;
       
    81 struct IfDirective;
       
    82 struct ElifDirective;
       
    83 struct IfdefLikeDirective;
       
    84 struct IfdefDirective;
       
    85 struct IfndefDirective;
       
    86 struct ElseDirective;
       
    87 struct EndifDirective;
       
    88 
       
    89 struct Text;
       
    90 struct Token;
       
    91 struct TokenComposite;
       
    92 struct IdToken;
       
    93 struct NonIdToken;
       
    94 struct PastingToken;
       
    95 struct LineComment;
       
    96 struct MultiLineComment;
       
    97 struct WhiteSpace;
       
    98 
       
    99 struct MacroDefinition;
       
   100 struct MacroFunctionDefinition;
       
   101 struct MacroParameters;
       
   102 struct MacroParameter;
       
   103 
       
   104 struct Expression;
       
   105 struct UnaryExpression;
       
   106 struct BinaryExpression;
       
   107 struct ConditionalExpression;
       
   108 
       
   109 struct StringLiteral;
       
   110 struct IntLiteral;
       
   111 struct MacroReference;
       
   112 struct MacroFunctionReference;
       
   113 struct MacroArguments;
       
   114 struct MacroArgument;
       
   115 
       
   116 struct Item
       
   117 {
       
   118     virtual ~Item() {}
       
   119 
       
   120     virtual Item *parent() const = 0;
       
   121 
       
   122     virtual ItemComposite *toItemComposite() const
       
   123     { return 0; }
       
   124 
       
   125     virtual Item *toItem() const
       
   126     { return const_cast<Item *>(this); }
       
   127 
       
   128     virtual Directive *toDirective() const
       
   129     { return 0; }
       
   130 
       
   131     virtual Text *toText() const
       
   132     { return 0; }
       
   133 
       
   134     virtual Token *toToken() const
       
   135     { return 0; }
       
   136 
       
   137     virtual Source *toSource() const
       
   138     { return 0; }
       
   139 
       
   140     virtual Expression *toExpression() const
       
   141     { return 0; }
       
   142 
       
   143     virtual IfSection *toIfSection() const
       
   144     { return 0; }
       
   145 
       
   146     // Text returns the original text for an item, e.g.
       
   147     // the way it is found in the source
       
   148     virtual TokenEngine::TokenSection text() const
       
   149      { return TokenEngine::TokenSection(); }
       
   150 
       
   151 protected:
       
   152     //using the default constructor for an item is
       
   153     //only allowded for subclasses.
       
   154     Item() {};
       
   155 };
       
   156 
       
   157 struct ItemComposite
       
   158 {
       
   159     virtual ~ItemComposite() {}
       
   160     virtual int count() const = 0;
       
   161     virtual Item *item(int index) const = 0;
       
   162     virtual void add(Item *item) = 0;
       
   163 /*
       
   164     Classes that inherit ItemComposite must implement this
       
   165     function themselves
       
   166     virtual ItemComposite *toItemComposite() const
       
   167     { return const_cast<ItemComposite *>(this); }
       
   168 */
       
   169 };
       
   170 
       
   171 struct Directive: public Item
       
   172 {
       
   173     inline Directive(Item *parent = 0)
       
   174         : m_parent(parent), m_numLines(0) {}
       
   175 
       
   176     virtual Item *parent() const
       
   177     { return m_parent; }
       
   178 
       
   179     inline void setParent(Item *parent)
       
   180     { m_parent = parent;}
       
   181 
       
   182     void setNumLines(const int numLines)
       
   183     {m_numLines = numLines;}
       
   184 
       
   185     virtual Directive *toDirective() const
       
   186     { return const_cast<Directive *>(this); }
       
   187 
       
   188     virtual EmptyDirective *toEmptyDirective() const
       
   189     { return 0; }
       
   190 
       
   191     virtual ErrorDirective *toErrorDirective() const
       
   192     { return 0; }
       
   193 
       
   194     virtual PragmaDirective *toPragmaDirective() const
       
   195     { return 0; }
       
   196 
       
   197     virtual IncludeDirective *toIncludeDirective() const
       
   198     { return 0; }
       
   199 
       
   200     virtual ConditionalDirective *toConditionalDirective() const
       
   201     { return 0; }
       
   202 
       
   203     virtual DefineDirective *toDefineDirective() const
       
   204     { return 0; }
       
   205 
       
   206     virtual UndefDirective *toUndefDirective() const
       
   207     { return 0; }
       
   208 
       
   209     virtual LineDirective *toLineDirective() const
       
   210     { return 0; }
       
   211 
       
   212     virtual NonDirective *toNonDirective() const
       
   213     { return 0; }
       
   214 
       
   215     void setTokenSection(TokenEngine::TokenSection section)
       
   216     { m_tokenSection = section; }
       
   217 
       
   218     TokenEngine::TokenSection text() const
       
   219     { return m_tokenSection; }
       
   220 
       
   221 protected:
       
   222     Item *m_parent;
       
   223     int m_numLines;
       
   224     TokenEngine::TokenSection m_tokenSection;
       
   225 };
       
   226 
       
   227 
       
   228 struct Token: public Item
       
   229 {
       
   230     inline Token(Item *parent = 0)
       
   231         : m_tokenIndex(0), m_parent(parent) {}
       
   232 
       
   233     virtual Item *parent() const
       
   234     { return m_parent; }
       
   235 
       
   236     virtual MacroArguments *toMacroArguments() const
       
   237     { return 0; }
       
   238 
       
   239     virtual IdToken *toIdToken() const
       
   240     { return 0; }
       
   241 
       
   242     virtual NonIdToken *toNonIdToken() const
       
   243     { return 0; }
       
   244 
       
   245     virtual LineComment *toLineComment() const
       
   246     { return 0; }
       
   247 
       
   248     virtual MultiLineComment *toMultiLineComment() const
       
   249     { return 0; }
       
   250 
       
   251     virtual WhiteSpace *toWhiteSpace() const
       
   252     { return 0; }
       
   253 
       
   254     virtual Token *toToken() const
       
   255     { return const_cast<Token *>(this); }
       
   256 
       
   257     void setToken(int tokenIndex)
       
   258     { m_tokenIndex = tokenIndex;}
       
   259 
       
   260     int index() const
       
   261     { return m_tokenIndex; }
       
   262 
       
   263 protected:
       
   264     int m_tokenIndex;
       
   265     Item *m_parent;
       
   266 };
       
   267 
       
   268 struct Text: public Item
       
   269 {
       
   270     inline Text(Item *parent = 0)
       
   271         : m_parent(parent) {}
       
   272 
       
   273     virtual Text *toText() const
       
   274     { return const_cast<Text *>(this); }
       
   275 
       
   276     virtual Item *parent() const
       
   277     { return m_parent; }
       
   278 
       
   279     void setTokenSection(TokenEngine::TokenSection tokenSection)
       
   280     {m_tokenSection = tokenSection; }
       
   281 
       
   282     TokenEngine::TokenSection text() const
       
   283     { return m_tokenSection; }
       
   284 
       
   285     QVector<TokenEngine::TokenSection> cleanedText() const
       
   286     { return m_cleanedSection; }
       
   287 
       
   288     void setTokens( const QVector<Token *> &tokens )
       
   289     { m_tokens = tokens; }
       
   290 
       
   291     void addToken(Token *token)
       
   292     {m_tokens.append(token);}
       
   293 
       
   294     Token *token(int index) const
       
   295     {return m_tokens.at(index);}
       
   296 
       
   297     inline int count() const
       
   298     {return m_tokens.count();}
       
   299 
       
   300     QVector<Token *> tokenList() const
       
   301     { return m_tokens; }
       
   302 
       
   303 protected:
       
   304     Item *m_parent;
       
   305     TokenEngine::TokenSection m_tokenSection;    // all tokens
       
   306     QVector<TokenEngine::TokenSection> m_cleanedSection; //comments removed
       
   307     QVector<Token *> m_tokens;
       
   308 };
       
   309 
       
   310 struct IdToken: public Token
       
   311 {
       
   312     inline IdToken(Item *parent = 0)
       
   313         : Token(parent) {}
       
   314 
       
   315     virtual IdToken *toIdToken() const
       
   316     { return const_cast<IdToken *>(this); }
       
   317 };
       
   318 
       
   319 struct NonIdToken: public Token
       
   320 {
       
   321     inline  NonIdToken(Item *parent = 0)
       
   322         : Token(parent) {}
       
   323 
       
   324     virtual NonIdToken *toNonIdToken() const
       
   325     { return const_cast< NonIdToken *>(this); }
       
   326 };
       
   327 
       
   328 struct LineComment : public NonIdToken
       
   329 {
       
   330     inline LineComment(Item *parent = 0)
       
   331        : NonIdToken(parent) {}
       
   332 
       
   333     virtual LineComment *toLineComment() const
       
   334     { return const_cast< LineComment *>(this); }
       
   335 };
       
   336 
       
   337 struct MultiLineComment: public NonIdToken
       
   338 {
       
   339     inline MultiLineComment(Item *parent = 0)
       
   340         : NonIdToken(parent) {}
       
   341 
       
   342     virtual MultiLineComment *toMultiLineComment() const
       
   343     { return const_cast< MultiLineComment *>(this); }
       
   344 protected:
       
   345 };
       
   346 
       
   347 struct WhiteSpace: public NonIdToken
       
   348 {
       
   349     inline WhiteSpace(Item *parent = 0)
       
   350         : NonIdToken(parent) {}
       
   351 
       
   352     virtual WhiteSpace *toWhiteSpace() const
       
   353     { return const_cast<WhiteSpace *>(this); }
       
   354 };
       
   355 
       
   356 struct Source: public Item, public ItemComposite
       
   357 {
       
   358     Source(Item *parent = 0)
       
   359         :m_parent(parent) {}
       
   360 
       
   361     virtual Source *toSource() const
       
   362     { return const_cast<Source *>(this); }
       
   363 
       
   364     ItemComposite *toItemComposite() const
       
   365     { return const_cast<Source *>(this); }
       
   366 
       
   367     virtual int count() const
       
   368     { return m_items.count(); }
       
   369 
       
   370     virtual Item *item(int index) const
       
   371     {  return m_items.at(index); }
       
   372 
       
   373     inline QString fileName() const
       
   374     { return m_fileName; }
       
   375 
       
   376     void setFileName(const QString &fileName);
       
   377 
       
   378     virtual Item *parent() const
       
   379     { return m_parent; }
       
   380 
       
   381     inline void add(Item *item)
       
   382     {  m_items.append(item); }
       
   383 
       
   384 private:
       
   385     Item *m_parent;
       
   386     QVector<Item *> m_items;
       
   387     QString m_fileName;
       
   388 };
       
   389 
       
   390 struct EmptyDirective: public Directive
       
   391 {
       
   392     EmptyDirective(Item *item)
       
   393     : Directive(item) {}
       
   394 
       
   395     virtual EmptyDirective *toEmptyDirective() const
       
   396     { return const_cast<EmptyDirective *>(this); }
       
   397 };
       
   398 
       
   399 struct ErrorDirective: public Directive
       
   400 {
       
   401     ErrorDirective(Item *item)
       
   402     : Directive(item) {}
       
   403 
       
   404     virtual ErrorDirective *toErrorDirective() const
       
   405     { return const_cast<ErrorDirective *>(this); }
       
   406 };
       
   407 
       
   408 struct PragmaDirective: public Directive
       
   409 {
       
   410     PragmaDirective(Item *item)
       
   411     : Directive(item) {}
       
   412 
       
   413     virtual PragmaDirective *toPragmaDirective() const
       
   414     { return const_cast<PragmaDirective *>(this); }
       
   415 };
       
   416 
       
   417 struct IncludeDirective: public Directive
       
   418 {
       
   419     enum IncludeType {QuoteInclude, AngleBracketInclude};
       
   420 
       
   421     IncludeDirective(Item *item)
       
   422     : Directive(item), m_includeType(QuoteInclude) {}
       
   423 
       
   424     IncludeDirective() : Directive() {}
       
   425 
       
   426     virtual IncludeDirective *toIncludeDirective() const
       
   427     { return const_cast<IncludeDirective *>(this); }
       
   428 
       
   429     void setFilenameTokens(const TokenEngine::TokenList &filenameTokens)
       
   430     { m_filenameTokens = filenameTokens; }
       
   431 
       
   432     TokenEngine::TokenList filenameTokens() const
       
   433     { return m_filenameTokens; }
       
   434 
       
   435     void setFilename(const QByteArray &filename)
       
   436     { m_filename = filename; }
       
   437 
       
   438     QByteArray filename() const
       
   439     { return m_filename;}
       
   440 
       
   441     void setIncludeType(IncludeType includeType)
       
   442     { m_includeType = includeType; }
       
   443 
       
   444     IncludeType includeType() const
       
   445     { return m_includeType; }
       
   446 private:
       
   447     TokenEngine::TokenList m_filenameTokens;
       
   448     QByteArray m_filename;
       
   449     IncludeType m_includeType;
       
   450 };
       
   451 
       
   452 struct ConditionalDirective: public Directive, public ItemComposite
       
   453 {
       
   454     inline ConditionalDirective(Item *parent = 0)
       
   455     :Directive(parent) {}
       
   456 
       
   457     virtual ConditionalDirective *toConditionalDirective() const
       
   458     { return const_cast<ConditionalDirective *>(this); }
       
   459 
       
   460     ItemComposite *toItemComposite() const
       
   461     { return const_cast<ConditionalDirective *>(this); }
       
   462 
       
   463     virtual IfDirective *toIfDirective() const
       
   464     { return 0; }
       
   465 
       
   466     virtual IfdefDirective *toIfdefDirective() const
       
   467     { return 0; }
       
   468 
       
   469     virtual IfndefDirective *toIfndefDirective() const
       
   470     { return 0; }
       
   471 
       
   472     virtual ElifDirective *toElifDirective() const
       
   473     { return 0; }
       
   474 
       
   475     virtual ElseDirective *toElseDirective() const
       
   476     { return 0; }
       
   477 
       
   478     int count() const
       
   479     { return m_items.count(); }
       
   480 
       
   481     Item *item(int index) const
       
   482     { return m_items.at(index); }
       
   483 
       
   484     void add(Item *item)
       
   485     { m_items.append(item); }
       
   486 protected:
       
   487     QVector<Item *> m_items;
       
   488 };
       
   489 
       
   490 struct IfSection: public Item, public ItemComposite
       
   491 {
       
   492     IfSection(Item *parent)
       
   493     :m_parent(parent), m_ifGroup(0), m_elseGroup(0), m_endifLine(0) {}
       
   494 
       
   495     IfSection *toIfSection() const
       
   496     { return const_cast<IfSection *>(this); }
       
   497 
       
   498     ItemComposite *toItemComposite() const
       
   499     { return const_cast<IfSection *>(this); }
       
   500 
       
   501     void setParent(Item *parent)
       
   502     { m_parent = parent; }
       
   503 
       
   504     Item *parent() const
       
   505     { return m_parent; }
       
   506 
       
   507     void setIfGroup(ConditionalDirective *ifGroup)
       
   508     { m_ifGroup = ifGroup; m_items.append(ifGroup); }
       
   509 
       
   510     ConditionalDirective *ifGroup() const
       
   511     { return m_ifGroup; }
       
   512 
       
   513     void addElifGroup(ConditionalDirective *elifGroup)
       
   514     { m_elifGroups.append(elifGroup); m_items.append(elifGroup); }
       
   515 
       
   516     QVector<ConditionalDirective *> elifGroups() const
       
   517     { return m_elifGroups; }
       
   518 
       
   519     void setElseGroup(ConditionalDirective *elseGroup)
       
   520     { m_elseGroup = elseGroup; m_items.append(elseGroup); }
       
   521 
       
   522     ConditionalDirective *elseGroup() const
       
   523     { return m_elseGroup; }
       
   524 
       
   525     void setEndifLine(Directive *endifLine)
       
   526     { m_endifLine = endifLine; m_items.append(endifLine); }
       
   527 
       
   528     Directive *endifLine() const
       
   529     { return m_endifLine; }
       
   530 
       
   531     int count() const
       
   532     { return m_items.count(); }
       
   533 
       
   534     Item *item(int index) const
       
   535     { return m_items.at(index);}
       
   536 
       
   537  private:
       
   538     void add(Item *item)
       
   539     { Q_UNUSED(item); }
       
   540 
       
   541     Item *m_parent;
       
   542     QVector<Item *> m_items;
       
   543     ConditionalDirective *m_ifGroup;
       
   544     QVector<ConditionalDirective *> m_elifGroups;
       
   545     ConditionalDirective *m_elseGroup;
       
   546     Directive *m_endifLine;
       
   547 };
       
   548 
       
   549 struct Expression: public Item
       
   550 {
       
   551     enum Operator
       
   552     {
       
   553         LtEqOp = 300,
       
   554         GtEqOp,
       
   555         LtOp,
       
   556         GtOp,
       
   557         EqOp,
       
   558         NotEqOp,
       
   559         OrOp,
       
   560         AndOp,
       
   561         LShiftOp,
       
   562         RShiftOp
       
   563     };
       
   564 
       
   565     inline Expression(Item *parent = 0)
       
   566         : m_parent(parent) {}
       
   567 
       
   568     inline Expression *parentExpression() const
       
   569     { return m_parent ? m_parent->toExpression() : 0; }
       
   570 
       
   571     virtual Item *parent() const
       
   572     { return m_parent; }
       
   573 
       
   574     virtual Expression *toExpression() const
       
   575     { return const_cast<Expression *>(this); }
       
   576 
       
   577     virtual UnaryExpression *toUnaryExpression() const
       
   578     { return 0; }
       
   579 
       
   580     virtual BinaryExpression *toBinaryExpression() const
       
   581     { return 0; }
       
   582 
       
   583     virtual StringLiteral *toStringLiteral() const
       
   584     { return 0; }
       
   585 
       
   586     virtual IntLiteral *toIntLiteral() const
       
   587     { return 0; }
       
   588 
       
   589     virtual MacroReference *toMacroReference() const
       
   590     { return 0; }
       
   591 
       
   592     virtual MacroFunctionReference *toMacroFunctionReference() const
       
   593     { return 0; }
       
   594 
       
   595     virtual ConditionalExpression *toConditionalExpression() const
       
   596     { return 0; }
       
   597 
       
   598     int evaluate(bool *ok = 0);
       
   599 
       
   600 private:
       
   601     Item *m_parent;
       
   602 };
       
   603 
       
   604 struct StringLiteral: public Expression
       
   605 {
       
   606     inline StringLiteral(const QByteArray &value, Item *parent)
       
   607         : Expression(parent), m_value(value) {}
       
   608 
       
   609     QByteArray value() const
       
   610     { return m_value; }
       
   611 
       
   612     virtual StringLiteral *toStringLiteral() const
       
   613     { return const_cast<StringLiteral *>(this); }
       
   614 
       
   615 private:
       
   616     QByteArray m_value;
       
   617 };
       
   618 
       
   619 struct IntLiteral: public Expression
       
   620 {
       
   621     inline IntLiteral(int value, Item *parent = 0)
       
   622         : Expression(parent), m_value(value) {}
       
   623 
       
   624     inline int value() const
       
   625     { return m_value; }
       
   626 
       
   627     virtual IntLiteral *toIntLiteral() const
       
   628     { return const_cast<IntLiteral *>(this); }
       
   629 
       
   630 private:
       
   631     int m_value;
       
   632 };
       
   633 
       
   634 struct MacroReference: public Expression
       
   635 {
       
   636     enum Type {
       
   637         DefinedRef,    //#if defined(foo)
       
   638         ValueRef
       
   639     };
       
   640 
       
   641     inline MacroReference(const TokenEngine::TokenList &name, Type type, Item *parent = 0)
       
   642         : Expression(parent), m_type(type), m_name(name) {}
       
   643 
       
   644     virtual MacroReference *toMacroReference() const
       
   645     { return const_cast<MacroReference *>(this); }
       
   646 
       
   647     inline TokenEngine::TokenList name() const
       
   648     { return m_name; }
       
   649 
       
   650     inline void setName(const TokenEngine::TokenList &name)
       
   651     { m_name = name; }
       
   652 
       
   653     inline int type() const
       
   654     { return m_type; }
       
   655 
       
   656 private:
       
   657     int m_type;
       
   658     TokenEngine::TokenList m_name;
       
   659 };
       
   660 
       
   661 struct MacroFunctionReference: public Expression
       
   662 {
       
   663     MacroFunctionReference(const QByteArray &name, Item *parent);
       
   664 
       
   665     inline QByteArray name() const
       
   666     { return m_name; }
       
   667 
       
   668     inline void setName(const QByteArray &name)
       
   669     { m_name = name; }
       
   670 
       
   671     inline MacroArguments *arguments() const
       
   672     { return m_arguments; }
       
   673 
       
   674     virtual MacroFunctionReference *toMacroFunctionReference() const
       
   675     { return const_cast<MacroFunctionReference *>(this); }
       
   676 
       
   677 private:
       
   678     QByteArray m_name;
       
   679     MacroArguments *m_arguments;
       
   680 };
       
   681 
       
   682 struct UnaryExpression: public Expression
       
   683 {
       
   684      inline UnaryExpression(int op, Expression *e, Expression *parent = 0)
       
   685         : Expression(parent), m_op(op), m_expression(e) {}
       
   686 
       
   687     inline int op() const
       
   688     { return m_op; }
       
   689 
       
   690     inline Expression *expression() const
       
   691     { return m_expression; }
       
   692 
       
   693     virtual UnaryExpression *toUnaryExpression() const
       
   694     { return const_cast<UnaryExpression *>(this); }
       
   695 
       
   696 private:
       
   697     int m_op;
       
   698     Expression *m_expression;
       
   699 };
       
   700 
       
   701 struct BinaryExpression: public Expression
       
   702 {
       
   703    inline BinaryExpression(int op, Expression *left, Expression *right, Expression *parent = 0)
       
   704         : Expression(parent),
       
   705           m_op(op),
       
   706           m_leftExpression(left),
       
   707           m_rightExpression(right) {}
       
   708 
       
   709     inline int op() const
       
   710     { return m_op; }
       
   711 
       
   712     inline Expression *leftExpression() const
       
   713     { return m_leftExpression; }
       
   714 
       
   715     inline Expression *rightExpression() const
       
   716     { return m_rightExpression; }
       
   717 
       
   718     virtual BinaryExpression *toBinaryExpression() const
       
   719     { return const_cast<BinaryExpression *>(this); }
       
   720 
       
   721 private:
       
   722     int m_op;
       
   723     Expression *m_leftExpression;
       
   724     Expression *m_rightExpression;
       
   725 };
       
   726 
       
   727 struct ConditionalExpression: public Expression
       
   728 {
       
   729     inline ConditionalExpression(Expression *condition, Expression *left, Expression *right, Expression *parent = 0)
       
   730         : Expression(parent),
       
   731           m_condition(condition),
       
   732           m_leftExpression(left),
       
   733           m_rightExpression(right) {}
       
   734 
       
   735     inline Expression *condition() const
       
   736     { return m_condition; }
       
   737 
       
   738     inline Expression *leftExpression() const
       
   739     { return m_leftExpression; }
       
   740 
       
   741     inline Expression *rightExpression() const
       
   742     { return m_rightExpression; }
       
   743 
       
   744     virtual ConditionalExpression *toConditionalExpression() const
       
   745     { return const_cast<ConditionalExpression *>(this); }
       
   746 
       
   747 private:
       
   748     Expression *m_condition;
       
   749     Expression *m_leftExpression;
       
   750     Expression *m_rightExpression;
       
   751 };
       
   752 
       
   753 
       
   754 struct IfLikeDirective: public ConditionalDirective
       
   755 {
       
   756     inline IfLikeDirective(Item *parent = 0)
       
   757         :ConditionalDirective(parent), m_expression(0) {}
       
   758 
       
   759     void setExpression(Expression *expression)
       
   760     { m_expression  = expression; }
       
   761 
       
   762     Expression *expression() const
       
   763     { return m_expression; }
       
   764 
       
   765 protected:
       
   766     Expression *m_expression;
       
   767 };
       
   768 
       
   769 struct IfDirective: public IfLikeDirective
       
   770 {
       
   771     inline IfDirective(Item *parent = 0)
       
   772         :IfLikeDirective(parent) {}
       
   773 
       
   774     virtual IfDirective *toIfDirective() const
       
   775     { return const_cast<IfDirective *>(this); }
       
   776 };
       
   777 
       
   778 
       
   779 struct ElifDirective: public IfLikeDirective
       
   780 {
       
   781     inline ElifDirective(Item *parent = 0)
       
   782     :IfLikeDirective(parent) {}
       
   783 
       
   784     virtual ElifDirective *toElifDirective() const
       
   785     { return const_cast<ElifDirective *>(this); }
       
   786 };
       
   787 
       
   788 struct IfdefLikeDirective: public ConditionalDirective
       
   789 {
       
   790     inline IfdefLikeDirective(Item *parent = 0)
       
   791     :ConditionalDirective(parent) {}
       
   792 
       
   793     inline TokenEngine::TokenList identifier() const
       
   794     { return m_identifier; }
       
   795 
       
   796     inline void setIdentifier(const TokenEngine::TokenList &identifier)
       
   797     { m_identifier = identifier; }
       
   798 protected:
       
   799     TokenEngine::TokenList m_identifier;
       
   800 };
       
   801 
       
   802 struct IfdefDirective: public IfdefLikeDirective
       
   803 {
       
   804     IfdefDirective(Item *parent)
       
   805     :IfdefLikeDirective(parent) {}
       
   806 
       
   807     virtual IfdefDirective *toIfdefDirective() const
       
   808     { return const_cast<IfdefDirective *>(this); }
       
   809 };
       
   810 
       
   811 struct IfndefDirective: public IfdefLikeDirective
       
   812 {
       
   813     inline IfndefDirective(Item *parent)
       
   814     :IfdefLikeDirective(parent) {}
       
   815 
       
   816     virtual IfndefDirective *toIfndefDirective() const
       
   817     { return const_cast<IfndefDirective *>(this); }
       
   818 };
       
   819 
       
   820 struct ElseDirective: public ConditionalDirective
       
   821 {
       
   822     ElseDirective(Item *parent)
       
   823     :ConditionalDirective(parent) {}
       
   824 
       
   825     virtual ElseDirective *toElseDirective() const
       
   826     { return const_cast<ElseDirective *>(this); }
       
   827 };
       
   828 
       
   829 struct EndifDirective : public Directive
       
   830 {
       
   831     EndifDirective(Item *parent)
       
   832     :Directive(parent) {}
       
   833 
       
   834     EndifDirective *toEndifDirective() const
       
   835     { return const_cast<EndifDirective *>(this); }
       
   836 };
       
   837 
       
   838 struct DefineDirective: public Directive
       
   839 {
       
   840     DefineDirective(Item *parent)
       
   841     : Directive(parent) {};
       
   842 
       
   843     inline TokenEngine::TokenList identifier() const
       
   844     { return m_identifier; }
       
   845 
       
   846     inline void setIdentifier(TokenEngine::TokenList identifier)
       
   847     { m_identifier = identifier; }
       
   848 
       
   849     inline void setReplacementList(TokenEngine::TokenList replacementList)
       
   850     { m_replacementList = replacementList; }
       
   851 
       
   852     inline TokenEngine::TokenList replacementList() const
       
   853     { return m_replacementList; }
       
   854 
       
   855     virtual DefineDirective *toDefineDirective() const
       
   856     { return const_cast<DefineDirective *>(this); }
       
   857 
       
   858     virtual MacroDefinition *toMacroDefinition() const
       
   859     { return 0; }
       
   860 
       
   861     virtual MacroFunctionDefinition *toMacroFunctionDefinition() const
       
   862     { return 0; }
       
   863 private:
       
   864     TokenEngine::TokenList m_identifier;
       
   865     TokenEngine::TokenList m_replacementList;
       
   866 };
       
   867 
       
   868 struct MacroDefinition: public DefineDirective
       
   869 {
       
   870     MacroDefinition(Item *parent)
       
   871     : DefineDirective(parent) {};
       
   872 
       
   873     virtual MacroDefinition *toMacroDefinition() const
       
   874     { return const_cast<MacroDefinition *>(this); }
       
   875 };
       
   876 
       
   877 struct MacroFunctionDefinition: public DefineDirective
       
   878 {
       
   879     MacroFunctionDefinition(Item *parent)
       
   880     : DefineDirective(parent) {}
       
   881 
       
   882     virtual MacroFunctionDefinition *toMacroFunctionDefinition() const
       
   883     { return const_cast<MacroFunctionDefinition *>(this); }
       
   884 
       
   885     void setParameters(TokenEngine::TokenList macroParameters)
       
   886     { m_parameters = macroParameters;}
       
   887 
       
   888     inline TokenEngine::TokenList parameters() const
       
   889     { return m_parameters; }
       
   890 
       
   891 private:
       
   892     TokenEngine::TokenList m_parameters;
       
   893 };
       
   894 
       
   895 struct MacroParameter: public Item
       
   896 {
       
   897     inline MacroParameter(Item *parent)
       
   898         : m_parent(parent) {}
       
   899 
       
   900     inline QByteArray name() const
       
   901     { return m_name; }
       
   902 
       
   903     inline void setName(const QByteArray &name)
       
   904     { m_name = name; }
       
   905 
       
   906     virtual Item *parent() const
       
   907     { return m_parent; }
       
   908 
       
   909 private:
       
   910     Item *m_parent;
       
   911     QByteArray m_name;
       
   912 };
       
   913 
       
   914 struct MacroParameters: public Item, public ItemComposite
       
   915 {
       
   916     MacroParameters(MacroFunctionDefinition *parent)
       
   917         : m_parent(parent) {}
       
   918 
       
   919     ItemComposite *toItemComposite() const
       
   920     { return const_cast<MacroParameters *>(this); }
       
   921 
       
   922     virtual Item *parent() const
       
   923     { return m_parent; }
       
   924 
       
   925     virtual int count() const
       
   926     { return m_items.count(); }
       
   927 
       
   928     virtual Item *item(int index) const
       
   929     { return m_items.at(index); }
       
   930 
       
   931     void addParameter(MacroParameter *param)
       
   932     { Q_ASSERT(param->parent() == this); m_items.append(param); }
       
   933 
       
   934     int indexOf(const QByteArray &param) const
       
   935     {
       
   936         for (int i=0; i<m_items.count(); ++i) {
       
   937          //   cout <<"checking |" << param.constData() << "| against |" << m_items.at(i)->name().constData() <<"|" << endl;
       
   938             if (m_items.at(i)->name() == param)
       
   939                 return i;
       
   940         }
       
   941         return -1;
       
   942     }
       
   943 
       
   944     inline bool contains(const QByteArray &param) const
       
   945     { return indexOf(param) != -1; }
       
   946 /*
       
   947     void add(const QByteArray &param)
       
   948     {
       
   949         MacroParameter *p = createNode<MacroParameter>(this);
       
   950         p->setName(param);
       
   951         addParameter(p);
       
   952     }
       
   953 */
       
   954 private:
       
   955     MacroFunctionDefinition *m_parent;
       
   956     QVector<MacroParameter*> m_items;
       
   957 };
       
   958 
       
   959 struct UndefDirective: public Directive
       
   960 {
       
   961     UndefDirective(Item *parent)
       
   962     :Directive(parent) {}
       
   963 
       
   964     inline TokenEngine::TokenList identifier() const
       
   965     { return m_identifier; }
       
   966 
       
   967     inline void setIdentifier(const TokenEngine::TokenList &identifier)
       
   968     { m_identifier = identifier; }
       
   969 
       
   970     virtual UndefDirective *toUndefDirective() const
       
   971     { return const_cast<UndefDirective *>(this); }
       
   972 private:
       
   973     TokenEngine::TokenList m_identifier;
       
   974 };
       
   975 
       
   976 struct LineDirective: public Directive
       
   977 {
       
   978     LineDirective(Item *parent)
       
   979     :Directive(parent) {}
       
   980 
       
   981     virtual LineDirective *toLineDirective() const
       
   982     { return const_cast<LineDirective *>(this); }
       
   983 };
       
   984 
       
   985 struct NonDirective: public Directive
       
   986 {
       
   987     NonDirective(Item *parent)
       
   988     :Directive(parent) {}
       
   989 
       
   990     virtual NonDirective *toNonDirective() const
       
   991     { return const_cast<NonDirective *>(this); }
       
   992 };
       
   993 
       
   994 class Preprocessor : public QObject
       
   995 {
       
   996 Q_OBJECT
       
   997 public:
       
   998     Preprocessor();
       
   999     Source *parse(const TokenEngine::TokenContainer &tokenContainer,
       
  1000                   const QVector<Type> &tokenTypeList, TypedPool<Item> *memoryPool);
       
  1001 signals:
       
  1002     void error(const QString type, const QString message);
       
  1003 private:
       
  1004     bool parseGroup(Item *node);
       
  1005     bool parseGroupPart(Item *node);
       
  1006 
       
  1007     bool parseIfSection(Item *node);
       
  1008     bool parseNonDirective(Item *node);
       
  1009     bool parseTextLine(Item *node);
       
  1010 
       
  1011     bool parseIfGroup(IfSection *node);
       
  1012     bool parseElifGroups(IfSection *node);
       
  1013     bool parseElifGroup(IfSection *node);
       
  1014     bool parseElseGroup(IfSection *node);
       
  1015     bool parseEndifLine(IfSection *node);
       
  1016 
       
  1017     bool parseIfdefLikeDirective(IfdefLikeDirective *node);
       
  1018     bool parseIfLikeDirective(IfLikeDirective *node);
       
  1019 
       
  1020     bool parseDefineDirective(Item *node);
       
  1021     bool parseUndefDirective(Item *node);
       
  1022     bool parseIncludeDirective(Item *node);
       
  1023     bool parseErrorDirective(Item *node);
       
  1024     bool parsePragmaDirective(Item*node);
       
  1025 
       
  1026     TokenEngine::TokenSection readLine();
       
  1027     inline bool isValidIndex(const int index) const;
       
  1028     inline bool isWhiteSpace(const int index) const;
       
  1029     Type lookAhead() const;
       
  1030     Type lookAheadSkipHash() const;
       
  1031     inline int skipWhiteSpaceAndComments() const;
       
  1032     inline int skipWhiteSpaceCommentsHash() const;
       
  1033     QVector<int> cleanEscapedNewLines(const TokenEngine::TokenSection &tokenSection) const;
       
  1034     QVector<int> cleanTokenRange(const TokenEngine::TokenSection &tokenSection) const;
       
  1035 
       
  1036     Source *m_source;
       
  1037     TokenEngine::TokenContainer m_tokenContainer;
       
  1038     QVector<Type> m_tokenTypeList;
       
  1039     TypedPool<Item> *m_memoryPool;
       
  1040     int lexerTokenIndex;
       
  1041     int numTokens;
       
  1042 };
       
  1043 
       
  1044 /*
       
  1045     T must be a subclass of Item, parent must implment
       
  1046     the ItemComposite interface
       
  1047 */
       
  1048 template <typename T>
       
  1049 T *createNode(TypedPool<Item> *memPool, Item *parent)
       
  1050 {
       
  1051     Q_ASSERT(parent);
       
  1052     T* node = new (memPool->allocate(sizeof(T))) T(parent);
       
  1053     Q_ASSERT(node);
       
  1054     return node;
       
  1055 }
       
  1056 
       
  1057 template <typename T>
       
  1058 T *createNode(TypedPool<Item> *memPool)
       
  1059 {
       
  1060     T* node = new (memPool->allocate(sizeof(T))) T(0);
       
  1061     Q_ASSERT(node);
       
  1062     return node;
       
  1063 }
       
  1064 
       
  1065 
       
  1066 QByteArray visitGetText(Item *item);
       
  1067 
       
  1068 } // namespace Rpp
       
  1069 
       
  1070 QT_END_NAMESPACE
       
  1071 
       
  1072 #endif