Chameleon

Chameleon Svn Source Tree

Root/branches/meklort/i386/modules/GUI/GUI_module.c

Source at commit 557 created 13 years 6 months ago.
By meklort, Disabled HelloWorld in makefile. Added some wifi specific code to the netwokr module.
1/*
2 * Copyright (c) 2009 Evan Lojewski. All rights reserved.
3 *
4 */
5
6#include "libsaio.h"
7#include "options.h"
8#include "graphic_utils.h"
9#include "ramdisk.h"
10#include "embedded.h"
11
12#include "picopng.h"
13#include "gui.h"
14
15#include "modules.h"
16
17/* Kabyl: BooterLog */
18#define BOOTER_LOG_SIZE(64 * 1024)
19#define SAFE_LOG_SIZE80
20
21
22bool useGUI;
23
24void GUI_Kernel_Start_hook(void* kernelEntry, void* arg2, void* arg3, void* arg4);
25void GUI_PreBoot_hook(void* arg1, void* arg2, void* arg3, void* arg4);
26
27int GUI_getBootOptions(bool firstRun);
28
29static void GUI_updateBootArgs( int key );
30void GUI_clearBootArgs(void);
31static void GUI_showBootPrompt(int row, bool visible);
32static void GUI_showMenu( const MenuItem * items, int count, int selection, int row, int height );
33static int GUI_updateMenu( int key, void ** paramPtr );
34static void GUI_showHelp(void);
35
36int GUI_printf(const char * fmt, ...);
37int GUI_verbose(const char * fmt, ...);
38int GUI_error(const char * fmt, ...);
39void GUI_stop(const char * fmt, ...);
40
41
42/* console.c */
43struct putc_info {
44 char * str;
45 char * last_str;
46};
47void sputc(int c, struct putc_info * pi);
48extern char *msgbuf;
49extern char *cursor;
50
51
52
53
54char GUI_bootRescanPrompt[] =
55"Press Enter to start up Darwin/x86 with no options, or you can:\n"
56" Press F5 after you swapped the media. The drive will be rescanned.\n"
57" Type -v and press Enter to start up with diagnostic messages\n"
58" Type ? and press Enter to learn about advanced startup options\n\n"
59"boot: ";
60
61
62
63/**
64 ** The kernel is about to start, draw the boot graphics if we are not in
65 ** verbose mode.
66 **/
67void GUI_ExecKernel_hook(void* kernelEntry, void* arg2, void* arg3, void* arg4)
68{
69if(!gVerboseMode)
70{
71drawBootGraphics();
72}
73else
74{
75setVideoMode( GRAPHICS_MODE, 0 );
76
77}
78}
79
80/**
81 ** A boot option has been selected, disable the graphical elements on screen.
82 **/
83void GUI_PreBoot_hook(void* arg1, void* arg2, void* arg3, void* arg4)
84{
85// Turn off any GUI elements
86if( bootArgs->Video.v_display == GRAPHICS_MODE )
87{
88gui.devicelist.draw = false;
89gui.bootprompt.draw = false;
90gui.menu.draw = false;
91gui.infobox.draw = false;
92gui.logo.draw = false;
93drawBackground();
94updateVRAM();
95}
96}
97
98/**
99 ** Module startup code. Replace console only print functions as well as
100 ** replace various menu functions. Finaly, initialize the gui and hook
101 ** into important events.
102 **/
103void GUI_start()
104{
105
106// Start the gui
107
108useGUI = true;
109// Override useGUI default
110getBoolForKey(kGUIKey, &useGUI, &bootInfo->bootConfig);
111if (useGUI && initGUI())
112{
113// initGUI() returned with an error, disabling GUI.
114useGUI = false;
115}
116else
117{
118replace_function("_initGraphicsMode", &GUI_initGraphicsMode);
119replace_function("_getBootOptions", &GUI_getBootOptions);
120replace_function("_clearBootArgs", &GUI_clearBootArgs);
121replace_function("_showHelp", &GUI_showHelp);
122
123replace_function("_printf", &GUI_printf);
124replace_function("_verbose", &GUI_verbose);
125replace_function("_error", &GUI_error);
126replace_function("_stop", &GUI_stop);
127}
128
129// Hoot for the boot screen
130//ExecKernel register_hook_callback("Kernel Start", &GUI_Kernel_Start_hook);
131register_hook_callback("ExecKernel", &GUI_ExecKernel_hook);
132register_hook_callback("PreBoot", &GUI_PreBoot_hook);
133
134}
135
136/**
137 ** Overriden chameleon function. Draws the updated menu.
138 **/
139static int GUI_updateMenu( int key, void ** paramPtr )
140{
141 int moved = 0;
142
143 union {
144 struct {
145 unsigned int
146selectionUp : 1,
147selectionDown : 1,
148scrollUp : 1,
149scrollDown : 1;
150 } f;
151 unsigned int w;
152 } draw = {{0}};
153
154 if ( gMenuItems == NULL )
155return 0;
156
157if( bootArgs->Video.v_display == GRAPHICS_MODE )
158{
159int res;
160
161// set navigation keys for horizontal layout as defaults
162int previous= 0x4B00;// left arrow
163int subsequent= 0x4D00;// right arrow
164int menu= 0x5000;// down arrow
165
166if ( gui.layout == VerticalLayout )
167{
168// set navigation keys for vertical layout
169previous= 0x4800;// up arrow
170subsequent= 0x5000;// down arrow
171menu= 0x4B00;// right arrow
172}
173
174if ( key == previous )
175{
176if ( gMenuSelection > gMenuTop )
177draw.f.selectionUp = 1;
178else if ( gMenuTop > 0 )
179draw.f.scrollDown = 1;
180
181}
182
183else if ( key == subsequent )
184{
185if ( gMenuSelection != gMenuBottom)
186draw.f.selectionDown = 1;
187else if ( gMenuBottom < ( gMenuItemCount - 1 ) )
188draw.f.scrollUp = 1;
189}
190
191else if ( key == menu )
192{
193if ( gui.menu.draw )
194updateInfoMenu(key);
195else
196drawInfoMenu();
197}
198
199else if ( gui.menu.draw )
200{
201res = updateInfoMenu(key);
202
203if ( res == CLOSE_INFO_MENU )
204gui.menu.draw = false;
205else
206{
207shouldboot = ( res != DO_NOT_BOOT );
208
209if ( shouldboot )
210gui.menu.draw = false;
211
212switch (res)
213{
214case BOOT_NORMAL:
215gVerboseMode = false;
216gBootMode = kBootModeNormal;
217break;
218
219case BOOT_VERBOSE:
220gVerboseMode = true;
221gBootMode = kBootModeNormal;
222addBootArg(kVerboseModeFlag);
223break;
224
225case BOOT_IGNORECACHE:
226gVerboseMode = false;
227gBootMode = kBootModeNormal;
228addBootArg(kIgnoreCachesFlag);
229break;
230
231case BOOT_SINGLEUSER:
232gVerboseMode = true;
233gBootMode = kBootModeNormal;
234addBootArg(kSingleUserModeFlag);
235break;
236}
237
238}
239
240}
241
242} else {
243switch ( key )
244{
245 case 0x4800: // Up Arrow
246if ( gMenuSelection != gMenuTop )
247{
248draw.f.selectionUp = 1;
249}
250else if ( gMenuTop > 0 )
251{
252draw.f.scrollDown = 1;
253}
254break;
255
256case 0x5000: // Down Arrow
257if ( gMenuSelection != gMenuBottom )
258{
259draw.f.selectionDown = 1;
260}
261else if ( gMenuBottom < (gMenuItemCount - 1) )
262{
263draw.f.scrollUp = 1;
264}
265break;
266}
267}
268
269 if ( draw.w )
270 {
271 if ( draw.f.scrollUp )
272 {
273 scollPage(0, gMenuRow, 40, gMenuRow + gMenuHeight - 1, 0x07, 1, 1);
274 gMenuTop++; gMenuBottom++;
275gMenuStart++; gMenuEnd++;
276 draw.f.selectionDown = 1;
277 }
278
279 if ( draw.f.scrollDown )
280 {
281 scollPage(0, gMenuRow, 40, gMenuRow + gMenuHeight - 1, 0x07, 1, -1);
282 gMenuTop--; gMenuBottom--;
283 gMenuStart--; gMenuEnd--;
284 draw.f.selectionUp = 1;
285 }
286
287 if ( draw.f.selectionUp || draw.f.selectionDown )
288 {
289
290CursorState cursorState;
291
292// Set cursor at current position, and clear inverse video.
293
294if( bootArgs->Video.v_display == VGA_TEXT_MODE )
295{
296changeCursor( 0, (gMenuRow + gMenuSelection - gMenuTop), kCursorTypeHidden, &cursorState );
297printMenuItem( &gMenuItems[gMenuSelection], 0 );
298}
299
300if ( draw.f.selectionUp )
301{
302gMenuSelection--;
303if(( gMenuSelection - gMenuStart) == -1 )
304{
305gMenuStart--;
306gMenuEnd--;
307}
308
309} else {
310gMenuSelection++;
311if(( gMenuSelection - ( gui.maxdevices - 1) - gMenuStart) > 0 )
312{
313gMenuStart++;
314gMenuEnd++;
315}
316}
317
318if( bootArgs->Video.v_display == VGA_TEXT_MODE )
319{
320moveCursor( 0, gMenuRow + gMenuSelection - gMenuTop );
321printMenuItem( &gMenuItems[gMenuSelection], 1 );
322restoreCursor( &cursorState );
323
324}
325else
326{
327drawDeviceList (gMenuStart, gMenuEnd, gMenuSelection);
328}
329
330}
331
332 *paramPtr = gMenuItems[gMenuSelection].param;
333 moved = 1;
334 }
335
336return moved;
337}
338
339
340static void GUI_showMenu( const MenuItem * items, int count,
341 int selection, int row, int height )
342{
343 int i;
344 CursorState cursorState;
345
346 if ( items == NULL || count == 0 )
347return;
348
349 // head and tail points to the start and the end of the list.
350 // top and bottom points to the first and last visible items
351 // in the menu window.
352
353 gMenuItems= items;
354 gMenuRow= row;
355 gMenuHeight= height;
356 gMenuItemCount= count;
357 gMenuTop= 0;
358 gMenuBottom= min( count, height ) - 1;
359 gMenuSelection= selection;
360
361 gMenuStart= 0;
362 gMenuEnd = min( count, gui.maxdevices ) - 1;
363
364// If the selected item is not visible, shift the list down.
365
366 if ( gMenuSelection > gMenuBottom )
367 {
368 gMenuTop += ( gMenuSelection - gMenuBottom );
369 gMenuBottom = gMenuSelection;
370 }
371
372if ( gMenuSelection > gMenuEnd )
373 {
374gMenuStart += ( gMenuSelection - gMenuEnd );
375 gMenuEnd = gMenuSelection;
376 }
377
378// Draw the visible items.
379
380if( bootArgs->Video.v_display == GRAPHICS_MODE )
381{
382drawDeviceList(gMenuStart, gMenuEnd, gMenuSelection);
383}
384else
385{
386
387changeCursor( 0, row, kCursorTypeHidden, &cursorState );
388
389for ( i = gMenuTop; i <= gMenuBottom; i++ )
390{
391printMenuItem( &items[i], (i == gMenuSelection) );
392}
393
394restoreCursor( &cursorState );
395 }
396}
397
398
399static void GUI_updateBootArgs( int key )
400{
401 key &= kASCIIKeyMask;
402
403 switch ( key )
404 {
405 case kBackspaceKey:
406 if ( gBootArgsPtr > gBootArgs )
407 {
408 int x, y, t;
409 getCursorPositionAndType( &x, &y, &t );
410 if ( x == 0 && y )
411 {
412 x = 80; y--;
413 }
414 if (x)
415x--;
416if( bootArgs->Video.v_display == VGA_TEXT_MODE )
417{
418setCursorPosition( x, y, 0 );
419putca(' ', 0x07, 1);
420} else
421{
422updateGraphicBootPrompt(kBackspaceKey);
423}
424
425*gBootArgsPtr-- = '\0';
426}
427
428break;
429
430 default:
431 if ( key >= ' ' && gBootArgsPtr < gBootArgsEnd)
432 {
433if( bootArgs->Video.v_display == VGA_TEXT_MODE )
434{
435putchar(key); // echo to screen
436}
437else
438{
439updateGraphicBootPrompt(key);
440}
441*gBootArgsPtr++ = key;
442}
443
444break;
445 }
446}
447
448
449static void GUI_showBootPrompt(int row, bool visible)
450{
451extern char bootPrompt[];
452
453if( bootArgs->Video.v_display == VGA_TEXT_MODE )
454{
455changeCursor( 0, row, kCursorTypeUnderline, 0 );
456clearScreenRows( row, kScreenLastRow );
457}
458
459clearBootArgs();
460
461if (visible)
462{
463if (bootArgs->Video.v_display == VGA_TEXT_MODE)
464{
465if (gEnableCDROMRescan)
466{
467printf( GUI_bootRescanPrompt );
468}
469else
470{
471printf( bootPrompt );
472}
473}
474}
475else
476{
477if (bootArgs->Video.v_display == GRAPHICS_MODE)
478{
479clearGraphicBootPrompt();
480}
481else
482{
483printf("Press Enter to start up the foreign OS. ");
484}
485}
486}
487
488
489void GUI_clearBootArgs(void)
490{
491gBootArgsPtr = gBootArgs;
492memset(gBootArgs, '\0', BOOT_STRING_LEN);
493
494if (bootArgs->Video.v_display == GRAPHICS_MODE)
495{
496clearGraphicBootPrompt();
497}
498}
499
500
501int GUI_getBootOptions(bool firstRun)
502{
503int i;
504int key;
505int nextRow;
506int timeout;
507int bvCount;
508BVRef bvr;
509BVRef menuBVR;
510bool showPrompt, newShowPrompt, isCDROM;
511
512// Initialize default menu selection entry.
513gBootVolume = menuBVR = selectBootVolume(bvChain);
514
515if (biosDevIsCDROM(gBIOSDev))
516{
517isCDROM = true;
518}
519else
520{
521isCDROM = false;
522}
523
524// ensure we're in graphics mode if gui is setup
525if (gui.initialised && bootArgs->Video.v_display == VGA_TEXT_MODE)
526{
527setVideoMode(GRAPHICS_MODE, 0);
528}
529
530// Clear command line boot arguments
531clearBootArgs();
532
533// Allow user to override default timeout.
534if (!getIntForKey(kTimeoutKey, &timeout, &bootInfo->bootConfig))
535{
536/* If there is no timeout key in the file use the default timeout
537 which is different for CDs vs. hard disks. However, if not booting
538 a CD and no config file could be loaded set the timeout
539 to zero which causes the menu to display immediately.
540 This way, if no partitions can be found, that is the disk is unpartitioned
541 or simply cannot be read) then an empty menu is displayed.
542 If some partitions are found, for example a Windows partition, then
543 these will be displayed in the menu as foreign partitions.
544 */
545if (isCDROM)
546{
547timeout = kCDBootTimeout;
548}
549else
550{
551timeout = sysConfigValid ? kBootTimeout : 0;
552}
553}
554
555if (timeout < 0)
556{
557gBootMode |= kBootModeQuiet;
558}
559
560// If the user is holding down a modifier key, enter safe mode.
561if ((readKeyboardShiftFlags() & 0x0F) != 0)
562{
563
564//gBootMode |= kBootModeSafe;
565}
566
567// Checking user pressed keys
568bool f8press = false, spress = false, vpress = false;
569while (readKeyboardStatus())
570{
571key = bgetc ();
572if (key == 0x4200) f8press = true;
573if ((key & 0xff) == 's' || (key & 0xff) == 'S') spress = true;
574if ((key & 0xff) == 'v' || (key & 0xff) == 'V') vpress = true;
575}
576// If user typed F8, abort quiet mode, and display the menu.
577if (f8press)
578{
579gBootMode &= ~kBootModeQuiet;
580timeout = 0;
581}
582// If user typed 'v' or 'V', boot in verbose mode.
583if ((gBootMode & kBootModeQuiet) && firstRun && vpress)
584{
585addBootArg(kVerboseModeFlag);
586}
587// If user typed 's' or 'S', boot in single user mode.
588if ((gBootMode & kBootModeQuiet) && firstRun && spress)
589{
590addBootArg(kSingleUserModeFlag);
591}
592
593if (bootArgs->Video.v_display == VGA_TEXT_MODE)
594{
595setCursorPosition(0, 0, 0);
596clearScreenRows(0, kScreenLastRow);
597if (!(gBootMode & kBootModeQuiet))
598{
599// Display banner and show hardware info.
600printf(bootBanner, (bootInfo->convmem + bootInfo->extmem) / 1024);
601printf(getVBEInfoString());
602}
603changeCursor(0, kMenuTopRow, kCursorTypeUnderline, 0);
604verbose("Scanning device %x...", gBIOSDev);
605}
606
607// When booting from CD, default to hard drive boot when possible.
608if (isCDROM && firstRun)
609{
610const char *val;
611char *prompt = NULL;
612char *name = NULL;
613int cnt;
614int optionKey;
615
616if (getValueForKey(kCDROMPromptKey, &val, &cnt, &bootInfo->bootConfig))
617{
618prompt = malloc(cnt + 1);
619strncat(prompt, val, cnt);
620}
621else
622{
623name = malloc(80);
624getBootVolumeDescription(gBootVolume, name, 79, false);
625prompt = malloc(256);
626sprintf(prompt, "Press any key to start up from %s, or press F8 to enter startup options.", name);
627free(name);
628}
629
630if (getIntForKey( kCDROMOptionKey, &optionKey, &bootInfo->bootConfig ))
631{
632// The key specified is a special key.
633}
634else
635{
636// Default to F8.
637optionKey = 0x4200;
638}
639
640// If the timeout is zero then it must have been set above due to the
641// early catch of F8 which means the user wants to set boot options
642// which we ought to interpret as meaning he wants to boot the CD.
643if (timeout != 0) {
644key = GUI_countdown(prompt, kMenuTopRow, timeout);
645}
646else
647{
648key = optionKey;
649}
650
651if (prompt != NULL)
652{
653free(prompt);
654}
655
656clearScreenRows( kMenuTopRow, kMenuTopRow + 2 );
657
658// Hit the option key ?
659if (key == optionKey)
660{
661gBootMode &= ~kBootModeQuiet;
662timeout = 0;
663}
664else
665{
666key = key & 0xFF;
667
668// Try booting hard disk if user pressed 'h'
669if (biosDevIsCDROM(gBIOSDev) && key == 'h')
670{
671BVRef bvr;
672
673// Look at partitions hosting OS X other than the CD-ROM
674for (bvr = bvChain; bvr; bvr=bvr->next)
675{
676if ((bvr->flags & kBVFlagSystemVolume) && bvr->biosdev != gBIOSDev)
677{
678gBootVolume = bvr;
679}
680}
681}
682goto done;
683}
684}
685
686if (gBootMode & kBootModeQuiet)
687{
688// No input allowed from user.
689goto done;
690}
691
692if (firstRun && timeout > 0 && GUI_countdown("Press any key to enter startup options.", kMenuTopRow, timeout) == 0)
693{
694// If the user is holding down a modifier key,
695// enter safe mode.
696if ((readKeyboardShiftFlags() & 0x0F) != 0)
697{
698gBootMode |= kBootModeSafe;
699}
700goto done;
701}
702
703if (gDeviceCount)
704{
705// Allocate memory for an array of menu items.
706menuItems = malloc(sizeof(MenuItem) * gDeviceCount);
707if (menuItems == NULL)
708{
709goto done;
710}
711
712// Associate a menu item for each BVRef.
713for (bvr=bvChain, i=gDeviceCount-1, selectIndex=0; bvr; bvr=bvr->next)
714{
715if (bvr->visible)
716{
717getBootVolumeDescription(bvr, menuItems[i].name, sizeof(menuItems[i].name) - 1, true);
718menuItems[i].param = (void *) bvr;
719if (bvr == menuBVR)
720{
721selectIndex = i;
722}
723i--;
724}
725}
726}
727
728if (bootArgs->Video.v_display == GRAPHICS_MODE)
729{
730// redraw the background buffer
731gui.logo.draw = true;
732drawBackground();
733gui.devicelist.draw = true;
734gui.redraw = true;
735if (!(gBootMode & kBootModeQuiet))
736{
737bool showBootBanner = true;
738
739// Check if "Boot Banner"=N switch is present in config file.
740getBoolForKey(kBootBannerKey, &showBootBanner, &bootInfo->bootConfig);
741if (showBootBanner)
742{
743// Display banner and show hardware info.
744gprintf(&gui.screen, bootBanner + 1, (bootInfo->convmem + bootInfo->extmem) / 1024);
745}
746
747// redraw background
748memcpy(gui.backbuffer->pixels, gui.screen.pixmap->pixels, gui.backbuffer->width * gui.backbuffer->height * 4);
749}
750}
751else
752{
753// Clear screen and hide the blinking cursor.
754clearScreenRows(kMenuTopRow, kMenuTopRow + 2);
755changeCursor(0, kMenuTopRow, kCursorTypeHidden, 0);
756}
757
758nextRow = kMenuTopRow;
759showPrompt = true;
760
761if (gDeviceCount)
762{
763if( bootArgs->Video.v_display == VGA_TEXT_MODE )
764{
765printf("Use \30\31 keys to select the startup volume.");
766}
767GUI_showMenu( menuItems, gDeviceCount, selectIndex, kMenuTopRow + 2, kMenuMaxItems );
768nextRow += min( gDeviceCount, kMenuMaxItems ) + 3;
769}
770
771// Show the boot prompt.
772showPrompt = (gDeviceCount == 0) || (menuBVR->flags & kBVFlagNativeBoot);
773GUI_showBootPrompt( nextRow, showPrompt );
774
775do {
776if (bootArgs->Video.v_display == GRAPHICS_MODE)
777{
778// redraw background
779memcpy( gui.backbuffer->pixels, gui.screen.pixmap->pixels, gui.backbuffer->width * gui.backbuffer->height * 4 );
780// reset cursor co-ords
781gui.debug.cursor = pos( gui.screen.width - 160 , 10 );
782}
783key = getc();
784GUI_updateMenu( key, (void **) &menuBVR );
785newShowPrompt = (gDeviceCount == 0) || (menuBVR->flags & kBVFlagNativeBoot);
786
787if (newShowPrompt != showPrompt)
788{
789showPrompt = newShowPrompt;
790GUI_showBootPrompt( nextRow, showPrompt );
791}
792
793if (showPrompt)
794{
795GUI_updateBootArgs(key);
796}
797
798switch (key)
799{
800case kReturnKey:
801if (gui.menu.draw)
802{
803key=0;
804break;
805}
806if (*gBootArgs == '?')
807{
808char * argPtr = gBootArgs;
809
810// Skip the leading "?" character.
811argPtr++;
812getNextArg(&argPtr, booterCommand);
813getNextArg(&argPtr, booterParam);
814
815/*
816 * TODO: this needs to be refactored.
817 */
818if (strcmp( booterCommand, "video" ) == 0)
819{
820if (bootArgs->Video.v_display == GRAPHICS_MODE)
821{
822showInfoBox(getVBEInfoString(), getVBEModeInfoString());
823}
824else
825{
826printVBEModeInfo();
827}
828}
829else if ( strcmp( booterCommand, "memory" ) == 0)
830{
831if (bootArgs->Video.v_display == GRAPHICS_MODE )
832{
833showInfoBox("Memory Map", getMemoryInfoString());
834}
835else
836{
837printMemoryInfo();
838}
839}
840else if (strcmp(booterCommand, "lspci") == 0)
841{
842lspci();
843}
844else if (strcmp(booterCommand, "more") == 0)
845{
846showTextFile(booterParam);
847}
848else if (strcmp(booterCommand, "rd") == 0)
849{
850processRAMDiskCommand(&argPtr, booterParam);
851}
852else if (strcmp(booterCommand, "norescan") == 0)
853{
854if (gEnableCDROMRescan)
855{
856gEnableCDROMRescan = false;
857break;
858}
859}
860else
861{
862showHelp();
863}
864key = 0;
865GUI_showBootPrompt(nextRow, showPrompt);
866break;
867}
868gBootVolume = menuBVR;
869setRootVolume(menuBVR);
870gBIOSDev = menuBVR->biosdev;
871break;
872
873case kEscapeKey:
874clearBootArgs();
875break;
876
877case kF5Key:
878// New behavior:
879// Clear gBootVolume to restart the loop
880// if the user enabled rescanning the optical drive.
881// Otherwise boot the default boot volume.
882if (gEnableCDROMRescan)
883{
884gBootVolume = NULL;
885clearBootArgs();
886}
887break;
888
889case kF10Key:
890gScanSingleDrive = false;
891scanDisks(gBIOSDev, &bvCount);
892gBootVolume = NULL;
893clearBootArgs();
894break;
895
896case kTabKey:
897// New behavior:
898// Switch between text & graphic interfaces
899// Only Permitted if started in graphics interface
900if (useGUI)
901{
902if (bootArgs->Video.v_display == GRAPHICS_MODE)
903{
904setVideoMode(VGA_TEXT_MODE, 0);
905
906setCursorPosition(0, 0, 0);
907clearScreenRows(0, kScreenLastRow);
908
909// Display banner and show hardware info.
910printf(bootBanner, (bootInfo->convmem + bootInfo->extmem) / 1024);
911printf(getVBEInfoString());
912
913clearScreenRows(kMenuTopRow, kMenuTopRow + 2);
914changeCursor(0, kMenuTopRow, kCursorTypeHidden, 0);
915
916nextRow = kMenuTopRow;
917showPrompt = true;
918
919if (gDeviceCount)
920{
921printf("Use \30\31 keys to select the startup volume.");
922GUI_showMenu(menuItems, gDeviceCount, selectIndex, kMenuTopRow + 2, kMenuMaxItems);
923nextRow += min(gDeviceCount, kMenuMaxItems) + 3;
924}
925
926showPrompt = (gDeviceCount == 0) || (menuBVR->flags & kBVFlagNativeBoot);
927GUI_showBootPrompt(nextRow, showPrompt);
928//changeCursor( 0, kMenuTopRow, kCursorTypeUnderline, 0 );
929}
930else
931{
932gui.redraw = true;
933setVideoMode(GRAPHICS_MODE, 0);
934updateVRAM();
935}
936}
937key = 0;
938break;
939
940default:
941key = 0;
942break;
943}
944} while (0 == key);
945
946done:
947if (bootArgs->Video.v_display == VGA_TEXT_MODE)
948{
949clearScreenRows(kMenuTopRow, kScreenLastRow);
950changeCursor(0, kMenuTopRow, kCursorTypeUnderline, 0);
951}
952shouldboot = false;
953gui.menu.draw = false;
954if (menuItems)
955{
956free(menuItems);
957menuItems = NULL;
958}
959return 0;
960}
961
962
963
964int GUI_error(const char * fmt, ...)
965{
966 va_list ap;
967 gErrors = true;
968 va_start(ap, fmt);
969
970if (bootArgs->Video.v_display == VGA_TEXT_MODE)
971{
972prf(fmt, ap, putchar, 0);
973 }
974else
975{
976vprf(fmt, ap);
977}
978
979va_end(ap);
980 return(0);
981}
982
983int GUI_verbose(const char * fmt, ...)
984{
985 va_list ap;
986
987va_start(ap, fmt);
988 if (gVerboseMode)
989 {
990if (bootArgs->Video.v_display == VGA_TEXT_MODE)
991{
992prf(fmt, ap, putchar, 0);
993}
994else
995{
996vprf(fmt, ap);
997}
998 }
999
1000/* Kabyl: BooterLog */
1001struct putc_info pi;
1002
1003if (!msgbuf)
1004return 0;
1005
1006if (((cursor - msgbuf) > (BOOTER_LOG_SIZE - SAFE_LOG_SIZE)))
1007return 0;
1008pi.str = cursor;
1009pi.last_str = 0;
1010prf(fmt, ap, sputc, &pi);
1011cursor += strlen((char *)cursor);
1012
1013
1014 va_end(ap);
1015 return(0);
1016}
1017
1018int GUI_printf(const char * fmt, ...)
1019{
1020 va_list ap;
1021va_start(ap, fmt);
1022if (bootArgs->Video.v_display == VGA_TEXT_MODE)
1023{
1024prf(fmt, ap, putchar, 0);
1025}
1026else
1027{
1028vprf(fmt, ap);
1029}
1030
1031/* Kabyl: BooterLog */
1032struct putc_info pi;
1033
1034if (!msgbuf)
1035return 0;
1036
1037if (((cursor - msgbuf) > (BOOTER_LOG_SIZE - SAFE_LOG_SIZE)))
1038return 0;
1039pi.str = cursor;
1040pi.last_str = 0;
1041prf(fmt, ap, sputc, &pi);
1042cursor += strlen((char *)cursor);
1043
1044va_end(ap);
1045 return 0;
1046}
1047
1048void GUI_stop(const char * fmt, ...)
1049{
1050va_list ap;
1051
1052printf("\n");
1053va_start(ap, fmt);
1054
1055if (bootArgs->Video.v_display == VGA_TEXT_MODE)
1056{
1057prf(fmt, ap, putchar, 0);
1058}
1059else
1060{
1061vprf(fmt, ap);
1062}
1063va_end(ap);
1064
1065printf("\nThis is a non recoverable error! System HALTED!!!");
1066halt();
1067while (1);
1068}
1069
1070void GUI_showHelp(void)
1071{
1072if (bootArgs->Video.v_display == GRAPHICS_MODE) {
1073showInfoBox("Help. Press q to quit.\n", (char *)BootHelp_txt);
1074} else {
1075showTextBuffer((char *)BootHelp_txt, BootHelp_txt_len);
1076}
1077}
1078

Archive Download this file

Revision: 557