tWin32 installer now installs NT Service following data in configuration file; test added for previously-installed program - vaccinewars - be a doctor and try to vaccinate the world
 (HTM) git clone git://src.adamsgaard.dk/vaccinewars
 (DIR) Log
 (DIR) Files
 (DIR) Refs
 (DIR) README
 (DIR) LICENSE
       ---
 (DIR) commit a5c069e284df893a0023bf42591d3776fc34731a
 (DIR) parent 40175d2751758efe185243f0d9a495a4566b9a9d
 (HTM) Author: Ben Webb <ben@salilab.org>
       Date:   Thu,  8 Nov 2001 14:44:59 +0000
       
       Win32 installer now installs NT Service following data in configuration file;
       ttest added for previously-installed program
       
       
       Diffstat:
         M win32/filelist                      |       2 +-
         M win32/makeinstall.c                 |      10 +++++++++-
         M win32/setup.c                       |      83 +++++++++++++++++++++++--------
         M win32/uninstall.c                   |      32 ++++++++++++++++++++++++++-----
         M win32/util.c                        |      52 +++++++++++++++++++++++++++++++
         M win32/util.h                        |      13 +++++++++++++
       
       6 files changed, 164 insertions(+), 28 deletions(-)
       ---
 (DIR) diff --git a/win32/filelist b/win32/filelist
       t@@ -4,7 +4,7 @@ dopewars-1.5.3
        [instdir]
        C:\Program Files\dopewars-1.5.3
        
       -[NTService]
       +[NT Service]
        dopewars-server
        dopewars server
        Server for the drug-dealing game "dopewars"
 (DIR) diff --git a/win32/makeinstall.c b/win32/makeinstall.c
       t@@ -50,7 +50,7 @@ char *read_line(HANDLE hin) {
        
        InstData *ReadInstallData() {
          HANDLE fin;
       -  char *line,*line2,*line3;
       +  char *line,*line2,*line3,*line4;
          InstFiles *lastinst=NULL,*lastextra=NULL;
          InstLink *lastmenu=NULL,*lastdesktop=NULL;
          InstData *idata;
       t@@ -69,6 +69,7 @@ InstData *ReadInstallData() {
          idata->installdir = idata->startmenudir = NULL;
          idata->instfiles = idata->extrafiles = NULL;
          idata->startmenu = idata->desktop = NULL;
       +  idata->service = NULL;
        
          fin = CreateFile("filelist",GENERIC_READ,0,NULL,OPEN_EXISTING,0,NULL);
        
       t@@ -108,6 +109,11 @@ printf("start menu dir = %s\n",line);
        printf("start menu entry = %s/%s/%s\n",line,line2,line3);
                  AddInstLink(line,line2,line3,&lastmenu,&idata->startmenu);
                  break;
       +        case S_NTSERVICE:
       +          line2=read_line(fin); line3=read_line(fin); line4=read_line(fin);
       +printf("NT Service = %s/%s/%s/%s\n",line,line2,line3,line4);
       +          AddServiceDetails(line,line2,line3,line4,&idata->service);
       +          break;
                case S_DESKTOP:
                  line2=read_line(fin); line3=read_line(fin);
        printf("desktop entry = %s/%s/%s\n",line,line2,line3);
       t@@ -245,6 +251,8 @@ int main() {
          WriteLinkList(fout,idata->startmenu);
          WriteLinkList(fout,idata->desktop);
        
       +  WriteServiceDetails(fout,idata->service);
       +
          CloseHandle(fout);
          bfree(inbuf);
          bfree(outbuf);
 (DIR) diff --git a/win32/setup.c b/win32/setup.c
       t@@ -43,16 +43,15 @@ HINSTANCE hInst=NULL;
        DWORD WINAPI DoInstall(LPVOID lpParam);
        static void GetWinText(char **text,HWND hWnd);
        
       -void InstallService(void) {
       +void InstallService(InstData *idata) {
          SC_HANDLE scManager,scService;
          HKEY key;
          bstr *str;
          static char keyprefix[] = "SYSTEM\\ControlSet001\\Services\\";
       +  NTService *service;
        
       -  static char servicename[] = "dopewars-server";
       -  static char servicedisp[] = "dopewars server";
       -  static char serviceexe[] = "dopewars.exe -N";
       -  static char servicedesc[] = "Server for the drug-dealing game \"dopewars\"";
       +  service = idata->service;
       +  if (!service) return;
        
          scManager = OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS);
        
       t@@ -63,9 +62,9 @@ void InstallService(void) {
        
          str = bstr_new();
          bstr_assign(str,idata->installdir);
       -  bstr_appendpath(str,serviceexe);
       +  bstr_appendpath(str,service->exe);
        
       -  scService = CreateService(scManager,servicename,servicedisp,
       +  scService = CreateService(scManager,service->name,service->display,
                                    SERVICE_ALL_ACCESS,SERVICE_WIN32_OWN_PROCESS,
                                    SERVICE_DEMAND_START,SERVICE_ERROR_NORMAL,
                                    str->text,NULL,NULL,NULL,NULL,NULL);
       t@@ -76,10 +75,11 @@ void InstallService(void) {
          }
        
          bstr_assign(str,keyprefix);
       -  bstr_append(str,servicename);
       +  bstr_append(str,service->name);
          if (RegOpenKeyEx(HKEY_LOCAL_MACHINE,str->text,0,KEY_WRITE,&key)
              ==ERROR_SUCCESS) {
       -    RegSetValueEx(key,"Description",0,REG_SZ,servicedesc,strlen(servicedesc));
       +    RegSetValueEx(key,"Description",0,REG_SZ,service->description,
       +                  strlen(service->description));
            RegCloseKey(key);
          }
        
       t@@ -253,7 +253,7 @@ LPVOID GetResource(LPCTSTR resname,LPCTSTR restype) {
        InstData *ReadInstData() {
          InstFiles *lastinst=NULL,*lastextra=NULL;
          InstLink *lastmenu=NULL,*lastdesktop=NULL;
       -  char *instdata,*pt,*filename,*line2,*line3;
       +  char *instdata,*pt,*filename,*line2,*line3,*line4;
          DWORD filesize;
          InstData *idata;
        
       t@@ -263,6 +263,7 @@ InstData *ReadInstData() {
          pt=instdata;
        
          idata = bmalloc(sizeof(InstData));
       +  idata->service = NULL;
          idata->totalsize = atol(pt);
          pt += strlen(pt)+1;
        
       t@@ -311,6 +312,13 @@ InstData *ReadInstData() {
              AddInstLink(filename,line2,line3,&lastdesktop,&idata->desktop);
            } else break;
          }
       +  filename=pt; pt += strlen(pt)+1;
       +  if (filename[0]) {
       +    line2=pt; pt += strlen(pt)+1;
       +    line3=pt; pt += strlen(pt)+1;
       +    line4=pt; pt += strlen(pt)+1;
       +    AddServiceDetails(filename,line2,line3,line4,&idata->service);
       +  }
        
          return idata;
        }
       t@@ -639,13 +647,15 @@ DWORD WINAPI DoInstall(LPVOID lpParam) {
        
          WriteFileList(logf,idata->extrafiles);
        
       -  InstallService();
       +  InstallService(idata);
        
          CoInitialize(NULL);
          SetupShortcuts(logf);
          SetupUninstall();
          CoUninitialize();
        
       +  WriteServiceDetails(logf,idata->service);
       +
          CloseHandle(logf);
        
          SetFileAttributes("install.log",FILE_ATTRIBUTE_HIDDEN);
       t@@ -688,6 +698,35 @@ void FillFolderList(void) {
          bstr_free(str,TRUE);
        }
        
       +BOOL CheckExistingInstall(InstData *idata) {
       +  bstr *str,*subkey;
       +  HKEY key;
       +  DWORD ind;
       +  FILETIME ftime;
       +  BOOL retval=TRUE;
       +
       +  str=bstr_new();
       +  bstr_assign(str,UninstallKey);
       +  bstr_appendpath(str,idata->product);
       +  
       +  if (RegOpenKeyEx(HKEY_LOCAL_MACHINE,str->text,0,KEY_READ,&key)
       +      ==ERROR_SUCCESS) {
       +    RegCloseKey(key);
       +    if (MessageBox(NULL,"This program appears to already be installed.\n"
       +                   "Are you sure you want to go ahead and install it anyway?",
       +                   idata->product,MB_YESNO)==IDNO) retval=FALSE;
       +  } else {
       +// TODO: Check for old versions to upgrade
       +    if (RegOpenKeyEx(HKEY_LOCAL_MACHINE,UninstallKey,0,KEY_READ,&key)
       +        ==ERROR_SUCCESS) {
       +/*    for (ind=0;RegEnumKeyEx(key,ind,subkey,subkey->len,
       +                              NULL,NULL,NULL,&ftime)==ERROR_SUCCESS;ind++) {
       +      }*/
       +    }
       +  }
       +  return retval;
       +}
       +
        int APIENTRY WinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,
                             LPSTR lpszCmdParam,int nCmdShow) {
          MSG msg;
       t@@ -730,17 +769,19 @@ int APIENTRY WinMain(HINSTANCE hInstance,HINSTANCE hPrevInstance,
        
          for (i=0;i<DL_NUM;i++) SetGuiFont(mainDlg[i]);
        
       -  CurrentDialog=DL_NUM;
       -  ShowNewDialog(DL_INTRO);
       +  if (CheckExistingInstall(idata)) {
       +    CurrentDialog=DL_NUM;
       +    ShowNewDialog(DL_INTRO);
        
       -  while (GetMessage(&msg,NULL,0,0)) {
       -    Handled=FALSE;
       -    for (i=0;i<DL_NUM && !Handled;i++) {
       -      Handled=IsDialogMessage(mainDlg[i],&msg);
       -    }
       -    if (!Handled) {
       -      TranslateMessage(&msg);
       -      DispatchMessage(&msg);
       +    while (GetMessage(&msg,NULL,0,0)) {
       +      Handled=FALSE;
       +      for (i=0;i<DL_NUM && !Handled;i++) {
       +        Handled=IsDialogMessage(mainDlg[i],&msg);
       +      }
       +      if (!Handled) {
       +        TranslateMessage(&msg);
       +        DispatchMessage(&msg);
       +      }
            }
          }
          FreeInstData(idata,FALSE);
 (DIR) diff --git a/win32/uninstall.c b/win32/uninstall.c
       t@@ -30,19 +30,20 @@ HINSTANCE hInst;
        HWND mainDlg;
        char *product;
        
       -void RemoveService(void) {
       +void RemoveService(NTService *service) {
          SC_HANDLE scManager,scService;
          SERVICE_STATUS status;
       -  static char servicename[] = "dopewars-server";
        
       -  scManager = OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS);
       +  if (!service) return;
       +
       +  scManager = OpenSCManager(NULL,NULL,GENERIC_READ);
        
          if (!scManager) {
            DisplayError("Cannot connect to service manager",TRUE,FALSE);
            return;
          }
        
       -  scService = OpenService(scManager,servicename,DELETE|SERVICE_STOP);
       +  scService = OpenService(scManager,service->name,DELETE|SERVICE_STOP);
          if (!scService) {
            DisplayError("Cannot open service",TRUE,FALSE);
          } else {
       t@@ -105,6 +106,25 @@ InstLink *ReadLinkList(HANDLE fin) {
          return first;
        }
        
       +NTService *ReadServiceDetails(HANDLE fin) {
       +  NTService *service=NULL;
       +  char *name,*disp,*desc,*exe;
       +
       +  name = read_line0(fin);
       +  if (name) {
       +    disp = read_line0(fin);
       +    desc = read_line0(fin);
       +    exe = read_line0(fin);
       +    if (!disp || !desc || !exe) {
       +      DisplayError("Corrupt install.log",FALSE,TRUE);
       +    } else {
       +      AddServiceDetails(name,disp,desc,exe,&service);
       +    }
       +  }
       +
       +  return service;
       +}
       +
        InstFiles *ReadFileList(HANDLE fin) {
          InstFiles *first=NULL,*listpt=NULL,*newpt;
          char *filename,*filesize;
       t@@ -181,6 +201,8 @@ InstData *ReadInstData(HANDLE fin,char *product,char *installdir) {
        
          idata->startmenu = ReadLinkList(fin);
          idata->desktop = ReadLinkList(fin);
       +
       +  idata->service = ReadServiceDetails(fin);
          return idata;
        }
        
       t@@ -273,7 +295,7 @@ DWORD WINAPI DoUninstall(LPVOID lpParam) {
            idata = ReadInstData(fin,product,installdir);
            CloseHandle(fin);
        
       -    RemoveService();
       +    RemoveService(idata->service);
        
            DeleteFile("install.log");
            DeleteFileList(idata->instfiles);
 (DIR) diff --git a/win32/util.c b/win32/util.c
       t@@ -284,6 +284,28 @@ void FreeFileList(InstFiles *filelist,BOOL freepts) {
          }
        }
        
       +void AddServiceDetails(char *servicename,char *servicedisp,
       +                       char *servicedesc,char *serviceexe,
       +                       NTService **service) {
       +  *service = bmalloc(sizeof(NTService));
       +  (*service)->name = servicename;
       +  (*service)->display = servicedisp;
       +  (*service)->description = servicedesc;
       +  (*service)->exe = serviceexe;
       +}
       +
       +void FreeServiceDetails(NTService *service,BOOL freepts) {
       +  if (!service) return;
       +
       +  if (freepts) {
       +    bfree(service->name);
       +    bfree(service->display);
       +    bfree(service->description);
       +    bfree(service->exe);
       +  }
       +  bfree(service);
       +}
       +
        void FreeInstData(InstData *idata,BOOL freepts) {
          FreeFileList(idata->instfiles,freepts);
          FreeFileList(idata->extrafiles,freepts);
       t@@ -291,6 +313,8 @@ void FreeInstData(InstData *idata,BOOL freepts) {
          FreeLinkList(idata->startmenu,freepts);
          FreeLinkList(idata->desktop,freepts);
        
       +  FreeServiceDetails(idata->service,freepts);
       +
          bfree(idata->product);
          bfree(idata->installdir);
          bfree(idata->startmenudir);
       t@@ -298,6 +322,34 @@ void FreeInstData(InstData *idata,BOOL freepts) {
          bfree(idata);
        }
        
       +void WriteServiceDetails(HANDLE fout,NTService *service) {
       +  DWORD bytes_written;
       +  char str[]="";
       +
       +  if (!service) {
       +    if (!WriteFile(fout,str,strlen(str)+1,&bytes_written,NULL)) {
       +      printf("Write error\n");
       +    }
       +  } else {
       +    if (!WriteFile(fout,service->name,strlen(service->name)+1,
       +                   &bytes_written,NULL)) {
       +      printf("Write error\n");
       +    }
       +    if (!WriteFile(fout,service->display,strlen(service->display)+1,
       +                   &bytes_written,NULL)) {
       +      printf("Write error\n");
       +    }
       +    if (!WriteFile(fout,service->description,strlen(service->description)+1,
       +                   &bytes_written,NULL)) {
       +      printf("Write error\n");
       +    }
       +    if (!WriteFile(fout,service->exe,strlen(service->exe)+1,
       +                   &bytes_written,NULL)) {
       +      printf("Write error\n");
       +    }
       +  }
       +}
       +
        void WriteLinkList(HANDLE fout,InstLink *listpt) {
          char str[]="";
          DWORD bytes_written;
 (DIR) diff --git a/win32/util.h b/win32/util.h
       t@@ -39,10 +39,18 @@ typedef struct _InstLink {
          struct _InstLink *next;
        } InstLink;
        
       +typedef struct _NTService {
       +  char *name;
       +  char *display;
       +  char *description;
       +  char *exe;
       +} NTService;
       +
        typedef struct _InstData {
          char *product;
          char *installdir,*startmenudir;
          DWORD totalsize;
       +  NTService *service;
          InstFiles *instfiles;
          InstFiles *extrafiles;
          InstLink *startmenu;
       t@@ -79,6 +87,11 @@ void AddInstLink(char *linkfile,char *origfile,char *args,InstLink **lastpt,
        void FreeLinkList(InstLink *linklist,BOOL freepts);
        void FreeFileList(InstFiles *filelist,BOOL freepts);
        void FreeInstData(InstData *idata,BOOL freepts);
       +void AddServiceDetails(char *servicename,char *servicedisp,
       +                       char *servicedesc,char *serviceexe,
       +                       NTService **service);
       +void FreeServiceDetails(NTService *service,BOOL freepts);
       +void WriteServiceDetails(HANDLE fout,NTService *service);
        void WriteLinkList(HANDLE fout,InstLink *listpt);
        void WriteFileList(HANDLE fout,InstFiles *listpt);
        char *GetStartMenuTopDir(void);