// This may look like C code, but it is really -*- C++ -*-
// Classe CxxExecutor  : Dynamic C++ compile/execution in piapp
// (c) DAPNIA (CEA)                 LAL (IN2P3/CNRS)
//                           C. Magneville  10/2000

#ifndef CXXEXECUTOR_H_SEEN
#define CXXEXECUTOR_H_SEEN

#include "machdefs.h"
#include <stdio.h>
#include <stdlib.h>
#include <iostream>

#include <vector>
#include <string>

#include "piacmd.h"
#include "nobjmgr.h"

class CxxExecutor : public CmdExecutor {
public:
           CxxExecutor(PIACmd* piac, PIStdImgApp* app);
  virtual ~CxxExecutor();

  virtual int Execute(string& keyw,vector<string>& args, string& toks);
  virtual bool  IsThreadable(string const & keyw);

  inline void SetPrtLevel(uint_2 lp=2) {mPrtLevel = lp;}

  int  ExecuteCXX(string usercode,string userfct="");

  // if true , declare ObjMgr variables as $varname 
  inline void DeclareObjMgrVar(bool fg=false) { mFgPutVar=fg; }

  int  CrFile(string cfilename="",string func="");
       void PutInclude(ofstream& os);
       void PutIncludeUser(ofstream& os);
       void PutObject(ofstream& os);
       void PutVar(ofstream& os);

  int  FillUserCode(string& usercode,uint_4 first);
  int  FillUserCode(string filename);

  int  FillUserFctFrS(string userfctcode="");
  int  FillUserFctFrF(string filefctname="");

  int  Compile(string rootfilename="");
  /* int CrMakefile(void); */

  int  Link(string libname="",string func="");
  int  Call(string func="");

  void   FillArgs(vector<string>& args);
  void   FillArgs(string& args);
  string GetArgs(void);

  void   FillInclude(vector<string>& inc);
  void   FillInclude(string& inc);
  string GetInclude(void);

  void   FillCompileOpt(vector<string>& copt);
  void   FillCompileOpt(string& copt);
  string GetCompileOpt(void);

  void   FillLinkOpt(vector<string>& lopt);
  void   FillLinkOpt(string& lopt);
  string GetLinkOpt(void);

  void   FillLinkLibs(vector<string>& llibs);
  void   FillLinkLibs(string& llibs);
  string GetLinkLibs(void);

  void FillModuleImport(vector<string>& import);
  void FillModuleImport(string& import);
  string GetModuleImport(void);

private:
  string mUserCodeFn;
  string mUserFctFn;
  string mCompOpt;
  string mLinkOpt;
  string mMyLibs;
  vector<string> mIncList;
  vector<string> mCallArgs;

  // Import des modules
  vector<string> mIncImportList;
  vector<string> mModuleImportList;
  vector<string> mModuleImportDefaultList;


  //  string mDefTmp; remplace par la methode TmpDir() - Reza 4/9/02
  inline string const& TmpDir() { NamedObjMgr omg; return omg.GetTmpDir(); }
  string mDefRoot;
  string mDefFunc;

  uint_2 mPrtLevel;
  bool   mFgPutVar;  // if true , declare ObjMgr variables as $varname, default=false

  // Mutex de controle de thread pour dynamic-link 
  ZMutex mutx_cxxe;

};

#endif
