2 -- Copyright (c) 2015 Pedro Souza <pedrosouza@freebsd.org>
3 -- All rights reserved.
5 -- Redistribution and use in source and binary forms, with or without
6 -- modification, are permitted provided that the following conditions
8 -- 1. Redistributions of source code must retain the above copyright
9 -- notice, this list of conditions and the following disclaimer.
10 -- 2. Redistributions in binary form must reproduce the above copyright
11 -- notice, this list of conditions and the following disclaimer in the
12 -- documentation and/or other materials provided with the distribution.
14 -- THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15 -- ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 -- IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 -- ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18 -- FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19 -- DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20 -- OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21 -- HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22 -- LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23 -- OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32 local core = require("core");
33 local color = require("color");
34 local config = require("config");
35 local screen = require("screen");
36 local drawer = require("drawer");
42 local carousel_choices = {};
45 --rooted at menu.welcome
46 --submenu declarations:
51 -- return to welcome menu
53 entry_type = core.MENU_RETURN,
55 return "Back to main menu"..color.highlight(" [Backspace]");
61 entry_type = core.MENU_ENTRY,
63 return "Load System "..color.highlight("D").."efaults";
72 entry_type = core.MENU_SEPARATOR,
79 entry_type = core.MENU_SEPARATOR,
81 return "Boot Options:";
87 entry_type = core.MENU_ENTRY,
89 return OnOff(color.highlight("A").."CPI :", core.acpi);
98 entry_type = core.MENU_ENTRY,
100 return OnOff("Safe "..color.highlight("M").."ode :", core.sm);
109 entry_type = core.MENU_ENTRY,
111 return OnOff(color.highlight("S").."ingle user:", core.su);
114 core.setSingleUser();
120 entry_type = core.MENU_ENTRY,
122 return OnOff(color.highlight("V").."erbose :", core.verbose);
134 entry_type = core.MENU_ENTRY,
136 return color.highlight("B").."oot Multi user "..color.highlight("[Enter]");
139 core.setSingleUser(false);
147 entry_type = core.MENU_ENTRY,
149 return "Boot "..color.highlight("S").."ingle user";
152 core.setSingleUser(true);
158 -- escape to interpreter
160 entry_type = core.MENU_RETURN,
162 return color.highlight("Esc").."ape to loader prompt";
165 loader.setenv("autoboot_delay", "NO")
167 alias = {core.KEYSTR_ESCAPE}
172 entry_type = core.MENU_ENTRY,
174 return color.highlight("R").."eboot";
177 loader.perform("reboot");
184 entry_type = core.MENU_SEPARATOR,
191 entry_type = core.MENU_SEPARATOR,
199 entry_type = core.MENU_CAROUSEL_ENTRY,
200 carousel_id = "kernel",
201 items = core.kernelList,
202 name = function(idx, choice, all_choices)
203 if #all_choices == 0 then
207 local kernel_name = color.escapef(color.GREEN) ..
208 choice .. color.default();
210 kernel_name = "default/" .. kernel_name;
212 return color.highlight("K").."ernel: " .. kernel_name ..
214 " of " .. #all_choices .. ")";
216 func = function(idx, choice, all_choices)
217 if (#all_choices > 1) then
218 config.reload(choice);
226 entry_type = core.MENU_SUBMENU,
228 return "Boot "..color.highlight("O").."ptions";
231 return menu.boot_options;
238 -- The first item in every carousel is always the default item.
239 function menu.getCarouselIndex(id)
240 local val = carousel_choices[id];
247 function menu.setCarouselIndex(id, idx)
248 carousel_choices[id] = idx;
253 if (menu.skip()) then
265 local alias_table = drawer.drawscreen(m);
271 local key = io.getchar();
273 -- Special key behaviors
274 if ((key == core.KEY_BACKSPACE) or (key == core.KEY_DELETE)) and
275 (m ~= menu.welcome) then
277 elseif (key == core.KEY_ENTER) then
282 key = string.char(key)
283 -- check to see if key is an alias
284 local sel_entry = nil;
285 for k, v in pairs(alias_table) do
291 -- if we have an alias do the assigned action:
292 if(sel_entry ~= nil) then
293 if (sel_entry.entry_type == core.MENU_ENTRY) then
296 elseif (sel_entry.entry_type == core.MENU_CAROUSEL_ENTRY) then
297 -- carousel (rotating) functionality
298 local carid = sel_entry.carousel_id;
299 local caridx = menu.getCarouselIndex(carid);
300 local choices = sel_entry.items();
302 if (#choices > 0) then
303 caridx = (caridx % #choices) + 1;
304 menu.setCarouselIndex(carid, caridx);
305 sel_entry.func(caridx, choices[caridx],
308 elseif (sel_entry.entry_type == core.MENU_SUBMENU) then
310 cont = menu.run(sel_entry.submenu());
311 elseif (sel_entry.entry_type == core.MENU_RETURN) then
312 -- allow entry to have a function/side effect
313 if (sel_entry.func ~= nil) then
319 -- if we got an alias key the screen is out of date:
322 alias_table = drawer.drawscreen(m);
326 if (m == menu.welcome) then
328 print("Exiting menu!");
336 if core.bootserial() then
339 local c = string.lower(loader.getenv("console") or "");
340 if (c:match("^efi[ ;]") or c:match("[ ;]efi[ ;]")) ~= nil then
344 c = string.lower(loader.getenv("beastie_disable") or "");
345 print("beastie_disable", c);
349 function menu.autoboot()
350 if menu.already_autoboot == true then
353 menu.already_autoboot = true;
355 local ab = loader.getenv("autoboot_delay");
356 if ab == "NO" or ab == "no" then
359 ab = tonumber(ab) or 10;
361 local x = loader.getenv("loader_menu_timeout_x") or 5;
362 local y = loader.getenv("loader_menu_timeout_y") or 22;
364 local endtime = loader.time() + ab;
368 time = endtime - loader.time();
369 screen.setcursor(x, y);
370 print("Autoboot in "..time.." seconds, hit [Enter] to boot"
371 .." or any other key to stop ");
374 local ch = io.getchar();
375 if ch == core.KEY_ENTER then
378 -- prevent autoboot when escaping to interpreter
379 loader.setenv("autoboot_delay", "NO");
380 -- erase autoboot msg
381 screen.setcursor(0, y);
395 function OnOff(str, b)
397 return str .. color.escapef(color.GREEN).."On"..color.escapef(color.WHITE);
399 return str .. color.escapef(color.RED).."off"..color.escapef(color.WHITE);