]> git.uio.no Git - u/mrichter/AliRoot.git/blob - PWG/muondep/AliMuonGridSubmitter.cxx
change way to check the origin of local maxima, add histogram depending on n overlaps...
[u/mrichter/AliRoot.git] / PWG / muondep / AliMuonGridSubmitter.cxx
1 /**************************************************************************
2  * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3  *                                                                        *
4  * Author: The ALICE Off-line Project.                                    *
5  * Contributors are mentioned in the code where appropriate.              *
6  *                                                                        *
7  * Permission to use, copy, modify and distribute this software and its   *
8  * documentation strictly for non-commercial purposes is hereby granted   *
9  * without fee, provided that the above copyright notice appears in all   *
10  * copies and that both the copyright notice and this permission notice   *
11  * appear in the supporting documentation. The authors make no claims     *
12  * about the suitability of this software for any purpose. It is          *
13  * provided "as is" without express or implied warranty.                  *
14  **************************************************************************/
15
16 //
17 // AliMuonGridSubmitter : a class to help submit jobs for several runs
18 //
19 // This class is dealing with 3 different directories :
20 //
21 // - template directory ($ALICE_ROOT/PWG/muondep/XXXTemplates) containing the
22 //   basic template files to be used for a particular job type (XXX). A template can contain
23 //   some variables that will be replaced during during the copy from template
24 //   to local dir
25 //
26 // - local directory, where the files from the template directory, are copied
27 //   once the class has been configured properly (i.e. using the various Set, Use,
28 //   etc... methods). Some other files (e.g. JDL ones) are generated from
29 //   scratch and also copied into this directory.
30 //   At this point one could(should) check the files, as they are the ones
31 //   to be copied to the remote directory for the production
32 //
33 // - remote directory, the alien directory where the files will be copied
34 //   (from the local directory) before the actual submission
35 //
36 // author: Laurent Aphecetche (Subatech
37 //
38
39 #include "AliMuonGridSubmitter.h"
40
41 #include "AliLog.h"
42 #include "TFile.h"
43 #include "TGrid.h"
44 #include "TGridResult.h"
45 #include "TMap.h"
46 #include "TMath.h"
47 #include "TObjString.h"
48 #include "TROOT.h"
49 #include "TString.h"
50 #include "TSystem.h"
51 #include <vector>
52 #include "AliAnalysisTriggerScalers.h"
53 #include "Riostream.h"
54
55 //______________________________________________________________________________
56 AliMuonGridSubmitter::AliMuonGridSubmitter(AliMuonGridSubmitter::EJobType jobType)
57 : TObject(),
58 fInternalMap(0x0),
59 fVars(0x0),
60 fIsValid(kFALSE),
61 fShouldOverwriteFiles(kFALSE),
62 fTemplateFileList(0x0),
63 fLocalFileList(0x0)
64 {
65   // ctor
66   
67   if (!gGrid)
68   {
69     TGrid::Connect("alien://");
70     if ( !gGrid )
71     {
72       AliError("cannot connect to grid");
73     }
74   }
75   
76   SetPackages("VO_ALICE@AliRoot::v5-04-46-AN","VO_ALICE@GEANT3::v1-15","VO_ALICE@ROOT::v5-34-05");
77
78   TString basedir = gSystem->ExpandPathName("$ALICE_ROOT/PWG/muondep");
79   
80   TString dir;
81   dir.Form("%s/%sTemplates",basedir.Data(),JobTypeName(jobType).Data());
82   
83   if (!SetTemplateDir(dir.Data()))
84   {
85     AliError(Form("Could not find %s directory. Please check.",dir.Data()));
86   }
87   
88   SetLocalDir(gSystem->pwd());
89 }
90
91 //______________________________________________________________________________
92 AliMuonGridSubmitter::~AliMuonGridSubmitter()
93 {
94   // dtor
95   delete fTemplateFileList;
96   delete fLocalFileList;
97   delete fInternalMap;
98   delete fVars;
99 }
100
101 //______________________________________________________________________________
102 void AliMuonGridSubmitter::AddToTemplateFileList(const char* filename)
103 {
104   // add a file to the list of templates
105   // and update the local file list if needed
106   
107   TObjArray* a = TemplateFileList();
108   
109   if ( !a->FindObject(filename) )
110   {
111     a->Add(new TObjString(filename));
112     UpdateLocalFileList();
113   }
114 }
115
116 //______________________________________________________________________________
117 Bool_t AliMuonGridSubmitter::CheckCompilation(const char* file) const
118 {
119   /// Check whether file can be compiled or not
120   /// FIXME: use gSystem->TempFileName for tmpfile !
121   
122   Bool_t rv(kTRUE);
123   
124   TString sfile(gSystem->BaseName(file));
125   TString tmpfile(Form("tmpfile_%s",sfile.Data()));
126   
127   gSystem->Exec(Form("cp %s %s",file,tmpfile.Data()));
128   
129   ReplaceVars(tmpfile.Data());
130   
131   gSystem->AddIncludePath("-I$ALICE_ROOT/include");
132   gSystem->AddIncludePath("-I$ALICE_ROOT/EVGEN");
133
134   if (gROOT->LoadMacro(Form("%s++",tmpfile.Data())))
135   {
136     AliError(Form("macro %s can not be compiled. Please check.",file));
137     rv = kFALSE;
138   }
139   
140   gSystem->Exec(Form("rm %s",tmpfile.Data()));
141   
142   return rv;
143 }
144
145
146 //______________________________________________________________________________
147 Bool_t AliMuonGridSubmitter::CheckLocal() const
148 {
149   /// Check whether all required local files are there
150   TIter next(LocalFileList());
151   TObjString* file;
152   
153   while ( ( file = static_cast<TObjString*>(next())) )
154   {
155       if ( gSystem->AccessPathName(file->String().Data()) )
156       {
157         return kFALSE;
158       }
159   }
160   
161   return kTRUE;
162 }
163
164 //______________________________________________________________________________
165 Bool_t AliMuonGridSubmitter::CheckRemote() const
166 {
167   /// Check whether all required remote files are there
168   AliWarning("implement me");
169   return kFALSE;
170 }
171
172 //______________________________________________________________________________
173 void AliMuonGridSubmitter::CleanLocal(const char* excludeList) const
174 {
175   /// Clean (remove) local generated files
176   /// exclude contains a list of comma separated pattern of files
177   /// to be avoided
178   
179   TIter next(LocalFileList());
180   TObjString* file;
181   TObjArray* excludeArray = TString(excludeList).Tokenize(",");
182   
183   while ( ( file = static_cast<TObjString*>(next())) )
184   {
185     Bool_t shouldExclude(kFALSE);
186     
187     TIter nextExclude(excludeArray);
188     TObjString* s;
189     
190     while ( ( s = static_cast<TObjString*>(nextExclude()))  && !shouldExclude )
191     {
192       if ( file->String().Contains(s->String()) ) shouldExclude=kTRUE;
193     }
194     
195     if (!shouldExclude)
196     {
197       gSystem->Unlink(file->String().Data());
198     }
199   }
200   
201   delete excludeArray;
202 }
203
204 //______________________________________________________________________________
205 Bool_t AliMuonGridSubmitter::CopyFile(const char* localFile)
206 {
207   /// copy a local file to remote destination
208   TString local;
209   
210   if ( gSystem->IsAbsoluteFileName(localFile) )
211   {
212     local = localFile;
213   }
214   else
215   {
216     local = Form("%s/%s",LocalDir().Data(),gSystem->ExpandPathName(localFile));
217   }
218   
219   if (gSystem->AccessPathName(local.Data()))
220   {
221     AliErrorClass(Form("Local file %s does not exist",local.Data()));
222     return kFALSE;
223   }
224   
225   TString remote;
226   
227   remote += RemoteDir().Data();
228   remote += "/";
229   
230   if ( gSystem->IsAbsoluteFileName(localFile) )
231   {
232     TString tmp(localFile);
233     tmp.ReplaceAll(GetMapValue("Snapshot"),"");
234     tmp.ReplaceAll(GetMapValue("Local"),"");
235     remote += tmp;
236   }
237   else
238   {
239     remote += localFile;
240   }
241   
242   TString dirName = gSystem->DirName(remote.Data());
243   
244   Bool_t ok(kTRUE);
245   
246   if (!RemoteDirectoryExists(dirName.Data()))
247   {
248     ok = gGrid->Mkdir(dirName.Data(),"-p");
249   }
250   
251   if ( ok )
252   {
253     AliDebugClass(1,Form("cp %s alien://%s",local.Data(),remote.Data()));
254     return TFile::Cp(local.Data(),Form("alien://%s",remote.Data()));
255   }
256   else
257   {
258     return kFALSE;
259   }
260 }
261
262 //______________________________________________________________________________
263 Bool_t AliMuonGridSubmitter::CheckRemoteDir() const
264 {
265   /// Check we have a grid connection and that the remote dir exists
266   
267   if (RemoteDir().IsNull())
268   {
269     AliError("you must provide the grid location where to copy the files");
270     return kFALSE;
271   }
272   
273   if (!RemoteDirectoryExists(RemoteDir()))
274   {
275     AliError(Form("directory %s does not exist", RemoteDir().Data()));
276     return kFALSE;
277   }
278
279   return kTRUE;
280 }
281
282 //______________________________________________________________________________
283 Bool_t AliMuonGridSubmitter::CopyLocalFilesToRemote()
284 {
285   /// copy all files necessary to run the simulation into remote directory
286   
287   TIter next(LocalFileList());
288   TObjString* ftc;
289     
290   Bool_t allok(kTRUE);
291     
292   while ( ( ftc = static_cast<TObjString*>(next())) )
293   {
294     allok = allok && CopyFile(ftc->String());
295   }
296   return allok;
297 }
298
299 //______________________________________________________________________________
300 Bool_t AliMuonGridSubmitter::CopyTemplateFilesToLocal()
301 {
302   // copy (or generate) local files from the template ones
303   
304   if (!IsValid()) return kFALSE;
305
306   AliDebug(1,"");
307
308   TIter next(TemplateFileList());
309   TObjString* file;
310   
311   Int_t err(0);
312   Bool_t potentialProblem(kFALSE);
313   
314   while ( ( file = static_cast<TObjString*>(next())) )
315   {
316     if ( file->String().Contains("OCDB") )
317     {
318       /// OCDB snapshots are not in template
319       continue;
320     }
321
322     if ( !ShouldOverwriteFiles() && !gSystem->AccessPathName(file->String().Data()) )
323     {
324       AliError(Form("Local file %s already exists. Remove it first if you want to update overwrite it",file->String().Data()));
325       potentialProblem = kTRUE;
326     }
327     else
328     {
329       TString stemplate(Form("%s/%s",TemplateDir().Data(),file->String().Data()));
330       TString slocal(Form("%s/%s",LocalDir().Data(),file->String().Data()));
331       
332       Int_t c =  gSystem->CopyFile(stemplate.Data(),slocal.Data(),ShouldOverwriteFiles());
333       if ( c )
334       {
335         Bool_t ok(kFALSE);
336         if ( stemplate.Contains(".jdl",TString::kIgnoreCase) )
337         {
338           ok = Generate(file->String().Data());
339         }
340         if (!ok)
341         {
342           AliError(Form("Error %d copying file %s",c,stemplate.Data()));
343         }
344         else
345         {
346           c=0;
347         }
348       }
349       else
350       {
351         if ( HasVars(slocal.Data()) )
352         {
353           if (!ReplaceVars(slocal.Data()))
354           {
355             AliError("pb in ReplaceVars");
356             c=1;
357           }
358         }
359       }
360       err += c;
361     }
362   }
363   
364   if ( potentialProblem )
365   {
366     AliWarning("At least one local file could not be overwritten. Cross-check that the local files are OK before we try to upload them to the Grid !");
367     return kFALSE;
368   }
369   return (err==0);
370 }
371
372 //______________________________________________________________________________
373 std::ostream* AliMuonGridSubmitter::CreateJDLFile(const char* name) const
374 {
375   /// Create a (local and empty) JDL file
376   
377   AliDebugClass(1,"");
378   
379   TString jdl(Form("%s/%s",LocalDir().Data(),name));
380   
381   if ( !ShouldOverwriteFiles() && !gSystem->AccessPathName(jdl.Data()) )
382   {
383     AliErrorClass(Form("File %s already exists. Remove it if you want to overwrite it",jdl.Data()));
384     return 0x0;
385   }
386   
387   std::ofstream* os = new std::ofstream(gSystem->ExpandPathName(jdl.Data()));
388   
389   if (os->bad())
390   {
391     AliErrorClass(Form("Cannot create file %s",jdl.Data()));
392     delete os;
393     os=0x0;
394   }
395   
396   return os;
397 }
398
399 //______________________________________________________________________________
400 Int_t AliMuonGridSubmitter::GetLastStage(const char* remoteDir)
401 {
402   /// Get the last staging phase already performed
403   
404   TGridResult* r = gGrid->Ls(remoteDir);
405   Int_t i(0);
406   Int_t lastStage(0);
407   Int_t offset = TString("Stage_").Length();
408   
409   while ( r->GetFileName(i) )
410   {
411     TString file(r->GetFileName(i));
412     if  (file.BeginsWith("Stage_") && !file.Contains("xml") )
413     {
414       Int_t n = TString(file(offset,file.Length()-offset)).Atoi();
415       lastStage = TMath::Max(lastStage,n);
416     }
417     ++i;
418   }
419   delete r;
420   return lastStage;
421 }
422
423 //______________________________________________________________________________
424 TString AliMuonGridSubmitter::GetMapValue(const char* key) const
425 {
426   // convenience method to access internal map of TObjStrings
427   if (!fInternalMap) return "";
428   
429   TObject* o = fInternalMap->GetValue(key);
430   
431   if (o)
432   {
433     return static_cast<TObjString*>(o)->String();
434   }
435   
436   return "";
437 }
438
439 //______________________________________________________________________________
440 TObjArray* AliMuonGridSubmitter::GetVariables(const char* file) const
441 {
442   /// Find the variables in the file
443   
444   std::ifstream in(file);
445   char line[1024];
446   TObjArray* variables(0x0);
447   
448   while ( in.getline(line,1023,'\n') )
449   {
450     TString sline(line);
451     while (sline.Contains("VAR_") && !sline.BeginsWith("//") )
452     {
453       Int_t i1 = sline.Index("VAR_");
454       Int_t i2(i1);
455       
456       while ( ( i2 < sline.Length() ) && ( isalnum(sline[i2]) || sline[i2]=='_' ) ) ++i2;
457       
458       if (!variables)
459       {
460         variables = new TObjArray;
461         variables->SetOwner(kTRUE);
462       }
463       
464       TString var = sline(i1,i2-i1);
465       if ( !variables->FindObject(var) )
466       {
467         variables->Add(new TObjString(var));
468       }
469       sline.ReplaceAll(var,"");
470     }
471   }
472   
473   in.close();
474   
475   return variables;
476 }
477
478 //______________________________________________________________________________
479 Bool_t AliMuonGridSubmitter::HasVars(const char* file) const
480 {
481   /// Whether or not the file contains variables that have to
482   /// be substituted
483   
484   std::ifstream in(file);
485   char line[1024];
486   while ( in.getline(line,1023,'\n') )
487   {
488     TString sline(line);
489     if (sline.Contains("VAR_") && !sline.BeginsWith("//") )
490     {
491       return kTRUE;
492     }
493   }
494   return kFALSE;
495 }
496
497 //______________________________________________________________________________
498 TMap* AliMuonGridSubmitter::InternalMap() const
499 {
500   if (!fInternalMap)
501   {
502     fInternalMap = new TMap;
503     fInternalMap->SetOwnerKeyValue(kTRUE,kTRUE);
504   }
505   return fInternalMap;
506 }
507
508 //______________________________________________________________________________
509 TString AliMuonGridSubmitter::JobTypeName(AliMuonGridSubmitter::EJobType jobType) const
510 {
511   if ( jobType == kAccEff )
512   {
513     return "AccEff";
514   }
515   else if ( jobType == kQAMerge)
516   {
517     return "QAMerge";
518   }
519   return "unknown";
520 }
521
522 //______________________________________________________________________________
523 TObjArray* AliMuonGridSubmitter::LocalFileList() const
524 {
525   /// Return (after createing and filling it if needed)
526   /// the internal file list with paths from the local directory
527   
528   if (!fLocalFileList)
529   {
530     fLocalFileList = static_cast<TObjArray*>(TemplateFileList()->Clone());
531   }
532   
533   return fLocalFileList;
534 }
535
536 //______________________________________________________________________________
537 UInt_t AliMuonGridSubmitter::NofRuns() const
538 {
539     // number of runs we're dealing with
540   return fRunList.size();
541 }
542
543 //______________________________________________________________________________
544 void AliMuonGridSubmitter::OutputToJDL(std::ostream& out, const char* key,
545                                     const TObjArray& values) const
546 {
547   /// output to ostream of key,{values} pair
548   
549   out << key << " = ";
550   
551   Int_t n = values.GetEntries();
552   
553   if ( n > 1 )
554   {
555     out << "{" << std::endl;
556     TIter next(&values);
557     TObjString* v;
558     
559     while ( ( v = static_cast<TObjString*>(next())) )
560     {
561       --n;
562       out << "\t\"" << v->String().Data() << "\"";
563       if  ( n ) out << ",";
564       out << std::endl;
565     }
566     out << "}";
567   }
568   else
569   {
570     TString& v1 = static_cast<TObjString*>(values.At(0))->String();
571     
572     if ( v1.IsDigit() && !(TString(key).Contains("SplitMax")) && !(TString(key).Contains("TTL")) )
573     {
574       out << v1.Atoi();
575     }
576     else
577     {
578       out << "\"" << v1.Data() << "\"";
579     }
580   }
581   out << ";" << std::endl;
582 }
583
584 //______________________________________________________________________________
585 void AliMuonGridSubmitter::OutputToJDL(std::ostream& out, const char* key, const char* v1,
586                                     const char* v2, const char* v3, const char* v4,
587                                     const char* v5, const char* v6, const char* v7,
588                                     const char* v8, const char* v9) const
589 {
590   /// output to ostream
591   
592   TObjArray values;
593   values.SetOwner(kTRUE);
594   
595   values.Add(new TObjString(v1));
596   if ( strlen(v2) > 0 ) values.Add(new TObjString(v2));
597   if ( strlen(v3) > 0 ) values.Add(new TObjString(v3));
598   if ( strlen(v4) > 0 ) values.Add(new TObjString(v4));
599   if ( strlen(v5) > 0 ) values.Add(new TObjString(v5));
600   if ( strlen(v6) > 0 ) values.Add(new TObjString(v6));
601   if ( strlen(v7) > 0 ) values.Add(new TObjString(v7));
602   if ( strlen(v8) > 0 ) values.Add(new TObjString(v8));
603   if ( strlen(v9) > 0 ) values.Add(new TObjString(v9));
604   
605   OutputToJDL(out,key,values);
606 }
607
608
609 //______________________________________________________________________________
610 void AliMuonGridSubmitter::Print(Option_t* /*opt*/) const
611 {
612   /// Printout
613   
614   if (!IsValid())
615   {
616     std::cout << std::string(80,'*') << std::endl;
617     std::cout << "INVALID OBJECT. CHECK BELOW THE CONFIGURATION." << std::endl;
618     std::cout << std::string(80,'*') << std::endl;
619   }
620
621   TIter next(fInternalMap);
622   TObjString* key;
623   
624   while ( ( key = static_cast<TObjString*>(next()) ) )
625   {
626     TString value = static_cast<TObjString*>(fInternalMap->GetValue(key->String()))->String();
627     
628     std::cout << key->String() << " : " << value.Data() << std::endl;
629   }
630   
631   if ( NofRuns() )
632   {
633     std::cout << NofRuns() << " run";
634     if ( NofRuns() > 1 ) std::cout << "s";
635     std::cout << " = ";
636     for ( std::vector<int>::size_type i = 0; i < fRunList.size(); ++i )
637     {
638       std::cout << fRunList[i] << " ";
639     }
640   }
641   
642   TIter nextVar(fVars);
643   while ( ( key = static_cast<TObjString*>(nextVar())) )
644   {
645     TObjString* value = static_cast<TObjString*>(fVars->GetValue(key->String()));
646     std::cout << "Variable " << key->String() << " will be replaced by " << value->String() << std::endl;
647   }
648   
649   std::cout << "Files to be uploaded:" << std::endl;
650   TIter nextFile(LocalFileList());
651   TObjString* sfile;
652   while ( ( sfile = static_cast<TObjString*>(nextFile())) )
653   {
654     std::cout << sfile->String().Data() << std::endl;
655   }
656 }
657
658
659 //______________________________________________________________________________
660 Bool_t AliMuonGridSubmitter::RemoteDirectoryExists(const char *dirname) const
661 {
662   // Returns true if directory exists. Can be also a path.
663   if (!gGrid) return kFALSE;
664   // Check if dirname is a path
665   TString dirstripped = dirname;
666   dirstripped = dirstripped.Strip();
667   dirstripped = dirstripped.Strip(TString::kTrailing, '/');
668   TString dir = gSystem->BaseName(dirstripped);
669   dir += "/";
670   TString path = gSystem->DirName(dirstripped);
671   TGridResult *res = gGrid->Ls(path, "-F");
672   if (!res) return kFALSE;
673   TIter next(res);
674   TMap *map;
675   TObject *obj;
676   while ((map=dynamic_cast<TMap*>(next()))) {
677     obj = map->GetValue("name");
678     if (!obj) break;
679     if (dir == obj->GetName()) {
680       delete res;
681       return kTRUE;
682     }
683   }
684   delete res;
685   return kFALSE;
686 }
687
688 //______________________________________________________________________________
689 Bool_t AliMuonGridSubmitter::RemoteFileExists(const char *lfn)
690 {
691   // Returns true if file exists.
692   if (!gGrid) return kFALSE;
693   TGridResult *res = gGrid->Ls(lfn);
694   if (!res) return kFALSE;
695   TMap *map = dynamic_cast<TMap*>(res->At(0));
696   if (!map) {
697     delete res;
698     return kFALSE;
699   }
700   TObjString *objs = dynamic_cast<TObjString*>(map->GetValue("name"));
701   if (!objs || !objs->GetString().Length()) {
702     delete res;
703     return kFALSE;
704   }
705   delete res;
706   return kTRUE;
707 }
708
709 //______________________________________________________________________________
710 Bool_t AliMuonGridSubmitter::ReplaceVars(const char* file) const
711 {
712   /// Replace the variables (i.e. things starting by VAR_) found in file
713   
714   std::ifstream in(file);
715   char line[1024];
716   TObjArray lines;
717   lines.SetOwner(kTRUE);
718   Int_t nvars(0);
719   Int_t nreplaced(0);
720
721   TIter next(fVars);
722
723   while ( in.getline(line,1023,'\n') )
724   {
725     TString sline(line);
726     while (sline.Contains("VAR_") && !sline.BeginsWith("//") )
727     {
728       ++nvars;
729       TObjString* key;
730       next.Reset();
731       while ( ( key = static_cast<TObjString*>(next())) )
732       {
733         if ( sline.Contains(key->String()) )
734         {
735           ++nreplaced;
736           TObjString* value = static_cast<TObjString*>(fVars->GetValue(key->String()));
737           sline.ReplaceAll(key->String(),value->String());
738           break;
739         }
740       }
741     }
742
743     lines.Add(new TObjString(sline));
744   }
745   
746   in.close();
747   
748   if ( nvars > 0 )
749   {
750     if ( nreplaced != nvars )
751     {
752       AliError(Form("nvars=%d nreplaced=%d",nvars,nreplaced));
753       return kFALSE;
754     }
755     std::ofstream out(file);
756     TIter nextLine(&lines);
757     TObjString* s;
758     while ( ( s = static_cast<TObjString*>(nextLine()) ) )
759     {
760       out << s->String().Data() << std::endl;
761     }
762     out.close();
763   }
764   
765   return kTRUE;
766 }
767
768 //______________________________________________________________________________
769 const std::vector<int>& AliMuonGridSubmitter::RunList() const
770 {
771   /// Return a reference to our runlist
772   return fRunList;
773 }
774
775 //______________________________________________________________________________
776 void AliMuonGridSubmitter::SetPackages(const char* aliroot,
777                                          const char* root,
778                                          const char* geant3,
779                                          const char* api)
780 {
781   /// Set the packages to be used by the jobs
782   /// Must be a valid combination, see http://alimonitor.cern.ch/packages/
783   ///
784   
785   SetMapKeyValue("AliRoot",aliroot);
786   SetMapKeyValue("Root",root);
787   SetMapKeyValue("Geant3",geant3);
788   SetMapKeyValue("API",api);
789 }
790
791 //______________________________________________________________________________
792 TString AliMuonGridSubmitter::GetRemoteDir(const char* dir, Bool_t create)
793 {
794   /// Set the target remote directory (on the grid)
795   
796   if (!RemoteDirectoryExists(dir))
797   {
798     if (!create)
799     {
800       AliErrorClass(Form("Remote directory %s does not exist", dir));
801       return "";
802     }
803     else
804     {
805       AliInfoClass(Form("Remote directory %s does not exist. Trying to create it...",dir));
806       if (!gGrid)
807       {
808           AliErrorClass("cannot connect to grid");
809           return "";
810       }
811       if ( !gGrid->Mkdir(dir,"-p") )
812       {
813         AliErrorClass(Form("Could not create remote dir. Sorry."));
814         return "";
815       }
816     }
817   }
818   return dir;
819 }
820
821 //______________________________________________________________________________
822 Bool_t AliMuonGridSubmitter::SetLocalDirectory(const char* type, const char* path)
823 {
824   if (gSystem->AccessPathName(path)==kFALSE)
825   {
826     SetMapKeyValue(type,path);
827     return kTRUE;
828   }
829   return kFALSE;
830 }
831
832 //______________________________________________________________________________
833 void AliMuonGridSubmitter::SetMapKeyValue(const char* key, const char* value)
834 {
835   TObjString skey(key);
836   InternalMap()->Remove(&skey);
837   InternalMap()->Add(new TObjString(key),new TObjString(value));
838 }
839
840 //______________________________________________________________________________
841 Bool_t AliMuonGridSubmitter::SetRemoteDirectory(const char* type, const char* path)
842 {
843   // Set the merged directory to be used
844   TString v = GetRemoteDir(path,kTRUE);
845   SetMapKeyValue(type,v);
846   return (v.Length()>0);
847 }
848
849 //______________________________________________________________________________
850 void AliMuonGridSubmitter::SetRunList(const char* runlist)
851 {
852     // set the runlist from a text file
853   AliAnalysisTriggerScalers ts(runlist);
854   fRunList = ts.GetRunList();
855 }
856
857 //______________________________________________________________________________
858 void AliMuonGridSubmitter::SetRunList(int runNumber)
859 {
860   // set the runlist from a text file
861   fRunList.clear();
862   fRunList.push_back(runNumber);
863 }
864
865 //______________________________________________________________________________
866 Bool_t AliMuonGridSubmitter::SetVar(const char* varname, const char* value)
867 {
868   /// Set a variable
869   
870   TString s(varname);
871   s.ToUpper();
872   if (!s.BeginsWith("VAR_"))
873   {
874     AliError("Variable name should start with VAR_");
875     return kFALSE;
876   }
877   if (!fVars)
878   {
879     fVars = new TMap;
880     fVars->SetOwnerKeyValue(kTRUE,kTRUE);
881   }
882   
883   TObject* o = new TObjString(s);
884   fVars->Remove(o);
885   
886   fVars->Add(o,new TObjString(value));
887   
888   return kTRUE;
889 }
890
891 //______________________________________________________________________________
892 TObjArray* AliMuonGridSubmitter::TemplateFileList() const
893 {
894   /// Return (after createing if needed)
895   
896   if (!fTemplateFileList)
897   {
898     fTemplateFileList = new TObjArray;
899     fTemplateFileList->SetOwner(kTRUE);
900   }
901   return fTemplateFileList;
902 }
903
904 //______________________________________________________________________________
905 void AliMuonGridSubmitter::UpdateLocalFileList()
906 {
907   // insure that local file list contains at least all of the template files
908   TIter next(TemplateFileList());
909   TObjString* s;
910   
911   while ( ( s = static_cast<TObjString*>(next())) )
912   {
913     TObjArray* local = LocalFileList();
914     if ( !local->FindObject(s->String()))
915     {
916       local->Add(new TObjString(*s));
917     }
918   }
919 }
920
921 //______________________________________________________________________________
922 TMap* AliMuonGridSubmitter::Vars() const
923 {
924   if (!fVars)
925   {
926     fVars = new TMap;
927     fVars->SetOwnerKeyValue(kTRUE,kTRUE);
928   }
929   return fVars;
930 }
931