2 * Copyright (c)2004 The DragonFly Project. All rights reserved.
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
8 * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
11 * Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in
13 * the documentation and/or other materials provided with the
16 * Neither the name of the DragonFly Project nor the names of its
17 * contributors may be used to endorse or promote products derived
18 * from this software without specific prior written permission.
20 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24 * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
25 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
26 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
27 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
29 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
31 * OF THE POSSIBILITY OF SUCH DAMAGE.
36 * Workflow logic for installer.
37 * $Id: flow.c,v 1.67 2005/04/08 08:09:23 cpressey Exp $
48 #include "libdfui/lang.h"
49 #define _(String) gettext (String)
50 extern int _nl_msg_cat_cntr
;
52 #define _(String) (String)
55 #include "libaura/mem.h"
56 #include "libaura/dict.h"
57 #include "libaura/fspred.h"
59 #include "libdfui/dfui.h"
61 #include "libdfui/dump.h"
63 #include "libdfui/system.h"
65 #include "libinstaller/commands.h"
66 #include "libinstaller/confed.h"
67 #include "libinstaller/diskutil.h"
68 #include "libinstaller/functions.h"
69 #include "libinstaller/package.h"
70 #include "libinstaller/uiutil.h"
74 #include "pathnames.h"
78 void (*state
)(struct i_fn_args
*) = NULL
;
84 * The installer works like a big state machine. Each major form is
85 * a state. When the user has filled out the form satisfactorily,
86 * and selects "OK", there is a transition to the next state, in a
87 * mostly-linear order towards the final, "successfully installed"
88 * state. The user may also "Cancel", which generally causes a
89 * transition to the previous state (but may also take them back to
90 * the very first state in some cases.)
93 * - Select localization optional
94 * - Welcome to DragonFly required
95 * - Begin Installation required
96 * - Select Disk required
97 * - Format Disk optional dd, fdisk
98 * - Select Partition required dd, disklabel
99 * - Create Subpartitions required disklabel, newfs
100 * - Install DragonFly required swapon, mkdir, mount, cpdup
101 * - Install Bootstrap optional boot0cfg
102 * - Reboot optional reboot
107 state_lang_menu(struct i_fn_args
*a
)
110 struct dfui_response
*r
;
116 f
= dfui_form_create(
118 _("Select Language"),
119 _("Please select the language you wish you use."),
124 "a", "default", "English",
125 "English Standard Default", "",
126 "a", "ru", "Russian",
127 "Russian KOI8-R", "",
131 if (!dfui_be_present(a
->c
, f
, &r
))
134 id
= aura_strdup(dfui_response_get_action_id(r
));
136 if (strcmp(id
, "default") == 0) {
137 state
= state_welcome
;
140 state
= state_welcome
;
145 dfui_response_free(r
);
148 /* set keymap, scrnmap, fonts */
149 if (!set_lang_syscons(id
))
153 if (!set_lang_envars(id
))
156 dfui_be_set_global_setting(a
->c
, "lang", id
, &cancelled
);
158 /* XXX if (!cancelled) ... ? */
160 /* let gettext know about changes */
166 * state_welcome_livecd: the start state of the installer state machine,
167 * when run from the Live CD. Briefly describe DragonFly to the user,
168 * and present them with a set of reasonable options of how to proceed.
171 state_welcome(struct i_fn_args
*a
)
174 struct dfui_action
*k
;
175 struct dfui_response
*r
;
176 char msg_buf
[2][1024];
178 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
179 _("Welcome to %s"), OPERATING_SYSTEM_NAME
);
181 snprintf(msg_buf
[1], sizeof(msg_buf
[1]),
182 _("Welcome to the %s Live CD."
184 "%s is an efficient and elegant BSD "
185 "Unix-derived operating system. For more information, see %s"
187 "From this CD, you can boot into %s ``live'' "
188 "(without installing it) to evaluate it, to install it "
189 "manually, or to troubleshoot problems with an "
190 "existing installation, using either a command prompt "
191 "or menu-driven utilities."
193 "Also, you can use this automated application to assist "
194 "you in installing %s on this computer and "
195 "configuring it once it is installed."
197 OPERATING_SYSTEM_NAME
, OPERATING_SYSTEM_NAME
, OPERATING_SYSTEM_URL
,
198 OPERATING_SYSTEM_NAME
, OPERATING_SYSTEM_NAME
);
200 if (!a
->booted_from_livecd
) {
201 state
= state_welcome_system
;
205 f
= dfui_form_create(
213 "p", "special", "dfinstaller_welcome",
218 if (a
->upgrade_menu_toggle
) {
219 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
220 _("Upgrade a FreeBSD 4.X system to %s"),
221 OPERATING_SYSTEM_NAME
);
222 dfui_form_action_add(f
, "upgrade",
223 dfui_info_new(_("Upgrade"),
226 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
227 _("Install %s"), OPERATING_SYSTEM_NAME
);
228 snprintf(msg_buf
[1], sizeof(msg_buf
[1]),
229 _("Install %s on a HDD or HDD partition on this computer"),
230 OPERATING_SYSTEM_NAME
);
231 dfui_form_action_add(f
, "install",
232 dfui_info_new(msg_buf
[0],
236 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
237 _("Configure a %s system once it has been installed on HDD"),
238 OPERATING_SYSTEM_NAME
);
239 dfui_form_action_add(f
, "configure",
240 dfui_info_new(_("Configure an Installed System"),
243 dfui_form_action_add(f
, "utilities",
244 dfui_info_new(_("Live CD Utilities"),
245 _("Utilities to work with disks, diagnostics, and the LiveCD Environment"), ""));
247 k
= dfui_form_action_add(f
, "exit",
248 dfui_info_new(_("Exit to Live CD"),
249 _("Exit this program to a login prompt with access to the LiveCD"), ""));
251 dfui_form_action_add(f
, "reboot",
252 dfui_info_new(_("Reboot this Computer"),
253 _("Reboot this computer (e.g. to boot into a newly installed system)"), ""));
255 dfui_form_action_add(f
, "configure_netboot",
256 dfui_info_new(_("Setup NetBoot Install Services"),
257 _("Setup machine as remote installation server"), ""));
259 if (!dfui_be_present(a
->c
, f
, &r
))
262 if (strcmp(dfui_response_get_action_id(r
), "install") == 0) {
263 state
= state_begin_install
;
264 } else if (strcmp(dfui_response_get_action_id(r
), "upgrade") == 0) {
265 state
= state_begin_upgrade
;
266 } else if (strcmp(dfui_response_get_action_id(r
), "configure") == 0) {
267 storage_set_selected_disk(a
->s
, NULL
);
268 storage_set_selected_slice(a
->s
, NULL
);
269 state
= state_configure_menu
;
270 } else if (strcmp(dfui_response_get_action_id(r
), "utilities") == 0) {
271 state
= state_utilities_menu
;
272 } else if (strcmp(dfui_response_get_action_id(r
), "exit") == 0) {
274 } else if (strcmp(dfui_response_get_action_id(r
), "configure_netboot") == 0) {
275 state
= state_setup_remote_installation_server
;
276 } else if (strcmp(dfui_response_get_action_id(r
), "reboot") == 0) {
277 state
= state_reboot
;
281 dfui_response_free(r
);
285 * state_welcome_system: the start state of the installer state machine,
286 * when run from the installed system. Allow the user to configure the
290 state_welcome_system(struct i_fn_args
*a
)
293 struct dfui_response
*r
;
294 char msg_buf
[2][1024];
296 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
297 _("Configure this %s System"), OPERATING_SYSTEM_NAME
);
299 snprintf(msg_buf
[1], sizeof(msg_buf
[1]),
300 _("Thank you for choosing %s."
302 "For up-to-date news and information on %s, "
303 "make sure to check out"
307 "You can use this automated application to assist "
308 "you in setting up this %s system."
310 OPERATING_SYSTEM_NAME
, OPERATING_SYSTEM_NAME
,
311 OPERATING_SYSTEM_URL
, OPERATING_SYSTEM_NAME
);
314 f
= dfui_form_create(
322 "p", "special", "dfinstaller_welcome",
327 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
328 _("Configure this %s system"), OPERATING_SYSTEM_NAME
);
330 dfui_form_action_add(f
, "environment",
331 dfui_info_new(_("Configure this System"),
334 dfui_form_action_add(f
, "utilities",
335 dfui_info_new(_("Utilities"),
336 _("Utilities to work with and diagnose disks and other subsystems"), ""));
338 dfui_form_action_add(f
, "exit",
339 dfui_info_new(_("Exit Installer"),
340 _("Exit this program and return to the system"), ""));
342 if (!dfui_be_present(a
->c
, f
, &r
))
345 if (strcmp(dfui_response_get_action_id(r
), "environment") == 0) {
346 state
= state_environment_menu
;
347 } else if (strcmp(dfui_response_get_action_id(r
), "utilities") == 0) {
348 state
= state_utilities_menu
;
349 } else if (strcmp(dfui_response_get_action_id(r
), "exit") == 0) {
351 } else if (strcmp(dfui_response_get_action_id(r
), "reboot") == 0) {
352 state
= state_reboot
;
356 dfui_response_free(r
);
360 state_configure_menu(struct i_fn_args
*a
)
362 struct dfui_form
*f
= NULL
;
363 struct dfui_response
*r
= NULL
;
364 struct commands
*cmds
;
366 char msg_buf
[2][1024];
368 if (storage_get_selected_disk(a
->s
) == NULL
|| storage_get_selected_slice(a
->s
) == NULL
) {
369 if (!survey_storage(a
)) {
370 inform(a
->c
, _("Errors occurred while probing "
371 "the system for its storage capabilities."));
374 a
->short_desc
= _("Select the disk containing the installation.");
375 a
->cancel_desc
= _("Return to Welcome Menu");
377 if (!a
->result
|| storage_get_selected_disk(a
->s
) == NULL
) {
378 state
= state_welcome
;
382 a
->short_desc
= _("Select the primary partition containing the installation.");
383 a
->cancel_desc
= _("Return to Welcome Menu");
386 if (!a
->result
|| storage_get_selected_slice(a
->s
) == NULL
) {
387 state
= state_welcome
;
394 if (during_install
== 0) {
395 switch (dfui_be_present_dialog(a
->c
, _("Select file system"),
396 _("HAMMER|UFS|Return to Welcome Menu"),
397 _("Please select the file system installed on the disk.\n\n")))
408 state
= state_welcome
;
418 if (!mount_target_system(a
)) {
419 inform(a
->c
, _("Target system could not be mounted."));
420 state
= state_welcome
;
424 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
425 _("The options on this menu allow you to configure a "
426 "%s system after it has already been "
427 "installed."), OPERATING_SYSTEM_NAME
);
430 f
= dfui_form_create(
432 _("Configure an Installed System"),
438 _("Select timezone"),
439 _("Set the Time Zone of your physical location"), "",
441 _("Set date and time"),
442 _("Set the Time and Date of your machine"), "",
444 "a", "root_passwd", _("Set root password"),
445 _("Set the password that the root (superuser) account will use"), "",
446 "a", "add_user", _("Add a user"),
447 _("Add a user to the system"), "",
449 "a", "cvsup_sources","Synchronize system sources", "", "",
451 "a", "assign_ip", _("Configure network interfaces"),
452 _("Set up network interfaces (NICs, ethernet, TCP/IP, etc)"), "",
453 "a", "assign_hostname_domain",
454 _("Configure hostname and domain"),
455 _("Configure the hostname and domain for this system"), "",
457 "a", "select_services", "Select Services",
458 "Enable/Disable system services (servers, daemons, etc.)", "",
461 _("Set keyboard map"),
462 _("Set what kind of keyboard layout you have"), "",
464 _("Set console font"),
465 _("Set how the characters on your video console look"), "",
468 _("Set how characters are translated before console display"), "",
470 "a", "install_pkgs", _("Install extra software packages"),
471 _("Install third-party software packages from the LiveCD"), "",
472 "a", "remove_pkgs", _("Remove software packages"),
473 _("Remove third-party software packages from the installed system"), "",
475 "a", "cancel", _("Return to Welcome Menu"), "", "",
476 "p", "accelerator", "ESC",
481 if (!dfui_be_present(a
->c
, f
, &r
))
485 a
->cfg_root
= "mnt/";
486 if (strcmp(dfui_response_get_action_id(r
), "root_passwd") == 0) {
488 } else if (strcmp(dfui_response_get_action_id(r
), "add_user") == 0) {
490 } else if (strcmp(dfui_response_get_action_id(r
), "cvsup_sources") == 0) {
492 } else if (strcmp(dfui_response_get_action_id(r
), "install_pkgs") == 0) {
493 fn_install_packages(a
);
494 } else if (strcmp(dfui_response_get_action_id(r
), "remove_pkgs") == 0) {
495 fn_remove_packages(a
);
496 } else if (strcmp(dfui_response_get_action_id(r
), "assign_ip") == 0) {
498 } else if (strcmp(dfui_response_get_action_id(r
), "assign_hostname_domain") == 0) {
499 fn_assign_hostname_domain(a
);
500 } else if (strcmp(dfui_response_get_action_id(r
), "select_services") == 0) {
501 fn_select_services(a
);
502 } else if (strcmp(dfui_response_get_action_id(r
), "set_kbdmap") == 0) {
504 } else if (strcmp(dfui_response_get_action_id(r
), "set_vidfont") == 0) {
506 } else if (strcmp(dfui_response_get_action_id(r
), "set_scrnmap") == 0) {
508 } else if (strcmp(dfui_response_get_action_id(r
), "set_timezone") == 0) {
510 } else if (strcmp(dfui_response_get_action_id(r
), "set_datetime") == 0) {
511 fn_assign_datetime(a
);
512 } else if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
513 state
= state_welcome
;
518 dfui_response_free(r
);
522 * Before unmounting the system, write out any changes to rc.conf.
524 config_vars_write(rc_conf
, CONFIG_TYPE_SH
,
525 "%s%setc/rc.conf", a
->os_root
, a
->cfg_root
);
528 * Clear out configuration variable table in memory.
530 config_vars_free(rc_conf
);
531 rc_conf
= config_vars_new();
534 * Finally, unmount the system we mounted on /mnt.
536 cmds
= commands_new();
537 unmount_all_under(a
, cmds
, "%smnt", a
->os_root
);
538 commands_execute(a
, cmds
);
543 state_utilities_menu(struct i_fn_args
*a
)
546 struct dfui_response
*r
;
548 if (!survey_storage(a
)) {
549 inform(a
->c
, _("Errors occurred while probing "
550 "the system for its storage capabilities."));
553 f
= dfui_form_create(
555 _("Live CD Utilities Menu"),
556 _("On these submenus you will find utilities to help "
557 "you set up your Live CD environment, diagnose "
558 "and analyse this system, and work with "
559 "the devices attached to this computer."),
562 "a", "environment", _("LiveCD Environment"),
563 _("Configure the LiveCD Environment"), "",
564 "a", "diagnostics", _("System Diagnostics"),
565 _("Probe and display detailed information about this system"), "",
566 "a", "diskutil", _("Disk Utilities"),
567 _("Format and check hard drives and floppy disks"), "",
568 "a", "livecd", _("Exit to Live CD"),
569 _("Exit this program to a login prompt with access to the LiveCD"), "",
571 _("Reboot this Computer"), "", "",
573 _("Return to Welcome Menu"), "", "",
574 "p", "accelerator", "ESC",
578 if (!dfui_be_present(a
->c
, f
, &r
))
581 if (strcmp(dfui_response_get_action_id(r
), "environment") == 0)
582 state
= state_environment_menu
;
583 else if (strcmp(dfui_response_get_action_id(r
), "diagnostics") == 0)
584 state
= state_diagnostics_menu
;
585 else if (strcmp(dfui_response_get_action_id(r
), "diskutil") == 0)
586 state
= state_diskutil_menu
;
587 else if (strcmp(dfui_response_get_action_id(r
), "livecd") == 0)
589 else if (strcmp(dfui_response_get_action_id(r
), "reboot") == 0)
590 state
= state_reboot
;
591 else if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0)
592 state
= state_welcome
;
595 dfui_response_free(r
);
599 state_environment_menu(struct i_fn_args
*a
)
602 struct dfui_response
*r
;
604 char msg_buf
[2][1024];
606 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
607 _("On this menu you will find utilities to help you "
608 "set up your Live CD environment.\n\nNote "
609 "that these functions affect only the LiveCD "
610 "environment you are currently using, and they will "
611 "not affect any system that may be installed on "
612 "this computer UNLESS you subsequently choose to "
613 "install %s from this environment, in which "
614 "case they will be copied to the newly installed "
615 "system."), OPERATING_SYSTEM_NAME
);
618 f
= dfui_form_create(
620 _("Live CD Environment Menu"),
626 _("Select timezone"),
627 _("Set the Time Zone of your physical location"), "",
629 _("Set date and time"),
630 _("Set the Time and Date of your machine"), "",
633 _("Set keyboard map"),
634 _("Set what kind of keyboard layout you have"), "",
636 _("Set console font"),
637 _("Set how the characters on your video console look"), "",
640 _("Set how characters are translated before console display"), "",
642 "a", "assign_hostname_domain",
643 _("Configure hostname and domain"),
644 _("Configure the hostname and domain for this system"), "",
646 _("Configure network interfaces"),
647 _("Set up network interfaces (NICs, ethernet, TCP/IP, etc)"), "",
650 _("Return to Utilities Menu"), "", "",
651 "p", "accelerator", "ESC",
656 if (!dfui_be_present(a
->c
, f
, &r
))
661 if (strcmp(dfui_response_get_action_id(r
), "set_kbdmap") == 0) {
663 } else if (strcmp(dfui_response_get_action_id(r
), "set_vidfont") == 0) {
665 } else if (strcmp(dfui_response_get_action_id(r
), "set_scrnmap") == 0) {
667 } else if (strcmp(dfui_response_get_action_id(r
), "assign_hostname_domain") == 0) {
668 fn_assign_hostname_domain(a
);
669 } else if (strcmp(dfui_response_get_action_id(r
), "assign_ip") == 0) {
671 } else if (strcmp(dfui_response_get_action_id(r
), "set_timezone") == 0) {
673 } else if (strcmp(dfui_response_get_action_id(r
), "set_datetime") == 0) {
674 fn_assign_datetime(a
);
675 } else if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
676 state
= state_utilities_menu
;
681 dfui_response_free(r
);
686 state_diagnostics_menu(struct i_fn_args
*a
)
689 struct dfui_action
*k
;
690 struct dfui_response
*r
;
694 f
= dfui_form_create(
696 _("Live CD Diagnostics Menu"),
697 _("These functions can help you diagnose this system."),
702 _("Display system startup messages"),
703 _("Display system startup messages (dmesg)"), "",
705 _("Display PCI devices"),
706 _("Display PCI devices (pciconf)"), "",
708 _("Display Plug'n'Play ISA devices"),
709 _("Display Plug'n'Play ISA devices (pnpinfo)"), "",
711 _("Display ATA devices"),
712 _("Display ATA devices (natacontrol)"), "",
716 if (is_file("%sboot/memtest86.flp.bz2", a
->os_root
)) {
717 dfui_form_action_add(f
, "memtest86",
718 dfui_info_new(_("Create memtest86 Floppy"),
719 _("Create a floppy which boots into a dedicated memory-test"),
723 if (is_program("%susr/local/bin/memtest", a
->os_root
)) {
724 dfui_form_action_add(f
, "memtest",
725 dfui_info_new(_("Run On-Line Memory Test"),
726 _("Test the memory in the machine while running"),
730 k
= dfui_form_action_add(f
, "cancel",
731 dfui_info_new(_("Return to Utilities Menu"), "", ""));
732 dfui_action_property_set(k
, "accelerator", "ESC");
734 if (!dfui_be_present(a
->c
, f
, &r
))
738 if (strcmp(dfui_response_get_action_id(r
), "show_dmesg") == 0) {
740 } else if (strcmp(dfui_response_get_action_id(r
), "pciconf") == 0) {
742 } else if (strcmp(dfui_response_get_action_id(r
), "pnpinfo") == 0) {
744 } else if (strcmp(dfui_response_get_action_id(r
), "natacontrol") == 0) {
745 fn_show_natacontrol(a
);
746 } else if (strcmp(dfui_response_get_action_id(r
), "memtest") == 0) {
748 } else if (strcmp(dfui_response_get_action_id(r
), "memtest86") == 0) {
749 fn_create_memtest86_floppy(a
);
750 } else if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
751 state
= state_utilities_menu
;
756 dfui_response_free(r
);
761 state_diskutil_menu(struct i_fn_args
*a
)
764 struct dfui_action
*k
;
765 struct dfui_response
*r
;
769 f
= dfui_form_create(
771 _("Disk Utilities Menu"),
772 _("These functions let you manipulate the storage devices "
773 "attached to this computer."),
779 _("Format a hard disk drive"), "", "",
780 "a", "wipe_start_of_disk",
781 _("Wipe out the start of a disk"), "", "",
782 "a", "wipe_start_of_slice",
783 _("Wipe out the start of a primary partition"), "", "",
784 "a", "install_bootblocks",
785 _("Install bootblocks on disks"), "", "",
786 "a", "format_msdos_floppy",
787 _("Format an MSDOS floppy"), "", "",
791 if (is_file("%sboot/cdboot.flp.bz2", a
->os_root
)) {
792 dfui_form_action_add(f
, "create_cdboot_floppy",
793 dfui_info_new(_("Create a CDBoot floppy"),
798 k
= dfui_form_action_add(f
, "cancel",
799 dfui_info_new(_("Return to Utilities Menu"), "", ""));
800 dfui_action_property_set(k
, "accelerator", "ESC");
802 if (!dfui_be_present(a
->c
, f
, &r
))
806 if (strcmp(dfui_response_get_action_id(r
), "format_hdd") == 0) {
807 storage_set_selected_disk(a
->s
, NULL
);
808 storage_set_selected_slice(a
->s
, NULL
);
810 } else if (strcmp(dfui_response_get_action_id(r
), "wipe_start_of_disk") == 0) {
811 fn_wipe_start_of_disk(a
);
812 } else if (strcmp(dfui_response_get_action_id(r
), "wipe_start_of_slice") == 0) {
813 fn_wipe_start_of_slice(a
);
814 } else if (strcmp(dfui_response_get_action_id(r
), "install_bootblocks") == 0) {
815 a
->short_desc
= _("Select the disks on which "
816 "you wish to install bootblocks.");
817 a
->cancel_desc
= _("Return to Utilities Menu");
818 fn_install_bootblocks(a
);
819 } else if (strcmp(dfui_response_get_action_id(r
), "format_msdos_floppy") == 0) {
820 fn_format_msdos_floppy(a
);
821 } else if (strcmp(dfui_response_get_action_id(r
), "create_cdboot_floppy") == 0) {
822 fn_create_cdboot_floppy(a
);
823 } else if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
824 state
= state_utilities_menu
;
829 dfui_response_free(r
);
833 /** INSTALLER STATES **/
836 * state_begin_upgrade: Ask the user where the freebsd
837 * 4.X install is and make sure its safe to proceed.
841 state_begin_upgrade(struct i_fn_args
*a
)
843 //struct dfui_form *f = NULL;
844 //struct dfui_response *r = NULL;
847 if (storage_get_selected_disk(a
->s
) == NULL
|| storage_get_selected_slice(a
->s
) == NULL
) {
848 if (!survey_storage(a
)) {
849 inform(a
->c
, _("Errors occurred while probing "
850 "the system for its storage capabilities."));
853 a
->short_desc
= _("Select the disk containing the installation that you would like to upgrade.");
854 a
->cancel_desc
= _("Return to Welcome Menu");
856 if (!a
->result
|| storage_get_selected_disk(a
->s
) == NULL
) {
857 state
= state_welcome
;
861 a
->short_desc
= _("Select the primary partition containing the installation you would like to upgrade.");
862 a
->cancel_desc
= _("Return to Welcome Menu");
865 if (!a
->result
|| storage_get_selected_slice(a
->s
) == NULL
) {
866 state
= state_welcome
;
872 if (!mount_target_system(a
)) {
873 inform(a
->c
, _("Target system could not be mounted."));
874 state
= state_welcome
;
880 * state_begin_install: Briefly describe the install process
881 * to the user, and let them proceed (or not.)
884 state_begin_install(struct i_fn_args
*a
)
887 struct dfui_response
*r
;
888 char msg_buf
[3][1024];
890 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
891 _("This experimental application will install %s"
892 " on one of the hard disk drives attached to this computer. "
893 "It has been designed to make it easy to install "
894 "%s in the typical case. "
895 "If you have special requirements that are not addressed "
896 "by this installer, or if you have problems using it, you "
897 "are welcome to install %s manually. "
898 "To do so select Exit to Live CD, login as root, and follow "
899 "the instructions given in the file /README ."
901 "NOTE! As with any installation process, YOU ARE "
902 "STRONGLY ENCOURAGED TO BACK UP ANY IMPORTANT DATA ON THIS "
903 "COMPUTER BEFORE PROCEEDING!"
905 OPERATING_SYSTEM_NAME
, OPERATING_SYSTEM_NAME
,
906 OPERATING_SYSTEM_NAME
);
908 snprintf(msg_buf
[1], sizeof(msg_buf
[1]),
909 _("Some situations in which you might not wish to use this "
911 "- you want to install %s onto a "
912 "logical/extended partition;\n"
913 "- you want to install %s "
914 "onto a ``dangerously dedicated'' disk; or\n"
915 "- you want full and utter control over the install process."
917 OPERATING_SYSTEM_NAME
, OPERATING_SYSTEM_NAME
);
919 snprintf(msg_buf
[2], sizeof(msg_buf
[2]),
920 _("Install %s"), OPERATING_SYSTEM_NAME
);
922 f
= dfui_form_create(
924 _("Begin Installation"),
928 "p", "special", "dfinstaller_begin_install",
929 "p", "minimum_width", "76",
931 "a", "proceed", msg_buf
[2],
933 "a", "cancel", _("Return to Welcome Menu"),
935 "p", "accelerator", "ESC",
936 "a", "livecd", _("Exit to Live CD"),
941 if (!dfui_be_present(a
->c
, f
, &r
))
944 if (strcmp(dfui_response_get_action_id(r
), "proceed") == 0) {
945 if (!survey_storage(a
)) {
946 inform(a
->c
, _("Errors occurred while probing "
947 "the system for its storage capabilities."));
949 state
= state_select_disk
;
950 } else if (strcmp(dfui_response_get_action_id(r
), "livecd") == 0) {
952 } else if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
953 state
= state_welcome
;
957 dfui_response_free(r
);
961 * state_select_disk: ask the user on which physical disk they wish
962 * to install DragonFly.
965 state_select_disk(struct i_fn_args
*a
)
969 char msg_buf
[1][1024];
971 for (d
= storage_disk_first(a
->s
); d
!= NULL
; d
= disk_next(d
))
974 if (num_disks
== 0) {
975 inform(a
->c
, _("The installer could not find any disks suitable "
976 "for installation (IDE or SCSI) attached to this "
977 "computer. If you wish to install %s"
978 " on an unorthodox storage device, you will have to "
979 "exit to a LiveCD command prompt and install it "
980 "manually, using the file /README as a guide."),
981 OPERATING_SYSTEM_NAME
);
982 state
= state_welcome
;
986 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
987 _("Select a disk on which to install %s"),
988 OPERATING_SYSTEM_NAME
);
989 a
->short_desc
= msg_buf
[0];
990 a
->cancel_desc
= _("Return to Begin Installation");
992 if (!a
->result
|| storage_get_selected_disk(a
->s
) == NULL
) {
993 state
= state_begin_install
;
996 if (disk_get_capacity(storage_get_selected_disk(a
->s
)) < DISK_MIN
) {
997 inform(a
->c
, _("WARNING: you should have a disk "
998 "at least %dM in size, or "
999 "you may encounter problems trying to "
1000 "install %s."), DISK_MIN
, OPERATING_SYSTEM_NAME
);
1003 state
= state_format_disk
;
1008 state_ask_fs(struct i_fn_args
*a
)
1012 switch (dfui_be_present_dialog(a
->c
, _("Select file system"),
1013 _("Use HAMMER|Use UFS|Return to Select Disk"),
1014 _("Please select the file system you want to use with %s.\n\n"
1015 "HAMMER is the new %s file system. UFS is the traditional BSD file system."),
1016 OPERATING_SYSTEM_NAME
,
1017 OPERATING_SYSTEM_NAME
))
1027 state
= state_select_disk
;
1035 state
= state_create_subpartitions
;
1039 * state_format_disk: ask the user if they wish to format the disk they
1043 state_format_disk(struct i_fn_args
*a
)
1046 switch (dfui_be_present_dialog(a
->c
, _("How Much Disk?"),
1047 _("Use Entire Disk|Use Part of Disk|Return to Select Disk"),
1048 _("Select how much of this disk you want to use for %s.\n\n%s"),
1049 OPERATING_SYSTEM_NAME
,
1050 disk_get_desc(storage_get_selected_disk(a
->s
)))) {
1053 if (measure_activated_swap_from_disk(a
, storage_get_selected_disk(a
->s
)) > 0) {
1054 switch(dfui_be_present_dialog(a
->c
,
1055 _("Swap already active"),
1056 _("Reboot|Return to Select Disk"),
1057 _("Some subpartitions on the primary partition "
1058 "of this disk are already activated as swap. "
1059 "Since there is no way to deactivate swap in "
1060 "%s once it is activated, in order "
1061 "to edit the subpartition layout of this "
1062 "primary partition, you must first reboot."),
1063 OPERATING_SYSTEM_NAME
)) {
1065 state
= state_reboot
;
1068 state
= state_select_disk
;
1077 state
= state_ask_fs
;
1079 state
= state_format_disk
;
1083 state
= state_select_slice
;
1087 state
= state_select_disk
;
1096 * state_select_slice: ask the user which slice they wish to install
1097 * DragonFly on. In order to avoid confusing them, refer to it as
1098 * a primary partition, but tell them what BSD has traditionally called
1102 state_select_slice(struct i_fn_args
*a
)
1104 char msg_buf
[1][1024];
1106 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
1107 _("Select the existing primary partition (also "
1108 "known as a `slice' in the BSD tradition) on "
1109 "which to install %s.\n\n"
1110 "Note that if you do not have any existing "
1111 "primary partitions on this disk, you must "
1112 "first create some. This installer does not "
1113 "currently have the ability to do this, so "
1114 "you will have to exit and run fdisk (in "
1115 "DOS or *BSD) or parted (in Linux) to do so."),
1116 OPERATING_SYSTEM_NAME
);
1118 a
->short_desc
= msg_buf
[0];
1119 a
->cancel_desc
= _("Return to Select Disk");
1121 if (!a
->result
|| storage_get_selected_slice(a
->s
) == NULL
) {
1122 state
= state_select_disk
;
1124 if (measure_activated_swap_from_slice(a
, storage_get_selected_disk(a
->s
),
1125 storage_get_selected_slice(a
->s
)) > 0) {
1126 switch(dfui_be_present_dialog(a
->c
,
1127 _("Swap already active"),
1128 _("Reboot|Return to Select Primary Partition"),
1129 _("Some subpartitions on the selected primary "
1130 "partition are already activated as swap. "
1131 "Since there is no way to deactivate swap in "
1132 "%s once it is activated, in order "
1133 "to edit the subpartition layout of this "
1134 "primary partition, you must first reboot."),
1135 OPERATING_SYSTEM_NAME
)) {
1137 state
= state_reboot
;
1140 state
= state_select_slice
;
1147 if (slice_get_capacity(storage_get_selected_slice(a
->s
)) < DISK_MIN
) {
1148 inform(a
->c
, _("WARNING: you should have a primary "
1149 "partition at least %dM in size, or "
1150 "you may encounter problems trying to "
1151 "install %s."), DISK_MIN
, OPERATING_SYSTEM_NAME
);
1154 if (confirm_dangerous_action(a
->c
,
1155 _("WARNING! ALL data in primary partition #%d,\n\n%s\n\non the "
1156 "disk\n\n%s\n\n will be IRREVOCABLY ERASED!\n\nAre you "
1157 "ABSOLUTELY SURE you wish to take this action? This is "
1158 "your LAST CHANCE to cancel!"),
1159 slice_get_number(storage_get_selected_slice(a
->s
)),
1160 slice_get_desc(storage_get_selected_slice(a
->s
)),
1161 disk_get_desc(storage_get_selected_disk(a
->s
)))) {
1162 if (!format_slice(a
)) {
1163 inform(a
->c
, _("Primary partition #%d was "
1164 "not correctly formatted, and may "
1165 "now be in an inconsistent state. "
1166 "We recommend re-formatting it "
1167 "before proceeding."),
1168 slice_get_number(storage_get_selected_slice(a
->s
)));
1170 inform(a
->c
, _("Primary partition #%d was formatted."),
1171 slice_get_number(storage_get_selected_slice(a
->s
)));
1172 state
= state_ask_fs
;
1175 inform(a
->c
, _("Action cancelled - no primary partitions were formatted."));
1176 state
= state_select_slice
;
1182 * state_create_subpartitions: let the user specify what subpartitions they
1183 * want on the disk, how large each should be, and where it should be mounted.
1186 state_create_subpartitions(struct i_fn_args
*a
)
1188 char msg_buf
[1][1024];
1190 if (measure_activated_swap_from_slice(a
, storage_get_selected_disk(a
->s
),
1191 storage_get_selected_slice(a
->s
)) > 0) {
1192 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
1193 _("Some subpartitions on the selected primary "
1194 "partition are already activated as swap. "
1195 "Since there is no way to deactivate swap in "
1196 "%s once it is activated, in order "
1197 "to edit the subpartition layout of this "
1198 "primary partition, you must first reboot."),
1199 OPERATING_SYSTEM_NAME
);
1200 switch(dfui_be_present_dialog(a
->c
, _("Swap already active"),
1201 disk_get_formatted(storage_get_selected_disk(a
->s
)) ?
1202 _("Reboot|Return to Select Disk") :
1203 _("Reboot|Return to Select Primary Partition"),
1206 state
= state_reboot
;
1209 state
= disk_get_formatted(storage_get_selected_disk(a
->s
)) ?
1210 state_select_disk
: state_select_slice
;
1217 fn_create_subpartitions(a
);
1219 state
= state_install_os
;
1221 state
= disk_get_formatted(storage_get_selected_disk(a
->s
)) ?
1222 state_select_disk
: state_select_slice
;
1227 * state_install_os: actually put DragonFly on the disk.
1230 state_install_os(struct i_fn_args
*a
)
1232 struct dfui_form
*f
;
1233 struct dfui_response
*r
;
1234 char msg_buf
[1][1024];
1236 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
1237 _("Everything is now ready to install the actual files which "
1238 "comprise the %s operating system "
1239 "on the selected partition of the selected disk.\n\n"
1240 "Note that this process will take quite a while to finish. "
1241 "You may wish to take a break now and come back to the "
1242 "computer in a short while."),
1243 OPERATING_SYSTEM_NAME
);
1245 f
= dfui_form_create(
1252 "p", "role", "confirm",
1253 "p", "special", "dfinstaller_install_os",
1255 "a", "ok", _("Begin Installing Files"), "", "",
1256 "a", "cancel", _("Return to Create Subpartitions"), "", "",
1257 "p", "accelerator", "ESC",
1262 if (!dfui_be_present(a
->c
, f
, &r
))
1265 if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
1266 state
= state_create_subpartitions
;
1270 state
= state_install_bootstrap
;
1274 dfui_response_free(r
);
1278 * state_install_bootstrap: put boot0 bootblocks on selected disks.
1281 state_install_bootstrap(struct i_fn_args
*a
)
1283 char msg_buf
[1][1024];
1285 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
1286 _("You may now wish to install bootblocks on one or more disks. "
1287 "If you already have a boot manager installed, you can skip "
1288 "this step (but you may have to configure your boot manager "
1289 "separately.) If you installed %s on a disk other "
1290 "than your first disk, you will need to put the bootblock "
1291 "on at least your first disk and the %s disk."),
1292 OPERATING_SYSTEM_NAME
, OPERATING_SYSTEM_NAME
);
1294 a
->short_desc
= msg_buf
[0];
1295 a
->cancel_desc
= _("Skip this Step");
1296 fn_install_bootblocks(a
);
1297 state
= state_finish_install
;
1301 * Finish up the install.
1304 state_finish_install(struct i_fn_args
*a
)
1306 char msg_buf
[1][1024];
1309 snprintf(msg_buf
[0], sizeof(msg_buf
[0]),
1311 OPERATING_SYSTEM_NAME
);
1313 switch (dfui_be_present_dialog(a
->c
, msg_buf
[0],
1314 _("Configure this System|Reboot|Return to Welcome Menu"),
1315 _("Congratulations!\n\n"
1316 "%s has successfully been installed on "
1317 "this computer. You may now proceed to configure "
1318 "the installation. Alternately, you may wish to "
1319 "reboot the computer and boot into the installed "
1320 "system to confirm that it works."),
1321 OPERATING_SYSTEM_NAME
)) {
1323 state
= state_configure_menu
;
1326 state
= state_reboot
;
1329 state
= state_welcome
;
1337 * state_reboot: reboot the machine.
1340 state_reboot(struct i_fn_args
*a
)
1342 struct dfui_form
*f
;
1343 struct dfui_response
*r
;
1345 f
= dfui_form_create(
1348 _("This machine is about to be shut down. "
1349 "After the machine has reached its shutdown state, "
1350 "you may remove the CD from the CD-ROM drive tray "
1351 "and press Enter to reboot from the HDD."),
1355 "p", "role", "confirm",
1357 "a", "ok", _("Reboot"), "", "",
1358 "a", "cancel", _("Return to Welcome Menu"), "", "",
1359 "p", "accelerator", "ESC",
1363 if (!dfui_be_present(a
->c
, f
, &r
))
1366 if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
1367 state
= state_welcome
;
1374 dfui_response_free(r
);
1379 * state_setup_remote_installation_server:
1380 * Setup a remote boot installation environment where a machine
1381 * can boot via DHCP/TFTP/NFS and have a running environment
1382 * where the installer can setup the machine.
1386 state_setup_remote_installation_server(struct i_fn_args
*a
)
1389 struct commands
*cmds
;
1390 struct dfui_form
*f
;
1391 struct dfui_action
*k
;
1392 struct dfui_response
*r
;
1394 char interface
[256];
1397 switch (dfui_be_present_dialog(a
->c
, _("Enable Netboot Installation Services?"),
1398 _("Enable NetBoot Installation Services|No thanks"),
1399 _("NetBoot Installation Services allows this machine to become "
1400 "a Installation Server that will allow the clients to boot over the network "
1401 "via PXE and start the Installation Environment."
1402 "\n\n*NOTE!* This will assign the IP Address of 10.1.0.1/24 to the selected interface."
1403 "\n\nWould you like to provision this machine to serve up the LiveCD/Installer?"))) {
1406 * Get interface list.
1408 p
= popen("/sbin/ifconfig -l", "r");
1409 /* XXX it's possible (though extremely unlikely) this will fail. */
1410 while (fgets(line
, 255, p
) != NULL
)
1411 line
[strlen(line
) - 1] = '\0';
1414 f
= dfui_form_create(
1416 _("Setup NetBoot Installation Environment"),
1417 _("Please select which interface you would like to configure:"),
1419 "p", "role", "menu",
1423 /* Loop through array. */
1424 word
= strtok(line
, " \t");
1425 while (word
!= NULL
) {
1426 dfui_form_action_add(f
, word
,
1427 dfui_info_new(word
, "", ""));
1428 word
= strtok(NULL
, " ");
1431 k
= dfui_form_action_add(f
, "cancel",
1432 dfui_info_new("Cancel", "", ""));
1433 dfui_action_property_set(k
, "accelerator", "ESC");
1435 if (!dfui_be_present(a
->c
, f
, &r
))
1438 strlcpy(interface
, dfui_response_get_action_id(r
), 256);
1440 if (strcmp(dfui_response_get_action_id(r
), "cancel") == 0) {
1442 dfui_response_free(r
);
1448 * Issues the necessary commands to setup the remote boot environment
1451 cmds
= commands_new();
1452 command_add(cmds
, "%s%s %s 10.1.0.1 netmask 255.255.255.0",
1453 a
->os_root
, cmd_name(a
, "IFCONFIG"), interface
);
1454 command_add(cmds
, "%s%s -p %stftpdroot",
1455 a
->os_root
, cmd_name(a
, "MKDIR"), a
->tmp
);
1456 command_add(cmds
, "%s%s %sboot/pxeboot %stftpdroot",
1457 a
->os_root
, cmd_name(a
, "CP"), a
->os_root
, a
->tmp
);
1458 command_add(cmds
, "%s%s %s -ro -alldirs -maproot=root: -network 10.1.0.0 -mask 255.255.255.0 >> %setc/exports",
1459 a
->os_root
, cmd_name(a
, "ECHO"), a
->os_root
, a
->os_root
);
1460 command_add(cmds
, "%s%s tftp dgram udp wait root %s%s tftpd -l -s %stftpdroot >> %setc/inetd.conf",
1461 a
->os_root
, cmd_name(a
, "ECHO"),
1462 a
->os_root
, cmd_name(a
, "TFTPD"),
1463 a
->tmp
, a
->os_root
);
1464 command_add(cmds
, "%s%s",
1465 a
->os_root
, cmd_name(a
, "INETD"));
1466 command_add(cmds
, "%s%s %svar/db/dhcpd.leases",
1467 a
->os_root
, cmd_name(a
, "TOUCH"), a
->os_root
);
1468 command_add(cmds
, "%s%s -cf /etc/dhcpd.conf >%sdev/null 2>&1",
1469 a
->os_root
, cmd_name(a
, "DHCPD"), a
->os_root
);
1470 command_add(cmds
, "%s%s >%sdev/null 2>&1",
1471 a
->os_root
, cmd_name(a
, "RPCBIND"), a
->os_root
);
1472 command_add(cmds
, "%s%s -ln >%sdev/null 2>&1",
1473 a
->os_root
, cmd_name(a
, "MOUNTD"), a
->os_root
);
1474 command_add(cmds
, "%s%s -u -t -n 6 >%sdev/null 2>&1",
1475 a
->os_root
, cmd_name(a
, "NFSD"), a
->os_root
);
1477 if (commands_execute(a
, cmds
)) {
1478 inform(a
->c
, _("NetBoot installation services are now started."));
1480 inform(a
->c
, _("A failure occurred while provisioning the NetBoot environment. Please check the logs."));
1483 commands_free(cmds
);
1485 dfui_response_free(r
);
1494 state
= state_welcome
;
1501 flow(int transport
, char *rendezvous
, char *os_root
,
1502 int booted_from_livecd __unused
, int upgrade_menu_toggle __unused
)
1504 struct i_fn_args
*a
;
1506 rc_conf
= config_vars_new();
1508 if ((a
= i_fn_args_new(os_root
, DEFAULT_INSTALLER_TEMP
,
1509 transport
, rendezvous
)) == NULL
) {
1514 * XXX We can't handle this yet.
1516 a->booted_from_livecd = booted_from_livecd;
1517 a->upgrade_menu_toggle = upgrade_menu_toggle;
1519 a
->booted_from_livecd
= 1;
1520 a
->upgrade_menu_toggle
= 0;
1523 * Execute the state machine here. The global function pointer
1524 * variable `state' points to the next state_* function to execute.
1525 * Before it exits, this function should set `state' to the next
1526 * state to make a transition to, or NULL to indicate that the
1527 * state machine is finished.
1530 state
= state_lang_menu
;
1532 state
= state_welcome
;
1534 for (; state
!= NULL
; )
1537 config_vars_free(rc_conf
);