Sync with trunk r58033.
[reactos.git] / boot / freeldr / freeldr / arch / i386 / custom.c
1 /*
2 * FreeLoader
3 * Copyright (C) 1998-2003 Brian Palmer <brianp@sginet.com>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #include <freeldr.h>
21
22
23 const CHAR BootDrivePrompt[] = "Enter the boot drive.\n\nExamples:\nfd0 - first floppy drive\nhd0 - first hard drive\nhd1 - second hard drive\ncd0 - first CD-ROM drive.\n\nBIOS drive numbers may also be used:\n0 - first floppy drive\n0x80 - first hard drive\n0x81 - second hard drive";
24 const CHAR BootPartitionPrompt[] = "Enter the boot partition.\n\nEnter 0 for the active (bootable) partition.";
25 const CHAR BootSectorFilePrompt[] = "Enter the boot sector file path.\n\nExamples:\n\\BOOTSECT.DOS\n/boot/bootsect.dos";
26 const CHAR LinuxKernelPrompt[] = "Enter the Linux kernel image path.\n\nExamples:\n/vmlinuz\n/boot/vmlinuz-2.4.18";
27 const CHAR LinuxInitrdPrompt[] = "Enter the initrd image path.\n\nExamples:\n/initrd.gz\n/boot/root.img.gz\n\nLeave blank for no initial ram disk.";
28 const CHAR LinuxCommandLinePrompt[] = "Enter the Linux kernel command line.\n\nExamples:\nroot=/dev/hda1\nroot=/dev/fd0 read-only\nroot=/dev/sdb1 init=/sbin/init";
29 const CHAR ReactOSSystemPathPrompt[] = "Enter the path to your ReactOS system directory.\n\nExamples:\n\\REACTOS\n\\ROS";
30 const CHAR ReactOSOptionsPrompt[] = "Enter the options you want passed to the kernel.\n\nExamples:\n/DEBUG /DEBUGPORT=COM1 /BAUDRATE=115200\n/FASTDETECT /SOS /NOGUIBOOT\n/BASEVIDEO /MAXMEM=64\n/KERNEL=NTKRNLMP.EXE /HAL=HALMPS.DLL";
31
32 const CHAR CustomBootPrompt[] = "Press ENTER to boot your custom boot setup.";
33
34 VOID OptionMenuCustomBoot(VOID)
35 {
36 PCSTR CustomBootMenuList[] = {
37 "Disk",
38 "Partition",
39 "Boot Sector File",
40 "ReactOS",
41 "Linux"
42 };
43 ULONG CustomBootMenuCount = sizeof(CustomBootMenuList) / sizeof(CustomBootMenuList[0]);
44 ULONG SelectedMenuItem;
45
46 if (!UiDisplayMenu("Please choose a boot method:", "",
47 FALSE,
48 CustomBootMenuList,
49 CustomBootMenuCount,
50 0, -1,
51 &SelectedMenuItem,
52 TRUE,
53 NULL))
54 {
55 // The user pressed ESC
56 return;
57 }
58
59 switch (SelectedMenuItem)
60 {
61 case 0: // Disk
62 OptionMenuCustomBootDisk();
63 break;
64 case 1: // Partition
65 OptionMenuCustomBootPartition();
66 break;
67 case 2: // Boot Sector File
68 OptionMenuCustomBootBootSectorFile();
69 break;
70 case 3: // ReactOS
71 OptionMenuCustomBootReactOS();
72 break;
73 case 4: // Linux
74 OptionMenuCustomBootLinux();
75 break;
76 }
77 }
78
79 VOID OptionMenuCustomBootDisk(VOID)
80 {
81 ULONG_PTR SectionId;
82 CHAR SectionName[100];
83 CHAR BootDriveString[20];
84 TIMEINFO* TimeInfo;
85 OperatingSystemItem OperatingSystem;
86
87 RtlZeroMemory(SectionName, sizeof(SectionName));
88 RtlZeroMemory(BootDriveString, sizeof(BootDriveString));
89
90 if (!UiEditBox(BootDrivePrompt, BootDriveString, 20))
91 {
92 return;
93 }
94
95 // Generate a unique section name
96 TimeInfo = ArcGetTime();
97 sprintf(SectionName, "CustomBootDisk%u%u%u%u%u%u", TimeInfo->Year, TimeInfo->Day, TimeInfo->Month, TimeInfo->Hour, TimeInfo->Minute, TimeInfo->Second);
98
99 // Add the section
100 if (!IniAddSection(SectionName, &SectionId))
101 {
102 return;
103 }
104
105 // Add the BootType
106 if (!IniAddSettingValueToSection(SectionId, "BootType", "Drive"))
107 {
108 return;
109 }
110
111 // Add the BootDrive
112 if (!IniAddSettingValueToSection(SectionId, "BootDrive", BootDriveString))
113 {
114 return;
115 }
116
117 UiMessageBox(CustomBootPrompt);
118
119 OperatingSystem.SystemPartition = SectionName;
120 OperatingSystem.LoadIdentifier = NULL;
121 OperatingSystem.OsLoadOptions = NULL;
122
123 // LoadAndBootDrive(&OperatingSystem, 0);
124 LoadOperatingSystem(&OperatingSystem);
125 }
126
127 VOID OptionMenuCustomBootPartition(VOID)
128 {
129 ULONG_PTR SectionId;
130 CHAR SectionName[100];
131 CHAR BootDriveString[20];
132 CHAR BootPartitionString[20];
133 TIMEINFO* TimeInfo;
134 OperatingSystemItem OperatingSystem;
135
136 RtlZeroMemory(SectionName, sizeof(SectionName));
137 RtlZeroMemory(BootDriveString, sizeof(BootDriveString));
138 RtlZeroMemory(BootPartitionString, sizeof(BootPartitionString));
139
140 if (!UiEditBox(BootDrivePrompt, BootDriveString, 20))
141 {
142 return;
143 }
144
145 if (!UiEditBox(BootPartitionPrompt, BootPartitionString, 20))
146 {
147 return;
148 }
149
150 // Generate a unique section name
151 TimeInfo = ArcGetTime();
152 sprintf(SectionName, "CustomBootPartition%u%u%u%u%u%u", TimeInfo->Year, TimeInfo->Day, TimeInfo->Month, TimeInfo->Hour, TimeInfo->Minute, TimeInfo->Second);
153
154 // Add the section
155 if (!IniAddSection(SectionName, &SectionId))
156 {
157 return;
158 }
159
160 // Add the BootType
161 if (!IniAddSettingValueToSection(SectionId, "BootType", "Partition"))
162 {
163 return;
164 }
165
166 // Add the BootDrive
167 if (!IniAddSettingValueToSection(SectionId, "BootDrive", BootDriveString))
168 {
169 return;
170 }
171
172 // Add the BootPartition
173 if (!IniAddSettingValueToSection(SectionId, "BootPartition", BootPartitionString))
174 {
175 return;
176 }
177
178 UiMessageBox(CustomBootPrompt);
179
180 OperatingSystem.SystemPartition = SectionName;
181 OperatingSystem.LoadIdentifier = NULL;
182 OperatingSystem.OsLoadOptions = NULL;
183
184 // LoadAndBootPartition(&OperatingSystem, 0);
185 LoadOperatingSystem(&OperatingSystem);
186 }
187
188 VOID OptionMenuCustomBootBootSectorFile(VOID)
189 {
190 ULONG_PTR SectionId;
191 CHAR SectionName[100];
192 CHAR BootDriveString[20];
193 CHAR BootPartitionString[20];
194 CHAR BootSectorFileString[200];
195 TIMEINFO* TimeInfo;
196 OperatingSystemItem OperatingSystem;
197
198 RtlZeroMemory(SectionName, sizeof(SectionName));
199 RtlZeroMemory(BootDriveString, sizeof(BootDriveString));
200 RtlZeroMemory(BootPartitionString, sizeof(BootPartitionString));
201 RtlZeroMemory(BootSectorFileString, sizeof(BootSectorFileString));
202
203 if (!UiEditBox(BootDrivePrompt, BootDriveString, 20))
204 {
205 return;
206 }
207
208 if (!UiEditBox(BootPartitionPrompt, BootPartitionString, 20))
209 {
210 return;
211 }
212
213 if (!UiEditBox(BootSectorFilePrompt, BootSectorFileString, 200))
214 {
215 return;
216 }
217
218 // Generate a unique section name
219 TimeInfo = ArcGetTime();
220 sprintf(SectionName, "CustomBootSectorFile%u%u%u%u%u%u", TimeInfo->Year, TimeInfo->Day, TimeInfo->Month, TimeInfo->Hour, TimeInfo->Minute, TimeInfo->Second);
221
222 // Add the section
223 if (!IniAddSection(SectionName, &SectionId))
224 {
225 return;
226 }
227
228 // Add the BootType
229 if (!IniAddSettingValueToSection(SectionId, "BootType", "BootSector"))
230 {
231 return;
232 }
233
234 // Add the BootDrive
235 if (!IniAddSettingValueToSection(SectionId, "BootDrive", BootDriveString))
236 {
237 return;
238 }
239
240 // Add the BootPartition
241 if (!IniAddSettingValueToSection(SectionId, "BootPartition", BootPartitionString))
242 {
243 return;
244 }
245
246 // Add the BootSectorFile
247 if (!IniAddSettingValueToSection(SectionId, "BootSectorFile", BootSectorFileString))
248 {
249 return;
250 }
251
252 UiMessageBox(CustomBootPrompt);
253
254 OperatingSystem.SystemPartition = SectionName;
255 OperatingSystem.LoadIdentifier = NULL;
256 OperatingSystem.OsLoadOptions = NULL;
257
258 // LoadAndBootBootSector(&OperatingSystem, 0);
259 LoadOperatingSystem(&OperatingSystem);
260 }
261
262 VOID OptionMenuCustomBootReactOS(VOID)
263 {
264 ULONG_PTR SectionId;
265 CHAR SectionName[100];
266 CHAR BootDriveString[20];
267 CHAR BootPartitionString[20];
268 CHAR ReactOSSystemPath[200];
269 CHAR ReactOSARCPath[200];
270 CHAR ReactOSOptions[200];
271 TIMEINFO* TimeInfo;
272 OperatingSystemItem OperatingSystem;
273
274 RtlZeroMemory(SectionName, sizeof(SectionName));
275 RtlZeroMemory(BootDriveString, sizeof(BootDriveString));
276 RtlZeroMemory(BootPartitionString, sizeof(BootPartitionString));
277 RtlZeroMemory(ReactOSSystemPath, sizeof(ReactOSSystemPath));
278 RtlZeroMemory(ReactOSOptions, sizeof(ReactOSOptions));
279
280 if (!UiEditBox(BootDrivePrompt, BootDriveString, 20))
281 {
282 return;
283 }
284
285 if (!UiEditBox(BootPartitionPrompt, BootPartitionString, 20))
286 {
287 return;
288 }
289
290 if (!UiEditBox(ReactOSSystemPathPrompt, ReactOSSystemPath, 200))
291 {
292 return;
293 }
294
295 if (!UiEditBox(ReactOSOptionsPrompt, ReactOSOptions, 200))
296 {
297 return;
298 }
299
300 // Generate a unique section name
301 TimeInfo = ArcGetTime();
302 sprintf(SectionName, "CustomReactOS%u%u%u%u%u%u", TimeInfo->Year, TimeInfo->Day, TimeInfo->Month, TimeInfo->Hour, TimeInfo->Minute, TimeInfo->Second);
303
304 // Add the section
305 if (!IniAddSection(SectionName, &SectionId))
306 {
307 return;
308 }
309
310 // Add the BootType
311 if (!IniAddSettingValueToSection(SectionId, "BootType", "Windows2003"))
312 {
313 return;
314 }
315
316 // Construct the ReactOS ARC system path
317 ConstructArcPath(ReactOSARCPath, ReactOSSystemPath, DriveMapGetBiosDriveNumber(BootDriveString), atoi(BootPartitionString));
318
319 // Add the system path
320 if (!IniAddSettingValueToSection(SectionId, "SystemPath", ReactOSARCPath))
321 {
322 return;
323 }
324
325 // Add the CommandLine
326 if (!IniAddSettingValueToSection(SectionId, "Options", ReactOSOptions))
327 {
328 return;
329 }
330
331 UiMessageBox(CustomBootPrompt);
332
333 OperatingSystem.SystemPartition = SectionName;
334 OperatingSystem.LoadIdentifier = NULL;
335 OperatingSystem.OsLoadOptions = NULL; // ReactOSOptions
336
337 // LoadAndBootWindows(&OperatingSystem, _WIN32_WINNT_WS03);
338 LoadOperatingSystem(&OperatingSystem);
339 }
340
341 VOID OptionMenuCustomBootLinux(VOID)
342 {
343 ULONG_PTR SectionId;
344 CHAR SectionName[100];
345 CHAR BootDriveString[20];
346 CHAR BootPartitionString[20];
347 CHAR LinuxKernelString[200];
348 CHAR LinuxInitrdString[200];
349 CHAR LinuxCommandLineString[200];
350 TIMEINFO* TimeInfo;
351 OperatingSystemItem OperatingSystem;
352
353 RtlZeroMemory(SectionName, sizeof(SectionName));
354 RtlZeroMemory(BootDriveString, sizeof(BootDriveString));
355 RtlZeroMemory(BootPartitionString, sizeof(BootPartitionString));
356 RtlZeroMemory(LinuxKernelString, sizeof(LinuxKernelString));
357 RtlZeroMemory(LinuxInitrdString, sizeof(LinuxInitrdString));
358 RtlZeroMemory(LinuxCommandLineString, sizeof(LinuxCommandLineString));
359
360 if (!UiEditBox(BootDrivePrompt, BootDriveString, 20))
361 {
362 return;
363 }
364
365 if (!UiEditBox(BootPartitionPrompt, BootPartitionString, 20))
366 {
367 return;
368 }
369
370 if (!UiEditBox(LinuxKernelPrompt, LinuxKernelString, 200))
371 {
372 return;
373 }
374
375 if (!UiEditBox(LinuxInitrdPrompt, LinuxInitrdString, 200))
376 {
377 return;
378 }
379
380 if (!UiEditBox(LinuxCommandLinePrompt, LinuxCommandLineString, 200))
381 {
382 return;
383 }
384
385 // Generate a unique section name
386 TimeInfo = ArcGetTime();
387 sprintf(SectionName, "CustomLinux%u%u%u%u%u%u", TimeInfo->Year, TimeInfo->Day, TimeInfo->Month, TimeInfo->Hour, TimeInfo->Minute, TimeInfo->Second);
388
389 // Add the section
390 if (!IniAddSection(SectionName, &SectionId))
391 {
392 return;
393 }
394
395 // Add the BootType
396 if (!IniAddSettingValueToSection(SectionId, "BootType", "Linux"))
397 {
398 return;
399 }
400
401 // Add the BootDrive
402 if (!IniAddSettingValueToSection(SectionId, "BootDrive", BootDriveString))
403 {
404 return;
405 }
406
407 // Add the BootPartition
408 if (!IniAddSettingValueToSection(SectionId, "BootPartition", BootPartitionString))
409 {
410 return;
411 }
412
413 // Add the Kernel
414 if (!IniAddSettingValueToSection(SectionId, "Kernel", LinuxKernelString))
415 {
416 return;
417 }
418
419 // Add the Initrd
420 if (strlen(LinuxInitrdString) > 0)
421 {
422 if (!IniAddSettingValueToSection(SectionId, "Initrd", LinuxInitrdString))
423 {
424 return;
425 }
426 }
427
428 // Add the CommandLine
429 if (!IniAddSettingValueToSection(SectionId, "CommandLine", LinuxCommandLineString))
430 {
431 return;
432 }
433
434 UiMessageBox(CustomBootPrompt);
435
436 OperatingSystem.SystemPartition = SectionName;
437 OperatingSystem.LoadIdentifier = "Custom Linux Setup";
438 OperatingSystem.OsLoadOptions = NULL;
439
440 // LoadAndBootLinux(&OperatingSystem, 0);
441 LoadOperatingSystem(&OperatingSystem);
442 }
443
444 VOID OptionMenuReboot(VOID)
445 {
446 UiMessageBox("The system will now reboot.");
447
448 DiskStopFloppyMotor();
449 Reboot();
450 }