Subversion Repositories SvarDOS

Rev

Rev 123 | Go to most recent revision | Only display areas with differences | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 123 Rev 128
1
/*
1
/*
2
 * SVAROG386 INSTALL
2
 * SVAROG386 INSTALL
3
 * COPYRIGHT (C) 2016 MATEUSZ VISTE, ALL RIGHTS RESERVED.
3
 * COPYRIGHT (C) 2016 MATEUSZ VISTE, ALL RIGHTS RESERVED.
4
 *
4
 *
5
 * Redistribution and use in source and binary forms, with or without
5
 * Redistribution and use in source and binary forms, with or without
6
 * modification, are permitted provided that the following conditions are met:
6
 * modification, are permitted provided that the following conditions are met:
7
 *
7
 *
8
 * 1. Redistributions of source code must retain the above copyright notice,
8
 * 1. Redistributions of source code must retain the above copyright notice,
9
 * this list of conditions and the following disclaimer.
9
 * this list of conditions and the following disclaimer.
10
 *
10
 *
11
 * 2. Redistributions in binary form must reproduce the above copyright
11
 * 2. Redistributions in binary form must reproduce the above copyright
12
 * notice, this list of conditions and the following disclaimer in the
12
 * notice, this list of conditions and the following disclaimer in the
13
 * documentation and/or other materials provided with the distribution.
13
 * documentation and/or other materials provided with the distribution.
14
 *
14
 *
15
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
16
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16
 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18
 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
18
 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
19
 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19
 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
20
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
21
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
22
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
23
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
24
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25
 * POSSIBILITY OF SUCH DAMAGE.
25
 * POSSIBILITY OF SUCH DAMAGE.
26
 *
26
 *
27
 * http://svarog386.sf.net
27
 * http://svarog386.sf.net
28
 */
28
 */
29
 
29
 
30
#include <dos.h>
30
#include <dos.h>
31
#include <direct.h>  /* mkdir() */
31
#include <direct.h>  /* mkdir() */
32
#include <stdio.h>   /* printf() and friends */
32
#include <stdio.h>   /* printf() and friends */
33
#include <stdlib.h>  /* system() */
33
#include <stdlib.h>  /* system() */
34
#include <string.h>  /* memcpy() */
34
#include <string.h>  /* memcpy() */
35
#include <unistd.h>
35
#include <unistd.h>
36
 
36
 
37
#include "kitten\kitten.h"
37
#include "kitten\kitten.h"
38
 
38
 
39
#include "cdrom.h"
39
#include "cdrom.h"
40
#include "input.h"
40
#include "input.h"
41
#include "video.h"
41
#include "video.h"
42
 
42
 
43
/* keyboard layouts and locales */
43
/* keyboard layouts and locales */
44
#include "keylay.h"
44
#include "keylay.h"
45
#include "keyoff.h"
45
#include "keyoff.h"
46
 
46
 
47
/* color scheme (color, mono) */
47
/* color scheme (color, mono) */
48
static unsigned short COLOR_TITLEBAR[2] = {0x7000,0x7000};
48
static unsigned short COLOR_TITLEBAR[2] = {0x7000,0x7000};
49
static unsigned short COLOR_BODY[2] = {0x1700,0x0700};
49
static unsigned short COLOR_BODY[2] = {0x1700,0x0700};
50
static unsigned short COLOR_SELECT[2] = {0x7000,0x7000};
50
static unsigned short COLOR_SELECT[2] = {0x7000,0x7000};
51
static unsigned short COLOR_SELECTCUR[2] = {0x1F00,0x0700};
51
static unsigned short COLOR_SELECTCUR[2] = {0x1F00,0x0700};
52
 
52
 
53
/* mono flag */
53
/* mono flag */
54
static int mono = 0;
54
static int mono = 0;
55
 
55
 
56
/* how much disk space does Svarog386 require (in MiB) */
56
/* how much disk space does Svarog386 require (in MiB) */
57
#define SVAROG_DISK_REQ 8
57
#define SVAROG_DISK_REQ 8
58
 
58
 
59
/* menu screens can output only one of these: */
59
/* menu screens can output only one of these: */
60
#define MENUNEXT 0
60
#define MENUNEXT 0
61
#define MENUPREV -1
61
#define MENUPREV -1
62
#define MENUQUIT -2
62
#define MENUQUIT -2
63
 
63
 
64
/* a convenience 'function' used for debugging */
64
/* a convenience 'function' used for debugging */
65
#define DBG(x) { video_putstringfix(24, 0, 0x4F00u, x, 80); }
65
#define DBG(x) { video_putstringfix(24, 0, 0x4F00u, x, 80); }
66
 
66
 
67
struct slocales {
67
struct slocales {
68
  char lang[4];
68
  char lang[4];
69
  char *keybcode;
69
  char *keybcode;
70
  unsigned int codepage;
70
  unsigned int codepage;
71
  int egafile;
71
  int egafile;
72
  int keybfile;
72
  int keybfile;
73
  int keyboff;
73
  int keyboff;
74
  int keyblen;
74
  int keyblen;
75
  unsigned int keybid;
75
  unsigned int keybid;
76
};
76
};
77
 
77
 
78
 
78
 
79
/* reboot the computer */
79
/* reboot the computer */
80
static void reboot(void) {
80
static void reboot(void) {
81
  void ((far *bootroutine)()) = (void (far *)()) 0xFFFF0000L;
81
  void ((far *bootroutine)()) = (void (far *)()) 0xFFFF0000L;
82
  int far *rstaddr = (int far *)0x00400072L; /* BIOS boot flag is at 0040:0072 */
82
  int far *rstaddr = (int far *)0x00400072L; /* BIOS boot flag is at 0040:0072 */
83
  *rstaddr = 0x1234; /* 0x1234 = warm boot, 0 = cold boot */
83
  *rstaddr = 0x1234; /* 0x1234 = warm boot, 0 = cold boot */
84
  (*bootroutine)(); /* jump to the BIOS reboot routine at FFFF:0000 */
84
  (*bootroutine)(); /* jump to the BIOS reboot routine at FFFF:0000 */
85
}
85
}
86
 
86
 
87
 
87
 
88
/* outputs a string to screen with taking care of word wrapping. returns amount of lines. */
88
/* outputs a string to screen with taking care of word wrapping. returns amount of lines. */
89
static int putstringwrap(int y, int x, unsigned short attr, char *s) {
89
static int putstringwrap(int y, int x, unsigned short attr, char *s) {
90
  int linew, lincount;
90
  int linew, lincount;
91
  linew = 80;
91
  linew = 80;
92
  if (x >= 0) linew -= (x << 1);
92
  if (x >= 0) linew -= (x << 1);
93
 
93
 
94
  for (lincount = 1; y+lincount < 25; lincount++) {
94
  for (lincount = 1; y+lincount < 25; lincount++) {
95
    int i, len = linew;
95
    int i, len = linew;
96
    for (i = 0; i <= linew; i++) {
96
    for (i = 0; i <= linew; i++) {
97
      if (s[i] == ' ') len = i;
97
      if (s[i] == ' ') len = i;
98
      if (s[i] == '\n') {
98
      if (s[i] == '\n') {
99
        len = i;
99
        len = i;
100
        break;
100
        break;
101
      }
101
      }
102
      if (s[i] == 0) {
102
      if (s[i] == 0) {
103
        len = i;
103
        len = i;
104
        break;
104
        break;
105
      }
105
      }
106
    }
106
    }
107
    video_putstring(y++, x, attr, s, len);
107
    video_putstring(y++, x, attr, s, len);
108
    s += len;
108
    s += len;
109
    if (*s == 0) break;
109
    if (*s == 0) break;
110
    s += 1; /* skip the whitespace char */
110
    s += 1; /* skip the whitespace char */
111
  }
111
  }
112
  return(lincount);
112
  return(lincount);
113
}
113
}
114
 
114
 
115
 
115
 
116
/* an NLS wrapper around video_putstring(), also performs line wrapping when
116
/* an NLS wrapper around video_putstring(), also performs line wrapping when
117
 * needed. returns the amount of lines that were output */
117
 * needed. returns the amount of lines that were output */
118
static int putstringnls(int y, int x, unsigned short attr, int nlsmaj, int nlsmin, char *s) {
118
static int putstringnls(int y, int x, unsigned short attr, int nlsmaj, int nlsmin, char *s) {
119
  s = kittengets(nlsmaj, nlsmin, s);
119
  s = kittengets(nlsmaj, nlsmin, s);
120
  return(putstringwrap(y, x, attr, s));
120
  return(putstringwrap(y, x, attr, s));
121
}
121
}
122
 
122
 
123
 
123
 
124
static int menuselect(int ypos, int xpos, int height, char **list, int listlen) {
124
static int menuselect(int ypos, int xpos, int height, char **list, int listlen) {
125
  int i, offset = 0, res = 0, count, width = 0;
125
  int i, offset = 0, res = 0, count, width = 0;
126
  /* count how many positions there is, and check their width */
126
  /* count how many positions there is, and check their width */
127
  for (count = 0; (list[count] != NULL) && (count != listlen); count++) {
127
  for (count = 0; (list[count] != NULL) && (count != listlen); count++) {
128
    int len = strlen(list[count]);
128
    int len = strlen(list[count]);
129
    if (len > width) width = len;
129
    if (len > width) width = len;
130
  }
130
  }
131
 
131
 
132
  /* if xpos negative, means 'center out' */
132
  /* if xpos negative, means 'center out' */
133
  if (xpos < 0) xpos = 39 - (width >> 1);
133
  if (xpos < 0) xpos = 39 - (width >> 1);
134
 
134
 
135
  video_putchar(ypos, xpos+width+2, COLOR_SELECT[mono], 0xBF);         /*       \ */
135
  video_putchar(ypos, xpos+width+2, COLOR_SELECT[mono], 0xBF);         /*       \ */
136
  video_putchar(ypos, xpos-1, COLOR_SELECT[mono], 0xDA);               /*  /      */
136
  video_putchar(ypos, xpos-1, COLOR_SELECT[mono], 0xDA);               /*  /      */
137
  video_putchar(ypos+height-1, xpos-1, COLOR_SELECT[mono], 0xC0);      /*  \      */
137
  video_putchar(ypos+height-1, xpos-1, COLOR_SELECT[mono], 0xC0);      /*  \      */
138
  video_putchar(ypos+height-1, xpos+width+2, COLOR_SELECT[mono], 0xD9);/*      /  */
138
  video_putchar(ypos+height-1, xpos+width+2, COLOR_SELECT[mono], 0xD9);/*      /  */
139
  video_putcharmulti(ypos, xpos, COLOR_SELECT[mono], 0xC4, width + 2, 1);
139
  video_putcharmulti(ypos, xpos, COLOR_SELECT[mono], 0xC4, width + 2, 1);
140
  video_putcharmulti(ypos+height-1, xpos, COLOR_SELECT[mono], 0xC4, width + 2, 1);
140
  video_putcharmulti(ypos+height-1, xpos, COLOR_SELECT[mono], 0xC4, width + 2, 1);
141
  video_putcharmulti(ypos+1, xpos-1, COLOR_SELECT[mono], 0xB3, height - 2, 80);
141
  video_putcharmulti(ypos+1, xpos-1, COLOR_SELECT[mono], 0xB3, height - 2, 80);
142
  video_putcharmulti(ypos+1, xpos+width+2, COLOR_SELECT[mono], 0xB3, height - 2, 80);
142
  video_putcharmulti(ypos+1, xpos+width+2, COLOR_SELECT[mono], 0xB3, height - 2, 80);
143
 
143
 
144
  for (;;) {
144
  for (;;) {
145
    int key;
145
    int key;
146
    /* list of selectable items */
146
    /* list of selectable items */
147
    for (i = 0; i < height - 2; i++) {
147
    for (i = 0; i < height - 2; i++) {
148
      if (i + offset == res) {
148
      if (i + offset == res) {
149
        video_putchar(ypos + 1 + i, xpos, COLOR_SELECTCUR[mono], 16);
149
        video_putchar(ypos + 1 + i, xpos, COLOR_SELECTCUR[mono], 16);
150
        video_putchar(ypos + 1 + i, xpos+width+1, COLOR_SELECTCUR[mono], 17);
150
        video_putchar(ypos + 1 + i, xpos+width+1, COLOR_SELECTCUR[mono], 17);
151
        video_movecursor(ypos + 1 + i, xpos);
151
        video_movecursor(ypos + 1 + i, xpos);
152
        video_putstringfix(ypos + 1 + i, xpos+1, COLOR_SELECTCUR[mono], list[i + offset], width);
152
        video_putstringfix(ypos + 1 + i, xpos+1, COLOR_SELECTCUR[mono], list[i + offset], width);
153
      } else if (i + offset < count) {
153
      } else if (i + offset < count) {
154
        video_putchar(ypos + 1 + i, xpos, COLOR_SELECT[mono], ' ');
154
        video_putchar(ypos + 1 + i, xpos, COLOR_SELECT[mono], ' ');
155
        video_putchar(ypos + 1 + i, xpos+width+1, COLOR_SELECT[mono], ' ');
155
        video_putchar(ypos + 1 + i, xpos+width+1, COLOR_SELECT[mono], ' ');
156
        video_putstringfix(ypos + 1 + i, xpos+1, COLOR_SELECT[mono], list[i + offset], width);
156
        video_putstringfix(ypos + 1 + i, xpos+1, COLOR_SELECT[mono], list[i + offset], width);
157
      } else {
157
      } else {
158
        video_putcharmulti(ypos + 1 + i, xpos, COLOR_SELECT[mono], ' ', width+2, 1);
158
        video_putcharmulti(ypos + 1 + i, xpos, COLOR_SELECT[mono], ' ', width+2, 1);
159
      }
159
      }
160
    }
160
    }
161
    key = input_getkey();
161
    key = input_getkey();
162
    if (key == 0x0D) { /* ENTER */
162
    if (key == 0x0D) { /* ENTER */
163
      return(res);
163
      return(res);
164
    } else if (key == 0x148) { /* up */
164
    } else if (key == 0x148) { /* up */
165
      if (res > 0) {
165
      if (res > 0) {
166
        res--;
166
        res--;
167
        if (res < offset) offset = res;
167
        if (res < offset) offset = res;
168
      }
168
      }
169
    } else if (key == 0x150) { /* down */
169
    } else if (key == 0x150) { /* down */
170
      if (res+1 < count) {
170
      if (res+1 < count) {
171
        res++;
171
        res++;
172
        if (res > offset + height - 3) offset = res - (height - 3);
172
        if (res > offset + height - 3) offset = res - (height - 3);
173
      }
173
      }
174
    } else if (key == 0x147) { /* home */
174
    } else if (key == 0x147) { /* home */
175
      res = 0;
175
      res = 0;
176
      offset = 0;
176
      offset = 0;
177
    } else if (key == 0x14F) { /* end */
177
    } else if (key == 0x14F) { /* end */
178
      res = count - 1;
178
      res = count - 1;
179
      if (res > offset + height - 3) offset = res - (height - 3);
179
      if (res > offset + height - 3) offset = res - (height - 3);
180
    } else if (key == 0x1B) {  /* ESC */
180
    } else if (key == 0x1B) {  /* ESC */
181
      return(-1);
181
      return(-1);
182
    }/* else {
182
    }/* else {
183
      char buf[8];
183
      char buf[8];
184
      snprintf(buf, sizeof(buf), "0x%02X ", key);
184
      snprintf(buf, sizeof(buf), "0x%02X ", key);
185
      video_putstring(1, 0, COLOR_BODY[mono], buf, -1);
185
      video_putstring(1, 0, COLOR_BODY[mono], buf, -1);
186
    }*/
186
    }*/
187
  }
187
  }
188
}
188
}
189
 
189
 
190
static void newscreen(int statusbartype) {
190
static void newscreen(int statusbartype) {
191
  char *msg;
191
  char *msg;
192
  msg = kittengets(0, 0, "SVAROG386 INSTALLATION");
192
  msg = kittengets(0, 0, "SVAROG386 INSTALLATION");
193
  video_putcharmulti(0, 0, COLOR_TITLEBAR[mono], ' ', 80, 1);
193
  video_putcharmulti(0, 0, COLOR_TITLEBAR[mono], ' ', 80, 1);
194
  video_putstring(0, 40 - (strlen(msg) >> 1), COLOR_TITLEBAR[mono], msg, -1);
194
  video_putstring(0, 40 - (strlen(msg) >> 1), COLOR_TITLEBAR[mono], msg, -1);
195
  video_clear(COLOR_BODY[mono], 80, -80);
195
  video_clear(COLOR_BODY[mono], 80, -80);
196
  switch (statusbartype) {
196
  switch (statusbartype) {
197
    case 1:
197
    case 1:
198
      msg = kittengets(0, 11, "Up/Down = Select entry | Enter = Validate your choice | ESC = Quit to DOS");
198
      msg = kittengets(0, 11, "Up/Down = Select entry | Enter = Validate your choice | ESC = Quit to DOS");
199
      break;
199
      break;
200
    case 2:
200
    case 2:
201
      msg = kittengets(0, 5, "Press any key...");
201
      msg = kittengets(0, 5, "Press any key...");
202
      break;
202
      break;
203
    case 3:
203
    case 3:
204
      msg = "";
204
      msg = "";
205
      break;
205
      break;
206
    default:
206
    default:
207
      msg = kittengets(0, 10, "Up/Down = Select entry | Enter = Validate your choice | ESC = Previous screen");
207
      msg = kittengets(0, 10, "Up/Down = Select entry | Enter = Validate your choice | ESC = Previous screen");
208
      break;
208
      break;
209
  }
209
  }
210
  video_putchar(24, 0, COLOR_TITLEBAR[mono], ' ');
210
  video_putchar(24, 0, COLOR_TITLEBAR[mono], ' ');
211
  video_putstringfix(24, 1, COLOR_TITLEBAR[mono], msg, 79);
211
  video_putstringfix(24, 1, COLOR_TITLEBAR[mono], msg, 79);
212
  video_movecursor(25,0);
212
  video_movecursor(25,0);
213
}
213
}
214
 
214
 
215
/* fills a slocales struct accordingly to the value of its keyboff member */
215
/* fills a slocales struct accordingly to the value of its keyboff member */
216
static void kblay2slocal(struct slocales *locales) {
216
static void kblay2slocal(struct slocales *locales) {
217
  char *m;
217
  char *m;
218
  for (m = kblayouts[locales->keyboff]; *m != 0; m++); /* skip layout name */
218
  for (m = kblayouts[locales->keyboff]; *m != 0; m++); /* skip layout name */
219
  m++;
219
  m++;
220
  /* skip keyb code and copy it to locales.keybcode */
220
  /* skip keyb code and copy it to locales.keybcode */
221
  locales->keybcode = m;
221
  locales->keybcode = m;
222
  for (; *m != 0; m++);
222
  for (; *m != 0; m++);
223
  /* */
223
  /* */
224
  locales->codepage = ((unsigned short)m[1] << 8) | m[2];
224
  locales->codepage = ((unsigned short)m[1] << 8) | m[2];
225
  locales->egafile = m[3];
225
  locales->egafile = m[3];
226
  locales->keybfile = m[4];
226
  locales->keybfile = m[4];
227
  locales->keybid = ((unsigned short)m[5] << 8) | m[6];
227
  locales->keybid = ((unsigned short)m[5] << 8) | m[6];
228
}
228
}
229
 
229
 
230
static int selectlang(struct slocales *locales) {
230
static int selectlang(struct slocales *locales) {
231
  int choice, x;
231
  int choice, x;
232
  char *msg;
232
  char *msg;
233
  char *langlist[] = {
233
  char *langlist[] = {
234
    "English",
234
    "English",
235
    "French",
235
    "French",
236
    "Italian",
236
    "Italian",
237
    "Polish",
237
    "Polish",
238
    "Russian",
238
    "Russian",
239
    "Slovene",
239
    "Slovene",
-
 
240
    "Swedish",
240
    "Turkish",
241
    "Turkish",
241
    NULL
242
    NULL
242
  };
243
  };
243
 
244
 
244
  newscreen(1);
245
  newscreen(1);
245
  msg = kittengets(1, 0, "Welcome to Svarog386");
246
  msg = kittengets(1, 0, "Welcome to Svarog386");
246
  x = 40 - (strlen(msg) >> 1);
247
  x = 40 - (strlen(msg) >> 1);
247
  video_putstring(4, x, COLOR_BODY[mono], msg, -1);
248
  video_putstring(4, x, COLOR_BODY[mono], msg, -1);
248
  video_putcharmulti(5, x, COLOR_BODY[mono], '=', strlen(msg), 1);
249
  video_putcharmulti(5, x, COLOR_BODY[mono], '=', strlen(msg), 1);
249
  putstringnls(8, -1, COLOR_BODY[mono], 1, 1, "Please select your language from the list below:");
250
  putstringnls(8, -1, COLOR_BODY[mono], 1, 1, "Please select your language from the list below:");
250
  choice = menuselect(11, -1, 9, langlist, -1);
251
  choice = menuselect(11, -1, 10, langlist, -1);
251
  if (choice < 0) return(MENUPREV);
252
  if (choice < 0) return(MENUPREV);
252
  /* populate locales with default values */
253
  /* populate locales with default values */
253
  memset(locales, 0, sizeof(struct slocales));
254
  memset(locales, 0, sizeof(struct slocales));
254
  switch (choice) {
255
  switch (choice) {
255
    case 1:
256
    case 1:
256
      strcpy(locales->lang, "FR");
257
      strcpy(locales->lang, "FR");
257
      locales->keyboff = OFFLOC_FR;
258
      locales->keyboff = OFFLOC_FR;
258
      locales->keyblen = OFFLEN_FR;
259
      locales->keyblen = OFFLEN_FR;
259
      break;
260
      break;
260
    case 2:
261
    case 2:
261
      strcpy(locales->lang, "IT");
262
      strcpy(locales->lang, "IT");
262
      locales->keyboff = OFFLOC_IT;
263
      locales->keyboff = OFFLOC_IT;
263
      locales->keyblen = OFFLEN_IT;
264
      locales->keyblen = OFFLEN_IT;
264
      break;
265
      break;
265
    case 3:
266
    case 3:
266
      strcpy(locales->lang, "PL");
267
      strcpy(locales->lang, "PL");
267
      locales->keyboff = OFFLOC_PL;
268
      locales->keyboff = OFFLOC_PL;
268
      locales->keyblen = OFFLEN_PL;
269
      locales->keyblen = OFFLEN_PL;
269
      break;
270
      break;
270
    case 4:
271
    case 4:
271
      strcpy(locales->lang, "RU");
272
      strcpy(locales->lang, "RU");
272
      locales->keyboff = OFFLOC_RU;
273
      locales->keyboff = OFFLOC_RU;
273
      locales->keyblen = OFFLEN_RU;
274
      locales->keyblen = OFFLEN_RU;
274
      break;
275
      break;
275
    case 5:
276
    case 5:
276
      strcpy(locales->lang, "SI");
277
      strcpy(locales->lang, "SI");
277
      locales->keyboff = OFFLOC_SI;
278
      locales->keyboff = OFFLOC_SI;
278
      locales->keyblen = OFFLEN_SI;
279
      locales->keyblen = OFFLEN_SI;
279
      break;
280
      break;
280
    case 6:
281
    case 6:
-
 
282
      strcpy(locales->lang, "SV");
-
 
283
      locales->keyboff = OFFLOC_SV;
-
 
284
      locales->keyblen = OFFLEN_SV;
-
 
285
      break;
-
 
286
    case 7:
281
      strcpy(locales->lang, "TR");
287
      strcpy(locales->lang, "TR");
282
      locales->keyboff = OFFLOC_TR;
288
      locales->keyboff = OFFLOC_TR;
283
      locales->keyblen = OFFLEN_TR;
289
      locales->keyblen = OFFLEN_TR;
284
      break;
290
      break;
285
    default:
291
    default:
286
      strcpy(locales->lang, "EN");
292
      strcpy(locales->lang, "EN");
287
      locales->keyboff = 0;
293
      locales->keyboff = 0;
288
      locales->keyblen = OFFCOUNT;
294
      locales->keyblen = OFFCOUNT;
289
      break;
295
      break;
290
  }
296
  }
291
  /* populate the slocales struct accordingly to the keyboff member */
297
  /* populate the slocales struct accordingly to the keyboff member */
292
  kblay2slocal(locales);
298
  kblay2slocal(locales);
293
  /* */
299
  /* */
294
  return(MENUNEXT);
300
  return(MENUNEXT);
295
}
301
}
296
 
302
 
297
 
303
 
298
static int selectkeyb(struct slocales *locales) {
304
static int selectkeyb(struct slocales *locales) {
299
  int menuheight, choice;
305
  int menuheight, choice;
300
  if (locales->keyblen == 1) return(MENUNEXT); /* do not ask for keyboard layout if only one is available for given language */
306
  if (locales->keyblen == 1) return(MENUNEXT); /* do not ask for keyboard layout if only one is available for given language */
301
  newscreen(0);
307
  newscreen(0);
302
  putstringnls(5, 1, COLOR_BODY[mono], 1, 5, "Svarog386 supports the keyboard layouts used in different countries. Choose the keyboard layout you want.");
308
  putstringnls(5, 1, COLOR_BODY[mono], 1, 5, "Svarog386 supports the keyboard layouts used in different countries. Choose the keyboard layout you want.");
303
  menuheight = locales->keyblen + 2;
309
  menuheight = locales->keyblen + 2;
304
  if (menuheight > 13) menuheight = 13;
310
  if (menuheight > 13) menuheight = 13;
305
  choice = menuselect(10, -1, menuheight, &(kblayouts[locales->keyboff]), locales->keyblen);
311
  choice = menuselect(10, -1, menuheight, &(kblayouts[locales->keyboff]), locales->keyblen);
306
  if (choice < 0) return(MENUPREV);
312
  if (choice < 0) return(MENUPREV);
307
  /* (re)load the keyboard layout & codepage setup */
313
  /* (re)load the keyboard layout & codepage setup */
308
  locales->keyboff += choice;
314
  locales->keyboff += choice;
309
  kblay2slocal(locales);
315
  kblay2slocal(locales);
310
  return(MENUNEXT);
316
  return(MENUNEXT);
311
}
317
}
312
 
318
 
313
 
319
 
314
/* returns 0 if installation must proceed, non-zero otherwise */
320
/* returns 0 if installation must proceed, non-zero otherwise */
315
static int welcomescreen(void) {
321
static int welcomescreen(void) {
316
  int c;
322
  int c;
317
  char *choice[] = {"Install Svarog386 to disk", "Quit to DOS", NULL};
323
  char *choice[] = {"Install Svarog386 to disk", "Quit to DOS", NULL};
318
  choice[0] = kittengets(0, 1, choice[0]);
324
  choice[0] = kittengets(0, 1, choice[0]);
319
  choice[1] = kittengets(0, 2, choice[1]);
325
  choice[1] = kittengets(0, 2, choice[1]);
320
  newscreen(0);
326
  newscreen(0);
321
  putstringnls(4, 1, COLOR_BODY[mono], 2, 0, "You are about to install Svarog386: a free, MSDOS-compatible operating system based on the FreeDOS kernel. Svarog386 targets 386+ computers and comes with a variety of third-party applications.\n\nWARNING: If your PC has another operating system installed, this other system might be unable to boot once Svarog386 is installed.");
327
  putstringnls(4, 1, COLOR_BODY[mono], 2, 0, "You are about to install Svarog386: a free, MSDOS-compatible operating system based on the FreeDOS kernel. Svarog386 targets 386+ computers and comes with a variety of third-party applications.\n\nWARNING: If your PC has another operating system installed, this other system might be unable to boot once Svarog386 is installed.");
322
  c = menuselect(13, -1, 4, choice, -1);
328
  c = menuselect(13, -1, 4, choice, -1);
323
  if (c < 0) return(MENUPREV);
329
  if (c < 0) return(MENUPREV);
324
  if (c == 0) return(MENUNEXT);
330
  if (c == 0) return(MENUNEXT);
325
  return(MENUQUIT);
331
  return(MENUQUIT);
326
}
332
}
327
 
333
 
328
 
334
 
329
/* returns 1 if drive is removable, 0 if not, -1 on error */
335
/* returns 1 if drive is removable, 0 if not, -1 on error */
330
static int isdriveremovable(int drv) {
336
static int isdriveremovable(int drv) {
331
  union REGS r;
337
  union REGS r;
332
  r.x.ax = 0x4408;
338
  r.x.ax = 0x4408;
333
  r.h.bl = drv;
339
  r.h.bl = drv;
334
  int86(0x21, &r, &r);
340
  int86(0x21, &r, &r);
335
  /* CF set on error, AX set to 0 if removable, 1 if fixed */
341
  /* CF set on error, AX set to 0 if removable, 1 if fixed */
336
  if (r.x.cflag != 0) return(-1);
342
  if (r.x.cflag != 0) return(-1);
337
  if (r.x.ax == 0) return(1);
343
  if (r.x.ax == 0) return(1);
338
  return(0);
344
  return(0);
339
}
345
}
340
 
346
 
341
 
347
 
342
/* returns total disk space of drive drv (in MiB, max 2048), or -1 if drive invalid */
348
/* returns total disk space of drive drv (in MiB, max 2048), or -1 if drive invalid */
343
static int disksize(int drv) {
349
static int disksize(int drv) {
344
  long res;
350
  long res;
345
  union REGS r;
351
  union REGS r;
346
  r.h.ah = 0x36; /* DOS 2+ get free disk space */
352
  r.h.ah = 0x36; /* DOS 2+ get free disk space */
347
  r.h.dl = drv;
353
  r.h.dl = drv;
348
  int86(0x21, &r, &r);
354
  int86(0x21, &r, &r);
349
  if (r.x.ax == 0xffffu) return(-1); /* AX set to FFFFh if drive invalid */
355
  if (r.x.ax == 0xffffu) return(-1); /* AX set to FFFFh if drive invalid */
350
  res = r.x.ax;  /* sectors per cluster */
356
  res = r.x.ax;  /* sectors per cluster */
351
  res *= r.x.dx; /* dx contains total clusters, bx contains free clusters */
357
  res *= r.x.dx; /* dx contains total clusters, bx contains free clusters */
352
  res *= r.x.cx; /* bytes per sector */
358
  res *= r.x.cx; /* bytes per sector */
353
  res >>= 20;    /* convert bytes to MiB */
359
  res >>= 20;    /* convert bytes to MiB */
354
  return(res);
360
  return(res);
355
}
361
}
356
 
362
 
357
 
363
 
358
/* returns 0 if disk is empty, non-zero otherwise */
364
/* returns 0 if disk is empty, non-zero otherwise */
359
static int diskempty(int drv) {
365
static int diskempty(int drv) {
360
  unsigned int rc;
366
  unsigned int rc;
361
  int res;
367
  int res;
362
  char buff[8];
368
  char buff[8];
363
  struct find_t fileinfo;
369
  struct find_t fileinfo;
364
  snprintf(buff, sizeof(buff), "%c:\\*.*", 'A' + drv - 1);
370
  snprintf(buff, sizeof(buff), "%c:\\*.*", 'A' + drv - 1);
365
  rc = _dos_findfirst(buff, _A_NORMAL | _A_SUBDIR | _A_HIDDEN | _A_SYSTEM, &fileinfo);
371
  rc = _dos_findfirst(buff, _A_NORMAL | _A_SUBDIR | _A_HIDDEN | _A_SYSTEM, &fileinfo);
366
  if (rc == 0) {
372
  if (rc == 0) {
367
    res = 1; /* call successfull means disk is not empty */
373
    res = 1; /* call successfull means disk is not empty */
368
  } else {
374
  } else {
369
    res = 0;
375
    res = 0;
370
  }
376
  }
371
  /* _dos_findclose(&fileinfo); */ /* apparently required only on OS/2 */
377
  /* _dos_findclose(&fileinfo); */ /* apparently required only on OS/2 */
372
  return(res);
378
  return(res);
373
}
379
}
374
 
380
 
375
 
381
 
376
static int preparedrive(void) {
382
static int preparedrive(void) {
377
  int driveremovable;
383
  int driveremovable;
378
  int selecteddrive = 3; /* hardcoded to 'C:' for now */
384
  int selecteddrive = 3; /* hardcoded to 'C:' for now */
379
  int cselecteddrive;
385
  int cselecteddrive;
380
  int ds;
386
  int ds;
381
  int choice;
387
  int choice;
382
  char buff[1024];
388
  char buff[1024];
383
  cselecteddrive = 'A' + selecteddrive - 1;
389
  cselecteddrive = 'A' + selecteddrive - 1;
384
  for (;;) {
390
  for (;;) {
385
    driveremovable = isdriveremovable(selecteddrive);
391
    driveremovable = isdriveremovable(selecteddrive);
386
    if (driveremovable < 0) {
392
    if (driveremovable < 0) {
387
      char *list[] = { "Create a partition automatically", "Run the FDISK partitioning tool", "Quit to DOS", NULL};
393
      char *list[] = { "Create a partition automatically", "Run the FDISK partitioning tool", "Quit to DOS", NULL};
388
      newscreen(0);
394
      newscreen(0);
389
      list[0] = kittengets(0, 3, list[0]);
395
      list[0] = kittengets(0, 3, list[0]);
390
      list[1] = kittengets(0, 4, list[1]);
396
      list[1] = kittengets(0, 4, list[1]);
391
      list[2] = kittengets(0, 2, list[2]);
397
      list[2] = kittengets(0, 2, list[2]);
392
      snprintf(buff, sizeof(buff), kittengets(3, 0, "ERROR: Drive %c: could not be found. Perhaps your hard disk needs to be partitioned first. Please create at least one partition on your hard disk, so Svarog386 can be installed on it. Note, that Svarog386 requires at least %d MiB of available disk space.\n\nYou can use the FDISK partitioning tool for creating the required partition manually, or you can let the installer partitioning your disk automatically. You can also abort the installation to use any other partition manager of your choice."), cselecteddrive, SVAROG_DISK_REQ);
398
      snprintf(buff, sizeof(buff), kittengets(3, 0, "ERROR: Drive %c: could not be found. Perhaps your hard disk needs to be partitioned first. Please create at least one partition on your hard disk, so Svarog386 can be installed on it. Note, that Svarog386 requires at least %d MiB of available disk space.\n\nYou can use the FDISK partitioning tool for creating the required partition manually, or you can let the installer partitioning your disk automatically. You can also abort the installation to use any other partition manager of your choice."), cselecteddrive, SVAROG_DISK_REQ);
393
      putstringwrap(4, 1, COLOR_BODY[mono], buff);
399
      putstringwrap(4, 1, COLOR_BODY[mono], buff);
394
      switch (menuselect(14, -1, 5, list, -1)) {
400
      switch (menuselect(14, -1, 5, list, -1)) {
395
        case 0:
401
        case 0:
396
          system("FDISK /AUTO");
402
          system("FDISK /AUTO");
397
          break;
403
          break;
398
        case 1:
404
        case 1:
399
          video_clear(0x0700, 0, 0);
405
          video_clear(0x0700, 0, 0);
400
          video_movecursor(0, 0);
406
          video_movecursor(0, 0);
401
          system("FDISK");
407
          system("FDISK");
402
          break;
408
          break;
403
        case 2:
409
        case 2:
404
          return(MENUQUIT);
410
          return(MENUQUIT);
405
        default:
411
        default:
406
          return(-1);
412
          return(-1);
407
      }
413
      }
408
      /* write a temporary MBR which only skips the drive (in case BIOS would
414
      /* write a temporary MBR which only skips the drive (in case BIOS would
409
       * try to boot off the not-yet-ready C: disk) */
415
       * try to boot off the not-yet-ready C: disk) */
410
      system("FDISK /AMBR"); /* writes BOOT.MBR into actual MBR */
416
      system("FDISK /AMBR"); /* writes BOOT.MBR into actual MBR */
411
      newscreen(2);
417
      newscreen(2);
412
      putstringnls(10, 10, COLOR_BODY[mono], 3, 1, "Your computer will reboot now.");
418
      putstringnls(10, 10, COLOR_BODY[mono], 3, 1, "Your computer will reboot now.");
413
      putstringnls(12, 10, COLOR_BODY[mono], 0, 5, "Press any key...");
419
      putstringnls(12, 10, COLOR_BODY[mono], 0, 5, "Press any key...");
414
      input_getkey();
420
      input_getkey();
415
      reboot();
421
      reboot();
416
      return(MENUQUIT);
422
      return(MENUQUIT);
417
    } else if (driveremovable > 0) {
423
    } else if (driveremovable > 0) {
418
      newscreen(2);
424
      newscreen(2);
419
      snprintf(buff, sizeof(buff), kittengets(3, 2, "ERROR: Drive %c: is a removable device. Installation aborted."), cselecteddrive);
425
      snprintf(buff, sizeof(buff), kittengets(3, 2, "ERROR: Drive %c: is a removable device. Installation aborted."), cselecteddrive);
420
      video_putstring(9, 1, COLOR_BODY[mono], buff, -1);
426
      video_putstring(9, 1, COLOR_BODY[mono], buff, -1);
421
      putstringnls(11, 2, COLOR_BODY[mono], 0, 5, "Press any key...");
427
      putstringnls(11, 2, COLOR_BODY[mono], 0, 5, "Press any key...");
422
      return(MENUQUIT);
428
      return(MENUQUIT);
423
    }
429
    }
424
    /* if not formatted, propose to format it right away (try to create a directory) */
430
    /* if not formatted, propose to format it right away (try to create a directory) */
425
    snprintf(buff, sizeof(buff), "%c:\\SVWRTEST.123", cselecteddrive);
431
    snprintf(buff, sizeof(buff), "%c:\\SVWRTEST.123", cselecteddrive);
426
    if (mkdir(buff) == 0) {
432
    if (mkdir(buff) == 0) {
427
      rmdir(buff);
433
      rmdir(buff);
428
    } else {
434
    } else {
429
      char *list[] = { "Proceed with formatting", "Quit to DOS", NULL};
435
      char *list[] = { "Proceed with formatting", "Quit to DOS", NULL};
430
      newscreen(0);
436
      newscreen(0);
431
      list[0] = kittengets(0, 6, list[0]);
437
      list[0] = kittengets(0, 6, list[0]);
432
      list[1] = kittengets(0, 2, list[1]);
438
      list[1] = kittengets(0, 2, list[1]);
433
      snprintf(buff, sizeof(buff), kittengets(3, 3, "ERROR: Drive %c: seems to be unformated. Do you wish to format it?"), cselecteddrive);
439
      snprintf(buff, sizeof(buff), kittengets(3, 3, "ERROR: Drive %c: seems to be unformated. Do you wish to format it?"), cselecteddrive);
434
      video_putstring(7, 1, COLOR_BODY[mono], buff, -1);
440
      video_putstring(7, 1, COLOR_BODY[mono], buff, -1);
435
      choice = menuselect(12, -1, 4, list, -1);
441
      choice = menuselect(12, -1, 4, list, -1);
436
      if (choice < 0) return(MENUPREV);
442
      if (choice < 0) return(MENUPREV);
437
      if (choice == 1) return(MENUQUIT);
443
      if (choice == 1) return(MENUQUIT);
438
      video_clear(0x0700, 0, 0);
444
      video_clear(0x0700, 0, 0);
439
      video_movecursor(0, 0);
445
      video_movecursor(0, 0);
440
      snprintf(buff, sizeof(buff), "FORMAT %c: /Q /U /Z:seriously /V:SVAROG386", cselecteddrive);
446
      snprintf(buff, sizeof(buff), "FORMAT %c: /Q /U /Z:seriously /V:SVAROG386", cselecteddrive);
441
      system(buff);
447
      system(buff);
442
      continue;
448
      continue;
443
    }
449
    }
444
    /* check total disk space */
450
    /* check total disk space */
445
    ds = disksize(selecteddrive);
451
    ds = disksize(selecteddrive);
446
    if (ds < SVAROG_DISK_REQ) {
452
    if (ds < SVAROG_DISK_REQ) {
447
      int y = 9;
453
      int y = 9;
448
      newscreen(2);
454
      newscreen(2);
449
      snprintf(buff, sizeof(buff), kittengets(3, 4, "ERROR: Drive %c: is not big enough! Svarog386 requires a disk of at least %d MiB."), cselecteddrive);
455
      snprintf(buff, sizeof(buff), kittengets(3, 4, "ERROR: Drive %c: is not big enough! Svarog386 requires a disk of at least %d MiB."), cselecteddrive);
450
      y += putstringwrap(y, 1, COLOR_BODY[mono], buff);
456
      y += putstringwrap(y, 1, COLOR_BODY[mono], buff);
451
      putstringnls(++y, 1, COLOR_BODY[mono], 0, 5, "Press any key...");
457
      putstringnls(++y, 1, COLOR_BODY[mono], 0, 5, "Press any key...");
452
      input_getkey();
458
      input_getkey();
453
      return(MENUQUIT);
459
      return(MENUQUIT);
454
    }
460
    }
455
    /* is the disk empty? */
461
    /* is the disk empty? */
456
    newscreen(0);
462
    newscreen(0);
457
    if (diskempty(selecteddrive) != 0) {
463
    if (diskempty(selecteddrive) != 0) {
458
      char *list[] = { "Proceed with formatting", "Quit to DOS", NULL};
464
      char *list[] = { "Proceed with formatting", "Quit to DOS", NULL};
459
      int y = 6;
465
      int y = 6;
460
      list[0] = kittengets(0, 6, list[0]);
466
      list[0] = kittengets(0, 6, list[0]);
461
      list[1] = kittengets(0, 2, list[1]);
467
      list[1] = kittengets(0, 2, list[1]);
462
      snprintf(buff, sizeof(buff), kittengets(3, 5, "ERROR: Drive %c: is not empty. Svarog386 must be installed on an empty disk.\n\nYou can format the disk now, to make it empty. Note however, that this will ERASE ALL CURRENT DATA on your disk."), cselecteddrive);
468
      snprintf(buff, sizeof(buff), kittengets(3, 5, "ERROR: Drive %c: is not empty. Svarog386 must be installed on an empty disk.\n\nYou can format the disk now, to make it empty. Note however, that this will ERASE ALL CURRENT DATA on your disk."), cselecteddrive);
463
      y += putstringwrap(y, 1, COLOR_BODY[mono], buff);
469
      y += putstringwrap(y, 1, COLOR_BODY[mono], buff);
464
      choice = menuselect(++y, -1, 4, list, -1);
470
      choice = menuselect(++y, -1, 4, list, -1);
465
      if (choice < 0) return(MENUPREV);
471
      if (choice < 0) return(MENUPREV);
466
      if (choice == 1) return(MENUQUIT);
472
      if (choice == 1) return(MENUQUIT);
467
      video_clear(0x0700, 0, 0);
473
      video_clear(0x0700, 0, 0);
468
      video_movecursor(0, 0);
474
      video_movecursor(0, 0);
469
      snprintf(buff, sizeof(buff), "FORMAT %c: /Q /U /Z:seriously /V:SVAROG386", cselecteddrive);
475
      snprintf(buff, sizeof(buff), "FORMAT %c: /Q /U /Z:seriously /V:SVAROG386", cselecteddrive);
470
      system(buff);
476
      system(buff);
471
      continue;
477
      continue;
472
    } else {
478
    } else {
473
      /* final confirmation */
479
      /* final confirmation */
474
      char *list[] = { "Install Svarog386", "Quit to DOS", NULL};
480
      char *list[] = { "Install Svarog386", "Quit to DOS", NULL};
475
      list[0] = kittengets(0, 1, list[0]);
481
      list[0] = kittengets(0, 1, list[0]);
476
      list[1] = kittengets(0, 2, list[1]);
482
      list[1] = kittengets(0, 2, list[1]);
477
      snprintf(buff, sizeof(buff), kittengets(3, 6, "The installation of Svarog386 to %c: is about to begin."), cselecteddrive);
483
      snprintf(buff, sizeof(buff), kittengets(3, 6, "The installation of Svarog386 to %c: is about to begin."), cselecteddrive);
478
      video_putstring(7, -1, COLOR_BODY[mono], buff, -1);
484
      video_putstring(7, -1, COLOR_BODY[mono], buff, -1);
479
      choice = menuselect(10, -1, 4, list, -1);
485
      choice = menuselect(10, -1, 4, list, -1);
480
      if (choice < 0) return(MENUPREV);
486
      if (choice < 0) return(MENUPREV);
481
      if (choice == 1) return(MENUQUIT);
487
      if (choice == 1) return(MENUQUIT);
482
      snprintf(buff, sizeof(buff), "SYS A: %c: > NUL", cselecteddrive);
488
      snprintf(buff, sizeof(buff), "SYS A: %c: > NUL", cselecteddrive);
483
      system(buff);
489
      system(buff);
484
      system("FDISK /MBR");
490
      system("FDISK /MBR");
485
      snprintf(buff, sizeof(buff), "%c:\\TEMP", cselecteddrive);
491
      snprintf(buff, sizeof(buff), "%c:\\TEMP", cselecteddrive);
486
      mkdir(buff);
492
      mkdir(buff);
487
      return(cselecteddrive);
493
      return(cselecteddrive);
488
    }
494
    }
489
  }
495
  }
490
}
496
}
491
 
497
 
492
 
498
 
493
/* copy file src into dst, substituting all characters c1 by c2 */
499
/* copy file src into dst, substituting all characters c1 by c2 */
494
static void fcopysub(char *dst, char *src, char c1, char c2) {
500
static void fcopysub(char *dst, char *src, char c1, char c2) {
495
  FILE *fdd, *fds;
501
  FILE *fdd, *fds;
496
  int buff;
502
  int buff;
497
  fds = fopen(src, "rb");
503
  fds = fopen(src, "rb");
498
  if (fds == NULL) return;
504
  if (fds == NULL) return;
499
  fdd = fopen(dst, "wb");
505
  fdd = fopen(dst, "wb");
500
  if (fdd == NULL) {
506
  if (fdd == NULL) {
501
    fclose(fds);
507
    fclose(fds);
502
    return;
508
    return;
503
  }
509
  }
504
  /* */
510
  /* */
505
  for (;;) {
511
  for (;;) {
506
    buff = fgetc(fds);
512
    buff = fgetc(fds);
507
    if (buff == EOF) break;
513
    if (buff == EOF) break;
508
    if (buff == c1) buff = c2;
514
    if (buff == c1) buff = c2;
509
    fprintf(fdd, "%c", buff);
515
    fprintf(fdd, "%c", buff);
510
  }
516
  }
511
  /* close files and return */
517
  /* close files and return */
512
  fclose(fdd);
518
  fclose(fdd);
513
  fclose(fds);
519
  fclose(fds);
514
}
520
}
515
 
521
 
516
 
522
 
517
static void bootfilesgen(int targetdrv, struct slocales *locales, int cdromdrv) {
523
static void bootfilesgen(int targetdrv, struct slocales *locales, int cdromdrv) {
518
  char buff[128];
524
  char buff[128];
519
  char buff2[16];
525
  char buff2[16];
520
  char buff3[16];
526
  char buff3[16];
521
  FILE *fd;
527
  FILE *fd;
522
  /*** CONFIG.SYS ***/
528
  /*** CONFIG.SYS ***/
523
  snprintf(buff, sizeof(buff), "%c:\\CONFIG.SYS", targetdrv);
529
  snprintf(buff, sizeof(buff), "%c:\\CONFIG.SYS", targetdrv);
524
  fd = fopen(buff, "wb");
530
  fd = fopen(buff, "wb");
525
  if (fd == NULL) return;
531
  if (fd == NULL) return;
526
  fprintf(fd, "DOS=UMB,HIGH\r\n"
532
  fprintf(fd, "DOS=UMB,HIGH\r\n"
527
              "LASTDRIVE=Z\r\n"
533
              "LASTDRIVE=Z\r\n"
528
              "FILES=50\r\n");
534
              "FILES=50\r\n");
529
  fprintf(fd, "DEVICE=%c:\\SYSTEM\\SVAROG.386\\BIN\\HIMEMX.EXE\r\n", targetdrv);
535
  fprintf(fd, "DEVICE=%c:\\SYSTEM\\SVAROG.386\\BIN\\HIMEMX.EXE\r\n", targetdrv);
530
  if (strcmp(locales->lang, "EN") == 0) {
536
  if (strcmp(locales->lang, "EN") == 0) {
531
    strcpy(buff, "COMMAND");
537
    strcpy(buff, "COMMAND");
532
  } else {
538
  } else {
533
    snprintf(buff, sizeof(buff), "CMD-%s", locales->lang);
539
    snprintf(buff, sizeof(buff), "CMD-%s", locales->lang);
534
  }
540
  }
535
  fprintf(fd, "SHELLHIGH=%c:\\SYSTEM\\SVAROG.386\\BIN\\%s.COM /E:512 /P\r\n", targetdrv, buff);
541
  fprintf(fd, "SHELLHIGH=%c:\\SYSTEM\\SVAROG.386\\BIN\\%s.COM /E:512 /P\r\n", targetdrv, buff);
536
  fprintf(fd, "REM COUNTRY=001,437,%c:\\SYSTEM\\CONF\\COUNTRY.SYS\r\n", targetdrv);
542
  fprintf(fd, "REM COUNTRY=001,437,%c:\\SYSTEM\\CONF\\COUNTRY.SYS\r\n", targetdrv);
537
  fprintf(fd, "DEVICE=%c:\\SYSTEM\\DRIVERS\\UDVD2\\UDVD2.SYS /D:SVCD0001 /H\r\n", targetdrv);
543
  fprintf(fd, "DEVICE=%c:\\SYSTEM\\DRIVERS\\UDVD2\\UDVD2.SYS /D:SVCD0001 /H\r\n", targetdrv);
538
  fclose(fd);
544
  fclose(fd);
539
  /*** AUTOEXEC.BAT ***/
545
  /*** AUTOEXEC.BAT ***/
540
  snprintf(buff, sizeof(buff), "%c:\\AUTOEXEC.BAT", targetdrv);
546
  snprintf(buff, sizeof(buff), "%c:\\AUTOEXEC.BAT", targetdrv);
541
  fd = fopen(buff, "wb");
547
  fd = fopen(buff, "wb");
542
  if (fd == NULL) return;
548
  if (fd == NULL) return;
543
  fprintf(fd, "@ECHO OFF\r\n");
549
  fprintf(fd, "@ECHO OFF\r\n");
544
  fprintf(fd, "SET TEMP=%c:\\TEMP\r\n", targetdrv);
550
  fprintf(fd, "SET TEMP=%c:\\TEMP\r\n", targetdrv);
545
  fprintf(fd, "SET DOSDIR=%c:\\SYSTEM\\SVAROG.386\r\n", targetdrv);
551
  fprintf(fd, "SET DOSDIR=%c:\\SYSTEM\\SVAROG.386\r\n", targetdrv);
546
  fprintf(fd, "SET NLSPATH=%%DOSDIR%%\\NLS\r\n");
552
  fprintf(fd, "SET NLSPATH=%%DOSDIR%%\\NLS\r\n");
547
  fprintf(fd, "SET LANG=%s\r\n", locales->lang);
553
  fprintf(fd, "SET LANG=%s\r\n", locales->lang);
548
  fprintf(fd, "SET DIRCMD=/OGNE/P/4\r\n");
554
  fprintf(fd, "SET DIRCMD=/OGNE/P/4\r\n");
549
  fprintf(fd, "SET FDNPKG.CFG=%c:\\SYSTEM\\CFG\\FDNPKG.CFG\r\n", targetdrv);
555
  fprintf(fd, "SET FDNPKG.CFG=%c:\\SYSTEM\\CFG\\FDNPKG.CFG\r\n", targetdrv);
550
  fprintf(fd, "SET WATTCP.CFG=%c:\\SYSTEM\\CFG\\WATTCP.CFG\r\n", targetdrv);
556
  fprintf(fd, "SET WATTCP.CFG=%c:\\SYSTEM\\CFG\\WATTCP.CFG\r\n", targetdrv);
551
  fprintf(fd, "PATH %%DOSDIR%%\\BIN;%c:\\SYSTEM\\LINKS\r\n", targetdrv);
557
  fprintf(fd, "PATH %%DOSDIR%%\\BIN;%c:\\SYSTEM\\LINKS\r\n", targetdrv);
552
  fprintf(fd, "PROMPT $P$G\r\n");
558
  fprintf(fd, "PROMPT $P$G\r\n");
553
  fprintf(fd, "ALIAS REBOOT=FDAPM COLDBOOT\r\n");
559
  fprintf(fd, "ALIAS REBOOT=FDAPM COLDBOOT\r\n");
554
  fprintf(fd, "ALIAS HALT=FDAPM POWEROFF\r\n");
560
  fprintf(fd, "ALIAS HALT=FDAPM POWEROFF\r\n");
555
  fprintf(fd, "FDAPM APMDOS\r\n");
561
  fprintf(fd, "FDAPM APMDOS\r\n");
556
  fprintf(fd, "\r\n");
562
  fprintf(fd, "\r\n");
557
  if (locales->egafile > 0) {
563
  if (locales->egafile > 0) {
558
    fprintf(fd, "DISPLAY CON=(EGA,,1)\r\n");
564
    fprintf(fd, "DISPLAY CON=(EGA,,1)\r\n");
559
    if (locales->egafile == 1) {
565
    if (locales->egafile == 1) {
560
      fprintf(fd, "MODE CON CP PREPARE=((%u) %c:\\SYSTEM\\SVAROG.386\\CPI\\EGA.CPX)\r\n", locales->codepage, targetdrv);
566
      fprintf(fd, "MODE CON CP PREPARE=((%u) %c:\\SYSTEM\\SVAROG.386\\CPI\\EGA.CPX)\r\n", locales->codepage, targetdrv);
561
    } else {
567
    } else {
562
      fprintf(fd, "MODE CON CP PREPARE=((%u) %c:\\SYSTEM\\SVAROG.386\\CPI\\EGA%d.CPX)\r\n", locales->codepage, targetdrv, locales->egafile);
568
      fprintf(fd, "MODE CON CP PREPARE=((%u) %c:\\SYSTEM\\SVAROG.386\\CPI\\EGA%d.CPX)\r\n", locales->codepage, targetdrv, locales->egafile);
563
    }
569
    }
564
    fprintf(fd, "MODE CON CP SELECT=%u\r\n", locales->codepage);
570
    fprintf(fd, "MODE CON CP SELECT=%u\r\n", locales->codepage);
565
  }
571
  }
566
  if (locales->keybfile > 0) {
572
  if (locales->keybfile > 0) {
567
    if (locales->keybfile == 1) {
573
    if (locales->keybfile == 1) {
568
      snprintf(buff2, sizeof(buff2), "KEYBOARD.SYS");
574
      snprintf(buff2, sizeof(buff2), "KEYBOARD.SYS");
569
    } else {
575
    } else {
570
      snprintf(buff2, sizeof(buff2), "KEYBRD%d.SYS", locales->keybfile);
576
      snprintf(buff2, sizeof(buff2), "KEYBRD%d.SYS", locales->keybfile);
571
    }
577
    }
572
    if (locales->keybid == 0) {
578
    if (locales->keybid == 0) {
573
      buff3[0] = 0;
579
      buff3[0] = 0;
574
    } else {
580
    } else {
575
      snprintf(buff3, sizeof(buff3), " /ID:%d", locales->keybid);
581
      snprintf(buff3, sizeof(buff3), " /ID:%d", locales->keybid);
576
    }
582
    }
577
    fprintf(fd, "KEYB %s,%d,%c:\\SYSTEM\\SVAROG.386\\BIN\\%s%s\r\n", locales->keybcode, locales->codepage, targetdrv, buff2, buff3);
583
    fprintf(fd, "KEYB %s,%d,%c:\\SYSTEM\\SVAROG.386\\BIN\\%s%s\r\n", locales->keybcode, locales->codepage, targetdrv, buff2, buff3);
578
    fprintf(fd, "\r\n");
584
    fprintf(fd, "\r\n");
579
  }
585
  }
580
  fprintf(fd, "SHSUCDX /d:SVCD0001\r\n");
586
  fprintf(fd, "SHSUCDX /d:SVCD0001\r\n");
581
  fprintf(fd, "\r\n");
587
  fprintf(fd, "\r\n");
582
  fprintf(fd, "REM Uncomment the line below for automatic mouse support\r\n");
588
  fprintf(fd, "REM Uncomment the line below for automatic mouse support\r\n");
583
  fprintf(fd, "REM CTMOUSE\r\n");
589
  fprintf(fd, "REM CTMOUSE\r\n");
584
  fprintf(fd, "\r\n");
590
  fprintf(fd, "\r\n");
585
  fprintf(fd, "ECHO.\r\n");
591
  fprintf(fd, "ECHO.\r\n");
586
  fprintf(fd, "ECHO %s\r\n", kittengets(6, 0, "Welcome to Svarog386! Type 'HELP' if you need help."));
592
  fprintf(fd, "ECHO %s\r\n", kittengets(6, 0, "Welcome to Svarog386! Type 'HELP' if you need help."));
587
  fclose(fd);
593
  fclose(fd);
588
  /*** CREATE DIRECTORY FOR OTHER CONFIGURATION FILES ***/
594
  /*** CREATE DIRECTORY FOR OTHER CONFIGURATION FILES ***/
589
  snprintf(buff, sizeof(buff), "%c:\\SYSTEM\\CFG", targetdrv);
595
  snprintf(buff, sizeof(buff), "%c:\\SYSTEM\\CFG", targetdrv);
590
  mkdir(buff);
596
  mkdir(buff);
591
  /*** FDNPKG.CFG ***/
597
  /*** FDNPKG.CFG ***/
592
  snprintf(buff, sizeof(buff), "%c:\\SYSTEM\\CFG\\FDNPKG.CFG", targetdrv);
598
  snprintf(buff, sizeof(buff), "%c:\\SYSTEM\\CFG\\FDNPKG.CFG", targetdrv);
593
  fcopysub(buff, "A:\\DAT\\FDNPKG.CFG", '$', cdromdrv);
599
  fcopysub(buff, "A:\\DAT\\FDNPKG.CFG", '$', cdromdrv);
594
  /*** COUNTRY.SYS ***/
600
  /*** COUNTRY.SYS ***/
595
  /*** PICOTCP ***/
601
  /*** PICOTCP ***/
596
  /*** WATTCP ***/
602
  /*** WATTCP ***/
597
}
603
}
598
 
604
 
599
 
605
 
600
static void installpackages(int targetdrv, int cdromdrv) {
606
static void installpackages(int targetdrv, int cdromdrv) {
601
  char *pkglist[] = {
607
  char *pkglist[] = {
602
    "A:\\UDVD2", /* this one's not part of CORE, hence it's stored right on the floppy */
608
    "A:\\UDVD2", /* this one's not part of CORE, hence it's stored right on the floppy */
603
    "APPEND",
609
    "APPEND",
604
    "ASSIGN",
610
    "ASSIGN",
605
    "ATTRIB",
611
    "ATTRIB",
606
    "CHKDSK",
612
    "CHKDSK",
607
    "CHOICE",
613
    "CHOICE",
608
    "COMMAND",
614
    "COMMAND",
609
    "COMP",
615
    "COMP",
610
    "CPIDOS",
616
    "CPIDOS",
611
    "CTMOUSE",
617
    "CTMOUSE",
612
    "DEBUG",
618
    "DEBUG",
613
    "DEFRAG",
619
    "DEFRAG",
614
    "DELTREE",
620
    "DELTREE",
615
    "DEVLOAD",
621
    "DEVLOAD",
616
    "DISKCOMP",
622
    "DISKCOMP",
617
    "DISKCOPY",
623
    "DISKCOPY",
618
    "DISPLAY",
624
    "DISPLAY",
619
    "DOSFSCK",
625
    "DOSFSCK",
620
    "EDIT",
626
    "EDIT",
621
    "EDLIN",
627
    "EDLIN",
622
    "EXE2BIN",
628
    "EXE2BIN",
623
    "FC",
629
    "FC",
624
    "FDAPM",
630
    "FDAPM",
625
    "FDISK",
631
    "FDISK",
626
    "FDNPKG",
632
    "FDNPKG",
627
    "FIND",
633
    "FIND",
628
    "FORMAT",
634
    "FORMAT",
629
    "HELP",
635
    "HELP",
630
    "HIMEMX",
636
    "HIMEMX",
631
    "KERNEL",
637
    "KERNEL",
632
    "KEYB",
638
    "KEYB",
633
    "KEYB_LAY",
639
    "KEYB_LAY",
634
    "LABEL",
640
    "LABEL",
635
    "LBACACHE",
641
    "LBACACHE",
636
    "MEM",
642
    "MEM",
637
    "MIRROR",
643
    "MIRROR",
638
    "MODE",
644
    "MODE",
639
    "MORE",
645
    "MORE",
640
    "MOVE",
646
    "MOVE",
641
    "NANSI",
647
    "NANSI",
642
    "NLSFUNC",
648
    "NLSFUNC",
643
    "PRINT",
649
    "PRINT",
644
    "RDISK",
650
    "RDISK",
645
    "RECOVER",
651
    "RECOVER",
646
    "REPLACE",
652
    "REPLACE",
647
    "SHARE",
653
    "SHARE",
648
    "SHSUCDX",
654
    "SHSUCDX",
649
    "SORT",
655
    "SORT",
650
    "SWSUBST",
656
    "SWSUBST",
651
    "TREE",
657
    "TREE",
652
    "UNDELETE",
658
    "UNDELETE",
653
    "XCOPY",
659
    "XCOPY",
654
    NULL
660
    NULL
655
  };
661
  };
656
  int i, pkglistlen;
662
  int i, pkglistlen;
657
  char buff[64];
663
  char buff[64];
658
  newscreen(3);
664
  newscreen(3);
659
  /* count how long the pkg list is */
665
  /* count how long the pkg list is */
660
  for (pkglistlen = 0; pkglist[pkglistlen] != NULL; pkglistlen++);
666
  for (pkglistlen = 0; pkglist[pkglistlen] != NULL; pkglistlen++);
661
  /* set DOSDIR and friends */
667
  /* set DOSDIR and friends */
662
  snprintf(buff, sizeof(buff), "%c:\\SYSTEM\\SVAROG.386", targetdrv);
668
  snprintf(buff, sizeof(buff), "%c:\\SYSTEM\\SVAROG.386", targetdrv);
663
  setenv("DOSDIR", buff, 1);
669
  setenv("DOSDIR", buff, 1);
664
  snprintf(buff, sizeof(buff), "%c:\\TEMP", targetdrv);
670
  snprintf(buff, sizeof(buff), "%c:\\TEMP", targetdrv);
665
  setenv("TEMP", buff, 1);
671
  setenv("TEMP", buff, 1);
666
  /* install packages */
672
  /* install packages */
667
  for (i = 0; pkglist[i] != NULL; i++) {
673
  for (i = 0; pkglist[i] != NULL; i++) {
668
    char buff[128];
674
    char buff[128];
669
    snprintf(buff, sizeof(buff), kittengets(4, 0, "Installing package %d/%d: %s"), i+1, pkglistlen, pkglist[i]);
675
    snprintf(buff, sizeof(buff), kittengets(4, 0, "Installing package %d/%d: %s"), i+1, pkglistlen, pkglist[i]);
670
    strcat(buff, "       ");
676
    strcat(buff, "       ");
671
    video_putstring(10, 1, COLOR_BODY[mono], buff, -1);
677
    video_putstring(10, 1, COLOR_BODY[mono], buff, -1);
672
    if (pkglist[i][1] == ':') {
678
    if (pkglist[i][1] == ':') {
673
      snprintf(buff, sizeof(buff), "FDINST INSTALL %s.ZIP > NUL", pkglist[i]);
679
      snprintf(buff, sizeof(buff), "FDINST INSTALL %s.ZIP > NUL", pkglist[i]);
674
    } else {
680
    } else {
675
      snprintf(buff, sizeof(buff), "FDINST INSTALL %c:\\CORE\\%s.ZIP > NUL", cdromdrv, pkglist[i]);
681
      snprintf(buff, sizeof(buff), "FDINST INSTALL %c:\\CORE\\%s.ZIP > NUL", cdromdrv, pkglist[i]);
676
    }
682
    }
677
    system(buff);
683
    system(buff);
678
  }
684
  }
679
}
685
}
680
 
686
 
681
 
687
 
682
static void finalreboot(void) {
688
static void finalreboot(void) {
683
  int y = 9;
689
  int y = 9;
684
  newscreen(2);
690
  newscreen(2);
685
  y += putstringnls(y, 1, COLOR_BODY[mono], 5, 0, "Svarog386 installation is over. Your computer will reboot now.\nPlease remove the installation disk from your drive.");
691
  y += putstringnls(y, 1, COLOR_BODY[mono], 5, 0, "Svarog386 installation is over. Your computer will reboot now.\nPlease remove the installation disk from your drive.");
686
  putstringnls(++y, 1, COLOR_BODY[mono], 0, 5, "Press any key...");
692
  putstringnls(++y, 1, COLOR_BODY[mono], 0, 5, "Press any key...");
687
  input_getkey();
693
  input_getkey();
688
  reboot();
694
  reboot();
689
}
695
}
690
 
696
 
691
 
697
 
692
static void loadcp(struct slocales *locales) {
698
static void loadcp(struct slocales *locales) {
693
  char buff[64];
699
  char buff[64];
694
  if (locales->codepage == 437) return;
700
  if (locales->codepage == 437) return;
695
  video_movecursor(1, 0);
701
  video_movecursor(1, 0);
696
  if (locales->egafile == 1) {
702
  if (locales->egafile == 1) {
697
    snprintf(buff, sizeof(buff), "MODE CON CP PREP=((%u) A:\\EGA.CPX) > NUL", locales->codepage);
703
    snprintf(buff, sizeof(buff), "MODE CON CP PREP=((%u) A:\\EGA.CPX) > NUL", locales->codepage);
698
  } else {
704
  } else {
699
    snprintf(buff, sizeof(buff), "MODE CON CP PREP=((%u) A:\\EGA%d.CPX) > NUL", locales->codepage, locales->egafile);
705
    snprintf(buff, sizeof(buff), "MODE CON CP PREP=((%u) A:\\EGA%d.CPX) > NUL", locales->codepage, locales->egafile);
700
  }
706
  }
701
  system(buff);
707
  system(buff);
702
  snprintf(buff, sizeof(buff), "MODE CON CP SEL=%u > NUL", locales->codepage);
708
  snprintf(buff, sizeof(buff), "MODE CON CP SEL=%u > NUL", locales->codepage);
703
  system(buff);
709
  system(buff);
704
  /* below I re-init the video controller - apparently this is required if
710
  /* below I re-init the video controller - apparently this is required if
705
   * I want the new glyph symbols to be actually applied, at least some
711
   * I want the new glyph symbols to be actually applied, at least some
706
   * (broken?) BIOSes, like VBox, apply glyphs only at next video mode change */
712
   * (broken?) BIOSes, like VBox, apply glyphs only at next video mode change */
707
  {
713
  {
708
  union REGS r;
714
  union REGS r;
709
  r.h.ah = 0x0F; /* get current video mode */
715
  r.h.ah = 0x0F; /* get current video mode */
710
  int86(0x10, &r, &r); /* r.h.al contains the current video mode now */
716
  int86(0x10, &r, &r); /* r.h.al contains the current video mode now */
711
  r.h.al |= 128; /* set the high bit of AL to instruct BIOS not to flush VRAM's content (EGA+) */
717
  r.h.al |= 128; /* set the high bit of AL to instruct BIOS not to flush VRAM's content (EGA+) */
712
  r.h.ah = 0; /* re-set video mode (to whatever is set in AL) */
718
  r.h.ah = 0; /* re-set video mode (to whatever is set in AL) */
713
  int86(0x10, &r, &r);
719
  int86(0x10, &r, &r);
714
  }
720
  }
715
}
721
}
716
 
722
 
717
/* checks CD drive drv for the presence of the Svarog386 install CD
723
/* checks CD drive drv for the presence of the Svarog386 install CD
718
 * returns 0 if found, non-zero otherwise */
724
 * returns 0 if found, non-zero otherwise */
719
static int checkcd(char drv) {
725
static int checkcd(char drv) {
720
  FILE *fd;
726
  FILE *fd;
721
  char fname[32];
727
  char fname[32];
722
  snprintf(fname, sizeof(fname), "%c:\\CORE\\MEM.ZIP", drv);
728
  snprintf(fname, sizeof(fname), "%c:\\CORE\\MEM.ZIP", drv);
723
  fd = fopen(fname, "rb");
729
  fd = fopen(fname, "rb");
724
  if (fd == NULL) return(-1);
730
  if (fd == NULL) return(-1);
725
  fclose(fd);
731
  fclose(fd);
726
  return(0);
732
  return(0);
727
}
733
}
728
 
734
 
729
 
735
 
730
int main(void) {
736
int main(void) {
731
  struct slocales locales;
737
  struct slocales locales;
732
  int targetdrv;
738
  int targetdrv;
733
  int cdromdrv;
739
  int cdromdrv;
734
  int action;
740
  int action;
735
 
741
 
736
  /* find where the cdrom drive is */
742
  /* find where the cdrom drive is */
737
  cdromdrv = cdrom_findfirst();
743
  cdromdrv = cdrom_findfirst();
738
  if (cdromdrv < 0) {
744
  if (cdromdrv < 0) {
739
    printf("ERROR: CD-ROM DRIVE NOT FOUND\r\n");
745
    printf("ERROR: CD-ROM DRIVE NOT FOUND\r\n");
740
    return(1);
746
    return(1);
741
  }
747
  }
742
  cdromdrv += 'A'; /* convert the cdrom 'id' (A=0) to an actual drive letter */
748
  cdromdrv += 'A'; /* convert the cdrom 'id' (A=0) to an actual drive letter */
743
  if (checkcd(cdromdrv) != 0) {
749
  if (checkcd(cdromdrv) != 0) {
744
    printf("ERROR: SVAROG386 INSTALLATION CD NOT FOUND IN THE DRIVE.\r\n");
750
    printf("ERROR: SVAROG386 INSTALLATION CD NOT FOUND IN THE DRIVE.\r\n");
745
    return(1);
751
    return(1);
746
  }
752
  }
747
 
753
 
748
  /* init screen and detect mono status */
754
  /* init screen and detect mono status */
749
  mono = video_init();
755
  mono = video_init();
750
 
756
 
751
  kittenopen("INSTALL"); /* load initial NLS support */
757
  kittenopen("INSTALL"); /* load initial NLS support */
752
 
758
 
753
 SelectLang:
759
 SelectLang:
754
  action = selectlang(&locales); /* welcome to svarog, select your language */
760
  action = selectlang(&locales); /* welcome to svarog, select your language */
755
  if (action != MENUNEXT) goto Quit;
761
  if (action != MENUNEXT) goto Quit;
756
  setenv("LANG", locales.lang, 1);
762
  setenv("LANG", locales.lang, 1);
757
  loadcp(&locales);
763
  loadcp(&locales);
758
  kittenclose(); /* reload NLS with new language */
764
  kittenclose(); /* reload NLS with new language */
759
  kittenopen("INSTALL"); /* NLS support */
765
  kittenopen("INSTALL"); /* NLS support */
760
  action = selectkeyb(&locales);  /* what keyb layout should we use? */
766
  action = selectkeyb(&locales);  /* what keyb layout should we use? */
761
  if (action == MENUQUIT) goto Quit;
767
  if (action == MENUQUIT) goto Quit;
762
  if (action == MENUPREV) goto SelectLang;
768
  if (action == MENUPREV) goto SelectLang;
763
 
769
 
764
 WelcomeScreen:
770
 WelcomeScreen:
765
  action = welcomescreen(); /* what svarog386 is, ask whether to run live dos or install */
771
  action = welcomescreen(); /* what svarog386 is, ask whether to run live dos or install */
766
  if (action == MENUQUIT) goto Quit;
772
  if (action == MENUQUIT) goto Quit;
767
  if (action == MENUPREV) goto SelectLang;
773
  if (action == MENUPREV) goto SelectLang;
768
  targetdrv = preparedrive(); /* what drive should we install to? check avail. space */
774
  targetdrv = preparedrive(); /* what drive should we install to? check avail. space */
769
  if (targetdrv == MENUQUIT) goto Quit;
775
  if (targetdrv == MENUQUIT) goto Quit;
770
  if (targetdrv == MENUPREV) goto WelcomeScreen;
776
  if (targetdrv == MENUPREV) goto WelcomeScreen;
771
  /*askaboutsources();*/ /* IF sources are available, ask if installing with them */
777
  /*askaboutsources();*/ /* IF sources are available, ask if installing with them */
772
  installpackages(targetdrv, cdromdrv);    /* install packages */
778
  installpackages(targetdrv, cdromdrv);    /* install packages */
773
  bootfilesgen(targetdrv, &locales, cdromdrv); /* generate boot files and other configurations */
779
  bootfilesgen(targetdrv, &locales, cdromdrv); /* generate boot files and other configurations */
774
  /*localcfg();*/ /* show local params (currency, etc), and propose to change them (based on localcfg) */
780
  /*localcfg();*/ /* show local params (currency, etc), and propose to change them (based on localcfg) */
775
  /*netcfg();*/ /* basic networking config */
781
  /*netcfg();*/ /* basic networking config */
776
  finalreboot(); /* remove the CD and reboot */
782
  finalreboot(); /* remove the CD and reboot */
777
 
783
 
778
 Quit:
784
 Quit:
779
  kittenclose(); /* close NLS support */
785
  kittenclose(); /* close NLS support */
780
  video_clear(0x0700, 0, 0);
786
  video_clear(0x0700, 0, 0);
781
  video_movecursor(0, 0);
787
  video_movecursor(0, 0);
782
  return(0);
788
  return(0);
783
}
789
}
784
 
790