[opengtl-commits] [497] * don't allow to affect values to constant

[ Thread Index | Date Index | More lists.tuxfamily.org/opengtl-commits Archives ]


Revision: 497
Author:   cyrille
Date:     2008-11-26 00:19:54 +0100 (Wed, 26 Nov 2008)

Log Message:
-----------
* don't allow to affect values to constant
* support for access to struct member and array values in constant expressions

Modified Paths:
--------------
    trunk/OpenGTL/OpenCTL/OpenCTL/Program.cpp
    trunk/OpenGTL/OpenCTL/tests/parse/CMakeLists.txt
    trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.cpp
    trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.h
    trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.cpp
    trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.h
    trunk/OpenGTL/OpenGTL/GTLCore/AST/FunctionDeclaration.cpp
    trunk/OpenGTL/OpenGTL/GTLCore/AST/Statement.cpp
    trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.cpp
    trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.h
    trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.cpp
    trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.h
    trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.cpp
    trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.h
    trunk/OpenGTL/OpenGTL/GTLCore/Visitor_p.cpp
    trunk/OpenGTL/OpenShiva/OpenShiva/CodeGenerator_p.cpp
    trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.cpp
    trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.h

Added Paths:
-----------
    trunk/OpenGTL/OpenCTL/tests/parse/affect_constant.ctl
    trunk/OpenGTL/OpenCTL/tests/parse/function_expression_complex.ctl


Modified: trunk/OpenGTL/OpenCTL/OpenCTL/Program.cpp
===================================================================
--- trunk/OpenGTL/OpenCTL/OpenCTL/Program.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenCTL/OpenCTL/Program.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -192,9 +192,9 @@
           GTLCore::VariableNG* vng = 0;
           if(dstChannelsTypes[i] == GTLCore::Type::Half)
           {
-            vng = new GTLCore::VariableNG(GTLCore::Type::Float, false );
+            vng = new GTLCore::VariableNG(GTLCore::Type::Float, false, false );
           } else {
-            vng = new GTLCore::VariableNG(GTLCore::Type::Integer32, false );
+            vng = new GTLCore::VariableNG(GTLCore::Type::Integer32, false, false );
           }
           vng->initialise( gc, initialBlock, GTLCore::ExpressionResult(), std::list<llvm::Value*>());
           buffer[i] = vng;
@@ -216,9 +216,9 @@
     // Construct the "conditions" of the loop
       //   int i = 0;
       OCTL_DEBUG("int i = 0");
-      GTLCore::VariableNG* posSrc = new GTLCore::VariableNG( GTLCore::Type::Integer32, false);
+      GTLCore::VariableNG* posSrc = new GTLCore::VariableNG( GTLCore::Type::Integer32, false, false );
       posSrc->initialise( gc, initialBlock, GTLCore::ExpressionResult(cg.integerToConstant(0), GTLCore::Type::Integer32), std::list<llvm::Value*>());
-      GTLCore::VariableNG* posDst = new GTLCore::VariableNG( GTLCore::Type::Integer32, false);
+      GTLCore::VariableNG* posDst = new GTLCore::VariableNG( GTLCore::Type::Integer32, false, false );
       posDst->initialise( gc, initialBlock, GTLCore::ExpressionResult(cg.integerToConstant(0), GTLCore::Type::Integer32), std::list<llvm::Value*>());
       // i < size
       OCTL_DEBUG("i < size");

Modified: trunk/OpenGTL/OpenCTL/tests/parse/CMakeLists.txt
===================================================================
--- trunk/OpenGTL/OpenCTL/tests/parse/CMakeLists.txt	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenCTL/tests/parse/CMakeLists.txt	2008-11-25 23:19:54 UTC (rev 497)
@@ -54,6 +54,7 @@
   global_const_non_const_initializer.ctl
   function_output_not_variable.ctl
   function_out_of_scope.ctl
+  affect_constant.ctl
   )
 
 FOREACH( TEST_FILE ${TESTS_FAIL_FILES} )

Added: trunk/OpenGTL/OpenCTL/tests/parse/affect_constant.ctl
===================================================================
--- trunk/OpenGTL/OpenCTL/tests/parse/affect_constant.ctl	                        (rev 0)
+++ trunk/OpenGTL/OpenCTL/tests/parse/affect_constant.ctl	2008-11-25 23:19:54 UTC (rev 497)
@@ -0,0 +1,7 @@
+
+const int hello = 10;
+
+void testFunction()
+{
+  hello = 11;
+}

Added: trunk/OpenGTL/OpenCTL/tests/parse/function_expression_complex.ctl
===================================================================
--- trunk/OpenGTL/OpenCTL/tests/parse/function_expression_complex.ctl	                        (rev 0)
+++ trunk/OpenGTL/OpenCTL/tests/parse/function_expression_complex.ctl	2008-11-25 23:19:54 UTC (rev 497)
@@ -0,0 +1,12 @@
+
+struct MyStruct {
+  bool array[6];
+};
+
+void function() 
+{
+  bool vrai = true;
+  MyStruct myStruct = { { 10 <= (4+5 % 4), 3 < 5, 4 == 2 *4 +4, true, true || false, 10 / 10 == 1 } };
+  int var1 = 1 + ( 5 / 10 *4 % ( 3 & 4 + 8 ) );
+  int var2 = myStruct.array[0] + myStruct.array[1] + myStruct.array[2] + myStruct.array[3];
+}

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -186,6 +186,11 @@
   return _gc.codeGenerator()->createModuloExpression(bb, leftHandSide()->generateValue( _gc, bb), leftHandSide()->type(), rightHandSide()->generateValue( _gc, bb), rightHandSide()->type() );
 }
 
+AssignementBinaryExpression::AssignementBinaryExpression( AccessorExpression* lhs, Expression* rhs ) : BinaryExpression( lhs, rhs ), m_lhs(lhs)
+{
+  GTL_ASSERT(not lhs->isConstant() );
+}
+
 llvm::BasicBlock* AssignementBinaryExpression::generateStatement( GenerationContext& _gc, llvm::BasicBlock* _bb) const
 {
   GTL_ASSERT( m_lhs);

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.h
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.h	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/BinaryExpression.h	2008-11-25 23:19:54 UTC (rev 497)
@@ -265,9 +265,7 @@
      */
     class AssignementBinaryExpression : public BinaryExpression {
       public:
-        AssignementBinaryExpression( AccessorExpression* lhs, Expression* rhs ) : BinaryExpression( lhs, rhs ), m_lhs(lhs)
-        {
-        }
+        AssignementBinaryExpression( AccessorExpression* lhs, Expression* rhs );
         virtual llvm::BasicBlock* generateStatement( GenerationContext&, llvm::BasicBlock* ) const;
         virtual GTLCore::ExpressionResult generateValue( GenerationContext& _gc, llvm::BasicBlock* bb ) const;
       private:

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -116,3 +116,8 @@
 {
   GTL_ABORT("ConstantCoumpoundExpression can't be in a return statement");
 }
+
+Expression* ConstantCoumpoundExpression::expressionAt(unsigned int _idx )
+{
+  return m_expressions[ _idx ];
+}

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.h
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.h	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/ConstantCoumpoundExpression.h	2008-11-25 23:19:54 UTC (rev 497)
@@ -38,6 +38,7 @@
         virtual GTLCore::ExpressionResult generateValue( GenerationContext& _gc, llvm::BasicBlock* _bb ) const;
         int size() { return m_expressions.size(); }
         void markAsReturnExpression();
+        Expression* expressionAt(unsigned int _idx );
       private:
         std::vector<Expression*> m_expressions;
         const GTLCore::Type* m_type;

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/FunctionDeclaration.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/FunctionDeclaration.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/FunctionDeclaration.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -66,7 +66,7 @@
     // Create parameters variable NG
     const GTLCore::Type* type = m_parameters[i]->parameter().type();
     m_parametersVariable.push_back( new GTLCore::VariableNG( type,
-                                    ( type->dataType() == Type::STRUCTURE or type->dataType() == Type::ARRAY ) and ( not m_parameters[i]->parameter().output() ) ) );
+                                    ( type->dataType() == Type::STRUCTURE or type->dataType() == Type::ARRAY ) and ( not m_parameters[i]->parameter().output() ), false ) );
   }
   m_functionData = new Function::Data( parameters, minimumParameters );
   m_function = new Function( _name, _returnType, m_functionData );

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/Statement.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/Statement.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/Statement.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -87,7 +87,7 @@
 //--------------- VariableDeclaration ---------------//
 //---------------------------------------------------//
 
-VariableDeclaration::VariableDeclaration( const GTLCore::Type* type, Expression* initialiser, bool constant, const std::list<Expression*>& _initialSizes) : m_variable( new GTLCore::VariableNG(type, constant) ), m_initialiser(initialiser), m_initialSizes(_initialSizes), m_functionInitialiser(0)
+VariableDeclaration::VariableDeclaration( const GTLCore::Type* type, Expression* initialiser, bool constant, const std::list<Expression*>& _initialSizes) : m_variable( new GTLCore::VariableNG(type, constant, false) ), m_initialiser(initialiser), m_initialSizes(_initialSizes), m_functionInitialiser(0)
 {
   GTL_ASSERT( (not _initialSizes.empty() and type->dataType() == GTLCore::Type::ARRAY ) or _initialSizes.empty() );
 }

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -38,14 +38,14 @@
 
 using namespace GTLCore::AST;
 
-GlobalConstantDeclaration::GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, Expression* _initialiser, bool _constant) :
-    m_name( _name), m_initialiser(_initialiser), m_variable( new GTLCore::VariableNG( _type, true ) ), m_type(_type), m_constant(_constant)
+GlobalConstantDeclaration::GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, Expression* _initialiser, bool _dependant) :
+    m_name( _name), m_initialiser(_initialiser), m_variable( new GTLCore::VariableNG( _type, true, _dependant ) ), m_type(_type), m_constant(not _dependant)
 {
   GTL_ASSERT( _initialiser );
 }
 
-GlobalConstantDeclaration::GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, const std::list< int >& sizes,bool _constant) :
-    m_name( _name), m_initialiser(0), m_variable( new GTLCore::VariableNG( _type, true ) ), m_type(_type), m_sizes(sizes), m_constant(_constant)
+GlobalConstantDeclaration::GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, const std::list< int >& sizes, bool _dependant) :
+    m_name( _name), m_initialiser(0), m_variable( new GTLCore::VariableNG( _type, true, _dependant ) ), m_type(_type), m_sizes(sizes), m_constant(not _dependant)
 {
 }
 

Modified: trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.h
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.h	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/AST/Tree.h	2008-11-25 23:19:54 UTC (rev 497)
@@ -41,8 +41,8 @@
      */
     class GlobalConstantDeclaration {
       public:
-        GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, Expression* _initialiser, bool _constant);
-        GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, const std::list< int >& sizes,bool _constant);
+        GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, Expression* _initialiser, bool _dependant);
+        GlobalConstantDeclaration( const GTLCore::ScopedName& _name, const GTLCore::Type* _type, const std::list< int >& sizes,bool _dependant);
         ~GlobalConstantDeclaration();
         GTLCore::ScopedName name() const { return m_name; }
         const Expression* initialiser() const { return m_initialiser; }

Modified: trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -126,7 +126,7 @@
           {
             reportError("Constant '" + scopedName.toString() + "' has allready been declared", currentToken());
           } else {
-            AST::GlobalConstantDeclaration* gcd = new AST::GlobalConstantDeclaration( scopedName, type , expression, true );
+            AST::GlobalConstantDeclaration* gcd = new AST::GlobalConstantDeclaration( scopedName, type , expression, false );
             variablesManager()->declareConstant( scopedName, gcd->variable() );
             tree()->append( gcd );
           }
@@ -204,8 +204,74 @@
   }
 }
 
+AST::Expression* ParserBase::parseMemberArrayConstantExpression(AST::Expression* _expression)
+{
+  if( d->currentToken.type == Token::DOT or d->currentToken.type == Token::STARTBOXBRACKET )
+  {
+    // Check we have a coumpound expression
+    AST::ConstantCoumpoundExpression* coumpound = dynamic_cast<AST::ConstantCoumpoundExpression*>( _expression );
+    if( not coumpound )
+    {
+      getNextToken();
+      reportError( "Expected value of array, structure or vector type.", d->currentToken );
+      return 0;
+    }
+    // Compute the idx
+    int idx = -1;
+    if( d->currentToken.type == Token::DOT )
+    {
+      getNextToken();
+      if( d->currentToken.type == Token::SIZE )
+      {
+        return new AST::NumberExpression<int>( coumpound->size() );
+      } else if( isOfType( d->currentToken, Token::IDENTIFIER ) ) {
+        String name = d->currentToken.string;
+        getNextToken();
+        if( _expression->type()->dataType() == Type::STRUCTURE ) {
+          idx = structMemberNameToIdx( _expression->type(), name );
+        } else if( _expression->type()->dataType() == Type::VECTOR ) {
+          idx = vectorMemberNameToIdx( name );
+        } 
+      }
+    } else if( d->currentToken.type == Token::STARTBOXBRACKET )
+    {
+      getNextToken();
+      AST::Expression* expr = parseExpression( true );
+      GTL_ASSERT( expr->isConstant() );
+      expr = d->compiler->convertCenter()->createConvertExpression( expr, GTLCore::Type::Integer32 );
+      if( expr and expr->isConstant() )
+      {
+        GenerationContext gc( 0, 0, 0 ,0 );
+        llvm::ConstantInt* idxCST = dynamic_cast<llvm::ConstantInt*>( expr->generateValue( gc, 0).constant() );
+        GTL_ASSERT( idxCST );
+        idx = idxCST->getLimitedValue();
+      } else {
+        reportError( "Expected integer constant", d->currentToken );
+        return 0;
+      }
+      if( isOfType( d->currentToken, Token::ENDBOXBRACKET ) )
+      {
+        getNextToken();
+      }
+    } else {
+      GTL_ABORT("Impossible error.");
+    }
+    GTL_DEBUG( idx );
+    if( idx >= 0 and idx < coumpound->size() )
+    {
+      return parseMemberArrayConstantExpression( coumpound->expressionAt( idx ) );
+    } else {
+      reportError( "Invalid index.", d->currentToken );
+      return 0;
+    }
+  } else {
+    return _expression;
+  }
+}
+
 AST::AccessorExpression* ParserBase::parseMemberArrayExpression(AST::AccessorExpression* _expression, bool _constantExpression)
 {
+  GTL_ASSERT( not _constantExpression);
   if( d->currentToken.type == Token::DOT )
   {
     getNextToken();
@@ -228,34 +294,9 @@
           return new AST::FunctionMemberAccessorExpression(_expression, sfm, arguments);
         }
       } else if( _expression->type()->dataType() == Type::STRUCTURE ) {
-        int index = _expression->type()->d->memberToIndex( name );
-        if( index == -1 )
-        {
-          reportError("Unknown member: '" + name + "' for structure " + _expression->type()->structName(), d->currentToken );
-          delete _expression;
-          return 0;
-        } else {
-          return parseMemberArrayExpression( new AST::StructAccessorExpression( _expression ,  index ), _constantExpression);
-        }
+        return parseMemberArrayExpression( new AST::StructAccessorExpression( _expression ,  structMemberNameToIdx( _expression->type(), name ) ), _constantExpression);
       } else if( _expression->type()->dataType() == Type::VECTOR ) {
-        int index = -1;
-        GTL_DEBUG(name);
-        if( name == "x" or name == "r" ) {
-          index = 0;
-        } else if( name == "y" or name == "g"  ) {
-          index = 1;
-        } else if( name == "z" or name == "b"  ) {
-          index = 2;
-        } else if( name == "w" or name == "a"  ) {
-          index = 3;
-        }
-        if( index == -1 )
-        {
-          GTL_DEBUG("unexpected");
-          reportUnexpected( d->currentToken );
-        } else {
-          return new AST::ArrayAccessorExpression( _expression, new AST::NumberExpression<int>( index ) );
-        }
+        return new AST::ArrayAccessorExpression( _expression, new AST::NumberExpression<int>( vectorMemberNameToIdx( name ) ) );
       } else {
         GTL_DEBUG("unexpected");
         reportUnexpected( d->currentToken );
@@ -742,6 +783,7 @@
   {
     Token nameToken = d->currentToken;
     ScopedName name( d->nameSpace, d->currentToken.string );
+    startParsingFunction( name.name() );
     getNextToken();
     // Next is start bracket
     if( isOfType( d->currentToken, Token::STARTBRACKET ) )
@@ -878,6 +920,7 @@
         }
       }
     }
+    endParsingFunction( name.name() );
   }
 }
 
@@ -1253,7 +1296,7 @@
           {
             getNextToken();
             // Put the expr in a proxy to avoid double free when the AST tree is deleted
-            return new AST::ProxyExpression(  (*it)->initialiser() );
+            return new AST::ProxyExpression( parseMemberArrayConstantExpression( (*it)->initialiser() ) );
           }
         }
         AST::Expression* stdconst = d->compiler->standardConstant( d->currentToken.string );
@@ -1447,7 +1490,15 @@
       } else if(token.type == Token::DIVIDEEQUAL) {
         rhs = new AST::DivisionBinaryExpression( new AST::ProxyExpression(ve), rhs );
       }
-      return new AST::AssignementBinaryExpression( ve, rhs );
+      if( ve->isConstant() )
+      {
+        delete lhs;
+        delete rhs;
+        reportError("Left hand side of an assignement expression can't be a constant.", token);
+        return 0;
+      } else {
+        return new AST::AssignementBinaryExpression( ve, rhs );
+      }
     }
     delete lhs;
     delete rhs;
@@ -1579,3 +1630,38 @@
 {
   return &d->variablesManager;
 }
+
+int ParserBase::vectorMemberNameToIdx( const GTLCore::String& _name )
+{
+  GTL_DEBUG(_name);
+  if( _name == "x" or _name == "r" ) {
+    return 0;
+  } else if( _name == "y" or _name == "g"  ) {
+    return 1;
+  } else if( _name == "z" or _name == "b"  ) {
+    return 2;
+  } else if( _name == "w" or _name == "a"  ) {
+    return 3;
+  }
+  GTL_DEBUG("unexpected");
+  reportUnexpected( d->currentToken );
+  return -1;
+}
+
+int ParserBase::structMemberNameToIdx( const GTLCore::Type* _type, const GTLCore::String& _name )
+{
+  int index = _type->d->memberToIndex( _name );
+  if( index == -1 )
+  {
+    reportError("Unknown member: '" + _name + "' for structure " + _type->structName(), d->currentToken );
+  }
+  return index;
+}
+
+void ParserBase::startParsingFunction( const GTLCore::String& _name )
+{
+}
+
+void ParserBase::endParsingFunction( const GTLCore::String& _name )
+{
+}

Modified: trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.h
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.h	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/ParserBase_p.h	2008-11-25 23:19:54 UTC (rev 497)
@@ -120,6 +120,7 @@
        *                            or not
        */
       std::list< AST::Expression* > parseArraySize(bool _constantExpression);
+      AST::Expression* parseMemberArrayConstantExpression(AST::Expression* _expression);
       AST::AccessorExpression* parseMemberArrayExpression(AST::AccessorExpression* _expression, bool _constantExpression);
       /**
        * Parse coumpound expression ( float3( 1, 2, 6 ) )
@@ -168,7 +169,13 @@
       void setNameSpace( const String& nameSpace );
       TypeManager* typeManager();
       VariablesManager* variablesManager();
+    protected: // Events
+      virtual void startParsingFunction( const GTLCore::String& _name );
+      virtual void endParsingFunction( const GTLCore::String& _name );
     private:
+      int vectorMemberNameToIdx( const GTLCore::String& _name );
+      int structMemberNameToIdx( const GTLCore::Type* _type, const GTLCore::String& _name );
+    private:
       struct Private;
       Private* const d;
   };

Modified: trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -43,9 +43,13 @@
   bool directlyOnTheStack;
   bool allocatedInMemory;
   bool constantPointer;
+  bool dependant;
+#ifndef NDEBUG
+  bool dependantWasChangedToConst;
+#endif
 };
 
-VariableNG::VariableNG(const GTLCore::Type* _type, bool _constant ) : d(new Private)
+VariableNG::VariableNG(const GTLCore::Type* _type, bool _constant, bool _dependant ) : d(new Private)
 {
   d->type = _type;
   d->constant = _constant;
@@ -54,6 +58,10 @@
   d->pointer = 0;
   d->constantPointer = false;
   d->allocatedInMemory = ( _type->dataType() == Type::ARRAY or _type->dataType() == Type::STRUCTURE );
+  d->dependant = _dependant;
+#ifndef NDEBUG
+  d->dependantWasChangedToConst = false;
+#endif
 }
 
 VariableNG::~VariableNG()
@@ -64,6 +72,20 @@
 {
   return d->constant;
 }
+
+void VariableNG::setConstant( bool v )
+{
+  GTL_ASSERT( d->dependant );
+#ifndef NDEBUG
+  if( not v )
+  {
+    GTL_ASSERT( not d->dependantWasChangedToConst );
+  }
+  d->dependantWasChangedToConst = true;
+#endif
+  d->constant = v;
+}
+
 const GTLCore::Type* VariableNG::type() const
 {
   return d->type;

Modified: trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.h
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.h	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/VariableNG_p.h	2008-11-25 23:19:54 UTC (rev 497)
@@ -42,7 +42,7 @@
        * @param _type the type of the variable
        * @param _constant set to true if the variable is a constant
        */
-      VariableNG(const GTLCore::Type* _type, bool _constant );
+      VariableNG(const GTLCore::Type* _type, bool _constant, bool _dependant );
       ~VariableNG();
       /**
        * Initialise a Variable with an initialiser. This function will call \ref Accessor::initialise .
@@ -60,6 +60,11 @@
        */
       bool constant() const;
       /**
+       * Set if a variable is constant or not.
+       * Only dependant can be changed from constant to non const, and only once
+       */
+      void setConstant( bool v );
+      /**
        * @return the type of the variable
        */
       const GTLCore::Type* type() const;

Modified: trunk/OpenGTL/OpenGTL/GTLCore/Visitor_p.cpp
===================================================================
--- trunk/OpenGTL/OpenGTL/GTLCore/Visitor_p.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenGTL/GTLCore/Visitor_p.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -188,7 +188,7 @@
     
     }
     //   int i = 0;
-    VariableNG* index = new VariableNG( Type::Integer32, false);
+    VariableNG* index = new VariableNG( Type::Integer32, false, false);
     index->initialise( _generationContext, _currentBlock, ExpressionResult( _generationContext.codeGenerator()->integerToConstant(0), Type::Integer32), std::list<llvm::Value*>());
     
     // Construct the body of the for loop
@@ -271,7 +271,7 @@
     std::list< llvm::Value*> sizeAfter = _sizes;
     sizeAfter.pop_front();
     //   int i = 0;
-    VariableNG* index = new VariableNG( Type::Integer32, false);
+    VariableNG* index = new VariableNG( Type::Integer32, false, false);
     index->initialise( _generationContext, _currentBlock, ExpressionResult(_generationContext.codeGenerator()->integerToConstant(0), Type::Integer32), std::list<llvm::Value*>());
     
     // Construct the body of the for loop
@@ -334,7 +334,7 @@
     _generationContext.llvmFunction()->getBasicBlockList().push_back( firstIfBlock);
     
     
-    VariableNG* index = new VariableNG( Type::Integer32, false);
+    VariableNG* index = new VariableNG( Type::Integer32, false, false);
     index->initialise( _generationContext, firstIfBlock, ExpressionResult( _generationContext.codeGenerator()->integerToConstant(0), Type::Integer32), std::list<llvm::Value*>());
     
     // Construct the body of the for loop
@@ -387,7 +387,7 @@
   CodeGenerator::incrementCountFieldOf( _currentBlock, _pointer, _increment );
     
   //   int i = 0;
-  VariableNG* index = new VariableNG( Type::Integer32, false);
+  VariableNG* index = new VariableNG( Type::Integer32, false, false);
   index->initialise( _generationContext, _currentBlock, ExpressionResult( _generationContext.codeGenerator()->integerToConstant(0), Type::Integer32), std::list<llvm::Value*>());
     
   // Construct the body of the for loop

Modified: trunk/OpenGTL/OpenShiva/OpenShiva/CodeGenerator_p.cpp
===================================================================
--- trunk/OpenGTL/OpenShiva/OpenShiva/CodeGenerator_p.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenShiva/OpenShiva/CodeGenerator_p.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -234,7 +234,7 @@
     ++arg_it;
     llvm::Value* arg_result = arg_it;
   // Create the pixel
-    GTLCore::VariableNG* resultVar = new GTLCore::VariableNG( _kernel->d->outputPixelType(), false );
+    GTLCore::VariableNG* resultVar = new GTLCore::VariableNG( _kernel->d->outputPixelType(), false, false );
   resultVar->initialise( generationContext, initialBlock, GTLCore::ExpressionResult(), std::list<llvm::Value*>());
   // Get the evaluatePixel function
     GTLCore::Function* ePFunction = moduleData->function( _kernel->name(), "evaluatePixel" );
@@ -254,7 +254,7 @@
     SHIVA_ASSERT( evaluatePixel_params.size() == countArguments );
   // Construct the "conditions" of the first loop
     // int j = 0;
-    GTLCore::VariableNG* incJ = new GTLCore::VariableNG( GTLCore::Type::Integer32, false);
+    GTLCore::VariableNG* incJ = new GTLCore::VariableNG( GTLCore::Type::Integer32, false, false);
     incJ->initialise( generationContext, initialBlock,
                       GTLCore::ExpressionResult( arg_x, GTLCore::Type::Integer32),
                       std::list<llvm::Value*>());
@@ -264,7 +264,7 @@
       func->getBasicBlockList().push_back( firstBlockJLoop );
       
       // int i = 0;
-      GTLCore::VariableNG* incI = new GTLCore::VariableNG( GTLCore::Type::Integer32, false);
+      GTLCore::VariableNG* incI = new GTLCore::VariableNG( GTLCore::Type::Integer32, false, false);
       incI->initialise( generationContext, firstBlockJLoop,
                         GTLCore::ExpressionResult( arg_y, GTLCore::Type::Integer32),
                         std::list<llvm::Value*>());

Modified: trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.cpp
===================================================================
--- trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.cpp	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.cpp	2008-11-25 23:19:54 UTC (rev 497)
@@ -27,8 +27,10 @@
 #include <GTLCore/AST/Statement.h>
 #include <GTLCore/AST/Tree.h>
 #include <GTLCore/CompilerBase_p.h>
+#include <GTLCore/Macros_p.h>
 #include <GTLCore/Type.h>
 #include <GTLCore/TypeManager.h>
+#include <GTLCore/VariableNG_p.h>
 #include <GTLCore/VariablesManager_p.h>
 
 namespace AST = GTLCore::AST;
@@ -38,6 +40,7 @@
   GTLCore::String kernelName;
   GTLCore::AST::Tree* tree;
   Compiler* compiler;
+  std::list<GTLCore::VariableNG*> dependents;
 };
 
 Parser::Parser( Compiler* _compiler , Lexer* _lexer) : ParserBase(_compiler, _lexer), d(new Private)
@@ -230,8 +233,9 @@
       {
         reportError("Constant '" + scopedName.toString() + "' has allready been declared", currentToken());
       } else {
-        AST::GlobalConstantDeclaration* gcd = new AST::GlobalConstantDeclaration( scopedName, type , memberArraySize, false );
+        AST::GlobalConstantDeclaration* gcd = new AST::GlobalConstantDeclaration( scopedName, type , memberArraySize, true );
         variablesManager()->declareConstant( scopedName, gcd->variable() );
+        d->dependents.push_back( gcd->variable() );
         tree()->append( gcd );
       }
     }
@@ -241,3 +245,25 @@
     reachNextSemi();
   }
 }
+
+void Parser::startParsingFunction( const GTLCore::String& _name )
+{
+  if( _name == "evaluateDependents" )
+  {
+    foreach( GTLCore::VariableNG* var, d->dependents )
+    {
+      var->setConstant( false );
+    }
+  }
+}
+
+void Parser::endParsingFunction( const GTLCore::String& _name )
+{
+  if( _name == "evaluateDependents" )
+  {
+    foreach( GTLCore::VariableNG* var, d->dependents )
+    {
+      var->setConstant( true );
+    }
+  }
+}

Modified: trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.h
===================================================================
--- trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.h	2008-11-22 22:29:33 UTC (rev 496)
+++ trunk/OpenGTL/OpenShiva/OpenShiva/Parser_p.h	2008-11-25 23:19:54 UTC (rev 497)
@@ -40,6 +40,9 @@
       virtual GTLCore::AST::Tree* tree();
       virtual GTLCore::AST::Statement* parseStatement();
       virtual const GTLCore::Type* parseType();
+    protected: // Events
+      virtual void startParsingFunction( const GTLCore::String& _name );
+      virtual void endParsingFunction( const GTLCore::String& _name );
     private:
       void parseDependentDeclaration();
       void parseKernelBody();


Mail converted by MHonArc 2.6.19+ http://listengine.tuxfamily.org/