]> Creatis software - bbtk.git/blob - kernel/src/bbtkUtilities.cxx
51724cd4b147cc862f47c7e89dd2cefc912ee20d
[bbtk.git] / kernel / src / bbtkUtilities.cxx
1 /*
2  # ---------------------------------------------------------------------
3  #
4  # Copyright (c) CREATIS (Centre de Recherche en Acquisition et Traitement de l'Image
5  #                        pour la SantÈ)
6  # Authors : Eduardo Davila, Frederic Cervenansky, Claire Mouton
7  # Previous Authors : Laurent Guigues, Jean-Pierre Roux
8  # CreaTools website : www.creatis.insa-lyon.fr/site/fr/creatools_accueil
9  #
10  #  This software is governed by the CeCILL-B license under French law and
11  #  abiding by the rules of distribution of free software. You can  use,
12  #  modify and/ or redistribute the software under the terms of the CeCILL-B
13  #  license as circulated by CEA, CNRS and INRIA at the following URL
14  #  http://www.cecill.info/licences/Licence_CeCILL-B_V1-en.html
15  #  or in the file LICENSE.txt.
16  #
17  #  As a counterpart to the access to the source code and  rights to copy,
18  #  modify and redistribute granted by the license, users are provided only
19  #  with a limited warranty  and the software's author,  the holder of the
20  #  economic rights,  and the successive licensors  have only  limited
21  #  liability.
22  #
23  #  The fact that you are presently reading this means that you have had
24  #  knowledge of the CeCILL-B license and that you accept its terms.
25  # ------------------------------------------------------------------------ */
26
27
28 /*=========================================================================
29   Program:   bbtk
30   Module:    $RCSfile: bbtkUtilities.cxx,v $
31   Language:  C++
32   Date:      $Date: 2012/11/16 08:49:01 $
33   Version:   $Revision: 1.15 $
34 =========================================================================*/
35
36
37
38
39 #include "bbtkUtilities.h"
40 #include "bbtkMessageManager.h"
41
42 //EED 2018-07-16
43 #if defined(_WIN32) 
44         #include <shlwapi.h>
45 #endif
46
47 #if defined(MACOSX) // assume this is OSX 
48 # include <sys/param.h>
49 # include <mach-o/dyld.h> // _NSGetExecutablePath : must add -framework CoreFoundation to link line 
50 # include <string.h>
51 # ifndef PATH_MAX
52 #  define PATH_MAX MAXPATHLEN
53 # endif
54 #endif // MACOSX
55
56 #ifndef PATH_MAX // If not defined yet : do it 
57 #  define PATH_MAX 2048
58 #endif 
59
60 namespace bbtk
61 {
62
63
64
65             // ======================================================================
66     // See : http://www.techbytes.ca/techbyte103.html for more O.S.
67     bool Utilities::FileExists(std::string strFilename) 
68     {
69       struct stat stFileInfo;
70      bool blnReturn;
71      int intStat;
72      
73      // Attempt to get the file attributes
74      intStat = stat(strFilename.c_str(),&stFileInfo);
75      if(intStat == 0) 
76        {
77          // We were able to get the file attributes
78          // so the file obviously exists.
79          blnReturn = true;
80        } 
81      else 
82        {
83          // We were not able to get the file attributes.
84          // This may mean that we don't have permission to
85          // access the folder which contains this file. If you
86          // need to do that level of checking, lookup the
87          // return values of stat which will give you
88          // more details on why stat failed.
89          blnReturn = false;
90        }
91      
92      return(blnReturn);
93     }
94     
95     
96     // =====================================================================
97     
98     std::string Utilities::ExtractPackageName(const std::string  &name, 
99                                           std::string& path)
100     {
101       std::string pkgname;
102       path = "";
103       
104       std::string::size_type slash_position = name.find_last_of("/\\");
105       if (slash_position != std::string::npos) 
106         {
107           pkgname = name.substr(slash_position+1,std::string::npos);
108           path = name.substr(0,slash_position);
109           //    std::cout << "F:P='"<<path<<"'"<<std::endl;//+1,std::string::npos);
110         }
111       else 
112         {
113           pkgname = name;
114         }
115       
116       // remove {.so | dll} if any
117       std::string::size_type dot_position = pkgname.find_last_of('.');      
118       if (dot_position != std::string::npos){
119         pkgname = pkgname.substr(0,dot_position);
120       }      
121 #if defined(__GNUC__)
122       
123       // GCC mechanism
124       // shared lib name = libbb<name>.so
125       
126       // remove {libbb} if any
127       if (memcmp ( pkgname.c_str(), "libbb", 5) == 0) {
128         pkgname =  pkgname.substr(5, pkgname.length());
129       }
130       /*
131      /// \ \todo     what would happen if (stupid) user names his package 'libbb' ?!?
132       /// \ --> Should be forbidden!
133       */
134 #elif defined(_WIN32)
135       
136       // WIN 32 mechanism
137       // shared lib name = <name>.dll
138       
139       // EED Problem loading package call bbtkTools
140       //     // remove {bb} if any
141       if (memcmp (pkgname.c_str(), "bb", 2) == 0) {
142         pkgname =  pkgname.substr(2, pkgname.length());  
143       }
144       
145       /*
146      /// \ \todo     what would happen if (stupid) user names his package 'bb' ?!?
147      /// \ --> Should be forbidden!
148      */
149 #else
150       bbtkError("neither __GNUC__ nor _WIN32 ?!? How did you compile ?");
151 #endif      
152       return pkgname;
153     }
154     
155     //=====================================================================
156     std::string Utilities::ExtractScriptName(const std::string &name,
157                                          std::string& path)
158     {
159       std::string pkgname;
160       
161       std::string::size_type slash_position = name.find_last_of("/\\");
162       if (slash_position != std::string::npos) {
163         pkgname =name.substr(slash_position+1,std::string::npos);
164         path = name.substr(0,slash_position);      
165       } else {
166         pkgname = name;
167       }
168       // remove {.bbs } if any
169       std::string::size_type dot_position = pkgname.find_last_of('.');
170       if (dot_position != std::string::npos){
171         pkgname = pkgname.substr(0,dot_position);
172       }
173       return pkgname;
174     }
175     
176     // ========================================================================
177
178     std::string Utilities::ExpandLibName(const std::string &name, bool verbose)
179     {
180       // -----   Think of expanding path name ( ./ ../ ../../ )
181       
182       char buf[2048]; // for getcwd
183       char * currentDir = getcwd(buf, 2048);
184       std::string cwd(currentDir);
185       std::string libname(name);
186       std::string fileSeparator;
187       fileSeparator = ConfigurationFile::GetInstance().Get_file_separator();
188       // tooHigh : true is user supplies a library pathname with too many "../"
189       bool tooHigh = false;
190       
191       //std::cout << "------------------cwd ["  << cwd << "] name [" << name << "]" << std::endl;
192       
193       if ( name[0] == '/' ||  name[1] == ':' ) // Linux or Windows absolute name
194         {
195           return(libname);
196         }
197       else if  ( name =="." )
198         {
199           libname = cwd  + fileSeparator;
200           return(libname);
201         }
202       else if  (name[0] == '.' && (name[1] == '/' || name[1] == '\\') )
203         {
204           libname = cwd  + fileSeparator + name.substr(2, name.length());
205           return(libname);
206         }
207       else if ( name[0] == '.' &&  name[1] == '.' /*  && (name[2] == '/' || name[2] == '\\') */ ) 
208         {
209           if ( IsAtRoot(cwd) )  // hope it gets / (for Linux),  C: D: (for Windows)
210       {  
211      // if we are already at / or c: --> hopeless  
212          if (verbose)
213            std::cout << "   File path [" <<  name << "] doesn't exist" << std::endl;
214          tooHigh = true;
215       }
216       else
217       {
218          // iterate on ../ and go up from the current working dir!
219          std::string a(name); 
220          bool alreadyProcessRoot = false;
221
222           //if (a[a.size()-1] != fileSeparator[0])
223           //   a.append(fileSeparator);
224 //std::cout << "------------------a ["  << a << "]" << std::endl;
225
226          for(;;)  // wild loop !
227          {
228             std::string::size_type slash_position = cwd.find_last_of(fileSeparator);
229             if (slash_position != std::string::npos) {
230              if (slash_position == 0)
231                 slash_position = 1;
232               cwd = cwd.substr(0,slash_position/*+1*/);
233 //std::cout << "------------------cwd ["  << cwd << "]" << std::endl;
234             //  if (a == "..") {
235             //    a = "";
236             //    break;
237             //   }
238             //   else
239                  a = a.substr(3, /*name.length()*/ a.length());  // remove ../
240 //std::cout << "------------------a ["  << a << "]" << std::endl;  
241               if (a == "" || alreadyProcessRoot)
242               {
243                 if (verbose)
244                   std::cout << "   File path : [" <<  name << "] doesn't exist" << std::endl;
245                 tooHigh = true;
246                 break;
247               }
248              // std::string b = cwd + a;
249               libname =  cwd;
250               char c = cwd[cwd.size()-1];
251               if (c != '/' && c != '\\' )
252                 libname += fileSeparator;
253               libname += a;
254
255               if ( a[0] != '.' ) // if . (probabely ../), loop again
256                 break;
257
258               if (IsAtRoot(cwd))
259                 alreadyProcessRoot = true;
260             }
261          } // end iterating on ../
262       }
263 //std::cout << "------------------out of loop]" << std::endl;        
264       if (tooHigh)
265          libname="";
266       return (libname);
267
268     }  // -----   End of expanding path name   ( ./ ../ ../../ )
269
270     std::cout <<"* ERROR in ExpandLibName : should never get here!" << std::endl;
271     // To avoid warning
272     return(""); // Will never get here!
273   }
274
275 // ===================================================================================
276
277   std::string Utilities::MakeLibnameFromPath(std::string path, std::string pkgname)
278   {
279     std::string libname = path;
280         if(path.size()>0){
281                 char c = path[path.size()-1];    
282 #if defined(__GNUC__)
283        if (c != '/')
284           libname += "/libbb";
285        else
286           libname += "libbb";
287        libname += pkgname;
288 #if defined(MACOSX)
289           libname += ".dylib";
290 #elif defined(WIN32)                 // mingw      
291           libname += ".dll";
292 #else                                // Linux
293           libname += ".so";
294 #endif  
295           
296 #elif defined(_WIN32)
297        if (c != '\\') 
298           libname += "\\bb";
299        else
300           libname += "bb";
301        libname += pkgname;
302        libname += ".dll";
303 #endif
304         }
305     
306     return libname;    
307   }
308
309 // ===================================================================================
310
311   std::string Utilities::MakePkgnameFromPath(std::string path, std::string pkgname, bool addExt)
312   {
313     std::string libname = path;
314         if(path.size()>0){
315                 char c = path[path.size()-1];
316                 if (c != '/' && c != '\\')
317                 {
318                    libname +=  ConfigurationFile::GetInstance().Get_file_separator ();
319                 }
320                 libname += pkgname;
321                 if (addExt)
322                 {
323                    int l = libname.size();
324                    if (l>4)
325                    {
326                           if (libname.substr(l-4, 4) != ".bbs")
327                           {
328                                    libname = libname + ".bbs";
329                           }
330                    }
331                 }
332         }
333     
334     return libname;
335   }
336   // =======================================================================
337
338   // =======================================================================
339   /// Returns the user settings dir, e.g. /home/username/.bbtk
340   std::string Utilities::GetUserSettingsDir()
341   {
342     std::string str_Home=Utilities::GetEnvHome();
343     std::string fullname = str_Home + "/.bbtk";
344     MakeValidFileName(fullname);
345     return fullname;
346   }
347   
348
349   // =======================================================================
350   /// Builds the complete path to the file 'name' located 
351   /// in user settings dir, e.g. /home/username/.bbtk/
352   std::string Utilities::MakeUserSettingsFullFileName(const std::string& name)
353   {
354     std::string str_home=Utilities::GetEnvHome();
355     std::string fullname = str_home + "/.bbtk/" + name;
356     MakeValidFileName(fullname);
357     return fullname;
358   }
359   // =======================================================================
360   
361
362   // =======================================================================
363   void Utilities::CreateDirectoryIfNeeded( std::string const &dirName)
364   {
365     if (FileExists(dirName)) return;
366     std::string cmd("mkdir \"");
367     cmd += dirName;
368     cmd += "\"";
369     system(cmd.c_str());
370   }  
371   // =======================================================================
372   
373   
374   //========================================================================
375   bool Utilities::IsAtRoot(std::string cwd)
376   {
377     if ( cwd == "/"              // hope it gets /     (for Linux)
378          || (cwd.size() <= 3 && cwd[1] == ':') ) // hope it gets C: D: (for Windows)
379       return (true);
380     else
381       return(false);
382   }
383   // ======================================================================
384
385   // ======================================================================
386   bool Utilities::IsDirectory(std::string const &dirName)
387   {
388     struct stat fs;
389     
390     if ( stat(dirName.c_str(), &fs) == 0 )
391       {
392 #if _WIN32
393         return ((fs.st_mode & _S_IFDIR) != 0);
394 #else
395         return S_ISDIR(fs.st_mode);
396 #endif
397       }
398     else
399       {
400         return false;
401       }
402   }
403   // =======================================================================
404     
405   // =======================================================================
406   void Utilities::SplitAroundFirstDot( const std::string& in,
407                                        std::string& left,
408                                        std::string& right)
409   {
410     std::string delimiter = ".";
411     std::string::size_type pos = in.find_first_of(delimiter);
412     if (std::string::npos != pos) 
413       {
414         left = in.substr(0,pos);
415         right = in.substr(pos+1,in.size());
416         
417       }
418     else
419       {
420         left ="";
421         right = "";
422         bbtkGlobalError("Token '"<<in<<"' : expected 'a.b' format but no dot found");
423       }
424   }
425   //=======================================================================
426
427   //=======================================================================
428   void Utilities::SplitString ( const std::string& str, 
429                                 const std::string& delimiters, 
430                                 std::vector<std::string>& tokens)
431   {
432     // Skip delimiters at beginning.
433     std::string::size_type lastPos = str.find_first_not_of(delimiters, 0);
434     // Find first delimiter.
435     std::string::size_type pos     = str.find_first_of(delimiters, lastPos);
436     
437     while (std::string::npos != pos || std::string::npos != lastPos)
438       {
439         // Found a token, add it to the vector.
440         tokens.push_back(str.substr(lastPos, pos - lastPos));
441         // Skip delimiters.  Note the "not_of"
442         lastPos = str.find_first_not_of(delimiters, pos);
443         // Find next delimiter
444         pos = str.find_first_of(delimiters, lastPos);
445       }
446     
447   }
448   //=======================================================================
449   
450   
451   // ======================================================================
452   std::string Utilities::get_file_name(const std::string& s) 
453   { 
454     std::string::size_type slash_position = s.find_last_of("/\\");
455     if (slash_position != std::string::npos) 
456       {
457         return  s.substr(slash_position+1,std::string::npos);   
458       }
459     else 
460       {
461         return s;
462       }
463   }
464   //=======================================================================
465  
466
467   // ========================================================================
468   /**
469    * \brief   Explore a directory with possibility of recursion
470    *          return number of files read
471    * @param  dirpath   directory to explore
472    * @param  recursive whether we want recursion or not
473    */
474   int Utilities::Explore(std::string const &dirpath, bool recursive, std::vector<std::string> &Filenames)
475   {
476     int numberOfFiles = 0;
477     std::string fileName;
478       
479       std::string dirName = dirpath;
480       
481 #ifdef _MSC_VER
482       WIN32_FIND_DATA fileData;
483    HANDLE hFile = FindFirstFile((dirName+"\\*").c_str(), &fileData);
484
485    for(BOOL b = (hFile != INVALID_HANDLE_VALUE); b;
486        b = FindNextFile(hFile, &fileData))
487    {
488       fileName = fileData.cFileName;
489       if ( fileData.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY )
490       {
491          // Need to check for . and .. to avoid infinite loop
492          if ( fileName != "." && fileName != ".." && recursive )
493          {
494             numberOfFiles += Explore(dirName+ "\\"+fileName,recursive,Filenames);
495          }
496       }
497       else
498       {
499          Filenames.push_back(dirName+"\\"+fileName);
500          numberOfFiles++;
501       }
502    }
503    DWORD dwError = GetLastError();
504    if (hFile != INVALID_HANDLE_VALUE) 
505       FindClose(hFile);
506    if (dwError != ERROR_NO_MORE_FILES) 
507    {
508       LPVOID lpMsgBuf;
509       FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER|
510                     FORMAT_MESSAGE_FROM_SYSTEM|
511                     FORMAT_MESSAGE_IGNORE_INSERTS,
512                     NULL,GetLastError(),
513                     MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), // Default language
514                     (LPTSTR) &lpMsgBuf,0,NULL);
515
516      // ErrorMacro("FindNextFile error. Error is " << (char *)lpMsgBuf
517      //             <<" for the directory : "<<dirName);
518       
519       return 0;
520    }
521
522 #else
523   // Real POSIX implementation: scandir is a BSD extension only, and doesn't 
524   // work on debian for example
525 //std::cout <<"in Explor dirname[" << dirName << "]" << std::endl; 
526    DIR* dir = opendir(dirName.c_str());
527    if (!dir)
528    {
529       return 0;
530    }
531 //std::cout <<"Open OK" << std::endl; 
532    // According to POSIX, the dirent structure contains a field char d_name[]
533    // of unspecified size, with at most NAME_MAX characters preceeding the
534    // terminating null character. Use of other fields will harm the  porta-
535    // bility of your programs.
536
537    struct stat buf;
538    dirent *d;
539    for (d = readdir(dir); d; d = readdir(dir))
540    {
541       fileName = dirName + "/" + d->d_name;
542 //std::cout <<"in Explor filename[" << fileName << "]" << std::endl;      
543       if( stat(fileName.c_str(), &buf) != 0 )
544       {
545          //ErrorMacro( strerror(errno) );
546       }
547       if ( S_ISREG(buf.st_mode) )    //is it a regular file?
548       {
549          Filenames.push_back( fileName );
550          numberOfFiles++;
551       }
552       else if ( S_ISDIR(buf.st_mode) ) //directory?
553       {
554          if ( d->d_name[0] != '.' && recursive ) //we also skip hidden files
555          {
556             numberOfFiles += Explore( fileName, recursive, Filenames);
557          }
558       }
559       else
560       {
561          //ErrorMacro( "Unexpected error" );
562          return -1;
563       }
564    }
565    if( closedir(dir) != 0 )
566    {
567      // ErrorMacro( strerror(errno) );
568    }
569 #endif
570
571   return numberOfFiles;
572
573 }
574   //=======================================================================
575  
576
577     //=======================================================================
578     // Replaces substrings "\\n" by a real carriage return "\n"
579     void Utilities::SubsBackslashN ( std::string& s )
580     {
581       std::string ss("\\n");
582       std::string::size_type pos = 0;
583       pos = s.find(ss,0);
584       const char* cr = "\n";
585       while ( pos != std::string::npos )
586         {
587           s.replace(pos,2,cr,1);
588           pos = s.find(ss, pos-1);
589         }
590     }
591     //=======================================================================
592
593
594    //=======================================================================
595
596   bool Utilities::loosematch(std::string stdLine,std::string stdOptions) 
597   {
598     bool result=false;
599     std::vector<std::string> tokens;
600     SplitString ( stdOptions,"|", tokens);
601     int i,size=tokens.size();  
602     for (i=0; i<size; i++)
603       {           
604 #ifdef WIN32
605         if ( strcmpi(stdLine.c_str(),tokens[i].c_str())==0) 
606           { 
607             result=true; 
608           }               
609 #else
610         if ( strcasecmp(stdLine.c_str(),tokens[i].c_str())==0) 
611           { 
612             result=true; 
613           }               
614 #endif
615         
616       }
617     return result;
618   }
619   //=========================================================================  
620   
621   //=========================================================================  
622   // From http://www.fltk.org/newsgroups.php?gfltk.general+v:22083
623   //
624   int get_app_path (char *pname, size_t pathsize)
625   {
626
627 #ifdef LINUX
628     /* Oddly, the readlink(2) man page says no NULL is appended. */
629     /* So you have to do it yourself, based on the return value: */
630     pathsize --; /* Preserve a space to add the trailing NULL */
631     long result = readlink("/proc/self/exe", pname, pathsize);
632     if (result > 0)
633       {
634         pname[result] = 0; /* add the #@!%ing NULL */
635         
636         if ((access(pname, 0) == 0))
637           return 0; /* file exists, return OK */
638         /*else name doesn't seem to exist, return FAIL (falls
639           through) */
640       }
641 #endif /* LINUX */
642     
643 #ifdef WIN32
644
645 //2018-07-06 mingw64
646     wchar_t pname2[512];
647     long result = GetModuleFileName(NULL, pname2, pathsize);
648         int ret = wcstombs ( pname, pname2, sizeof(pname) );    
649 //    long result = GetModuleFileName(NULL, pname, pathsize);
650     if (result > 0)
651       {
652         /* fix up the dir slashes... */
653         int len = strlen(pname);
654         int idx;
655         for (idx = 0; idx < len; idx++)
656           {
657             if (pname[idx] == '\\') pname[idx] = '/';
658           }
659         
660         for (idx = len-1; idx >=0 ; idx--)
661           {
662             if (pname[idx] == '/')
663               { 
664                 pname[idx+1] = '\0';
665                 idx = -1;
666               }
667           }
668         
669         if ((access(pname, 0) == 0))
670           return 0; /* file exists, return OK */
671         /*else name doesn't seem to exist, return FAIL (falls
672           through) */
673       }
674 #endif /* WIN32 */
675     
676 #ifdef SOLARIS
677     char *p = getexecname();
678     if (p)
679       {
680         /* According to the Sun manpages, getexecname will
681            "normally" return an */
682         /* absolute path - BUT might not... AND that IF it is not,
683            pre-pending */
684         /* getcwd() will "usually" be the correct thing... Urgh!
685          */
686         
687         /* check pathname is absolute (begins with a / ???) */
688         if (p[0] == '/') /* assume this means we have an
689                             absolute path */
690           {
691             strncpy(pname, p, pathsize);
692             if ((access(pname, 0) == 0))
693               return 0; /* file exists, return OK */
694           }
695         else /* if not, prepend getcwd() then check if file
696                 exists */
697           {
698             getcwd(pname, pathsize);
699             long result = strlen(pname);
700             strncat(pname, "/", (pathsize - result));
701             result ++;
702             strncat(pname, p, (pathsize - result));
703             
704             if ((access(pname, 0) == 0))
705               return 0; /* file exists, return OK */
706             /*else name doesn't seem to exist, return FAIL
707               (falls through) */
708           }
709       }
710 #endif /* SOLARIS */
711     
712 #ifdef MACOSX /* assume this is OSX */
713     /*
714       from http://www.hmug.org/man/3/NSModule.html
715       
716       extern int _NSGetExecutablePath(char *buf, unsigned long
717       *bufsize);
718       
719       _NSGetExecutablePath  copies  the  path  of the executable
720       into the buffer and returns 0 if the path was successfully
721       copied  in the provided buffer. If the buffer is not large
722       enough, -1 is returned and the  expected  buffer  size  is
723       copied  in  *bufsize.  Note that _NSGetExecutablePath will
724       return "a path" to the executable not a "real path" to the
725       executable.  That  is  the path may be a symbolic link and
726       not the real file. And with  deep  directories  the  total
727       bufsize needed could be more than MAXPATHLEN.
728     */
729     int status = -1;
730     char *given_path = (char*)malloc(MAXPATHLEN * 2);
731     if (!given_path) return status;
732     
733     uint32_t npathsize = MAXPATHLEN * 2;
734     long result = _NSGetExecutablePath(given_path, &npathsize);
735     if (result == 0)
736       { /* OK, we got something - now try and resolve the real path...
737          */
738         if (realpath(given_path, pname) != NULL)
739           {
740             if ((access(pname, 0) == 0))
741               status = 0; /* file exists, return OK */
742           }
743       }
744     free (given_path);
745     return status;
746 #endif /* MACOSX */
747
748     
749     return -1; /* Path Lookup Failed */
750   } 
751   //=========================================================================
752         
753
754         
755   //=========================================================================
756   std::string Utilities::GetExecutablePath()
757   {
758     char name[PATH_MAX];
759     int err = get_app_path(name, PATH_MAX);
760     if (err) 
761     {
762                 try 
763                 {
764                         bbtkGlobalError("Could not determine current executable path ?");  
765                 }
766                 catch (bbtk::Exception e)
767                 {
768                         std::cerr << e.GetErrorMessage() << std::endl;
769                 }
770     }
771               
772     // remove the exe name
773     char *slash;                
774     slash = strrchr(name, VALID_FILE_SEPARATOR_CHAR);
775     if (slash)
776     {
777                 *slash = 0;
778     }
779     return name;
780   }
781   //=========================================================================
782
783
784 std::string Utilities::GetEnvHome()
785 {
786 #if defined(__GNUC__)
787         std::string strHome;
788     char *envHome=getenv("HOME");
789     if (envHome!=NULL)  
790         { 
791                 strHome=envHome; 
792         } else {
793                 strHome = "/var/www/testwtdbg/docroot";
794         } // if
795 #elif defined(_WIN32)
796         std::string strHome( getenv("USERPROFILE") );
797 #endif
798         return strHome;
799 }   
800
801
802
803 //TAD Arbol CFT
804
805
806 //---------NodeTree---------------
807
808 NodeTreeC::NodeTreeC() 
809 {
810         
811 }
812
813 NodeTreeC::NodeTreeC(std::string _data)
814 {
815         data = _data;
816 }
817
818 NodeTreeC::~NodeTreeC()
819 {
820
821 }
822 void NodeTreeC::deleteTree()
823 {
824         data = "";
825         std::cout<<"NodeTreeC::deleteTree 1"<<std::endl;
826         childs.erase(childs.begin(),childs.begin()+childs.size());
827         std::cout<<"NodeTreeC::deleteTree 2"<<std::endl;
828 }
829
830 void NodeTreeC::insertChild(std::string _data)
831 {
832         NodeTreeC temp = NodeTreeC(_data);
833         childs.push_back(temp);
834         //std::cout<<"NodeTreeC::insertChild"<<std::endl;
835 }
836
837 void NodeTreeC::treeTour(int lvl)
838 {
839         std::string space = "";
840         for (int j=0; j<lvl ; j++){
841                                 space += "   ";
842         }
843         lvl++;
844         std::cout <<space<<"data: "<< data << "  size: "<< childs.size() << std::endl;
845         for(int i = 0 ; i < childs.size(); i++)
846         {
847                 childs[i].treeTour(lvl);                
848         }
849 }
850
851 void NodeTreeC::setData(std::string _data)
852 {
853         data = _data;
854         //std::cout<<"NodeTreeC::setData"<<std::endl;
855 }
856
857 }