Переглянути джерело

[menu] Add the abstract concept of a menu

Inspired-by: Robin Smidsrød <robin@smidsrod.no>
Tested-by: Robin Smidsrød <robin@smidsrod.no>
Signed-off-by: Michael Brown <mcb30@ipxe.org>
tags/v1.20.1
Michael Brown 12 роки тому
джерело
коміт
0d2fba2887
2 змінених файлів з 224 додано та 0 видалено
  1. 177
    0
      src/core/menu.c
  2. 47
    0
      src/include/ipxe/menu.h

+ 177
- 0
src/core/menu.c Переглянути файл

@@ -0,0 +1,177 @@
1
+/*
2
+ * Copyright (C) 2012 Michael Brown <mbrown@fensystems.co.uk>.
3
+ *
4
+ * This program is free software; you can redistribute it and/or
5
+ * modify it under the terms of the GNU General Public License as
6
+ * published by the Free Software Foundation; either version 2 of the
7
+ * License, or any later version.
8
+ *
9
+ * This program is distributed in the hope that it will be useful, but
10
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12
+ * General Public License for more details.
13
+ *
14
+ * You should have received a copy of the GNU General Public License
15
+ * along with this program; if not, write to the Free Software
16
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17
+ */
18
+
19
+FILE_LICENCE ( GPL2_OR_LATER );
20
+
21
+/** @file
22
+ *
23
+ * Menu selection
24
+ *
25
+ */
26
+
27
+#include <stdlib.h>
28
+#include <string.h>
29
+#include <assert.h>
30
+#include <ipxe/list.h>
31
+#include <ipxe/menu.h>
32
+
33
+/** List of all menus */
34
+static LIST_HEAD ( menus );
35
+
36
+/**
37
+ * Create menu
38
+ *
39
+ * @v name		Menu name, or NULL
40
+ * @v title		Menu title, or NULL
41
+ * @ret menu		Menu, or NULL on failure
42
+ */
43
+struct menu * create_menu ( const char *name, const char *title ) {
44
+	size_t name_len;
45
+	size_t title_len;
46
+	size_t len;
47
+	struct menu *menu;
48
+	char *name_copy;
49
+	char *title_copy;
50
+
51
+	/* Destroy any existing menu of this name */
52
+	menu = find_menu ( name );
53
+	if ( menu )
54
+		destroy_menu ( menu );
55
+
56
+	/* Use empty title if none given */
57
+	if ( ! title )
58
+		title = "";
59
+
60
+	/* Allocate menu */
61
+	name_len = ( name ? ( strlen ( name ) + 1 /* NUL */ ) : 0 );
62
+	title_len = ( strlen ( title ) + 1 /* NUL */ );
63
+	len = ( sizeof ( *menu ) + name_len + title_len );
64
+	menu = zalloc ( len );
65
+	if ( ! menu )
66
+		return NULL;
67
+	name_copy = ( ( void * ) ( menu + 1 ) );
68
+	title_copy = ( name_copy + name_len );
69
+
70
+	/* Initialise menu */
71
+	if ( name ) {
72
+		strcpy ( name_copy, name );
73
+		menu->name = name_copy;
74
+	}
75
+	strcpy ( title_copy, title );
76
+	menu->title = title_copy;
77
+	INIT_LIST_HEAD ( &menu->items );
78
+
79
+	/* Add to list of menus */
80
+	list_add_tail ( &menu->list, &menus );
81
+
82
+	DBGC ( menu, "MENU %s created with title \"%s\"\n",
83
+	       menu->name, menu->title );
84
+
85
+	return menu;
86
+}
87
+
88
+/**
89
+ * Add menu item
90
+ *
91
+ * @v menu		Menu
92
+ * @v label		Label, or NULL
93
+ * @v text		Text, or NULL
94
+ * @v shortcut		Shortcut key
95
+ * @v is_default	Item is the default item
96
+ * @ret item		Menu item, or NULL on failure
97
+ */
98
+struct menu_item * add_menu_item ( struct menu *menu, const char *label,
99
+				   const char *text, int shortcut,
100
+				   int is_default ) {
101
+	size_t label_len;
102
+	size_t text_len;
103
+	size_t len;
104
+	struct menu_item *item;
105
+	char *label_copy;
106
+	char *text_copy;
107
+
108
+	/* Use empty text if none given */
109
+	if ( ! text )
110
+		text = "";
111
+
112
+	/* Allocate item */
113
+	label_len = ( label ? ( strlen ( label ) + 1 /* NUL */ ) : 0 );
114
+	text_len = ( strlen ( text ) + 1 /* NUL */ );
115
+	len = ( sizeof ( *item ) + label_len + text_len );
116
+	item = zalloc ( len );
117
+	if ( ! item )
118
+		return NULL;
119
+	label_copy = ( ( void * ) ( item + 1 ) );
120
+	text_copy = ( label_copy + label_len );
121
+
122
+	/* Initialise item */
123
+	if ( label ) {
124
+		strcpy ( label_copy, label );
125
+		item->label = label_copy;
126
+	}
127
+	strcpy ( text_copy, text );
128
+	item->text = text_copy;
129
+	item->shortcut = shortcut;
130
+	item->is_default = is_default;
131
+
132
+	/* Add to list of items */
133
+	list_add_tail ( &item->list, &menu->items );
134
+
135
+	return item;
136
+}
137
+
138
+/**
139
+ * Destroy menu
140
+ *
141
+ * @v menu		Menu
142
+ */
143
+void destroy_menu ( struct menu *menu ) {
144
+	struct menu_item *item;
145
+	struct menu_item *tmp;
146
+
147
+	/* Remove from list of menus */
148
+	list_del ( &menu->list );
149
+
150
+	/* Free items */
151
+	list_for_each_entry_safe ( item, tmp, &menu->items, list ) {
152
+		list_del ( &item->list );
153
+		free ( item );
154
+	}
155
+
156
+	/* Free menu */
157
+	free ( menu );
158
+}
159
+
160
+/**
161
+ * Find menu
162
+ *
163
+ * @v name		Menu name, or NULL
164
+ * @ret menu		Menu, or NULL if not found
165
+ */
166
+struct menu * find_menu ( const char *name ) {
167
+	struct menu *menu;
168
+
169
+	list_for_each_entry ( menu, &menus, list ) {
170
+		if ( ( menu->name == name ) ||
171
+		     ( strcmp ( menu->name, name ) == 0 ) ) {
172
+			return menu;
173
+		}
174
+	}
175
+
176
+	return NULL;
177
+}

+ 47
- 0
src/include/ipxe/menu.h Переглянути файл

@@ -0,0 +1,47 @@
1
+#ifndef _IPXE_MENU_H
2
+#define _IPXE_MENU_H
3
+
4
+/** @file
5
+ *
6
+ * Menu selection
7
+ *
8
+ */
9
+
10
+FILE_LICENCE ( GPL2_OR_LATER );
11
+
12
+#include <ipxe/list.h>
13
+
14
+/** A menu */
15
+struct menu {
16
+	/** List of menus */
17
+	struct list_head list;
18
+	/** Name */
19
+	const char *name;
20
+	/** Title */
21
+	const char *title;
22
+	/** Menu items */
23
+	struct list_head items;
24
+};
25
+
26
+/** A menu item */
27
+struct menu_item {
28
+	/** List of menu items */
29
+	struct list_head list;
30
+	/** Label */
31
+	const char *label;
32
+	/** Text */
33
+	const char *text;
34
+	/** Shortcut key */
35
+	int shortcut;
36
+	/** Is default item */
37
+	int is_default;
38
+};
39
+
40
+extern struct menu * create_menu ( const char *name, const char *title );
41
+extern struct menu_item * add_menu_item ( struct menu *menu, const char *label,
42
+					  const char *text, int shortcut,
43
+					  int is_default );
44
+extern void destroy_menu ( struct menu *menu );
45
+extern struct menu * find_menu ( const char *name );
46
+
47
+#endif /* _IPXE_MENU_H */

Завантаження…
Відмінити
Зберегти