Files correlati : tuttissimi Ricompilazione Demo : [ ] Commento : Aggiunto supporto per ListBox in stile Outlook Migliorata gestione Status Bar git-svn-id: svn://10.65.10.50/trunk@16064 c028cbd2-c16b-5b4b-a496-9718f37d4682
		
			
				
	
	
		
			530 lines
		
	
	
		
			14 KiB
		
	
	
	
		
			C++
		
	
	
		
			Executable File
		
	
	
	
	
			
		
		
	
	
			530 lines
		
	
	
		
			14 KiB
		
	
	
	
		
			C++
		
	
	
		
			Executable File
		
	
	
	
	
#include <agasys.h>
 | 
						||
#include <archives.h>
 | 
						||
#include <config.h>
 | 
						||
#include <diction.h>
 | 
						||
#include <isam.h>
 | 
						||
#include <progind.h>
 | 
						||
#include <utility.h>
 | 
						||
 | 
						||
#include <nditte.h>
 | 
						||
 | 
						||
///////////////////////////////////////////////////////////
 | 
						||
// TArchive
 | 
						||
///////////////////////////////////////////////////////////
 | 
						||
 | 
						||
int TArchive::build_backup_list(int mode, long firm, TString_array& fl) const
 | 
						||
{
 | 
						||
  fl.destroy();
 | 
						||
  
 | 
						||
  if (mode & 0x1)
 | 
						||
    fl.add(firm2dir(0L));
 | 
						||
 | 
						||
  if (mode & 0x2)
 | 
						||
  {
 | 
						||
    if (firm <= 0L)
 | 
						||
    {                     
 | 
						||
      TLocalisamfile ditte(LF_NDITTE);
 | 
						||
      for (int err = ditte.first(); err == NOERR; err = ditte.next())
 | 
						||
      {
 | 
						||
        const char* dir = firm2dir(ditte.get_long(NDT_CODDITTA));
 | 
						||
        if (fexist(dir))
 | 
						||
          fl.add(dir);
 | 
						||
      }  
 | 
						||
    }
 | 
						||
    else
 | 
						||
      fl.add(firm2dir(firm));
 | 
						||
  }
 | 
						||
  
 | 
						||
  if (mode & 0x4)
 | 
						||
  {
 | 
						||
    TFilename name(firm2dir(-1));     // __ptprf
 | 
						||
    name.add("config");               // Aggiungi configurazioni
 | 
						||
    if (name.exist())
 | 
						||
      fl.add(name);                                                
 | 
						||
  }  
 | 
						||
  
 | 
						||
  if (mode & 0x8)
 | 
						||
  {
 | 
						||
    TFilename name(firm2dir(-1));     // __ptprf
 | 
						||
    name.add("M770");                 // Aggiungi 770
 | 
						||
    if (fexist(name))
 | 
						||
      fl.add(name);                                                
 | 
						||
  }  
 | 
						||
 | 
						||
  return fl.items();  
 | 
						||
}
 | 
						||
 | 
						||
// @doc EXTERNAL
 | 
						||
 | 
						||
// @mfunc Costruisce la lista delle directory da scompattare
 | 
						||
//
 | 
						||
// @rdesc Ritorna il numero di cartelle da ripristinare
 | 
						||
int TArchive::build_restore_list(
 | 
						||
    int& mode, 
 | 
						||
    long firm,                // @parm Ditta di cui effettuare il salvataggio
 | 
						||
    char floppy,              // @parm Floppy su cui effettuare il backup
 | 
						||
    TString_array& fl) const  // @parm Nomi dell cartelle da ripristinare
 | 
						||
{   
 | 
						||
  fl.destroy();
 | 
						||
 | 
						||
  if (!yesno_box("Inserire il dischetto nel drive %c e continuare?\n"
 | 
						||
                 "(Rispondere NO se si desidera interrompere la procedura)", floppy))
 | 
						||
    return -1;
 | 
						||
  
 | 
						||
  TFilename name("a:/backup.ini"); name[0] = floppy;
 | 
						||
  TConfig ini(name);                                                      
 | 
						||
  TString_array pl;
 | 
						||
  const int max = ini.list_paragraphs(pl);          // Lista degli archivi
 | 
						||
  for (int i = 0; i < max; i++)
 | 
						||
  {
 | 
						||
    const TString& name = pl.row(i);
 | 
						||
    const int disk = ini.get_int("Disk", name);
 | 
						||
    if (disk == 1) 
 | 
						||
    {      
 | 
						||
      if (atol(name) > 0L)
 | 
						||
      {                        
 | 
						||
        if (mode & 0x2)
 | 
						||
        {
 | 
						||
          const long frm = atol(name);
 | 
						||
          if (firm <= 0L || firm == frm)
 | 
						||
            fl.add(firm2dir(frm)); // Aggiungi gli archivi della ditta
 | 
						||
          if (firm > 0L)  
 | 
						||
            mode &= ~0x2;
 | 
						||
        }  
 | 
						||
      }
 | 
						||
      else
 | 
						||
      {
 | 
						||
        if (name.compare("com", -1, TRUE) == 0)
 | 
						||
        {
 | 
						||
          if (mode & 0x1)
 | 
						||
            mode &= ~0x1;
 | 
						||
          else  
 | 
						||
            continue;
 | 
						||
        }  
 | 
						||
        if (name.compare("config", -1, TRUE) == 0)
 | 
						||
        {
 | 
						||
          if (mode & 0x4)
 | 
						||
            mode &= ~0x4;
 | 
						||
          else  
 | 
						||
            continue;
 | 
						||
        }  
 | 
						||
        if (name.compare("m770", -1, TRUE) == 0)
 | 
						||
        {
 | 
						||
          if (mode & 0x8)
 | 
						||
            mode &= ~0x8;
 | 
						||
          else  
 | 
						||
            continue;
 | 
						||
        }  
 | 
						||
        
 | 
						||
        TFilename fn(firm2dir(-1)); // __ptprf
 | 
						||
        fn.add(name);               
 | 
						||
        fl.add(fn);
 | 
						||
      }
 | 
						||
    }
 | 
						||
  } 
 | 
						||
  
 | 
						||
  return fl.items();    
 | 
						||
}
 | 
						||
 | 
						||
// @doc EXTERNAL
 | 
						||
 | 
						||
// @mfunc Scrive il file backup.ini sul drive indicato
 | 
						||
//
 | 
						||
// @rdesc Ritorna se e' riuscito a scrivere il file
 | 
						||
bool TArchive::write_ini(TFilename& work, int disk, long tot, const char* desc, char floppy) const
 | 
						||
 | 
						||
{
 | 
						||
  TFilename parag(work.name()); parag.ext("");
 | 
						||
  TFilename ini("a:/backup.ini"); ini[0] = floppy;
 | 
						||
  bool ok = TRUE;
 | 
						||
          
 | 
						||
  if (fexist(ini)) 
 | 
						||
  {
 | 
						||
    TConfig c(ini, parag);
 | 
						||
    const int d = c.get_int("Disk");
 | 
						||
    if (d == disk)
 | 
						||
    {
 | 
						||
      ok = yesno_box(FR("Il disco %d contiene gia' un backup della cartella %s del %s"
 | 
						||
                     "\nSi desidera continuare?"), 
 | 
						||
                     disk, (const char*)parag, (const char*)c.get("Date"));
 | 
						||
    }    
 | 
						||
  }  
 | 
						||
  else
 | 
						||
  {
 | 
						||
    FILE* i = fopen(ini, "w");    // Crea il file backup.ini per evitare messaggi
 | 
						||
    fclose(i);
 | 
						||
  }
 | 
						||
 | 
						||
  if (ok)
 | 
						||
  {        
 | 
						||
    TConfig c(ini, parag);
 | 
						||
    const char* oggi = TDate(TODAY).string();
 | 
						||
    c.set("Size", tot , NULL, TRUE); 
 | 
						||
    c.set("Disk", disk, NULL, TRUE);
 | 
						||
    c.set("Description", desc, NULL, TRUE);
 | 
						||
    c.set("Date", oggi, NULL, TRUE);
 | 
						||
  }
 | 
						||
  
 | 
						||
  return ok;
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::move_file(const TFilename& file, const char* dir) const
 | 
						||
{
 | 
						||
  TFilename dest(dir);
 | 
						||
  dest.add(file.name());
 | 
						||
  
 | 
						||
  const long needed = fsize(file) - fsize(dest);
 | 
						||
  bool space_ok = needed <= 0;
 | 
						||
  while (!space_ok)
 | 
						||
  {
 | 
						||
    space_ok = xvt_fsys_test_disk_free_space(dir, needed) != 0;
 | 
						||
    if (!space_ok)
 | 
						||
    {
 | 
						||
      TString msg(128);
 | 
						||
      msg.format(FR("Lo spazio disponibile e' insufficiente:\nNecessario: %.1lf Mb; Disponibile: %ld Mb\n"),
 | 
						||
                    needed/(1024.0*1024.0), xvt_fsys_get_disk_free_space(dir, 'M'));
 | 
						||
      if (xvt_fsys_is_floppy_drive(dir))
 | 
						||
        msg << TR("Inserire un nuovo disco e ritentare?");
 | 
						||
      else                                               
 | 
						||
        msg << TR("Liberare dello spazio e ritentare?");
 | 
						||
      if (!yesno_box(msg))
 | 
						||
        return FALSE;
 | 
						||
    }  
 | 
						||
  }  
 | 
						||
 | 
						||
  bool write_ok = TRUE;
 | 
						||
  bool user_abort = FALSE;
 | 
						||
  do
 | 
						||
  {
 | 
						||
    write_ok = ::fcopy(file, dest);
 | 
						||
    if (write_ok) 
 | 
						||
      ::remove(file);  
 | 
						||
    else
 | 
						||
    {
 | 
						||
      if (!yesno_box(FR("Errore di copia del file %s.\nSi desidera riprovare?"),
 | 
						||
                     (const char*)file))
 | 
						||
        user_abort = TRUE;
 | 
						||
    }    
 | 
						||
  } while (!write_ok && !user_abort);
 | 
						||
    
 | 
						||
  return write_ok;
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::split_file(const TFilename& archive, unsigned long max_chunk) const
 | 
						||
{
 | 
						||
  TFilename output(archive);
 | 
						||
  output.ext("z00");
 | 
						||
  
 | 
						||
  int disk = 0;
 | 
						||
  unsigned long scritti = 0;
 | 
						||
 | 
						||
  FILE* i = fopen(archive, "rb");
 | 
						||
  if (i == NULL)
 | 
						||
    return FALSE;
 | 
						||
  
 | 
						||
  FILE* o = fopen(output, "wb");
 | 
						||
  
 | 
						||
  const int BUFSIZE = 1024*16; 
 | 
						||
  TString buf(BUFSIZE);
 | 
						||
  char* buffer = buf.get_buffer();
 | 
						||
  
 | 
						||
  bool ok = TRUE;
 | 
						||
  while (ok)
 | 
						||
  {
 | 
						||
    const size_t letti = fread(buffer, 1, BUFSIZE, i);
 | 
						||
    if (letti == 0)
 | 
						||
      break;
 | 
						||
    
 | 
						||
    if (scritti >= max_chunk)
 | 
						||
    {
 | 
						||
      fclose(o);    
 | 
						||
       
 | 
						||
      TString16 ext; ext.format("z%02d", ++disk);
 | 
						||
      output.ext(ext);
 | 
						||
      o = fopen(output, "wb");
 | 
						||
      scritti = 0;
 | 
						||
    }
 | 
						||
 | 
						||
    ok = fwrite(buffer, letti, 1, o) > 0;
 | 
						||
    scritti += letti;
 | 
						||
  }    
 | 
						||
  fclose(i);
 | 
						||
  fclose(o);
 | 
						||
  
 | 
						||
  return ok;
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::fsplit_zip(
 | 
						||
     const char* filename,    // @parm Nome del file da spezzare
 | 
						||
     char floppy,             // @parm Floppy su cui scaricare il file
 | 
						||
     const char* desc) const  // @parm Descrizione dell'archivio
 | 
						||
{                  
 | 
						||
  const TFilename archive(filename);
 | 
						||
                    
 | 
						||
  unsigned long size = 0;                  
 | 
						||
  TFilename path; path << floppy << ':';
 | 
						||
  
 | 
						||
  while (size <= 0)
 | 
						||
  {
 | 
						||
    if (xvt_fsys_is_floppy_drive(path))
 | 
						||
      message_box(FR("Inserire il disco 1 nel drive %c:"), floppy);
 | 
						||
    size = xvt_fsys_get_disk_size(path, 'K') - 64;
 | 
						||
    if (size <= 0)
 | 
						||
    {
 | 
						||
      if (!yesno_box(FR("Errore di accesso al drive %c\nSi desidera ritentare?"), floppy))
 | 
						||
        return FALSE;
 | 
						||
    }
 | 
						||
    do_events();
 | 
						||
  } 
 | 
						||
 | 
						||
  const unsigned long minsize = 360*1024L;
 | 
						||
  if (size < minsize)
 | 
						||
    size = minsize;
 | 
						||
 | 
						||
	if (!split_file(archive, size))
 | 
						||
    return error_box(FR("Errore durante lo splitting del file %s"), (const char*)archive);
 | 
						||
  
 | 
						||
  size = ::fsize(archive);
 | 
						||
  ::remove(archive);
 | 
						||
 | 
						||
  for (int d = 0; ; d++)
 | 
						||
  {            
 | 
						||
    TString16 ext; ext.format("z%02d", d);
 | 
						||
    TFilename src(archive);
 | 
						||
    src.ext(ext);
 | 
						||
    if (src.exist())
 | 
						||
    {            
 | 
						||
      if (d > 0)
 | 
						||
      {
 | 
						||
        message_box(FR("Inserire il disco %d nel drive %c:"), d+1, floppy);
 | 
						||
        do_events();
 | 
						||
      }
 | 
						||
    
 | 
						||
      if (move_file(src, path))
 | 
						||
      {
 | 
						||
        TFilename ini(path);
 | 
						||
        ini.add("backup.ini");
 | 
						||
        TConfig c(ini, archive.name());
 | 
						||
        c.set("Size", size); 
 | 
						||
        c.set("Disk", d+1);
 | 
						||
        c.set("Description", desc);
 | 
						||
        c.set("Date", TDate(TODAY).string());
 | 
						||
      }
 | 
						||
      else
 | 
						||
        break;
 | 
						||
    } 
 | 
						||
    else
 | 
						||
      break;
 | 
						||
  }  
 | 
						||
                                                            
 | 
						||
  return TRUE;                                                          
 | 
						||
}
 | 
						||
 | 
						||
// @doc EXTERNAL
 | 
						||
 | 
						||
// @mfunc Effettua il backup della directory
 | 
						||
//
 | 
						||
// @rdesc Ritorna il risultato dell'operazione
 | 
						||
bool TArchive::zip(
 | 
						||
     const char* dir,  // @parm Directory di cui effettuare il backup
 | 
						||
     char floppy,      // @parm Floppy su cui effettuare il backup
 | 
						||
     const char* desc) // @parm Descrizione da assegnare al backup
 | 
						||
                       // @parm long | firm | Ditta di cui effettuare il backup
 | 
						||
                       
 | 
						||
// @syntax bool backup(const char* dir, char floppy, const char* desc, bool pr_set);
 | 
						||
// @syntax bool backup(long firm, char floppy, const char* desc, bool pr_set);
 | 
						||
 | 
						||
// @comm Il parametro <p pr_set> e' utilizzato per evitare errori di riaperture di files.
 | 
						||
 | 
						||
{                                      
 | 
						||
  safely_close_closeable_isamfiles();
 | 
						||
 | 
						||
  DIRECTORY currdir, newdir;
 | 
						||
  xvt_fsys_get_dir( &currdir);  //memorizza la directory dove e'
 | 
						||
 | 
						||
  xvt_fsys_convert_str_to_dir(dir, &newdir);  //converte il nome della directory
 | 
						||
  xvt_fsys_set_dir( &newdir);  //passa alla directory dir che gli viene passata
 | 
						||
  
 | 
						||
  const TFilename workdir = dir;
 | 
						||
  const TString name = workdir.name();
 | 
						||
  
 | 
						||
  // Nome del file compresso
 | 
						||
  TFilename work; work.tempdir(); work.add(name); work.ext("zip");
 | 
						||
 | 
						||
  TString title(TR("Archiviazione")); title << ' ' << workdir;
 | 
						||
  TIndwin waitw(100,title,FALSE,FALSE); 
 | 
						||
  TWait_cursor hourglass;
 | 
						||
 | 
						||
  TString_array filenames;
 | 
						||
  list_files("*.*", filenames);
 | 
						||
  
 | 
						||
  // Crea il file con la lista dei file da comprimere
 | 
						||
  const char* const ZIPLIST = "ziplist.txt";
 | 
						||
  FILE* flist = fopen(ZIPLIST, "w");
 | 
						||
 | 
						||
  FOR_EACH_ARRAY_ROW(filenames, r, row)
 | 
						||
    fprintf(flist, "%s\n",(const char *)*row);
 | 
						||
 | 
						||
  fclose(flist);
 | 
						||
 | 
						||
  bool ok = ::aga_zip_filelist(ZIPLIST, work);
 | 
						||
 | 
						||
  remove(ZIPLIST);  //elimina il file di testo con la lista dei files
 | 
						||
 | 
						||
  xvt_fsys_set_dir( &currdir);  //torna a posizionarsi nella directory iniziale
 | 
						||
 | 
						||
  if (ok)
 | 
						||
    ok = fsplit_zip(work, floppy, desc);
 | 
						||
  else  
 | 
						||
    error_box(TR("Compressione degli archivi errata o incompleta"));
 | 
						||
  
 | 
						||
  return ok;
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::zip(int mode, long firm, char floppy, const char* desc)
 | 
						||
{                     
 | 
						||
  TString_array fl;
 | 
						||
  const int num_ditte = build_backup_list(mode, firm, fl);
 | 
						||
  
 | 
						||
  bool ok = TRUE;
 | 
						||
  for (int f = 0; f < num_ditte; f++)
 | 
						||
  {                                  
 | 
						||
    ok = zip(fl.row(f), floppy, desc);
 | 
						||
    if (!ok) break;
 | 
						||
  }
 | 
						||
  
 | 
						||
  return ok;  
 | 
						||
}
 | 
						||
 | 
						||
// @doc EXTERNAL
 | 
						||
 | 
						||
// @mfunc Effettua il restore della directory
 | 
						||
//
 | 
						||
// @rdesc Ritorna il risultato dell'operazione
 | 
						||
bool TArchive::unzip(
 | 
						||
     const char* dir,   // @parm Directory di cui effettuare il restore
 | 
						||
     char floppy,       // @parm Unita' da cui leggere i dati
 | 
						||
     bool tmp)          // @parm Directory temporanea da utilizzare
 | 
						||
// @syntax bool restore(const char* dir, char floppy, bool temp, bool pr_set);
 | 
						||
// @syntax bool restore(long firm, char floppy, bool temp, bool pr_set);
 | 
						||
// @comm Il parametro <p pr_set> e' utilizzato per evitare errori di riaperture di files.
 | 
						||
{                 
 | 
						||
  TFilename work;
 | 
						||
  if (tmp) 
 | 
						||
    work.tempdir();
 | 
						||
  else 
 | 
						||
    work = dir;
 | 
						||
  
 | 
						||
  TFilename output(dir); 
 | 
						||
  output = output.name(); 
 | 
						||
  output.ext("zip");
 | 
						||
 | 
						||
  if (!yesno_box(FR("Attenzione l'archivio %c:\\%s verra' ripristinato\n"
 | 
						||
                 "nel direttorio %s. Continuare?"), 
 | 
						||
                 floppy, (const char*)output, (const char*)work))
 | 
						||
    return FALSE;             
 | 
						||
  
 | 
						||
  bool ok = work.exist();
 | 
						||
  if (!ok) 
 | 
						||
  {
 | 
						||
    ok = yesno_box(FR("Non esiste il direttorio %s: si desidera crearlo?"), (const char*)work);
 | 
						||
    if (ok) 
 | 
						||
    {
 | 
						||
      make_dir(work);
 | 
						||
      ok = work.exist();
 | 
						||
    }  
 | 
						||
    if (!ok)
 | 
						||
      return error_box(FR("Impossibile accedere a %s"), (const char*)work);
 | 
						||
  }  
 | 
						||
  
 | 
						||
  TString title(TR("Ripristino")); title << ' ' << output;
 | 
						||
  TIndwin waitw(100,title,FALSE,FALSE); 
 | 
						||
 | 
						||
  safely_close_closeable_isamfiles();
 | 
						||
  
 | 
						||
  TFilename cfg;
 | 
						||
  cfg << floppy << ':';
 | 
						||
  cfg.add("backup.ini");
 | 
						||
  TConfig c(cfg, output.name());
 | 
						||
  const unsigned long total_size = c.get_long("Size");
 | 
						||
  unsigned long read_size = 0;
 | 
						||
 | 
						||
	TFilename restored;
 | 
						||
	restored.tempdir();
 | 
						||
	restored.add(output.name());
 | 
						||
	restored.ext("zip");
 | 
						||
 | 
						||
  for (int d = 0; read_size < total_size; d++)
 | 
						||
  {
 | 
						||
		TString16 ext; ext.format("z%02d", d);
 | 
						||
    TFilename src;
 | 
						||
    src << floppy << ':' << SLASH;
 | 
						||
    src << output.name();
 | 
						||
    src.ext(ext);
 | 
						||
    if (xvt_fsys_is_floppy_drive(src))
 | 
						||
      message_box("Inserire il disco %d contenente il file %s", d+1, (const char*)src);
 | 
						||
    
 | 
						||
    while (!src.exist())
 | 
						||
    {
 | 
						||
      if (!yesno_box("Impossibile aprire il file %s:\nSi desidera ritentare?", 
 | 
						||
                     (const char *)src))
 | 
						||
        break;
 | 
						||
    }
 | 
						||
    
 | 
						||
    if (src.exist())
 | 
						||
    {
 | 
						||
			fcopy(src, restored, d > 0);
 | 
						||
      read_size = ::fsize(restored);
 | 
						||
    }
 | 
						||
    else
 | 
						||
      break;
 | 
						||
  }
 | 
						||
	ok = read_size == total_size;
 | 
						||
	if (ok)
 | 
						||
  {
 | 
						||
	  ok = ::aga_unzip(restored, work);
 | 
						||
    if (ok)
 | 
						||
      remove(restored);
 | 
						||
  }
 | 
						||
	else
 | 
						||
		error_box("Il file %s non <20> stato ripristinato completamente", (const char*)restored);
 | 
						||
 | 
						||
  return ok;
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::unzip(int mode, long firm, char floppy, bool temp)
 | 
						||
{
 | 
						||
  TString_array fl;
 | 
						||
  const int num_ditte = build_restore_list(mode, firm, floppy, fl);
 | 
						||
  
 | 
						||
  bool ok = TRUE;
 | 
						||
  for (int f = 0; f < num_ditte; f++)
 | 
						||
  {                                  
 | 
						||
    ok = unzip(fl.row(f), floppy, temp);
 | 
						||
    if (!ok) break;
 | 
						||
  }
 | 
						||
  return ok;  
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::backup(const char* dir, char floppy, const char* desc, bool)
 | 
						||
{
 | 
						||
  return zip(dir, floppy, desc);
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::backup(int mode, long firm, char floppy, const char* desc, bool)
 | 
						||
{
 | 
						||
  return zip(mode, firm, floppy, desc);
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::restore(const char* dir, char floppy, bool tmp, bool)   
 | 
						||
{
 | 
						||
  return unzip(dir, floppy, tmp);
 | 
						||
}
 | 
						||
 | 
						||
bool TArchive::restore(int mode, long firm, char floppy, bool tmp, bool)
 | 
						||
{
 | 
						||
  return unzip(mode, firm, floppy, tmp);
 | 
						||
}
 | 
						||
 | 
						||
 |