All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature
@ 2013-04-15 14:13 Benjamin Poirier
  2013-04-15 14:13 ` [PATCH 2/2] menuconfig: Add "breadcrumbs" navigation aid Benjamin Poirier
  2013-04-15 21:54 ` [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature Yann E. MORIN
  0 siblings, 2 replies; 9+ messages in thread
From: Benjamin Poirier @ 2013-04-15 14:13 UTC (permalink / raw)
  To: Michal Marek
  Cc: Yann E. MORIN, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

Fixes the memory leak of struct jump_key allocated in get_prompt_str()

Signed-off-by: Benjamin Poirier <bpoirier@suse.de>
---
 scripts/kconfig/list.h  |   13 +++++++++++++
 scripts/kconfig/mconf.c |    3 +++
 2 files changed, 16 insertions(+)

diff --git a/scripts/kconfig/list.h b/scripts/kconfig/list.h
index 0ae730b..b87206c 100644
--- a/scripts/kconfig/list.h
+++ b/scripts/kconfig/list.h
@@ -51,6 +51,19 @@ struct list_head {
 	     pos = list_entry(pos->member.next, typeof(*pos), member))
 
 /**
+ * list_for_each_entry_safe - iterate over list of given type safe against removal of list entry
+ * @pos:	the type * to use as a loop cursor.
+ * @n:		another type * to use as temporary storage
+ * @head:	the head for your list.
+ * @member:	the name of the list_struct within the struct.
+ */
+#define list_for_each_entry_safe(pos, n, head, member)			\
+	for (pos = list_entry((head)->next, typeof(*pos), member),	\
+		n = list_entry(pos->member.next, typeof(*pos), member);	\
+	     &pos->member != (head);					\
+	     pos = n, n = list_entry(n->member.next, typeof(*n), member))
+
+/**
  * list_empty - tests whether a list is empty
  * @head: the list to test.
  */
diff --git a/scripts/kconfig/mconf.c b/scripts/kconfig/mconf.c
index 566288a..c5418d6 100644
--- a/scripts/kconfig/mconf.c
+++ b/scripts/kconfig/mconf.c
@@ -389,6 +389,7 @@ again:
 			.targets = targets,
 			.keys = keys,
 		};
+		struct jump_key *pos, *tmp;
 
 		res = get_relations_str(sym_arr, &head);
 		dres = show_textbox_ext(_("Search Results"), (char *)
@@ -402,6 +403,8 @@ again:
 				again = true;
 			}
 		str_free(&res);
+		list_for_each_entry_safe(pos, tmp, &head, entries)
+			free(pos);
 	} while (again);
 	free(sym_arr);
 	str_free(&title);
-- 
1.7.10.4


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 2/2] menuconfig: Add "breadcrumbs" navigation aid
  2013-04-15 14:13 [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature Benjamin Poirier
@ 2013-04-15 14:13 ` Benjamin Poirier
  2013-04-15 21:39   ` Yann E. MORIN
  2013-04-15 21:54 ` [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature Yann E. MORIN
  1 sibling, 1 reply; 9+ messages in thread
From: Benjamin Poirier @ 2013-04-15 14:13 UTC (permalink / raw)
  To: Michal Marek
  Cc: Yann E. MORIN, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

Displays a trail of the menu entries used to get to the current menu.

Signed-off-by: Benjamin Poirier <bpoirier@suse.de>
---
 scripts/kconfig/list.h            |   27 ++++++++++++++
 scripts/kconfig/lxdialog/dialog.h |    7 ++++
 scripts/kconfig/lxdialog/util.c   |   48 ++++++++++++++++++++++++-
 scripts/kconfig/mconf.c           |   71 ++++++++++++++++++++++++++++++++++++-
 4 files changed, 151 insertions(+), 2 deletions(-)

diff --git a/scripts/kconfig/list.h b/scripts/kconfig/list.h
index b87206c..ea1d581 100644
--- a/scripts/kconfig/list.h
+++ b/scripts/kconfig/list.h
@@ -101,4 +101,31 @@ static inline void list_add_tail(struct list_head *_new, struct list_head *head)
 	__list_add(_new, head->prev, head);
 }
 
+/*
+ * Delete a list entry by making the prev/next entries
+ * point to each other.
+ *
+ * This is only for internal list manipulation where we know
+ * the prev/next entries already!
+ */
+static inline void __list_del(struct list_head *prev, struct list_head *next)
+{
+	next->prev = prev;
+	prev->next = next;
+}
+
+#define LIST_POISON1  ((void *) 0x00100100)
+#define LIST_POISON2  ((void *) 0x00200200)
+/**
+ * list_del - deletes entry from list.
+ * @entry: the element to delete from the list.
+ * Note: list_empty() on entry does not return true after this, the entry is
+ * in an undefined state.
+ */
+static inline void list_del(struct list_head *entry)
+{
+	__list_del(entry->prev, entry->next);
+	entry->next = LIST_POISON1;
+	entry->prev = LIST_POISON2;
+}
 #endif
diff --git a/scripts/kconfig/lxdialog/dialog.h b/scripts/kconfig/lxdialog/dialog.h
index 307022a..10993370 100644
--- a/scripts/kconfig/lxdialog/dialog.h
+++ b/scripts/kconfig/lxdialog/dialog.h
@@ -106,8 +106,14 @@ struct dialog_color {
 	int hl;		/* highlight this item */
 };
 
+struct subtitle_list {
+	struct subtitle_list *next;
+	const char *text;
+};
+
 struct dialog_info {
 	const char *backtitle;
+	struct subtitle_list *subtitles;
 	struct dialog_color screen;
 	struct dialog_color shadow;
 	struct dialog_color dialog;
@@ -196,6 +202,7 @@ int on_key_resize(void);
 
 int init_dialog(const char *backtitle);
 void set_dialog_backtitle(const char *backtitle);
+void set_dialog_subtitles(struct subtitle_list *subtitles);
 void end_dialog(int x, int y);
 void attr_clear(WINDOW * win, int height, int width, chtype attr);
 void dialog_clear(void);
diff --git a/scripts/kconfig/lxdialog/util.c b/scripts/kconfig/lxdialog/util.c
index 109d531..9a41d78 100644
--- a/scripts/kconfig/lxdialog/util.c
+++ b/scripts/kconfig/lxdialog/util.c
@@ -257,13 +257,54 @@ void dialog_clear(void)
 	attr_clear(stdscr, LINES, COLS, dlg.screen.atr);
 	/* Display background title if it exists ... - SLH */
 	if (dlg.backtitle != NULL) {
-		int i;
+		int i, len = 0;
+		struct subtitle_list *pos;
 
 		wattrset(stdscr, dlg.screen.atr);
 		mvwaddstr(stdscr, 0, 1, (char *)dlg.backtitle);
 		wmove(stdscr, 1, 1);
 		for (i = 1; i < COLS - 1; i++)
 			waddch(stdscr, ACS_HLINE);
+
+		for (pos = dlg.subtitles; pos != NULL; pos = pos->next) {
+			/* 3 is for the arrow and spaces */
+			len += strlen(pos->text) + 3;
+		}
+
+		if (len) {
+			int skip = 0;
+
+			wmove(stdscr, 1, 1);
+			if (len > COLS - 2) {
+				const char *ellipsis = "[...] ";
+				waddstr(stdscr, ellipsis);
+				skip = len - (COLS - 2 - strlen(ellipsis));
+			}
+
+			for (pos = dlg.subtitles; pos != NULL; pos =
+			     pos->next) {
+				if (skip == 0)
+					waddch(stdscr, ACS_RARROW);
+				else
+					skip--;
+
+				if (skip == 0)
+					waddch(stdscr, ' ');
+				else
+					skip--;
+
+				if (skip < strlen(pos->text)) {
+					waddstr(stdscr, pos->text + skip);
+					skip = 0;
+				} else
+					skip -= strlen(pos->text);
+
+				if (skip == 0)
+					waddch(stdscr, ' ');
+				else
+					skip--;
+			}
+		}
 	}
 	wnoutrefresh(stdscr);
 }
@@ -302,6 +343,11 @@ void set_dialog_backtitle(const char *backtitle)
 	dlg.backtitle = backtitle;
 }
 
+void set_dialog_subtitles(struct subtitle_list *subtitles)
+{
+	dlg.subtitles = subtitles;
+}
+
 /*
  * End using dialog functions.
  */
diff --git a/scripts/kconfig/mconf.c b/scripts/kconfig/mconf.c
index c5418d6..387dc8d 100644
--- a/scripts/kconfig/mconf.c
+++ b/scripts/kconfig/mconf.c
@@ -311,6 +311,50 @@ static void set_config_filename(const char *config_filename)
 		filename[sizeof(filename)-1] = '\0';
 }
 
+struct subtitle_part {
+	struct list_head entries;
+	const char *text;
+};
+static LIST_HEAD(trail);
+
+static struct subtitle_list *subtitles;
+static void set_subtitle(void)
+{
+	struct subtitle_part *sp;
+	struct subtitle_list *pos, *tmp;
+
+	for (pos = subtitles; pos != NULL; pos = tmp) {
+		tmp = pos->next;
+		free(pos);
+	}
+
+	subtitles = NULL;
+	list_for_each_entry(sp, &trail, entries) {
+		if (sp->text) {
+			if (pos) {
+				pos->next = xcalloc(sizeof(*pos), 1);
+				pos = pos->next;
+			} else {
+				subtitles = pos = xcalloc(sizeof(*pos), 1);
+			}
+			pos->text = sp->text;
+		}
+	}
+
+	set_dialog_subtitles(subtitles);
+}
+
+static void reset_subtitle(void)
+{
+	struct subtitle_list *pos, *tmp;
+
+	for (pos = subtitles; pos != NULL; pos = tmp) {
+		tmp = pos->next;
+		free(pos);
+	}
+	subtitles = NULL;
+	set_dialog_subtitles(subtitles);
+}
 
 struct search_data {
 	struct list_head *head;
@@ -353,6 +397,8 @@ static void search_conf(void)
 	char *dialog_input;
 	int dres, vscroll = 0, hscroll = 0;
 	bool again;
+	struct gstr sttext;
+	struct subtitle_part stpart;
 
 	title = str_new();
 	str_printf( &title, _("Enter %s (sub)string to search for "
@@ -379,6 +425,11 @@ again:
 	if (strncasecmp(dialog_input_result, CONFIG_, strlen(CONFIG_)) == 0)
 		dialog_input += strlen(CONFIG_);
 
+	sttext = str_new();
+	str_printf(&sttext, "Search (%s)", dialog_input_result);
+	stpart.text = str_get(&sttext);
+	list_add_tail(&stpart.entries, &trail);
+
 	sym_arr = sym_re_search(dialog_input);
 	do {
 		LIST_HEAD(head);
@@ -392,6 +443,7 @@ again:
 		struct jump_key *pos, *tmp;
 
 		res = get_relations_str(sym_arr, &head);
+		set_subtitle();
 		dres = show_textbox_ext(_("Search Results"), (char *)
 					str_get(&res), 0, 0, keys, &vscroll,
 					&hscroll, &update_text, (void *)
@@ -408,6 +460,8 @@ again:
 	} while (again);
 	free(sym_arr);
 	str_free(&title);
+	list_del(trail.prev);
+	str_free(&sttext);
 }
 
 static void build_conf(struct menu *menu)
@@ -592,16 +646,24 @@ static void conf(struct menu *menu, struct menu *active_menu)
 {
 	struct menu *submenu;
 	const char *prompt = menu_get_prompt(menu);
+	struct subtitle_part stpart;
 	struct symbol *sym;
 	int res;
 	int s_scroll = 0;
 
+	if (menu != &rootmenu)
+		stpart.text = menu_get_prompt(menu);
+	else
+		stpart.text = NULL;
+	list_add_tail(&stpart.entries, &trail);
+
 	while (1) {
 		item_reset();
 		current_menu = menu;
 		build_conf(menu);
 		if (!child_count)
 			break;
+		set_subtitle();
 		dialog_clear();
 		res = dialog_menu(prompt ? _(prompt) : _("Main Menu"),
 				  _(menu_instructions),
@@ -643,13 +705,17 @@ static void conf(struct menu *menu, struct menu *active_menu)
 		case 2:
 			if (sym)
 				show_help(submenu);
-			else
+			else {
+				reset_subtitle();
 				show_helptext(_("README"), _(mconf_readme));
+			}
 			break;
 		case 3:
+			reset_subtitle();
 			conf_save();
 			break;
 		case 4:
+			reset_subtitle();
 			conf_load();
 			break;
 		case 5:
@@ -682,6 +748,8 @@ static void conf(struct menu *menu, struct menu *active_menu)
 			break;
 		}
 	}
+
+	list_del(trail.prev);
 }
 
 static int show_textbox_ext(const char *title, char *text, int r, int c, int
@@ -884,6 +952,7 @@ static int handle_exit(void)
 	int res;
 
 	save_and_exit = 1;
+	reset_subtitle();
 	dialog_clear();
 	if (conf_get_changed())
 		res = dialog_yesno(NULL,
-- 
1.7.10.4


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCH 2/2] menuconfig: Add "breadcrumbs" navigation aid
  2013-04-15 14:13 ` [PATCH 2/2] menuconfig: Add "breadcrumbs" navigation aid Benjamin Poirier
@ 2013-04-15 21:39   ` Yann E. MORIN
  2013-04-16 14:07     ` [PATCH v3] " Benjamin Poirier
  0 siblings, 1 reply; 9+ messages in thread
From: Yann E. MORIN @ 2013-04-15 21:39 UTC (permalink / raw)
  To: Benjamin Poirier
  Cc: Michal Marek, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

Benjamin, All,

On Mon, Apr 15, 2013 at 10:13:51AM -0400, Benjamin Poirier wrote:
> Displays a trail of the menu entries used to get to the current menu.

Very good idea, indeed! :-)

> diff --git a/scripts/kconfig/lxdialog/util.c b/scripts/kconfig/lxdialog/util.c
> index 109d531..9a41d78 100644
> --- a/scripts/kconfig/lxdialog/util.c
> +++ b/scripts/kconfig/lxdialog/util.c
> @@ -257,13 +257,54 @@ void dialog_clear(void)
>  	attr_clear(stdscr, LINES, COLS, dlg.screen.atr);
>  	/* Display background title if it exists ... - SLH */
>  	if (dlg.backtitle != NULL) {
> -		int i;
> +		int i, len = 0;
> +		struct subtitle_list *pos;
>  
>  		wattrset(stdscr, dlg.screen.atr);
>  		mvwaddstr(stdscr, 0, 1, (char *)dlg.backtitle);
>  		wmove(stdscr, 1, 1);
>  		for (i = 1; i < COLS - 1; i++)
>  			waddch(stdscr, ACS_HLINE);

This means you'll be re-writing over this line with the following
code... (follow at [*], below)

> +		for (pos = dlg.subtitles; pos != NULL; pos = pos->next) {
> +			/* 3 is for the arrow and spaces */
> +			len += strlen(pos->text) + 3;
> +		}
> +
> +		if (len) {
> +			int skip = 0;
> +
> +			wmove(stdscr, 1, 1);
> +			if (len > COLS - 2) {
> +				const char *ellipsis = "[...] ";
> +				waddstr(stdscr, ellipsis);
> +				skip = len - (COLS - 2 - strlen(ellipsis));
> +			}
> +
> +			for (pos = dlg.subtitles; pos != NULL; pos =
> +			     pos->next) {
> +				if (skip == 0)
> +					waddch(stdscr, ACS_RARROW);
> +				else
> +					skip--;
> +
> +				if (skip == 0)
> +					waddch(stdscr, ' ');
> +				else
> +					skip--;
> +
> +				if (skip < strlen(pos->text)) {
> +					waddstr(stdscr, pos->text + skip);
> +					skip = 0;
> +				} else
> +					skip -= strlen(pos->text);
> +
> +				if (skip == 0)
> +					waddch(stdscr, ' ');
> +				else
> +					skip--;
> +			}
> +		}

[*] ... when you could have drawn only the needed part here:

+		wmove(stdscr, 1, len+1);
+		for (i = len + 1; i < COLS - 1; i++)
+			waddch(stdscr, ACS_HLINE);

[--SNIP--]

Queued (with that change) into:
https://git.gitorious.org/linux-kconfig/linux-kconfig.git yem-kconfig-for-next

Regards,
Yann E. MORIN.

-- 
.-----------------.--------------------.------------------.--------------------.
|  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
| +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
| +33 223 225 172 `------------.-------:  X  AGAINST      |  \e/  There is no  |
| http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
'------------------------------^-------^------------------^--------------------'

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature
  2013-04-15 14:13 [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature Benjamin Poirier
  2013-04-15 14:13 ` [PATCH 2/2] menuconfig: Add "breadcrumbs" navigation aid Benjamin Poirier
@ 2013-04-15 21:54 ` Yann E. MORIN
  2013-04-16  8:21   ` Michal Marek
  1 sibling, 1 reply; 9+ messages in thread
From: Yann E. MORIN @ 2013-04-15 21:54 UTC (permalink / raw)
  To: Benjamin Poirier
  Cc: Michal Marek, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

Benjamin, All,

On Mon, Apr 15, 2013 at 10:13:50AM -0400, Benjamin Poirier wrote:
> Fixes the memory leak of struct jump_key allocated in get_prompt_str()

Queued into:
https://git.gitorious.org/linux-kconfig/linux-kconfig.git yem-kconfig-rc-fixes

Although this is strictly a bug fix, I would lean toward waiting for the
next merge window to open before pulling this in.

We can't really say that the kconfig frontends are critical, long-running
processes. If they leak a bit of memory, that's not too cumbersome, I
think. OTOH, I think breaking the frontends so close to the end of the
-rc cycle is a bit dangerous (heck, I would not like to be part of the
cause of a new flaming, just for this! ;-) )

So, unless Michal really wants to pull this one and push it to Linus
before he cuts v3.9 final, I'll merge this later in my -for-next branch.

Thank you!

Regards,
Yann E. MORIN.

-- 
.-----------------.--------------------.------------------.--------------------.
|  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
| +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
| +33 223 225 172 `------------.-------:  X  AGAINST      |  \e/  There is no  |
| http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
'------------------------------^-------^------------------^--------------------'

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature
  2013-04-15 21:54 ` [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature Yann E. MORIN
@ 2013-04-16  8:21   ` Michal Marek
  2013-04-16  9:12     ` Michal Marek
  0 siblings, 1 reply; 9+ messages in thread
From: Michal Marek @ 2013-04-16  8:21 UTC (permalink / raw)
  To: Yann E. MORIN
  Cc: Benjamin Poirier, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

On 15.4.2013 23:54, Yann E. MORIN wrote:
> So, unless Michal really wants to pull this one and push it to Linus
> before he cuts v3.9 final, I'll merge this later in my -for-next branch.

That's fine with me.

Michal

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature
  2013-04-16  8:21   ` Michal Marek
@ 2013-04-16  9:12     ` Michal Marek
  2013-04-16 16:38       ` Yann E. MORIN
  0 siblings, 1 reply; 9+ messages in thread
From: Michal Marek @ 2013-04-16  9:12 UTC (permalink / raw)
  To: Yann E. MORIN
  Cc: Benjamin Poirier, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

On 16.4.2013 10:21, Michal Marek wrote:
> On 15.4.2013 23:54, Yann E. MORIN wrote:
>> So, unless Michal really wants to pull this one and push it to Linus
>> before he cuts v3.9 final, I'll merge this later in my -for-next branch.
> 
> That's fine with me.

BTW, in you are going to rebase the commit, it would be good idea to add
Cc: <stable@vger.kernel.org> to the changelog.

Thanks,
Michal

^ permalink raw reply	[flat|nested] 9+ messages in thread

* [PATCH v3] menuconfig: Add "breadcrumbs" navigation aid
  2013-04-15 21:39   ` Yann E. MORIN
@ 2013-04-16 14:07     ` Benjamin Poirier
  2013-04-16 17:20       ` Yann E. MORIN
  0 siblings, 1 reply; 9+ messages in thread
From: Benjamin Poirier @ 2013-04-16 14:07 UTC (permalink / raw)
  To: Michal Marek, Yann E. MORIN
  Cc: Wang YanQing, Dirk Gouders, Paul Gortmaker, linux-kbuild, linux-kernel

Displays a trail of the menu entries used to get to the current menu.

Signed-off-by: Benjamin Poirier <bpoirier@suse.de>
Tested-by: "Yann E. MORIN" <yann.morin.1998@free.fr>
[yann.morin.1998@free.fr: small, trivial code re-ordering]
Signed-off-by: "Yann E. MORIN" <yann.morin.1998@free.fr>
---

Indeed Yann, we can even remove one wmove() and one level of indentation in
dialog_clear().

I'm not sure who's pulling from who and where patches are going, but this
would supersede what's in yem-kconfig-for-next now.


 scripts/kconfig/list.h            |   27 ++++++++++++++
 scripts/kconfig/lxdialog/dialog.h |    7 ++++
 scripts/kconfig/lxdialog/util.c   |   45 +++++++++++++++++++++--
 scripts/kconfig/mconf.c           |   71 ++++++++++++++++++++++++++++++++++++-
 4 files changed, 147 insertions(+), 3 deletions(-)

diff --git a/scripts/kconfig/list.h b/scripts/kconfig/list.h
index 0ae730b..2f02a3b 100644
--- a/scripts/kconfig/list.h
+++ b/scripts/kconfig/list.h
@@ -88,4 +88,31 @@ static inline void list_add_tail(struct list_head *_new, struct list_head *head)
 	__list_add(_new, head->prev, head);
 }
 
+/*
+ * Delete a list entry by making the prev/next entries
+ * point to each other.
+ *
+ * This is only for internal list manipulation where we know
+ * the prev/next entries already!
+ */
+static inline void __list_del(struct list_head *prev, struct list_head *next)
+{
+	next->prev = prev;
+	prev->next = next;
+}
+
+#define LIST_POISON1  ((void *) 0x00100100)
+#define LIST_POISON2  ((void *) 0x00200200)
+/**
+ * list_del - deletes entry from list.
+ * @entry: the element to delete from the list.
+ * Note: list_empty() on entry does not return true after this, the entry is
+ * in an undefined state.
+ */
+static inline void list_del(struct list_head *entry)
+{
+	__list_del(entry->prev, entry->next);
+	entry->next = LIST_POISON1;
+	entry->prev = LIST_POISON2;
+}
 #endif
diff --git a/scripts/kconfig/lxdialog/dialog.h b/scripts/kconfig/lxdialog/dialog.h
index 307022a..10993370 100644
--- a/scripts/kconfig/lxdialog/dialog.h
+++ b/scripts/kconfig/lxdialog/dialog.h
@@ -106,8 +106,14 @@ struct dialog_color {
 	int hl;		/* highlight this item */
 };
 
+struct subtitle_list {
+	struct subtitle_list *next;
+	const char *text;
+};
+
 struct dialog_info {
 	const char *backtitle;
+	struct subtitle_list *subtitles;
 	struct dialog_color screen;
 	struct dialog_color shadow;
 	struct dialog_color dialog;
@@ -196,6 +202,7 @@ int on_key_resize(void);
 
 int init_dialog(const char *backtitle);
 void set_dialog_backtitle(const char *backtitle);
+void set_dialog_subtitles(struct subtitle_list *subtitles);
 void end_dialog(int x, int y);
 void attr_clear(WINDOW * win, int height, int width, chtype attr);
 void dialog_clear(void);
diff --git a/scripts/kconfig/lxdialog/util.c b/scripts/kconfig/lxdialog/util.c
index 109d531..a0e97c2 100644
--- a/scripts/kconfig/lxdialog/util.c
+++ b/scripts/kconfig/lxdialog/util.c
@@ -257,12 +257,48 @@ void dialog_clear(void)
 	attr_clear(stdscr, LINES, COLS, dlg.screen.atr);
 	/* Display background title if it exists ... - SLH */
 	if (dlg.backtitle != NULL) {
-		int i;
+		int i, len = 0, skip = 0;
+		struct subtitle_list *pos;
 
 		wattrset(stdscr, dlg.screen.atr);
 		mvwaddstr(stdscr, 0, 1, (char *)dlg.backtitle);
+
+		for (pos = dlg.subtitles; pos != NULL; pos = pos->next) {
+			/* 3 is for the arrow and spaces */
+			len += strlen(pos->text) + 3;
+		}
+
 		wmove(stdscr, 1, 1);
-		for (i = 1; i < COLS - 1; i++)
+		if (len > COLS - 2) {
+			const char *ellipsis = "[...] ";
+			waddstr(stdscr, ellipsis);
+			skip = len - (COLS - 2 - strlen(ellipsis));
+		}
+
+		for (pos = dlg.subtitles; pos != NULL; pos = pos->next) {
+			if (skip == 0)
+				waddch(stdscr, ACS_RARROW);
+			else
+				skip--;
+
+			if (skip == 0)
+				waddch(stdscr, ' ');
+			else
+				skip--;
+
+			if (skip < strlen(pos->text)) {
+				waddstr(stdscr, pos->text + skip);
+				skip = 0;
+			} else
+				skip -= strlen(pos->text);
+
+			if (skip == 0)
+				waddch(stdscr, ' ');
+			else
+				skip--;
+		}
+
+		for (i = len + 1; i < COLS - 1; i++)
 			waddch(stdscr, ACS_HLINE);
 	}
 	wnoutrefresh(stdscr);
@@ -302,6 +338,11 @@ void set_dialog_backtitle(const char *backtitle)
 	dlg.backtitle = backtitle;
 }
 
+void set_dialog_subtitles(struct subtitle_list *subtitles)
+{
+	dlg.subtitles = subtitles;
+}
+
 /*
  * End using dialog functions.
  */
diff --git a/scripts/kconfig/mconf.c b/scripts/kconfig/mconf.c
index 566288a..4b6f1f3 100644
--- a/scripts/kconfig/mconf.c
+++ b/scripts/kconfig/mconf.c
@@ -311,6 +311,50 @@ static void set_config_filename(const char *config_filename)
 		filename[sizeof(filename)-1] = '\0';
 }
 
+struct subtitle_part {
+	struct list_head entries;
+	const char *text;
+};
+static LIST_HEAD(trail);
+
+static struct subtitle_list *subtitles;
+static void set_subtitle(void)
+{
+	struct subtitle_part *sp;
+	struct subtitle_list *pos, *tmp;
+
+	for (pos = subtitles; pos != NULL; pos = tmp) {
+		tmp = pos->next;
+		free(pos);
+	}
+
+	subtitles = NULL;
+	list_for_each_entry(sp, &trail, entries) {
+		if (sp->text) {
+			if (pos) {
+				pos->next = xcalloc(sizeof(*pos), 1);
+				pos = pos->next;
+			} else {
+				subtitles = pos = xcalloc(sizeof(*pos), 1);
+			}
+			pos->text = sp->text;
+		}
+	}
+
+	set_dialog_subtitles(subtitles);
+}
+
+static void reset_subtitle(void)
+{
+	struct subtitle_list *pos, *tmp;
+
+	for (pos = subtitles; pos != NULL; pos = tmp) {
+		tmp = pos->next;
+		free(pos);
+	}
+	subtitles = NULL;
+	set_dialog_subtitles(subtitles);
+}
 
 struct search_data {
 	struct list_head *head;
@@ -353,6 +397,8 @@ static void search_conf(void)
 	char *dialog_input;
 	int dres, vscroll = 0, hscroll = 0;
 	bool again;
+	struct gstr sttext;
+	struct subtitle_part stpart;
 
 	title = str_new();
 	str_printf( &title, _("Enter %s (sub)string to search for "
@@ -379,6 +425,11 @@ again:
 	if (strncasecmp(dialog_input_result, CONFIG_, strlen(CONFIG_)) == 0)
 		dialog_input += strlen(CONFIG_);
 
+	sttext = str_new();
+	str_printf(&sttext, "Search (%s)", dialog_input_result);
+	stpart.text = str_get(&sttext);
+	list_add_tail(&stpart.entries, &trail);
+
 	sym_arr = sym_re_search(dialog_input);
 	do {
 		LIST_HEAD(head);
@@ -391,6 +442,7 @@ again:
 		};
 
 		res = get_relations_str(sym_arr, &head);
+		set_subtitle();
 		dres = show_textbox_ext(_("Search Results"), (char *)
 					str_get(&res), 0, 0, keys, &vscroll,
 					&hscroll, &update_text, (void *)
@@ -405,6 +457,8 @@ again:
 	} while (again);
 	free(sym_arr);
 	str_free(&title);
+	list_del(trail.prev);
+	str_free(&sttext);
 }
 
 static void build_conf(struct menu *menu)
@@ -589,16 +643,24 @@ static void conf(struct menu *menu, struct menu *active_menu)
 {
 	struct menu *submenu;
 	const char *prompt = menu_get_prompt(menu);
+	struct subtitle_part stpart;
 	struct symbol *sym;
 	int res;
 	int s_scroll = 0;
 
+	if (menu != &rootmenu)
+		stpart.text = menu_get_prompt(menu);
+	else
+		stpart.text = NULL;
+	list_add_tail(&stpart.entries, &trail);
+
 	while (1) {
 		item_reset();
 		current_menu = menu;
 		build_conf(menu);
 		if (!child_count)
 			break;
+		set_subtitle();
 		dialog_clear();
 		res = dialog_menu(prompt ? _(prompt) : _("Main Menu"),
 				  _(menu_instructions),
@@ -640,13 +702,17 @@ static void conf(struct menu *menu, struct menu *active_menu)
 		case 2:
 			if (sym)
 				show_help(submenu);
-			else
+			else {
+				reset_subtitle();
 				show_helptext(_("README"), _(mconf_readme));
+			}
 			break;
 		case 3:
+			reset_subtitle();
 			conf_save();
 			break;
 		case 4:
+			reset_subtitle();
 			conf_load();
 			break;
 		case 5:
@@ -679,6 +745,8 @@ static void conf(struct menu *menu, struct menu *active_menu)
 			break;
 		}
 	}
+
+	list_del(trail.prev);
 }
 
 static int show_textbox_ext(const char *title, char *text, int r, int c, int
@@ -881,6 +949,7 @@ static int handle_exit(void)
 	int res;
 
 	save_and_exit = 1;
+	reset_subtitle();
 	dialog_clear();
 	if (conf_get_changed())
 		res = dialog_yesno(NULL,
-- 
1.7.10.4


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature
  2013-04-16  9:12     ` Michal Marek
@ 2013-04-16 16:38       ` Yann E. MORIN
  0 siblings, 0 replies; 9+ messages in thread
From: Yann E. MORIN @ 2013-04-16 16:38 UTC (permalink / raw)
  To: Michal Marek
  Cc: Benjamin Poirier, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

Michal, All,

On Tue, Apr 16, 2013 at 11:12:41AM +0200, Michal Marek wrote:
> > On 15.4.2013 23:54, Yann E. MORIN wrote:
> >> So, unless Michal really wants to pull this one and push it to Linus
> >> before he cuts v3.9 final, I'll merge this later in my -for-next branch.
> BTW, in you are going to rebase the commit, it would be good idea to add
> Cc: <stable@vger.kernel.org> to the changelog.

Yes sure.

Regards,
Yann E. MORIN.

-- 
.-----------------.--------------------.------------------.--------------------.
|  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
| +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
| +33 223 225 172 `------------.-------:  X  AGAINST      |  \e/  There is no  |
| http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
'------------------------------^-------^------------------^--------------------'

^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH v3] menuconfig: Add "breadcrumbs" navigation aid
  2013-04-16 14:07     ` [PATCH v3] " Benjamin Poirier
@ 2013-04-16 17:20       ` Yann E. MORIN
  0 siblings, 0 replies; 9+ messages in thread
From: Yann E. MORIN @ 2013-04-16 17:20 UTC (permalink / raw)
  To: Benjamin Poirier
  Cc: Michal Marek, Wang YanQing, Dirk Gouders, Paul Gortmaker,
	linux-kbuild, linux-kernel

Benjamin, All,

On Tue, Apr 16, 2013 at 10:07:23AM -0400, Benjamin Poirier wrote:
> Displays a trail of the menu entries used to get to the current menu.
> 
> Signed-off-by: Benjamin Poirier <bpoirier@suse.de>
> Tested-by: "Yann E. MORIN" <yann.morin.1998@free.fr>
> [yann.morin.1998@free.fr: small, trivial code re-ordering]
> Signed-off-by: "Yann E. MORIN" <yann.morin.1998@free.fr>
> ---
> 
> Indeed Yann, we can even remove one wmove() and one level of indentation in
> dialog_clear().
> 
> I'm not sure who's pulling from who and where patches are going,

It would be me aggregating all kconfig-related changes in my repo during
the devel phase, and then sending Michal a pull-request slightly before
each merge window (which should be real-soon-now...).

> but this would supersede what's in yem-kconfig-for-next now.

OK, I've reintegrated this here. Thank you!

Regards,
Yann E. MORIN.

-- 
.-----------------.--------------------.------------------.--------------------.
|  Yann E. MORIN  | Real-Time Embedded | /"\ ASCII RIBBON | Erics' conspiracy: |
| +33 662 376 056 | Software  Designer | \ / CAMPAIGN     |  ___               |
| +33 223 225 172 `------------.-------:  X  AGAINST      |  \e/  There is no  |
| http://ymorin.is-a-geek.org/ | _/*\_ | / \ HTML MAIL    |   v   conspiracy.  |
'------------------------------^-------^------------------^--------------------'

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2013-04-16 17:20 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2013-04-15 14:13 [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature Benjamin Poirier
2013-04-15 14:13 ` [PATCH 2/2] menuconfig: Add "breadcrumbs" navigation aid Benjamin Poirier
2013-04-15 21:39   ` Yann E. MORIN
2013-04-16 14:07     ` [PATCH v3] " Benjamin Poirier
2013-04-16 17:20       ` Yann E. MORIN
2013-04-15 21:54 ` [PATCH 1/2] menuconfig: Fix memory leak introduced by jump keys feature Yann E. MORIN
2013-04-16  8:21   ` Michal Marek
2013-04-16  9:12     ` Michal Marek
2013-04-16 16:38       ` Yann E. MORIN

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.