Files correlati :ba1.exe, sys.z Ricompilazione Demo : [ ] Commento :sistemata doppia conversione archivi in installazione (quando si installava SY) e problema, nella seconda conversione, del golem git-svn-id: svn://10.65.10.50/trunk@12255 c028cbd2-c16b-5b4b-a496-9718f37d4682
1473 lines
41 KiB
C++
Executable File
1473 lines
41 KiB
C++
Executable File
#include <stdio.h>
|
||
|
||
#include <cfiles.h>
|
||
|
||
#include <agasys.h>
|
||
#include <applicat.h>
|
||
#include <defmask.h>
|
||
#include <dongle.h>
|
||
#include <execp.h>
|
||
#include <isamrpc.h>
|
||
#include <modaut.h>
|
||
#include <progind.h>
|
||
#include <sheet.h>
|
||
#include <utility.h>
|
||
|
||
#include "ba1.h"
|
||
#include "ba1500.h"
|
||
#include "ba1600.h"
|
||
#include "ba1700a.h"
|
||
|
||
// definizioni delle colonne dello sheet
|
||
#define C_MODULE 1
|
||
#define C_CODE 2
|
||
#define C_RELEASE 3
|
||
#define C_PATCH 4
|
||
#define C_DATAREL 5
|
||
#define C_CURRRELEASE 6
|
||
#define C_CURRPATCH 7
|
||
#define C_CURRDATAREL 8
|
||
#define C_ISPATCH 9
|
||
#define C_BASEPATCH 10
|
||
|
||
#ifdef _DEMO_
|
||
const char* const http_default_path = "/aga/demo/zip/";
|
||
#else
|
||
const char* const http_default_path = "/aga/program/zip/";
|
||
#endif
|
||
|
||
HIDDEN int compare_version(const char* v1, int p1, const char* v2, int p2)
|
||
{
|
||
TString16 ver1(v1), ver2(v2);
|
||
ver1.trim();
|
||
if (ver1.len() == 4)
|
||
ver1.insert((v1[0] == '9') ? "19" : "20", 0);
|
||
ver2.trim();
|
||
if (ver2.len() == 4)
|
||
ver2.insert((v2[0] == '9') ? "19" : "20", 0);
|
||
|
||
int res = ver1.compare(ver2, -1, TRUE);
|
||
if (res == 0)
|
||
res = p1 - p2;
|
||
|
||
return res;
|
||
}
|
||
|
||
HIDDEN word version2year(const char* v)
|
||
{
|
||
TString16 ver(v);
|
||
if (ver.len() == 4)
|
||
ver.insert((v[0] == '9') ? "19" : "20", 0);
|
||
ver.cut(4);
|
||
return atoi(ver);
|
||
}
|
||
|
||
bool is_internet_path(const TString& addr)
|
||
{
|
||
if (addr.compare("www.", 4, TRUE) == 0)
|
||
return TRUE;
|
||
|
||
if (addr.compare("http:", 5, TRUE) == 0)
|
||
return TRUE;
|
||
|
||
int a1, a2, a3, a4;
|
||
if (sscanf(addr, "%d.%d.%d.%d", &a1, &a2, &a3, &a4) == 4)
|
||
return TRUE;
|
||
|
||
return FALSE;
|
||
}
|
||
|
||
///////////////////////////////////////////////////////////
|
||
// Maschera principale
|
||
///////////////////////////////////////////////////////////
|
||
|
||
class TInstaller_mask : public TArray_sheet
|
||
{
|
||
static TInstaller_mask* _curr_mask;
|
||
bool _installed; // Flag per verificare se almeno un modulo e' stato installato
|
||
bool _sys_installed; //Flag per controllare l'installazione del modulo di sistema SY
|
||
|
||
enum { NONE = 0, NEW_MENU = 1, NEW_MENUPRG = 2, NEW_INSTALLER = 4, NEW_DLL = 8 };
|
||
int _reboot_program;
|
||
|
||
protected: // TSheet
|
||
virtual bool on_key(KEY key);
|
||
static bool quit_handler(TMask_field& f, KEY k);
|
||
static bool tutti_handler(TMask_field& f, KEY k);
|
||
int get_module_number(const TString& module) const;
|
||
bool has_module(int modnumber) const;
|
||
bool is_zip_file(const TFilename& n) const;
|
||
|
||
void create_dirs(const char* path) const;
|
||
|
||
protected:
|
||
static bool path_handler(TMask_field& fld, KEY key);
|
||
static bool sheet_notify(TSheet_field& s, int r, KEY k);
|
||
static bool install_handler(TMask_field& fld, KEY key);
|
||
static bool update_handler(TMask_field& f, KEY k);
|
||
|
||
bool add_module(TConfig& ini, const TString& module, bool patch, int pos=-1);
|
||
bool add_header(TConfig& ini, const TString& module, bool patch);
|
||
int precheck_modules(bool only_newer=TRUE);
|
||
void update_version();
|
||
|
||
int needs_reboot(const TFilename& file) const;
|
||
bool move_file(const TFilename& src, const TFilename& dst) const;
|
||
bool move_module(const TString& module, TInstall_ini& ini, bool update) const;
|
||
|
||
bool can_install(const char* module, TInstall_ini& ini);
|
||
void install_selection();
|
||
bool install_patches(const TString& module, const TString& lastrelease, int lastpatch , bool onlynew=TRUE);
|
||
KEY askdisk(TString & path, TFilename & cmdline, int d, int dischi, const char * modulo);
|
||
|
||
bool do_process(TToken_string& commands) const;
|
||
bool pre_process(TInstall_ini& ini, const char* module) const;
|
||
bool post_process(TInstall_ini& ini, const char* module) const;
|
||
bool get_internet_path(TFilename& ininame) const;
|
||
void parse_internet_path(TString& http_server, TFilename& http_path) const;
|
||
|
||
public:
|
||
bool installed() const { return _installed;}
|
||
bool sys_installed() const { return _sys_installed;}
|
||
bool autoload();
|
||
bool install(const TString& module, int patch);
|
||
bool run_ba0close() const { return _reboot_program >= NEW_MENUPRG; }
|
||
|
||
TInstaller_mask();
|
||
virtual ~TInstaller_mask();
|
||
};
|
||
|
||
TInstaller_mask* TInstaller_mask::_curr_mask = NULL;
|
||
|
||
// Copia nello sheet i dati di un modulo prendendoli da un .ini
|
||
bool TInstaller_mask::add_module(TConfig& ini, const TString& module, bool patch, int pos)
|
||
{
|
||
ini.write_protect();
|
||
bool ok = ini.set_paragraph(module);
|
||
if (ok)
|
||
{
|
||
const int numpatch = ini.get_int("Patch");
|
||
TString16 strpatch;
|
||
if (numpatch > 0)
|
||
strpatch.format("%03d", numpatch);
|
||
|
||
TToken_string row;
|
||
row = " "; // Not selected
|
||
row.add(ini.get("Descrizione"));
|
||
row.add(module);
|
||
row.add(ini.get("Versione"));
|
||
row.add(strpatch);
|
||
row.add(ini.get("Data"));
|
||
row.add(patch ? "X" : " ", C_ISPATCH);
|
||
if (pos==-1)
|
||
add(row);
|
||
else
|
||
insert(row,pos);
|
||
}
|
||
return ok;
|
||
}
|
||
|
||
// Copia nello sheet i dati di un modulo prendendoli da un .ini
|
||
bool TInstaller_mask::add_header(TConfig& ini, const TString& module, bool patch)
|
||
{
|
||
ini.write_protect();
|
||
bool ok = ini.set_paragraph(module);
|
||
if (ok)
|
||
{
|
||
TToken_string row;
|
||
row = " "; // Not selected
|
||
row.add(ini.get("Descrizione"));
|
||
row.add(ini.get(" "));
|
||
enable_row(add(row),FALSE);
|
||
}
|
||
return ok;
|
||
}
|
||
|
||
static int compare_modules(const TObject** o1, const TObject** o2)
|
||
{
|
||
TToken_string& ts1 = *(TToken_string*)(*o1);
|
||
TToken_string& ts2 = *(TToken_string*)(*o2);
|
||
|
||
int res = 0;
|
||
for (int i = 2; i < 5 && res == 0; i++)
|
||
{
|
||
TString16 s1 = ts1.get(i);
|
||
const char* s2 = ts2.get(i);
|
||
res = s1.compare(s2);
|
||
}
|
||
return res;
|
||
}
|
||
|
||
bool TInstaller_mask::has_module(int modnumber) const
|
||
{
|
||
if (modnumber == SRAUT)
|
||
{
|
||
char s[16];
|
||
if (xvt_fsys_get_campo_stp_value("Servers", s, sizeof(s)) || xvt_fsys_get_campo_stp_value("Sy", s, sizeof(s))) //***aggiunto il modulo sy
|
||
return atoi(s) > 0;
|
||
}
|
||
return main_app().has_module(modnumber, CHK_DONGLE);
|
||
}
|
||
|
||
int TInstaller_mask::precheck_modules(bool only_newer)
|
||
{
|
||
TString16 release,currrelease;
|
||
TString4 cod_module;
|
||
int patchlevel,modnumber,currpatch;
|
||
|
||
TString_array& array = rows_array();
|
||
FOR_EACH_ARRAY_ROW(array, r, row)
|
||
{
|
||
TToken_string& rigar = *row;
|
||
cod_module = rigar.get(C_CODE);
|
||
release = rigar.get(C_RELEASE);
|
||
patchlevel = rigar.get_int(C_PATCH);
|
||
currrelease = rigar.get(C_CURRRELEASE);
|
||
currpatch = rigar.get_int(C_CURRPATCH);
|
||
modnumber = get_module_number(cod_module);
|
||
if (modnumber >= 0 && has_module(modnumber) &&
|
||
!release.blank() &&
|
||
((release > currrelease) ||
|
||
(release == currrelease && (only_newer ? patchlevel>currpatch: patchlevel>=currpatch) ))
|
||
)
|
||
{
|
||
// checca il modulo o la patch se ho installata la stessa versione
|
||
const bool chk = rigar.get_char(C_ISPATCH) != 'X' || release == currrelease;
|
||
check(r, chk);
|
||
if (chk && only_newer && cod_module == "sy") //se viene checkato il modulo sy (sistema) deve togliere..
|
||
{ //..la possibilita' di installare altri moduli..
|
||
for (int i = 0; i < array.items(); i++)
|
||
disable_row(i); //disabilita tutte le righe dello sheet
|
||
disable(DLG_USER);
|
||
break; //..ed uscire
|
||
}
|
||
}
|
||
}
|
||
force_update(); // Indispensabile per vedere le righe aggiornate
|
||
return items();
|
||
}
|
||
|
||
|
||
int TInstaller_mask::get_module_number(const TString& module) const
|
||
{
|
||
int aut = -1;
|
||
bool ok = FALSE;
|
||
if (module.not_empty())
|
||
{
|
||
if (module == "ba" || module == "sy") //moduli base e sistema: deve ritornare 0;
|
||
return 0;
|
||
|
||
TScanner scanner(AUT_FILE);
|
||
for (aut = 0; scanner.line() != ""; aut++)
|
||
if (scanner.token().starts_with(module))
|
||
{ ok = TRUE; break; }
|
||
}
|
||
return ok ? aut : -1;
|
||
}
|
||
|
||
|
||
void TInstaller_mask::update_version()
|
||
{
|
||
TInstall_ini ini;
|
||
|
||
TString_array& array = rows_array();
|
||
FOR_EACH_ARRAY_ROW_BACK(array, m, row)
|
||
{
|
||
if (*row->get(C_CODE) != ' ')
|
||
{
|
||
const TString16 module = row->get(C_CODE);
|
||
ini.set_paragraph(module);
|
||
|
||
const TString16 newver = row->get(C_RELEASE);
|
||
const TString16 oldver = ini.get("Versione");
|
||
const int numpatch = ini.get_int("Patch");
|
||
TString16 strpatch;
|
||
if (numpatch > 0) strpatch.format("%03d", numpatch);
|
||
row->add(oldver, C_CURRRELEASE);
|
||
row->add(strpatch, C_CURRPATCH);
|
||
row->add(ini.get("Data"), C_CURRDATAREL);
|
||
}
|
||
}
|
||
force_update();
|
||
}
|
||
|
||
// Cerca nel percorso specificato sulla maschera tutti i possibili files .ini
|
||
// utilizzabili per un'installazione e li inserisce nello spreadsheet
|
||
bool TInstaller_mask::autoload()
|
||
{
|
||
TString_array& mask_rows = rows_array();
|
||
|
||
TString http_server;
|
||
TFilename http_path;
|
||
|
||
TFilename path ;
|
||
TFilename ininame;
|
||
|
||
const bool internet = get_internet_path(path);
|
||
|
||
if (internet)
|
||
{
|
||
parse_internet_path(http_server,http_path);
|
||
|
||
make_dir(path);
|
||
|
||
ininame = path;
|
||
ininame.add(TInstall_ini::default_name());
|
||
|
||
if (ininame.exist() && yesno_box(TR("Si desidera svuotare la cache dei files scaricati dal sito?")))
|
||
{
|
||
TString_array list;
|
||
TFilename name = path; name.add("*.*");
|
||
::list_files(name, list);
|
||
|
||
FOR_EACH_ARRAY_ROW(list, i, row)
|
||
::remove(*row);
|
||
}
|
||
if (!ininame.exist())
|
||
{
|
||
bool httpresult;
|
||
TFilename remote_ini = http_path;
|
||
remote_ini << TInstall_ini::default_name();
|
||
{
|
||
TIndwin contacting(60,TR("Connessione al server HTTP..."),FALSE,FALSE);
|
||
httpresult=http_get(http_server, remote_ini, ininame);
|
||
}
|
||
}
|
||
}
|
||
|
||
if (path.exist())
|
||
{
|
||
ininame = path;
|
||
ininame.add(TInstall_ini::default_name());
|
||
}
|
||
else
|
||
return error_box(TR("Specificare un percorso valido"));
|
||
|
||
TWait_cursor hourglass;
|
||
destroy();
|
||
force_update();
|
||
|
||
TString_array modules;
|
||
|
||
if (ininame.exist())
|
||
{
|
||
// Presente il file ini generale "install.ini" (moduli;immagine cd)
|
||
TInstall_ini ini(ininame);
|
||
ini.list_paragraphs(modules); //riempie modules con la lista dei paragrafi sul .ini ***
|
||
|
||
FOR_EACH_ARRAY_ROW(modules, i, row)
|
||
{
|
||
const TString& module = *row;
|
||
if (module[0] == '_' || module.len() == 2)
|
||
{
|
||
|
||
if (module[0] == '_')
|
||
add_header(ini, module, FALSE);
|
||
else
|
||
{
|
||
TFilename mod_ini = ininame.path();
|
||
mod_ini.add(module);
|
||
mod_ini << "inst.ini";
|
||
if (mod_ini.exist())
|
||
{
|
||
TInstall_ini moduleini(mod_ini);
|
||
add_module(moduleini, module, FALSE);
|
||
}
|
||
else
|
||
add_module(ini, module, FALSE);
|
||
}
|
||
}
|
||
}
|
||
}
|
||
else
|
||
{
|
||
// Presenti i singoli file .ini dei moduli (pacchi ma non patches!)
|
||
ininame = path;
|
||
ininame.add("??inst.ini");
|
||
list_files(ininame, modules); //ritorna la lista dei files presenti nel .ini della patch ***
|
||
FOR_EACH_ARRAY_ROW(modules, m, row)
|
||
{
|
||
TString& ininame = *row;
|
||
ininame.lower();
|
||
const int pos = ininame.find("inst.ini");
|
||
CHECKS(pos >= 2, "Invalid installation configuration: ", (const char*)ininame);
|
||
const TString16 module = ininame.mid(pos-2, 2);
|
||
TConfig ini(ininame, module);
|
||
add_module(ini, module, FALSE);
|
||
}
|
||
}
|
||
|
||
modules.destroy();
|
||
|
||
if (internet) //internet patches
|
||
{
|
||
http_dir(http_server, http_path, modules);
|
||
for (int i = modules.last(); i >= 0; i--)
|
||
{
|
||
TString& str = modules.row(i);
|
||
if (str.match("??0???A.INI") || str.match("??0???a.ini"))
|
||
{
|
||
TFilename remote = http_path;
|
||
remote << str;
|
||
|
||
ininame = path;
|
||
ininame.add(str);
|
||
|
||
if (!ininame.exist() && !http_get(http_server, remote, ininame))
|
||
{
|
||
error_box(FR("Errore di trasferimento del file %s"), (const char*)remote);
|
||
modules.destroy(i);
|
||
}
|
||
str = ininame;
|
||
}
|
||
else
|
||
modules.destroy(i);
|
||
}
|
||
modules.pack();
|
||
}
|
||
else //normal patches
|
||
{
|
||
ininame = path;
|
||
ininame.add("??0???a.ini");
|
||
list_files(ininame, modules);
|
||
}
|
||
|
||
if (modules.items() > 0) //ordina i moduli come sull'install.ini locale (per avere SY come primo
|
||
{ //modulo e via via gli altri)
|
||
TInstall_ini installini;
|
||
TString_array paragrafi;
|
||
installini.list_paragraphs(paragrafi);
|
||
TFilename file;
|
||
FOR_EACH_ARRAY_ROW(modules, am, arow)
|
||
{
|
||
file = *arow;
|
||
file = file.name();
|
||
int pos = paragrafi.find(file.left(2));
|
||
if (pos <= 0)
|
||
pos = 10000+am;
|
||
TString8 str;
|
||
str.format("%05d", pos); //aggiunge un numero d'ordine sulla sinistra del nome del file..
|
||
arow->insert(str);
|
||
}
|
||
modules.sort(); //..cosi' che la sort (che ordina alfabeticamente) sistemi la lista moduli
|
||
|
||
FOR_EACH_ARRAY_ROW(modules, bm, brow) //rimette i nomi dei moduli a posto (toglie il numero d'ordine)
|
||
brow->ltrim(5);
|
||
}
|
||
//genera le righe dello sheet di installazione
|
||
FOR_EACH_ARRAY_ROW(modules, am, arow)
|
||
{
|
||
TString& ininame = *arow;
|
||
ininame.lower();
|
||
const int pos = ininame.find("a.ini");
|
||
CHECKS(pos >= 6, TR("Configurazione di installazione non valida: "), (const char*)ininame);
|
||
const TString16 module = ininame.mid(pos-6, 2);
|
||
TConfig ini(ininame, module);
|
||
ini.write_protect();
|
||
for (int r = int(items()-1); r >=0; r--)
|
||
if (module == row(r).get(C_CODE))
|
||
break;
|
||
if (r >= 0)
|
||
{
|
||
const TString16 patchversion = ini.get("Versione");
|
||
const int patchlevel = ini.get_int("Patch");
|
||
TToken_string& row = mask_rows.row(r);
|
||
if (patchversion == row.get(C_RELEASE) // se le versioni corrispondono ...
|
||
&& patchlevel > row.get_int(C_PATCH)) // ..e il patchlevel <20> superiore
|
||
{
|
||
TString16 patch; patch.format("%03d", patchlevel); //aggiunge zeri per avere 3 cifre sempre
|
||
if (*row.get(C_ISPATCH)<=' ') // se era un modulo ...
|
||
{
|
||
row.add("+", C_ISPATCH); // .....setta la presenza di patches
|
||
row.add(row.get(C_PATCH), C_BASEPATCH); // memorizza patch del modulo
|
||
}
|
||
row.add(patch, C_PATCH); // aggiorna il patchlevel mostrato per il modulo
|
||
}
|
||
}
|
||
else
|
||
add_module(ini, module, TRUE);
|
||
}
|
||
update_version();
|
||
const bool ok = precheck_modules() > 0;
|
||
|
||
if (!ok)
|
||
error_box(FR("Non e' stato trovato nessun modulo da installare\nin %s"), (const char*)path);
|
||
|
||
return ok;
|
||
}
|
||
|
||
bool TInstaller_mask::do_process(TToken_string& commands) const
|
||
{
|
||
bool ok = TRUE;
|
||
TFilename cmd;
|
||
for (const char* c = commands.get(0); c && ok; c = commands.get())
|
||
{
|
||
cmd = c;
|
||
if (!cmd.blank())
|
||
{
|
||
TWait_cursor hourglass;
|
||
TExternal_app app(cmd);
|
||
ok = app.run(FALSE,3,TRUE) == 0;
|
||
}
|
||
}
|
||
return ok;
|
||
}
|
||
|
||
bool TInstaller_mask::pre_process(TInstall_ini& ini, const char* module) const
|
||
{
|
||
TAuto_token_string commands(ini.get("PreProcess", module));
|
||
bool ok = do_process(commands);
|
||
return ok;
|
||
}
|
||
|
||
bool TInstaller_mask::post_process(TInstall_ini& ini, const char* module) const
|
||
{
|
||
TAuto_token_string commands(ini.get("PostProcess", module));
|
||
return do_process(commands);
|
||
}
|
||
|
||
bool TInstaller_mask::can_install(const char* module, TInstall_ini& ini)
|
||
{
|
||
TInstall_ini curini;
|
||
if (curini.demo() != ini.demo())
|
||
{
|
||
TString msg;
|
||
msg << TR("Attenzione: Non e' possibile installare la versione ");
|
||
msg << (ini.demo() ? TR("dimostrativa") : TR("normale"));
|
||
msg << TR(" nella cartella della versione ");
|
||
msg << (curini.demo() ? TR("dimostrativa") : TR("normale"));
|
||
return error_box(msg);
|
||
}
|
||
|
||
const TString& version = ini.version(module);
|
||
const word year = version2year(version);
|
||
if (year < 1997)
|
||
return error_box(FR("Il modulo '%s' non ha una versione valida."), module);
|
||
|
||
#ifndef _DEMO_
|
||
if (year > dongle().year_assist())
|
||
return error_box(FR("Per installare la versione %s del modulo '%s'\noccorre il contratto di assistenza per l'anno %d."),
|
||
|
||
(const char*)version, module, year);
|
||
#endif
|
||
|
||
TAuto_token_string altri(ini.get("Moduli", module));
|
||
if (stricmp(module, "sy") != 0) //SY e' indipendente dagli altri moduli
|
||
{
|
||
if (stricmp(module, "ba") != 0 && altri.get_pos("ba") < 0)
|
||
altri.add("ba");
|
||
}
|
||
|
||
bool ok = TRUE;
|
||
TString submodule;
|
||
for (const char* mod = altri.get(0); mod && ok; mod = altri.get())
|
||
{
|
||
submodule = mod;
|
||
if (submodule.len() == 2)
|
||
{
|
||
if (curini.get("Versione", submodule).empty())
|
||
{
|
||
TString msg;
|
||
msg.format(FR("L'installazione del modulo %s richiede la presenza del modulo %s."),
|
||
(const char*)module, (const char*)submodule);
|
||
msg << '\n' << TR("Si desidera procedere alla sua installazione?");
|
||
ok = yesno_box(msg);
|
||
if (ok)
|
||
ok = install(submodule, 0);
|
||
}
|
||
}
|
||
}
|
||
|
||
return ok;
|
||
}
|
||
|
||
int TInstaller_mask::needs_reboot(const TFilename& file) const
|
||
{
|
||
char fname[_MAX_FNAME], ext[_MAX_EXT];
|
||
xvt_fsys_parse_pathname(file, NULL, NULL, fname, ext, NULL);
|
||
|
||
int underscore = NONE;
|
||
if (xvt_str_compare_ignoring_case(ext, "exe") == 0)
|
||
{
|
||
if (xvt_str_compare_ignoring_case(fname, "ba0") == 0)
|
||
underscore = NEW_MENUPRG; else
|
||
if (xvt_str_compare_ignoring_case(fname, "ba1") == 0)
|
||
underscore = NEW_INSTALLER;
|
||
} else
|
||
if (xvt_str_compare_ignoring_case(ext, "dll") == 0)
|
||
underscore = NEW_DLL; else
|
||
if (xvt_str_compare_ignoring_case(ext, "men") == 0)
|
||
underscore = NEW_MENU;
|
||
return underscore;
|
||
}
|
||
|
||
bool TInstaller_mask::is_zip_file(const TFilename& n) const
|
||
{
|
||
const char* ext = n.ext();
|
||
return xvt_str_compare_ignoring_case(ext, "zip") == 0;
|
||
}
|
||
|
||
void TInstaller_mask::create_dirs(const char* path) const
|
||
{
|
||
TToken_string dirs(path, SLASH);
|
||
if (SLASH == '\\')
|
||
dirs.replace('/', SLASH);
|
||
else
|
||
dirs.replace('\\', SLASH);
|
||
|
||
// file contains non existent subdir specification ?
|
||
TFilename subdir;
|
||
for (int c=0; c < dirs.items()-1; c++)
|
||
{
|
||
subdir.add(dirs.get(c));
|
||
if (subdir.right(1) == ":" )
|
||
subdir << SLASH;
|
||
if (!subdir.exist() )
|
||
// build destination directory
|
||
make_dir(subdir);
|
||
}
|
||
}
|
||
|
||
// sposta il file dal direttorio temporaneo a quello passato come destinazione
|
||
bool TInstaller_mask::move_file(const TFilename& src, const TFilename& dst) const
|
||
{
|
||
TFilename dest = dst;
|
||
const int reboot = needs_reboot(dest);
|
||
if (reboot > NEW_MENU && dst.exist())
|
||
{
|
||
dest.rtrim(1);
|
||
dest << '_';
|
||
}
|
||
|
||
if (!dest.exist())
|
||
create_dirs(dest.path());
|
||
|
||
const bool is_zip = is_zip_file(src);
|
||
const long filesize = fsize(src) * (is_zip ? 4 : 1);
|
||
|
||
if (xvt_fsys_test_disk_free_space(dest, filesize) == 0)
|
||
return error_box(TR("Lo spazio sull'unita' di destinazione e' insufficiente"));
|
||
|
||
const bool write_ok = ::fcopy(src, dest);
|
||
if (write_ok && is_zip)
|
||
aga_unzip(src, dest.path());
|
||
|
||
if (write_ok)
|
||
::remove(src);
|
||
|
||
if (write_ok)
|
||
{
|
||
(int&)_reboot_program |= reboot; // Skip const!
|
||
}
|
||
return write_ok;
|
||
}
|
||
|
||
bool TInstaller_mask::move_module(const TString& module, TInstall_ini& ini, bool update) const
|
||
{
|
||
bool ok = TRUE;
|
||
|
||
TFilename tempdir; tempdir.tempdir();
|
||
const TString& destdir = get(F_CURPATH);
|
||
|
||
TString_array list;
|
||
ini.build_list(module, list);
|
||
FOR_EACH_ARRAY_ROW(list, f, file)
|
||
{
|
||
TFilename src = tempdir;
|
||
src.add(file->get(0));
|
||
if (update)
|
||
{
|
||
TFilename dst = destdir;
|
||
dst.add(file->get(0));
|
||
const bool move_ok = move_file(src, dst);
|
||
if (!move_ok)
|
||
ok = update = FALSE;
|
||
}
|
||
if (!update)
|
||
::remove(src);
|
||
}
|
||
|
||
return ok;
|
||
}
|
||
|
||
KEY TInstaller_mask::askdisk(TString & path, TFilename & cmdline, int d, int dischi, const char * modulo)
|
||
{
|
||
TMask retry_mask(TR("Inserimento disco"),1,80,10);
|
||
|
||
retry_mask.add_static((F_PATH==101 ? 102:101),0,
|
||
format(FR("Inserire il disco %d di %d del modulo'%s' nell'unit<69>"), d, dischi, modulo)
|
||
,2,2);
|
||
retry_mask.add_static(F_PATH+3,0,TR("oppure indicare un percorso diverso"),2,3);
|
||
|
||
retry_mask.add_string(F_PATH,0,"",2,5,48);
|
||
retry_mask.add_button(DLG_OK,0,TR("Riprova"),-12,7,9,2);
|
||
retry_mask.add_button(DLG_QUIT,0,"",-22,7,9,2);
|
||
retry_mask.set(F_PATH,path);
|
||
KEY k;
|
||
do {
|
||
if ((k=retry_mask.run())==K_QUIT )
|
||
break;
|
||
if (!retry_mask.get(F_PATH).blank())
|
||
{
|
||
if (fexist(retry_mask.get(F_PATH)))
|
||
{
|
||
TString16 tmpname(cmdline.name() );
|
||
cmdline= path = retry_mask.get(F_PATH);
|
||
cmdline.add(tmpname);
|
||
break;
|
||
}
|
||
else
|
||
error_box(TR("Il percorso indicato non e' valido"));
|
||
}
|
||
} while (TRUE);
|
||
return k;
|
||
}
|
||
|
||
bool TInstaller_mask::install(const TString& module, int patchlevel)
|
||
{
|
||
bool cancelled=FALSE;
|
||
bool ok = FALSE;
|
||
TString msg; // stringa per i messaggi
|
||
TString16 lastrelease; // release che sto installando
|
||
int lastpatch=patchlevel; // patchlevel che sto installando
|
||
|
||
TFilename path ;
|
||
TString http_server;
|
||
TFilename http_path;
|
||
|
||
const bool internet = get_internet_path(path);
|
||
if (internet)
|
||
parse_internet_path(http_server,http_path );
|
||
|
||
const bool is_a_patch=(patchlevel > 0);
|
||
TFilename ininame = path;
|
||
ininame.add(module);
|
||
|
||
if (is_a_patch)
|
||
{
|
||
TString16 name;
|
||
name.format("%04da.ini", patchlevel);
|
||
ininame << name;
|
||
}
|
||
else
|
||
ininame << "inst.ini";
|
||
|
||
if (internet && !ininame.exist())
|
||
{
|
||
TFilename remote = ininame.name();
|
||
remote.insert(http_path, 0);
|
||
http_get(http_server, remote, ininame);
|
||
}
|
||
|
||
if (ininame.exist())
|
||
{
|
||
// esiste un particolare .ini con formato XXinst.ini (moduli) o con XX9999a.ini (patch)
|
||
// (installazione da directory con .zip)
|
||
TInstall_ini* ini = new TInstall_ini(ininame);
|
||
ini->write_protect();
|
||
lastpatch=ini->get_int("Patch",module);
|
||
lastrelease=ini->get("Versione",module);
|
||
if (!can_install(module, *ini))
|
||
{
|
||
delete ini;
|
||
return FALSE;
|
||
}
|
||
const int dischi = ini->get_int("Dischi", module);
|
||
ok = dischi > 0;
|
||
if (!ok)
|
||
return error_box(FR("Impossibile determinare il numero dei dischetti in %s"),ininame.name());
|
||
else
|
||
{
|
||
if (patchlevel==0)
|
||
ok = pre_process(*ini, module);
|
||
if (!ok)
|
||
{
|
||
delete ini;
|
||
return FALSE;
|
||
}
|
||
}
|
||
// ==============
|
||
// decompressione
|
||
msg = TR("Decompressione");
|
||
if (is_a_patch)
|
||
msg << TR(" della patch ") << patchlevel ;
|
||
msg << TR(" del modulo '") << module << TR("' in corso...");
|
||
TProgind pi(dischi, msg, FALSE, TRUE);
|
||
TFilename tempdir; tempdir.tempdir();
|
||
|
||
// File tottale dei vari sotto-zip
|
||
TFilename totti = tempdir; totti.add(module); totti.ext("zip");
|
||
|
||
for (int d = 1; d <= dischi && ok; d++)
|
||
{
|
||
TFilename chunk = path;
|
||
chunk.add(module);
|
||
if (patchlevel > 0)
|
||
{
|
||
TString16 name;
|
||
name.format("%04da", patchlevel);
|
||
chunk << name;
|
||
}
|
||
else
|
||
chunk << "inst";
|
||
chunk << d << ".zip";
|
||
|
||
if (internet && !chunk.exist())
|
||
{
|
||
TFilename remote = chunk.name();
|
||
remote.insert(http_path, 0);
|
||
if (!http_get(http_server, remote, chunk))
|
||
error_box(FR("Errore di trasferimento del file '%s'"), (const char*)remote);
|
||
}
|
||
|
||
ok = chunk.exist();
|
||
if (!ok && !internet) // Chiedi cambio disco (solo se non sta scaricando da internet)
|
||
{
|
||
while (!ok)
|
||
{
|
||
if (askdisk(path,chunk,d,dischi,(const char*)ini->get("Descrizione"))==K_QUIT)
|
||
break;
|
||
ok = chunk.exist();
|
||
if (!ok)
|
||
message_box(FR("Impossibile trovare il file '%s'"),(const char*)chunk);
|
||
}
|
||
}
|
||
|
||
if (ok)
|
||
{
|
||
const long required = fsize(chunk) * (dischi-d+1) * 4;
|
||
if (!xvt_fsys_test_disk_free_space(tempdir, required))
|
||
{
|
||
ok = yesno_box(TR("Lo spazio su disco potrebbe essere insufficiente:\nSi desidera continuare ugualmente?"));
|
||
}
|
||
}
|
||
|
||
if (ok)
|
||
{
|
||
::fcopy(chunk, totti, d > 1); // Somma il chunk al totale
|
||
pi.addstatus(1);
|
||
}
|
||
}
|
||
aga_unzip(totti, tempdir); // Scompatta il file totale
|
||
::remove(totti);
|
||
|
||
// =============
|
||
// trasferimento
|
||
if (ok)
|
||
{
|
||
// si assicura che sia leggibile il .ini del primo disco
|
||
do
|
||
{
|
||
TFilename cmdline = path;
|
||
cmdline.add(ininame.name());
|
||
ok = cmdline.exist();
|
||
if (!ok)
|
||
{
|
||
if (askdisk(path,cmdline,1,dischi,(const char*)ini->get("Descrizione"))==K_QUIT)
|
||
break;
|
||
ok = fexist(cmdline);
|
||
if (!ok)
|
||
message_box(FR("Impossibile trovare %s\n"),(const char*)cmdline);
|
||
else
|
||
{
|
||
delete ini;
|
||
ini = new TInstall_ini (cmdline);
|
||
}
|
||
}
|
||
} while (!ok);
|
||
if (ok)
|
||
{
|
||
msg.cut(0);
|
||
msg << TR("Aggiornamento del modulo '") << module << TR("' in corso...");
|
||
pi.set_text(msg);
|
||
ok = move_module(module, *ini, TRUE);
|
||
|
||
if (ok)
|
||
{
|
||
TAuto_token_string altri(ini->get("Moduli", module));
|
||
FOR_EACH_TOKEN(altri, mod)
|
||
{
|
||
const TString16 submod = mod;
|
||
if (submod.len() > 2) // sposta sottomoduli esterni
|
||
{
|
||
bool upd = ok;
|
||
if (ok)
|
||
{
|
||
TInstall_ini curini;
|
||
const TString16 curver = curini.version(submod);
|
||
const int curpatch = curini.patch(submod);
|
||
const TString16 reqver = ini->version(submod);
|
||
const int reqpatch = ini->patch(submod);
|
||
|
||
int distance = compare_version(reqver, reqpatch, curver, curpatch);
|
||
upd = distance > 0;
|
||
}
|
||
ok &= move_module(submod, *ini, upd);
|
||
if (upd && ok) // marca sull'install.ini di destinazione l'avvenuta installazione del sottomodulo "esterno"
|
||
ini->export_paragraph(submod, ini->default_name(),!is_a_patch);
|
||
}
|
||
}
|
||
}
|
||
if (ok) //rimozione files da eliminare indicati nel .ini
|
||
{
|
||
TString killmod;
|
||
killmod << module << 99;
|
||
if (ini->set_paragraph(killmod))
|
||
{
|
||
TToken_string rigaini;
|
||
TFilename filetokill;
|
||
for (int k=0; ;k++)
|
||
{
|
||
rigaini = ini->get("Kill", NULL, k, "");
|
||
if (rigaini.empty())
|
||
break;
|
||
filetokill = rigaini.get(0);
|
||
::remove(filetokill);
|
||
}
|
||
}
|
||
}
|
||
}
|
||
}
|
||
if (ok) // marca sull'install.ini di destinazione l'avvenuta installazione del modulo
|
||
ini->export_module_paragraphs(module, ini->default_name(),!is_a_patch);
|
||
} // installazione da directory con zip
|
||
else
|
||
if (!is_a_patch)
|
||
{
|
||
//
|
||
// non c'e' il .ini del modulo ma un unico "install.ini"
|
||
// (installazione da directory con eseguibili)
|
||
ininame = path;
|
||
ininame.add(TInstall_ini::default_name());
|
||
ok = fexist(ininame);
|
||
if (ok)
|
||
{
|
||
TInstall_ini ini(ininame);
|
||
ini.write_protect();
|
||
lastpatch=ini.get_int("Patch",module);
|
||
lastrelease=ini.get("Versione",module);
|
||
if (!can_install(module, ini))
|
||
return FALSE;
|
||
|
||
TString_array list;
|
||
const int files = ini.build_complete_list(module, list);
|
||
if (files > 0)
|
||
{
|
||
if (patchlevel==0)
|
||
ok = pre_process(ini, module);
|
||
|
||
if (ok)
|
||
{
|
||
msg.cut(0) << TR("Copia del modulo ") << module;
|
||
TProgind pi(files, msg, TRUE, TRUE);
|
||
TFilename src, dst;
|
||
for (int f = 0; f < files && ok; f++)
|
||
{
|
||
pi.addstatus(1);
|
||
dst = list.row(f).get(0);
|
||
dst.lower();
|
||
src = path;
|
||
src.add(dst);
|
||
const int reboot = needs_reboot(dst);
|
||
if (reboot > NEW_MENU && dst.exist())
|
||
{
|
||
dst.rtrim(1);
|
||
dst << '_';
|
||
}
|
||
if (!dst.exist())
|
||
create_dirs(dst.path());
|
||
|
||
ok = ::fcopy(src, dst);
|
||
if (ok && is_zip_file(src))
|
||
aga_unzip(src, dst.path());
|
||
|
||
if (ok && reboot != NONE)
|
||
_reboot_program |= reboot;
|
||
|
||
cancelled = pi.iscancelled();
|
||
}
|
||
ok &= !cancelled;
|
||
}
|
||
|
||
if (ok) // marca sull'install.ini di destinazione l'avvenuta installazione del modulo
|
||
ini.export_module_paragraphs(module, ini.default_name(),TRUE);
|
||
} // controllo esistenza lista di file non vuota per questo modulo
|
||
} // controllo esistenza install.ini
|
||
} // fine installazione da directory con eseguibili
|
||
|
||
if (ok)
|
||
{
|
||
{
|
||
TInstall_ini ini;
|
||
ini.set("DiskPath", get(F_PATH));
|
||
ini.set("Data", TDate(TODAY), module);
|
||
ini.update_prices(ininame);
|
||
}
|
||
// Non togliere le parentesi graffe soprastanti per permettere l'aggiornamento fisico del .ini (CON LA CHIAMATA DEL DISTRUTTORE)
|
||
update_version();
|
||
}
|
||
|
||
|
||
if (ok && patchlevel == 0) // Se installo un modulo pricipale ...
|
||
{
|
||
// ... installo DOPO tutte le patches successive
|
||
install_patches(module, lastrelease, lastpatch);
|
||
TInstall_ini ini;
|
||
ok &= post_process(ini, module);
|
||
}
|
||
|
||
return ok;
|
||
}
|
||
|
||
|
||
bool TInstaller_mask::get_internet_path(TFilename &ininame) const
|
||
{
|
||
ininame = get(F_PATH);
|
||
if (is_internet_path(ininame))
|
||
{
|
||
ininame.tempdir();
|
||
ininame.add("www");
|
||
return TRUE;
|
||
}
|
||
return FALSE;
|
||
}
|
||
|
||
void TInstaller_mask::parse_internet_path(TString & http_server, TFilename &http_path) const
|
||
{
|
||
http_server = get(F_PATH);
|
||
if (http_server.compare("http://", 7, TRUE) == 0)
|
||
http_server.ltrim(7);
|
||
|
||
const int slash = http_server.find('/');
|
||
if (slash > 0)
|
||
{
|
||
http_path = http_server.mid(slash);
|
||
if (http_path.right(1) != "/")
|
||
http_path << '/';
|
||
http_server.cut(slash);
|
||
}
|
||
else
|
||
http_path = http_default_path;
|
||
}
|
||
|
||
bool TInstaller_mask::install_patches(const TString& module, const TString& lastrelease, int lastpatch, bool only_newer)
|
||
{
|
||
bool ok = TRUE;
|
||
TString_array modules;
|
||
TFilename ininame;
|
||
get_internet_path(ininame);
|
||
|
||
ininame.add(module);
|
||
ininame << "0???a.ini";
|
||
modules.destroy();
|
||
list_files(ininame, modules);
|
||
modules.sort();
|
||
FOR_EACH_ARRAY_ROW(modules, am, arow)
|
||
{
|
||
TString& ininame = *arow;
|
||
ininame.lower();
|
||
const int pos = ininame.find("a.ini");
|
||
CHECKS(pos >= 6, "Invalid installation configuration: ", (const char*)ininame);
|
||
const TString16 patchmodule = ininame.mid(pos-6, 2);
|
||
TConfig ini(ininame, patchmodule);
|
||
const int patchlevel = ini.get_int("Patch");
|
||
const char * patchversion = ini.get("Versione");
|
||
if (ok && lastrelease == patchversion // installa solo le patch della stessa ver..
|
||
&& (only_newer ? lastpatch < patchlevel : lastpatch <= patchlevel)) // ... e patch superiore o uguale (reinstalla l'ultima patch)
|
||
ok = install(module, patchlevel);
|
||
}
|
||
return ok;
|
||
}
|
||
|
||
bool TInstaller_mask::update_handler(TMask_field& f, KEY k)
|
||
{
|
||
if (k == K_SPACE)
|
||
{
|
||
TInstaller_mask& m = (TInstaller_mask&)f.mask();
|
||
m.autoload();
|
||
}
|
||
return TRUE;
|
||
}
|
||
|
||
bool TInstaller_mask::path_handler(TMask_field& fld, KEY key)
|
||
{
|
||
bool ok = TRUE;
|
||
if (key == K_TAB && fld.focusdirty())
|
||
{
|
||
TFilename path = fld.get();
|
||
if (path.not_empty())
|
||
{
|
||
if (path.len() == 2 && isalpha(path[0]) && path[1] == ':')
|
||
{
|
||
path << SLASH;
|
||
fld.set(path);
|
||
}
|
||
if (path.exist() || ::is_internet_path(path))
|
||
_curr_mask->autoload();
|
||
else
|
||
ok = fld.error_box(TR("Specificare un percorso valido"));
|
||
}
|
||
}
|
||
return ok;
|
||
}
|
||
|
||
|
||
void TInstaller_mask::install_selection()
|
||
{
|
||
TString_array& arr = rows_array();
|
||
|
||
_sys_installed = false;
|
||
|
||
FOR_EACH_ARRAY_ROW(arr, r, row) if (checked(r))
|
||
{
|
||
|
||
const TString newver = row->get(C_RELEASE);
|
||
|
||
if (newver.blank())
|
||
{
|
||
check(r, FALSE);
|
||
continue;
|
||
}
|
||
|
||
const TString modulo = row->get(C_CODE);
|
||
const int newpatch = row->get_int(C_PATCH);
|
||
const TString oldver = row->get(C_CURRRELEASE);
|
||
const int oldpatch = row->get_int(C_CURRPATCH);
|
||
|
||
if (version2year(newver) < 1998)
|
||
{
|
||
error_box(FR("Il modulo '%s' non ha una versione valida."), (const char*)modulo);
|
||
continue;
|
||
}
|
||
|
||
bool ok = TRUE;
|
||
bool is_patch = row->get_char(C_ISPATCH) == 'X';
|
||
bool has_patch = row->get_char(C_ISPATCH) == '+';
|
||
const int cmp = compare_version(oldver, oldpatch, newver, newpatch);
|
||
if (cmp == 0)
|
||
ok = noyes_box(FR("Si desidera reinstallare la versione %s.%d del modulo '%s' ?"), (const char*)newver, newpatch, (const char*)modulo);
|
||
if (!is_patch && cmp > 0)
|
||
{
|
||
TString256 msg;
|
||
msg.format(FR("Si desidera ritornare alla versione %s.%d del modulo '%s' ?\nAttenzione: non e' garantito il corretto\nfunzionamento di tutti i programmi!"), (const char*)newver, newpatch, (const char*)modulo);
|
||
ok = noyes_box(msg);
|
||
}
|
||
if (ok && is_patch)
|
||
{
|
||
// installo le patch solo se esiste gi<67> un modulo installato della stessa versione
|
||
if (!oldver.blank() )
|
||
{
|
||
if (oldver != newver)
|
||
ok = error_box(FR("Il modulo '%s' installato ha versione %s:\nimpossibile installare le patch della versione %s"),(const char *)modulo,(const char *)oldver,(const char *)newver);
|
||
} else
|
||
ok =FALSE;//error_box("Impossibile installare le patch perche' il modulo '%s' non e' installato",(const char *)modulo);
|
||
}
|
||
if (ok)
|
||
{
|
||
if (has_patch)
|
||
{
|
||
if (newver == oldver && newpatch >= oldpatch)
|
||
{
|
||
const int basepatch = row->get_int(C_BASEPATCH);
|
||
if (oldpatch >= basepatch)
|
||
is_patch = !noyes_box(FR("Si desidera reinstallare l'intero modulo '%s'?"
|
||
"\nRispondendo NO verranno installate le sole patch"),
|
||
(const char *)modulo);
|
||
else
|
||
is_patch = FALSE; // Quando la versione installata precede la patch base devo reinstallare il modulo!
|
||
}
|
||
}
|
||
|
||
if (is_patch)
|
||
{
|
||
ok = install_patches(modulo, oldver, oldpatch, FALSE) ; // installa l'ultima patch
|
||
if (!ok)
|
||
message_box(TR("Impossibile installare le patch del modulo '%s'"),(const char *)modulo);
|
||
}
|
||
else
|
||
{
|
||
ok = install(modulo, 0); // installa il modulo
|
||
}
|
||
if (ok)
|
||
{
|
||
_installed = true; // Setta il flag di almeno un modulo installato
|
||
if (modulo == "sy") //se ha installato il modulo 'sy' esce
|
||
{
|
||
_sys_installed = true;
|
||
enable_row(r); //deve abilitare la riga di system senno' non la puo' uncheckare dopo
|
||
uncheck(-1); //uncheck di tutti i moduli
|
||
break;
|
||
}
|
||
uncheck(r); //finalmente unchecka i moduli installati
|
||
}
|
||
}
|
||
else
|
||
uncheck(r); // se non ci sono patch o moduli -> uncheck
|
||
}
|
||
force_update(); //serve per togliere il check al modulo 'sy' quando viene installato
|
||
if (installed())
|
||
{
|
||
if (_sys_installed)
|
||
{
|
||
warning_box("Modulo SY installato: altri moduli presenti dovranno essere installati successivamente");
|
||
send_key(K_SPACE, DLG_QUIT);
|
||
}
|
||
else
|
||
message_box(TR("Installazione conclusa"));
|
||
}
|
||
}
|
||
|
||
bool TInstaller_mask::install_handler(TMask_field& fld, KEY key)
|
||
{
|
||
if (key == K_SPACE)
|
||
{
|
||
if (_curr_mask->items() == 1)
|
||
_curr_mask->check(0);
|
||
const bool check_on = _curr_mask->check_enabled();
|
||
_curr_mask->enable_check(TRUE);
|
||
const bool some = _curr_mask->one_checked();
|
||
_curr_mask->enable_check(check_on);
|
||
if (some)
|
||
_curr_mask->install_selection();
|
||
else
|
||
error_box(TR("Selezionare uno o piu' moduli da installare."));
|
||
}
|
||
return TRUE;
|
||
}
|
||
|
||
|
||
bool TInstaller_mask::quit_handler(TMask_field& f, KEY k)
|
||
{
|
||
if (k == K_SPACE)
|
||
{
|
||
TInstaller_mask & m=(TInstaller_mask &) f.mask();
|
||
const bool check_on = _curr_mask->check_enabled();
|
||
_curr_mask->enable_check(TRUE);
|
||
const bool some = _curr_mask->one_checked();
|
||
_curr_mask->enable_check(check_on);
|
||
if (some)
|
||
return noyes_box(TR("Alcuni moduli sono selezionati per l'installazione.\nConfermare l'uscita"));
|
||
}
|
||
return TRUE;
|
||
}
|
||
|
||
|
||
bool TInstaller_mask::tutti_handler(TMask_field& f, KEY k)
|
||
{
|
||
if (k == K_SPACE)
|
||
{
|
||
TInstaller_mask & m=(TInstaller_mask &) f.mask();
|
||
if (m.check_enabled())
|
||
{
|
||
if (m.one_checked())
|
||
m.uncheck(-1);
|
||
else
|
||
m.precheck_modules(FALSE);
|
||
}
|
||
}
|
||
return TRUE;
|
||
}
|
||
|
||
bool TInstaller_mask::on_key(KEY key)
|
||
{
|
||
bool ok = TRUE;
|
||
switch (key)
|
||
{
|
||
case K_F7: autoload(); break;
|
||
case K_F8: field(DLG_USER).on_hit(); break;
|
||
default : ok = TArray_sheet::on_key(key); break;
|
||
}
|
||
return ok;
|
||
}
|
||
|
||
TInstaller_mask::TInstaller_mask()
|
||
: TArray_sheet(0, 0, 0, 0, TR("Installazione"),
|
||
HR("@1|Modulo@30|Cod.@3|Versione da\ninstallare@11|Liv.\nPatch@6|Data\nRilascio@10|Versione\nInstallata@10|Liv.\nPatch@6|Data\nInstallazione@13|Aggiornamento|Patch Base"),
|
||
0x18, 3)
|
||
{
|
||
_curr_mask = this;
|
||
_installed = FALSE;
|
||
_reboot_program= NONE;
|
||
|
||
add_string(F_PATH, 0, PR("Installa da "), 1, 1, 80, "", 60);
|
||
add_string(F_CURPATH, 0, PR("Installa in "), 1, 2, 80, "D", 60);
|
||
|
||
add_button(F_UPDATE, BR("Rileggi", 9), '\0');
|
||
add_button(F_INSTALL, BR("Installa", 9), '\0'); // NON mettere 'I'
|
||
|
||
set_handler(F_PATH, path_handler);
|
||
set_handler(F_INSTALL, install_handler);
|
||
set_handler(F_UPDATE, update_handler);
|
||
set_handler(DLG_QUIT, quit_handler);
|
||
set_handler(DLG_USER, tutti_handler);
|
||
|
||
TInstall_ini ini;
|
||
TFilename path = ini.get("DiskPath");
|
||
set(F_PATH, path);
|
||
|
||
const bool floppy = xvt_fsys_is_removable_drive(path) != 0;
|
||
if (path.not_empty() && !floppy && !is_internet_path(path))
|
||
autoload();
|
||
|
||
DIRECTORY dir;
|
||
xvt_fsys_get_dir(&dir);
|
||
xvt_fsys_convert_dir_to_str(&dir, path.get_buffer(), path.size());
|
||
set(F_CURPATH, path);
|
||
}
|
||
|
||
TInstaller_mask::~TInstaller_mask()
|
||
{
|
||
_curr_mask = NULL;
|
||
|
||
if (_reboot_program != NONE)
|
||
{
|
||
TString msg;
|
||
msg << TR("Sono stati aggiornati i seguenti elementi:") < '\n';
|
||
|
||
if (_reboot_program & NEW_MENU)
|
||
msg << TR("voci di menu;");
|
||
if (_reboot_program & NEW_MENUPRG)
|
||
msg << TR("navigatore dei menu;");
|
||
if (_reboot_program & NEW_INSTALLER)
|
||
msg << TR("installatore;");
|
||
if (_reboot_program & NEW_DLL)
|
||
msg << TR("librerie di base;");
|
||
|
||
msg.rtrim(1);
|
||
msg << '\n' << TR("E' necessario uscire e rientrare dal programma.");
|
||
warning_box(msg);
|
||
}
|
||
}
|
||
|
||
///////////////////////////////////////////////////////////
|
||
// Programma principale
|
||
///////////////////////////////////////////////////////////
|
||
|
||
class TInstaller : public TSkeleton_application
|
||
{
|
||
protected:
|
||
TInstaller_mask * _m;
|
||
|
||
protected:
|
||
virtual bool create();
|
||
virtual bool use_files() const { return FALSE; }
|
||
virtual bool test_assistance_year() const;
|
||
virtual void main_loop();
|
||
|
||
bool testdatabase() const;
|
||
bool testprograms() const;
|
||
};
|
||
|
||
bool TInstaller::testdatabase() const
|
||
{
|
||
TConfig ini(CONFIG_INSTALL, "Main");
|
||
return ini.get("TestDatabase","Main",-1,"Y") != "N";
|
||
}
|
||
|
||
bool TInstaller::testprograms() const
|
||
{
|
||
TConfig ini(CONFIG_INSTALL, "Main");
|
||
char c = ini.get("TestPrograms","Main",-1,"N")[0];
|
||
return c == 'X' || c == 'Y';
|
||
}
|
||
|
||
bool TInstaller::test_assistance_year() const
|
||
{
|
||
// Per il momento lascia continuare: ci pensa poi la create
|
||
return TRUE;
|
||
}
|
||
|
||
bool TInstaller::create()
|
||
{
|
||
if (!TApplication::test_assistance_year())
|
||
{
|
||
TExternal_app attivazione("ba1 -4");
|
||
attivazione.run();
|
||
dongle().login(); // Rilegge anno assistenza
|
||
}
|
||
else
|
||
update_dninst(FALSE); // Aggiorna se necessario
|
||
|
||
if (testprograms())
|
||
{
|
||
_m = new TInstaller_mask() ;
|
||
_m->disable_check();
|
||
_m->disable(F_PATH);
|
||
_m->disable(F_UPDATE);
|
||
_m->disable(DLG_USER);
|
||
return TSkeleton_application::create();
|
||
}
|
||
|
||
return error_box(FR("L'utente %s non <20> abilitato all'uso di questo programma"), (const char *)user());
|
||
}
|
||
|
||
void TInstaller::main_loop()
|
||
{
|
||
_m->run();
|
||
if (_m->installed() && !_m->sys_installed() && testdatabase()) // Almeno 1 modulo installato ?
|
||
{
|
||
// Lancia conversione: ba1 -0 -C -uADMIN
|
||
TExternal_app conversion("ba1 -0 -C");
|
||
conversion.run();
|
||
}
|
||
delete _m; _m = NULL;
|
||
}
|
||
|
||
class TExtendedInstaller : public TInstaller
|
||
{
|
||
protected:
|
||
virtual bool create();
|
||
virtual void main_loop();
|
||
};
|
||
|
||
bool TExtendedInstaller::create()
|
||
{
|
||
if (!TApplication::test_assistance_year())
|
||
{
|
||
TExternal_app attivazione("ba1 -4");
|
||
attivazione.run();
|
||
dongle().login(); // Rilegge anno assistenza
|
||
}
|
||
else
|
||
update_dninst(FALSE); // Aggiorna se necessario
|
||
|
||
_m = new TInstaller_mask() ;
|
||
return TSkeleton_application::create();
|
||
}
|
||
|
||
void TExtendedInstaller::main_loop()
|
||
{
|
||
_m->run();
|
||
if (_m->installed() && !_m->sys_installed() && testdatabase()) // Almeno 1 modulo installato ?
|
||
{
|
||
// Lancia conversione: ba1 -0 -C -uADMIN
|
||
TExternal_app conversion("ba1 -0 -C");
|
||
conversion.run();
|
||
}
|
||
|
||
const bool reboot = _m->run_ba0close();
|
||
delete _m; _m = NULL;
|
||
|
||
if (reboot && !fexist("ba3.exe")) //e' una prima installazione (non ha ancora installato la base)
|
||
{
|
||
TExternal_app ba0close("ba0close.exe");
|
||
ba0close.run(TRUE,TRUE,TRUE); // run asynchronous...
|
||
}
|
||
}
|
||
|
||
int ba1700(int argc, char* argv[])
|
||
{
|
||
const char* const PROGNAME = "Installazione moduli";
|
||
|
||
if (user() != ::dongle().administrator())
|
||
{
|
||
TInstaller app;
|
||
app.run(argc, argv, PROGNAME);
|
||
}
|
||
else
|
||
{
|
||
TExtendedInstaller app;
|
||
app.run(argc, argv, PROGNAME);
|
||
}
|
||
return 0;
|
||
} |