Index: /XIOS/trunk/src/node/context.cpp
===================================================================
--- /XIOS/trunk/src/node/context.cpp	(revision 458)
+++ /XIOS/trunk/src/node/context.cpp	(revision 459)
@@ -175,44 +175,5 @@
    }
    
-   //----------------------------------------------------------------
-/*
-   void CContext::toBinary(StdOStream & os) const
-   {
-      SuperClass::toBinary(os);
-
-#define DECLARE_NODE(Name_, name_)                                         \
-   {                                                                       \
-      ENodeType renum = C##Name_##Definition::GetType();                   \
-      bool val = C##Name_##Definition::has(C##Name_##Definition::GetDefName()); \
-      os.write (reinterpret_cast<const char*>(&renum), sizeof(ENodeType)); \
-      os.write (reinterpret_cast<const char*>(&val), sizeof(bool));        \
-      if (val) C##Name_##Definition::get(C##Name_##Definition::GetDefName())->toBinary(os);   \
-   }   
-#define DECLARE_NODE_PAR(Name_, name_)
-#include "node_type.conf"
-   }
-*/
-   //----------------------------------------------------------------
-/*
-   void CContext::fromBinary(StdIStream & is)
-   {
-      SuperClass::fromBinary(is);
-#define DECLARE_NODE(Name_, name_)                                         \
-   {                                                                       \
-      bool val = false;                                                    \
-      ENodeType renum = Unknown;                                           \
-      is.read (reinterpret_cast<char*>(&renum), sizeof(ENodeType));        \
-      is.read (reinterpret_cast<char*>(&val), sizeof(bool));               \
-      if (renum != C##Name_##Definition::GetType())                        \
-         ERROR("CContext::fromBinary(StdIStream & is)",                    \
-               << "[ renum = " << renum << "] Bad type !");                \
-      if (val) C##Name_##Definition::create(C##Name_##Definition::GetDefName()) -> fromBinary(is); \
-   }   
-#define DECLARE_NODE_PAR(Name_, name_)
-#include "node_type.conf"
-      
-   }
- */
-   
+
    //----------------------------------------------------------------
 
@@ -337,4 +298,8 @@
       this->findEnabledFiles();
 
+        
+      this->processEnabledFiles() ;
+
+/*        
       //Recherche des champs Ã  sortir (enable Ã  true + niveau de sortie correct)
       // pour chaque fichier prÃ©cÃ©demment listÃ©.
@@ -347,4 +312,7 @@
       this->solveAllOperation();
 
+      // Traitement des expressions.
+      this->solveAllExpression();
+*/
       // Nettoyage de l'arborescence
       CleanTree();
@@ -357,4 +325,11 @@
      (void)this->enabledFiles[i]->getEnabledFields();
    }
+   
+    void CContext::processEnabledFiles(void)
+   {
+     for (unsigned int i = 0; i < this->enabledFiles.size(); i++)
+     this->enabledFiles[i]->processEnabledFile();
+   }
+  
 
    void CContext::solveAllGridRef(void)
@@ -370,4 +345,10 @@
    }
 
+   void CContext::solveAllExpression(void)
+   {
+      for (unsigned int i = 0; i < this->enabledFiles.size(); i++)
+      this->enabledFiles[i]->solveEFExpression();
+   }
+   
    void CContext::solveAllInheritance(bool apply)
    {
Index: /XIOS/trunk/src/node/context.hpp
===================================================================
--- /XIOS/trunk/src/node/context.hpp	(revision 458)
+++ /XIOS/trunk/src/node/context.hpp	(revision 459)
@@ -110,6 +110,8 @@
          void closeDefinition(void) ;
          void findAllEnabledFields(void);
+         void processEnabledFiles(void) ;
          void solveAllGridRef(void);
          void solveAllOperation(void);
+         void solveAllExpression(void);
          void solveAllInheritance(bool apply=true) ;
          void findEnabledFiles(void);
Index: /XIOS/trunk/src/node/field.cpp
===================================================================
--- /XIOS/trunk/src/node/field.cpp	(revision 458)
+++ /XIOS/trunk/src/node/field.cpp	(revision 459)
@@ -11,4 +11,5 @@
 #include "type.hpp"
 #include "context_client.hpp"
+#include <set>
 
 namespace xios{
@@ -23,5 +24,7 @@
       , nstep(0)
       , last_Write(), last_operation()
-      , foperation()
+      , foperation(), hasInstantData(false), hasExpression(false)
+      , active(false) , hasOutputFile(false), slotUpdateDate(NULL)
+      , processed(false)
       { /* Ne rien faire de plus */ }
 
@@ -33,5 +36,7 @@
       , nstep(0)
       , last_Write(), last_operation()
-      , foperation()
+      , foperation(), hasExpression(false)
+      , active(false), hasOutputFile(false), slotUpdateDate(NULL)
+      , processed(false)
    { /* Ne rien faire de plus */ }
 
@@ -41,4 +46,7 @@
 //      this->file.reset() ;
       this->foperation.reset() ;
+      if (hasExpression) delete expression ;
+      if (slotUpdateDate!=NULL) delete slotUpdateDate ;
+        
    }
 
@@ -199,5 +207,6 @@
    void CField::setRelFile(CFile* _file)
    { 
-      this->file = _file; 
+      this->file = _file;
+      hasOutputFile=true ; 
    }
 
@@ -327,4 +336,19 @@
    //----------------------------------------------------------------
 
+   void CField::processEnabledField(void)
+   {
+      if (!processed)
+      {
+        processed=true ;
+        solveRefInheritance(true) ;
+        solveOperation() ;
+        solveGridReference() ;
+      
+        if (hasDirectFieldReference()) baseRefObject->processEnabledField() ;
+        buildExpression(); 
+        active=true;
+      }
+    }
+    
    void CField::solveRefInheritance(bool apply)
    {
@@ -333,5 +357,6 @@
       CField * refer_ptr = this;
       
-      this->baseRefObject = CField::get(this);
+      if (this->hasDirectFieldReference())  baseRefObject = getDirectFieldReference();
+      else  baseRefObject = CField::get(this);
       
       while (refer_ptr->hasDirectFieldReference())
@@ -349,7 +374,9 @@
          SuperClassAttribute::setAttributes(refer_ptr, apply);
          sset.insert(refer_ptr);
-         baseRefObject = refer_sptr;
+//ym         baseRefObject = refer_sptr;
 //ym         refObject.push_back(refer_sptr);
       }
+      
+      if (hasDirectFieldReference()) baseRefObject->addReference(this) ;
    }
 
@@ -359,11 +386,17 @@
    {
       using namespace func;
-       
-      StdString id = this->getBaseFieldReference()->getId();
+      
+      if (!hasOutputFile) return ;
+      
+      StdString id ;
+      if (hasId()) id=getId();
+      else if (!name.isEmpty()) id=name ;
+      else if (hasDirectFieldReference()) id=baseRefObject->getId() ;
+      
       CContext* context = CContext::getCurrent();
       
       if (freq_op.isEmpty()) freq_op=string("1ts") ;
       
-      if (operation.isEmpty()  || this->file->output_freq.isEmpty())
+      if (operation.isEmpty() )
       {
          ERROR("CField::solveOperation(void)",
@@ -548,4 +581,5 @@
 
      grid->solveReference() ;
+
    }
 
@@ -598,3 +632,92 @@
    ///-------------------------------------------------------------------
 
+   void CField::parse(xml::CXMLNode & node)
+   {
+      SuperClass::parse(node);
+      node.getContent(this->content) ;
+    }
+    
+  CArray<double,1>* CField::getInstantData(void)
+  {
+    if (!hasInstantData) 
+    {
+      instantData.resize(grid->storeIndex_client.numElements()) ;
+      hasInstantData=true ;
+    }
+    return &instantData ;
+  }
+  
+  void CField::addReference(CField* field)
+  {
+    refObject.push_back(field) ;
+  }
+  
+  void CField::addDependency(CField* field, int slotId)
+  {
+    fieldDependency.push_back(pair<CField*,int>(field,slotId)) ;
+  }
+  
+  void CField::buildExpression(void)
+  {
+    if (content.size() > 0) 
+    {
+      CSimpleNodeExpr* simpleExpr=parseExpr(content+'\0') ;
+      expression=CFieldNode::newNode(simpleExpr) ;
+      delete simpleExpr ;
+      set<string> fieldIds ;
+      expression->getFieldIds(fieldIds) ;
+      for (set<string>::iterator it=fieldIds.begin() ; it!=fieldIds.end();++it) if (*it!="this") CField::get(*it)->processEnabledField() ;
+      
+      expression->reduce(this) ;
+
+      slots.resize(fieldIds.size()) ;
+      resetSlots() ;
+      int slotId=0 ;
+      set<CField*> fields ;
+      expression->getFields(fields) ;
+      for (set<CField*>::iterator it=fields.begin() ; it!=fields.end();++it,++slotId) (*it)->addDependency(this,slotId) ;
+      hasExpression=true; 
+    }
+  }
+  
+  void CField::resetSlots(void)
+  {
+    for(vector<bool>::iterator it=slots.begin();it!=slots.end();++it) *it=false ;
+  }
+  
+  bool CField::slotsFull(void)
+  {
+    bool ret=true ;
+    for(vector<bool>::iterator it=slots.begin();it!=slots.end();++it) ret &= *it;
+    return ret ;
+  }
+
+  
+  void CField::setSlot(int slotId)
+  {
+    CContext* context = CContext::getCurrent() ;
+    const CDate & currDate = context->getCalendar()->getCurrentDate();
+    if (slotUpdateDate==NULL || currDate!=*slotUpdateDate) 
+    {
+      resetSlots() ;
+      if (slotUpdateDate==NULL) slotUpdateDate=new CDate(currDate) ;
+      else *slotUpdateDate=currDate ;
+    }
+    slots[slotId]=true ;
+    if (slotsFull())
+    {
+      CArray<double,1> expr(expression->compute()) ;
+      
+      if (hasInstantData) 
+      {
+        instantData=expr ;
+        for(list< pair<CField *,int> >::iterator it=fieldDependency.begin(); it!=fieldDependency.end(); ++it)  
+          if (it->first!=this) it->first->setSlot(it->second) ;
+      }
+      
+      if (hasOutputFile) updateDataFromExpression(expr) ;
+      
+    }
+  }
+  
 } // namespace xios
Index: /XIOS/trunk/src/node/field.hpp
===================================================================
--- /XIOS/trunk/src/node/field.hpp	(revision 458)
+++ /XIOS/trunk/src/node/field.hpp	(revision 459)
@@ -13,4 +13,5 @@
 #include "array_new.hpp"
 #include "attribute_array.hpp"
+#include "expr_node.hpp"
 //#include "context.hpp"
 
@@ -65,4 +66,5 @@
          CField* getDirectFieldReference(void) const;
          CField* getBaseFieldReference(void)   const;
+         void addReference(CField* field) ;
          const std::vector<CField*> & getAllReference(void) const;
 
@@ -92,4 +94,5 @@
 
          template <int N> bool updateData(const CArray<double, N>&   data);
+         bool updateDataFromExpression(const CArray<double, 1>&   data);
          
          bool updateDataServer
@@ -102,6 +105,9 @@
          bool hasDirectFieldReference(void) const;
          bool isActive(void) const;
+         bool active ;
+         bool hasOutputFile ;
 
          /// Traitements ///
+         void processEnabledField(void) ;
          void solveRefInheritance(bool apply);
          void solveGridReference(void);
@@ -127,5 +133,6 @@
         void outputField(CArray<double,3>& fieldOut) ;
         void outputField(CArray<double,2>& fieldOut) ;
-        
+        void parse(xml::CXMLNode & node) ;
+        CArray<double,1>* getInstantData(void)  ;
       public :
 
@@ -148,7 +155,22 @@
          
          CArray<double, 1> data;
+         CArray<double, 1> instantData;
+         bool hasInstantData ;
          map<int, CArray<double,1>* > data_srv ;
          bool isOnceOperation ;
          bool isFirstOperation ;
+         string content ;
+         
+         list< pair<CField *,int> > fieldDependency ;
+         void buildExpression(void) ;
+         void addDependency(CField* field, int slotId) ;
+         void resetSlots(void) ;
+         vector<bool> slots ;
+         CDate* slotUpdateDate ;
+         CFieldNode * expression ;
+         bool hasExpression ;
+         bool slotsFull(void) ;
+         void setSlot(int slotId);
+         bool processed ;
 
    }; // class CField
Index: /XIOS/trunk/src/node/field_impl.hpp
===================================================================
--- /XIOS/trunk/src/node/field_impl.hpp	(revision 458)
+++ /XIOS/trunk/src/node/field_impl.hpp	(revision 459)
@@ -13,32 +13,43 @@
 namespace xios {
 
-   template <int N>
-   void CField::setData(const CArray<double, N>& _data)
-   {
-     const std::vector<CField*>& refField=getAllReference();
-     std::vector<CField*>::const_iterator  it = refField.begin(), end = refField.end();
-     
-     for (; it != end; it++) (*it)->updateData(_data) ;
+  template <int N>
+  void CField::setData(const CArray<double, N>& _data)
+  {
+    if (hasInstantData) 
+    {
+      grid->inputField(_data, instantData); 
+      for(list< pair<CField *,int> >::iterator it=fieldDependency.begin(); it!=fieldDependency.end(); ++it)  it->first->setSlot(it->second) ;
     }
     
+    if (!hasExpression)
+    {
+      const std::vector<CField*>& refField=getAllReference();
+      std::vector<CField*>::const_iterator  it = refField.begin(), end = refField.end();
+     
+      for (; it != end; it++) (*it)->setData(_data) ;
+      if (hasOutputFile) updateData(_data) ;
+    }
+     
+  }
+
+
    template <int N>
-      bool CField::updateData(const CArray<double, N>& _data)
+   bool CField::updateData(const CArray<double, N>& _data)
    {        
       CContext* context=CContext::getCurrent();
       const CDate & currDate = context->getCalendar()->getCurrentDate();
       const CDate opeDate      = *last_operation + freq_operation;
-      const CDate writeDate    = *last_Write     + freq_write;
+      const CDate writeDate    = *last_Write     + freq_write;       
       bool doOperation, doWrite; 
-         
 
    
       info(50) << "CField::updateData " << currDate <<  " : send data to " << this->getBaseFieldId() << std::endl;
       info(50) << "Next operation "  << opeDate<<std::endl;
-      
+
       doOperation = (opeDate <= currDate) ;
       if (isOnceOperation)
         if (isFirstOperation) doOperation=true ;
         else doOperation=false ;
-      
+
       if (doOperation)
       {
@@ -55,6 +66,60 @@
          info(50) << "(*last_operation = currDate) : " << *last_operation << " = " << currDate << std::endl; 
       }
+
+      doWrite = (writeDate < (currDate + freq_operation)) ;
+      if (isOnceOperation)
+      { 
+        if(isFirstOperation) 
+        {
+          doWrite=true ;
+          isFirstOperation=false ;
+        }
+        else doWrite=false ;
+      }
       
-      
+      if (doWrite)
+      {
+         this->foperation->final();
+         *last_Write = writeDate;
+         info(50) << "(*last_Write = currDate) : " << *last_Write << " = " << currDate << std::endl;
+         CTimer::get("XIOS Send Data").resume() ;
+         sendUpdateData() ;
+         CTimer::get("XIOS Send Data").suspend() ;
+         return (true);        
+      }
+
+      return (false);
+   }
+   
+   bool CField::updateDataFromExpression(const CArray<double, 1>& _data)
+   {        
+      CContext* context=CContext::getCurrent();
+      const CDate & currDate = context->getCalendar()->getCurrentDate();
+      const CDate opeDate      = *last_operation + freq_operation;
+      const CDate writeDate    = *last_Write     + freq_write;       
+      bool doOperation, doWrite; 
+
+   
+      info(50) << "CField::updateData " << currDate <<  " : send data to " << this->getBaseFieldId() << std::endl;
+      info(50) << "Next operation "  << opeDate<<std::endl;
+
+      doOperation = (opeDate <= currDate) ;
+      if (isOnceOperation)
+        if (isFirstOperation) doOperation=true ;
+        else doOperation=false ;
+
+      if (doOperation)
+      {
+         if (this->data.numElements() != this->grid->storeIndex_client.numElements())
+         {
+            this->data.resize(this->grid->storeIndex_client.numElements());
+         }
+            
+        (*this->foperation)(_data);
+         
+         *last_operation = currDate;
+         info(50) << "(*last_operation = currDate) : " << *last_operation << " = " << currDate << std::endl; 
+      }
+
       doWrite = (writeDate < (currDate + freq_operation)) ;
       if (isOnceOperation)
Index: /XIOS/trunk/src/node/file.cpp
===================================================================
--- /XIOS/trunk/src/node/file.cpp	(revision 458)
+++ /XIOS/trunk/src/node/file.cpp	(revision 459)
@@ -102,8 +102,8 @@
          newEnabledFields.push_back(*it) ;
          // Le champ est finalement actif, on y ajoute sa propre reference.
-         (*it)->refObject.push_back(*it);
+//         (*it)->refObject.push_back(*it);
          // Le champ est finalement actif, on y ajoute la rÃ©fÃ©rence au champ de base.
          (*it)->setRelFile(CFile::get(this));
-         (*it)->baseRefObject->refObject.push_back(*it);
+//         (*it)->baseRefObject->refObject.push_back(*it);
          // A faire, ajouter les references intermediaires...
       }
@@ -366,4 +366,21 @@
    //----------------------------------------------------------------
 
+   void CFile::processEnabledFile(void)
+   {
+     if (output_freq.isEmpty()) ERROR("void CFile::processEnabledFile(void)",
+                                       <<"File attribute <<output_freq>> is undefined"); 
+     solveFieldRefInheritance(true) ;
+     getEnabledFields() ;
+     processEnabledFields() ;
+   }
+   
+   void CFile::processEnabledFields(void)
+   {
+      for (unsigned int i = 0; i < this->enabledFields.size(); i++)
+      {
+        this->enabledFields[i]->processEnabledField() ;
+      }
+    }
+    
    void CFile::solveFieldRefInheritance(bool apply)
    {
@@ -389,40 +406,11 @@
          this->enabledFields[i]->solveOperation();
    }
-   
-   //---------------------------------------------------------------
-/*
-   void CFile::toBinary  (StdOStream & os) const
-   {
-      ENodeType genum = CFileGroup::GetType();
-      bool hasVFG = (this->getVirtualFieldGroup() != NULL);
-      SuperClass::toBinary(os);
-      
-      os.write (reinterpret_cast<const char*>(&genum) , sizeof(ENodeType));
-      os.write (reinterpret_cast<const char*>(&hasVFG) , sizeof(bool));
-      
-      if (hasVFG)this->getVirtualFieldGroup()->toBinary(os);
-         
-   }
-   
-   //----------------------------------------------------------------
-   
-   void CFile::fromBinary(StdIStream & is)
-   {
-      ENodeType renum = Unknown;
-      bool hasVFG = false;
-      SuperClass::fromBinary(is);
-      
-      is.read (reinterpret_cast<char*>(&renum), sizeof(ENodeType));
-      is.read (reinterpret_cast<char*>(&hasVFG), sizeof(bool));
-      
-      if (renum != CFileGroup::GetType())
-         ERROR("CFile::fromBinary(StdIStream & is)",
-               << "[ renum = " << renum << "] Bad type !");
-      
-//      this->setVirtualFieldGroup(this->getId());
-      if (hasVFG)this->getVirtualFieldGroup()->fromBinary(is);
-      
-   }
-*/
+ 
+   void CFile::solveEFExpression(void)
+   {
+      for (unsigned int i = 0; i < this->enabledFields.size(); i++)
+         this->enabledFields[i]->buildExpression();
+   }   
+ 
 
    CField* CFile::addField(const string& id)
Index: /XIOS/trunk/src/node/file.hpp
===================================================================
--- /XIOS/trunk/src/node/file.hpp	(revision 458)
+++ /XIOS/trunk/src/node/file.hpp	(revision 459)
@@ -68,5 +68,6 @@
          void setVirtualFieldGroup(CFieldGroup* newVFieldGroup);
          void setVirtualFieldGroup(void);
-
+         void processEnabledFile(void) ;
+         void processEnabledFields(void) ;
          void createHeader(void);
          void close(void) ;
@@ -77,4 +78,5 @@
          void solveEFGridRef(void);
          void solveEFOperation(void);
+         void solveEFExpression(void);
 
          /// Destructeur ///
Index: /XIOS/trunk/src/node/variable.hpp
===================================================================
--- /XIOS/trunk/src/node/variable.hpp	(revision 458)
+++ /XIOS/trunk/src/node/variable.hpp	(revision 459)
@@ -5,6 +5,6 @@
 #include "xmlioserver_spl.hpp"
 #include "declare_group.hpp"
-
-#include "data_output.hpp"
+#include "group_template.hpp"
+#include "array_new.hpp"
 
 namespace xios
