>From 86a868045b8f4b132222e11fe87f5296a63eb544 Mon Sep 17 00:00:00 2001
From: Tamas TEVESZ <[email protected]>
Date: Fri, 8 Oct 2010 23:22:25 +0200
Subject: [PATCH] wmmenugen: Finish Wmconfig parser, touch up PropList writer
As far as i can tell this finishes the Wmconfig parser (all bits we are
interested in/can use are parsed and converted).
The PropList writer gained ability to properly react to and handle various
flags passed by parsers.
Signed-off-by: Tamas TEVESZ <[email protected]>
---
util/wmmenugen.c | 46 ++++++++++++++++++----
util/wmmenugen.h | 6 ++-
util/wmmenugen_parse_wmconfig.c | 80 ++++++++++++++++++++++++++++++++------
util/wmmenugen_parse_xdg.c | 1 +
4 files changed, 111 insertions(+), 22 deletions(-)
diff --git a/util/wmmenugen.c b/util/wmmenugen.c
index 030e7ba..cbb55d8 100644
--- a/util/wmmenugen.c
+++ b/util/wmmenugen.c
@@ -46,12 +46,12 @@ static WMTreeNode *findPositionInMenu(char *submenu);
static void (*parse)(const char *file, void
(*addWMMenuEntryCallback)(WMMenuEntry *aEntry));
static WMArray *plMenuNodes;
+char *terminal;
extern char *__progname;
int main(int argc, char **argv)
{
- char *terminal;
struct stat st;
int i;
int *previousDepth;
@@ -91,7 +91,7 @@ int main(int argc, char **argv)
#endif
parse = &parse_wmconfig;
} else {
- fprintf(stderr, "%s: Unknown parser \"%s\"\n",
__progname, argv[i] + 1);
+ fprintf(stderr, "%s: Unknown parser \"%s\"\n",
__progname, argv[i] + 8);
}
continue;
}
@@ -210,12 +210,42 @@ static void assemblePLMenuFunc(WMTreeNode *aNode, void
*data)
WMAddToArray(plMenuNodes,
WMCreatePLArray(WMCreatePLString(wm->Name), NULL));
} else { /* new menu item */
pl = WMPopFromArray(plMenuNodes);
- WMAddToPLArray(pl, WMCreatePLArray(
- WMCreatePLString(wm->Name),
- WMCreatePLString(wm->Flags & F_RESTART ? "RESTART" :
"SHEXEC"),
- WMCreatePLString(wm->CmdLine),
- NULL)
- );
+ if (wm->Flags & F_RESTART_OTHER) { /* RESTART, somewm */
+ char buf[1024];
+ memset(buf, 0, sizeof(buf));
+ snprintf(buf, sizeof(buf), "%s %s", _("Restart"),
wm->Name);
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(buf),
+ WMCreatePLString("RESTART"),
+ WMCreatePLString(wm->CmdLine),
+ NULL)
+ );
+ } else if (wm->Flags & F_RESTART_SELF) {/* RESTART */
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(_("Restart Window Maker")),
+ WMCreatePLString("RESTART"),
+ NULL)
+ );
+ } else if (wm->Flags & F_QUIT) { /* EXIT */
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(_("Exit Window Maker")),
+ WMCreatePLString("EXIT"),
+ NULL)
+ );
+ } else { /* plain simple command
*/
+ char buf[1024];
+ memset(buf, 0, sizeof(buf));
+ if (wm->Flags & F_TERMINAL) /* XXX: quoting! */
+ snprintf(buf, sizeof(buf), "%s -e \"%s\"",
terminal, wm->CmdLine);
+ else
+ snprintf(buf, sizeof(buf), "%s", wm->CmdLine);
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(wm->Name),
+ WMCreatePLString("SHEXEC"),
+ WMCreatePLString(buf),
+ NULL)
+ );
+ }
WMAddToArray(plMenuNodes, pl);
}
diff --git a/util/wmmenugen.h b/util/wmmenugen.h
index 8b75ebc..a1d7ea5 100644
--- a/util/wmmenugen.h
+++ b/util/wmmenugen.h
@@ -20,9 +20,13 @@
#include <WINGs/WUtil.h>
+#include "../src/wconfig.h"
+
/* flags attached to a particular WMMenuEntry */
#define F_TERMINAL (1 << 0)
-#define F_RESTART (1 << 1)
+#define F_RESTART_SELF (1 << 1)
+#define F_RESTART_OTHER (1 << 2)
+#define F_QUIT (1 << 3)
/* a representation of a Window Maker menu entry. all menus are
diff --git a/util/wmmenugen_parse_wmconfig.c b/util/wmmenugen_parse_wmconfig.c
index 6c53c9f..a03e62e 100644
--- a/util/wmmenugen_parse_wmconfig.c
+++ b/util/wmmenugen_parse_wmconfig.c
@@ -35,11 +35,13 @@ typedef struct {
char *Name;
char *Exec;
char *Category;
+ char *Restart;
int Flags;
} WMConfigMenuEntry;
static Bool wmc_to_wm(WMConfigMenuEntry **wmc, WMMenuEntry **wm);
static void parse_wmconfig_line(char **label, char **key, char **value, char
*line);
+static void init_wmconfig_storage(WMConfigMenuEntry **wmc);
void parse_wmconfig(const char *file, void
(*addWMMenuEntryCallback)(WMMenuEntry *aEntry))
{
@@ -63,6 +65,7 @@ void parse_wmconfig(const char *file, void
(*addWMMenuEntryCallback)(WMMenuEntry
wmc->Name = NULL;
wmc->Exec = NULL;
wmc->Category = NULL;
+ wmc->Restart = NULL;
wmc->Flags = 0;
wm = (WMMenuEntry *)wmalloc(sizeof(WMMenuEntry));
@@ -94,17 +97,11 @@ void parse_wmconfig(const char *file, void
(*addWMMenuEntryCallback)(WMMenuEntry
lastlabel = wstrdup(label);
if (strcmp(lastlabel, label) != 0) {
- if (wmc->Name && wmc->Exec && wmc->Category &&
- wmc_to_wm(&wmc, &wm))
+ if (wmc_to_wm(&wmc, &wm)) {
(*addWMMenuEntryCallback)(wm);
+ init_wmconfig_storage(&wmc);
+ }
- wfree(wmc->Name);
- wmc->Name = NULL;
- wfree(wmc->Exec);
- wmc->Exec = NULL;
- wfree(wmc->Category);
- wmc->Category = NULL;
- wmc->Flags = 0;
wfree(lastlabel);
lastlabel = wstrdup(label);
}
@@ -117,7 +114,7 @@ void parse_wmconfig(const char *file, void
(*addWMMenuEntryCallback)(WMMenuEntry
else if (strcmp(key, "group") == 0)
wmc->Category = value;
else if (strcmp(key, "restart") == 0)
- wmc->Flags |= F_RESTART;
+ wmc->Restart = value;
else if (strcmp(key, "terminal") == 0)
wmc->Flags |= F_TERMINAL;
}
@@ -126,9 +123,10 @@ void parse_wmconfig(const char *file, void
(*addWMMenuEntryCallback)(WMMenuEntry
fclose(fp);
- if (wmc_to_wm(&wmc, &wm))
+ if (wmc_to_wm(&wmc, &wm)) {
(*addWMMenuEntryCallback)(wm);
-
+ init_wmconfig_storage(&wmc);
+ }
}
/* get a line allocating label, key and value as necessary */
@@ -181,11 +179,52 @@ static void parse_wmconfig_line(char **label, char **key,
char **value, char *li
*value = wstrndup(p + kstart, kend - kstart);
}
+/* normalize and convert one wmconfig-format entry to wm format */
static Bool wmc_to_wm(WMConfigMenuEntry **wmc, WMMenuEntry **wm)
{
- if (!*wmc || !(*wmc)->Name)
+ char *p;
+ size_t slen;
+
+ /* only Exec is mandatory */
+ if (!*wmc || !(*wmc)->Exec || !*(*wmc)->Exec)
return False;
+ /* normalize Exec: wmconfig tends to stuck an ampersand
+ * at the end of everything, which we don't need */
+ slen = strlen((*wmc)->Exec) - 1;
+ p = (*wmc)->Exec;
+ while (slen > 0 && (isspace(*(p + slen)) || *(p + slen) == '&'))
+ *(p + slen--) = '\0';
+
+ /* if there's no Name, use the first word of Exec; still better
+ * than nothing. i realize it's highly arguable whether `xterm' from
+ * `xterm -e "ssh dev push-to-prod"' is helpful or not, but since
+ * the alternative is to completely lose the entry, i opt for this.
+ * you could just fix the descriptor file to have a label <G> */
+ if (!(*wmc)->Name) {
+ (*wmc)->Name = wstrdup((*wmc)->Exec);
+ p = strchr((*wmc)->Name, ' ');
+ if (p)
+ *p = '\0';
+ }
+
+ /* if there's no Category, use "Applications"; apparently "no category"
+ * can manifest both as no `group' descriptor at all, or a group
+ * descriptor of "" */
+ if (!(*wmc)->Category || !*(*wmc)->Category)
+ (*wmc)->Category = wstrdup("Applications");
+
+ /* the `restart' type is used for restart, restart other
+ * wm and quit current wm too. separate these cases. */
+ if ((*wmc)->Restart) {
+ if (strcmp((*wmc)->Restart, "restart") == 0)
+ (*wmc)->Flags |= F_RESTART_SELF;
+ else if (strcmp((*wmc)->Restart, "quit") == 0)
+ (*wmc)->Flags |= F_QUIT;
+ else
+ (*wmc)->Flags |= F_RESTART_OTHER;
+ }
+
(*wm)->Name = (*wmc)->Name;
(*wm)->CmdLine = (*wmc)->Exec;
(*wm)->SubMenu = (*wmc)->Category;
@@ -193,3 +232,18 @@ static Bool wmc_to_wm(WMConfigMenuEntry **wmc, WMMenuEntry
**wm)
return True;
}
+
+static void init_wmconfig_storage(WMConfigMenuEntry **wmc)
+{
+ if ((*wmc)->Category)
+ wfree((*wmc)->Category);
+ (*wmc)->Category = NULL;
+ if ((*wmc)->Name)
+ wfree((*wmc)->Name);
+ (*wmc)->Name = NULL;
+ if ((*wmc)->Restart)
+ wfree((*wmc)->Restart);
+ (*wmc)->Restart = NULL;
+ (*wmc)->Flags = 0;
+}
+
diff --git a/util/wmmenugen_parse_xdg.c b/util/wmmenugen_parse_xdg.c
index 0ee23f8..e19c0a2 100644
--- a/util/wmmenugen_parse_xdg.c
+++ b/util/wmmenugen_parse_xdg.c
@@ -467,3 +467,4 @@ static Bool compare_matchlevel(int *current_level, const
char *found_locale)
return False;
}
+
--
1.7.0.4
--
[-]
mkdir /nonexistentFrom 86a868045b8f4b132222e11fe87f5296a63eb544 Mon Sep 17 00:00:00 2001
From: Tamas TEVESZ <[email protected]>
Date: Fri, 8 Oct 2010 23:22:25 +0200
Subject: [PATCH] wmmenugen: Finish Wmconfig parser, touch up PropList writer
As far as i can tell this finishes the Wmconfig parser (all bits we are
interested in/can use are parsed and converted).
The PropList writer gained ability to properly react to and handle various
flags passed by parsers.
Signed-off-by: Tamas TEVESZ <[email protected]>
---
util/wmmenugen.c | 46 ++++++++++++++++++----
util/wmmenugen.h | 6 ++-
util/wmmenugen_parse_wmconfig.c | 80 ++++++++++++++++++++++++++++++++------
util/wmmenugen_parse_xdg.c | 1 +
4 files changed, 111 insertions(+), 22 deletions(-)
diff --git a/util/wmmenugen.c b/util/wmmenugen.c
index 030e7ba..cbb55d8 100644
--- a/util/wmmenugen.c
+++ b/util/wmmenugen.c
@@ -46,12 +46,12 @@ static WMTreeNode *findPositionInMenu(char *submenu);
static void (*parse)(const char *file, void (*addWMMenuEntryCallback)(WMMenuEntry *aEntry));
static WMArray *plMenuNodes;
+char *terminal;
extern char *__progname;
int main(int argc, char **argv)
{
- char *terminal;
struct stat st;
int i;
int *previousDepth;
@@ -91,7 +91,7 @@ int main(int argc, char **argv)
#endif
parse = &parse_wmconfig;
} else {
- fprintf(stderr, "%s: Unknown parser \"%s\"\n", __progname, argv[i] + 1);
+ fprintf(stderr, "%s: Unknown parser \"%s\"\n", __progname, argv[i] + 8);
}
continue;
}
@@ -210,12 +210,42 @@ static void assemblePLMenuFunc(WMTreeNode *aNode, void *data)
WMAddToArray(plMenuNodes, WMCreatePLArray(WMCreatePLString(wm->Name), NULL));
} else { /* new menu item */
pl = WMPopFromArray(plMenuNodes);
- WMAddToPLArray(pl, WMCreatePLArray(
- WMCreatePLString(wm->Name),
- WMCreatePLString(wm->Flags & F_RESTART ? "RESTART" : "SHEXEC"),
- WMCreatePLString(wm->CmdLine),
- NULL)
- );
+ if (wm->Flags & F_RESTART_OTHER) { /* RESTART, somewm */
+ char buf[1024];
+ memset(buf, 0, sizeof(buf));
+ snprintf(buf, sizeof(buf), "%s %s", _("Restart"), wm->Name);
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(buf),
+ WMCreatePLString("RESTART"),
+ WMCreatePLString(wm->CmdLine),
+ NULL)
+ );
+ } else if (wm->Flags & F_RESTART_SELF) {/* RESTART */
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(_("Restart Window Maker")),
+ WMCreatePLString("RESTART"),
+ NULL)
+ );
+ } else if (wm->Flags & F_QUIT) { /* EXIT */
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(_("Exit Window Maker")),
+ WMCreatePLString("EXIT"),
+ NULL)
+ );
+ } else { /* plain simple command */
+ char buf[1024];
+ memset(buf, 0, sizeof(buf));
+ if (wm->Flags & F_TERMINAL) /* XXX: quoting! */
+ snprintf(buf, sizeof(buf), "%s -e \"%s\"", terminal, wm->CmdLine);
+ else
+ snprintf(buf, sizeof(buf), "%s", wm->CmdLine);
+ WMAddToPLArray(pl, WMCreatePLArray(
+ WMCreatePLString(wm->Name),
+ WMCreatePLString("SHEXEC"),
+ WMCreatePLString(buf),
+ NULL)
+ );
+ }
WMAddToArray(plMenuNodes, pl);
}
diff --git a/util/wmmenugen.h b/util/wmmenugen.h
index 8b75ebc..a1d7ea5 100644
--- a/util/wmmenugen.h
+++ b/util/wmmenugen.h
@@ -20,9 +20,13 @@
#include <WINGs/WUtil.h>
+#include "../src/wconfig.h"
+
/* flags attached to a particular WMMenuEntry */
#define F_TERMINAL (1 << 0)
-#define F_RESTART (1 << 1)
+#define F_RESTART_SELF (1 << 1)
+#define F_RESTART_OTHER (1 << 2)
+#define F_QUIT (1 << 3)
/* a representation of a Window Maker menu entry. all menus are
diff --git a/util/wmmenugen_parse_wmconfig.c b/util/wmmenugen_parse_wmconfig.c
index 6c53c9f..a03e62e 100644
--- a/util/wmmenugen_parse_wmconfig.c
+++ b/util/wmmenugen_parse_wmconfig.c
@@ -35,11 +35,13 @@ typedef struct {
char *Name;
char *Exec;
char *Category;
+ char *Restart;
int Flags;
} WMConfigMenuEntry;
static Bool wmc_to_wm(WMConfigMenuEntry **wmc, WMMenuEntry **wm);
static void parse_wmconfig_line(char **label, char **key, char **value, char *line);
+static void init_wmconfig_storage(WMConfigMenuEntry **wmc);
void parse_wmconfig(const char *file, void (*addWMMenuEntryCallback)(WMMenuEntry *aEntry))
{
@@ -63,6 +65,7 @@ void parse_wmconfig(const char *file, void (*addWMMenuEntryCallback)(WMMenuEntry
wmc->Name = NULL;
wmc->Exec = NULL;
wmc->Category = NULL;
+ wmc->Restart = NULL;
wmc->Flags = 0;
wm = (WMMenuEntry *)wmalloc(sizeof(WMMenuEntry));
@@ -94,17 +97,11 @@ void parse_wmconfig(const char *file, void (*addWMMenuEntryCallback)(WMMenuEntry
lastlabel = wstrdup(label);
if (strcmp(lastlabel, label) != 0) {
- if (wmc->Name && wmc->Exec && wmc->Category &&
- wmc_to_wm(&wmc, &wm))
+ if (wmc_to_wm(&wmc, &wm)) {
(*addWMMenuEntryCallback)(wm);
+ init_wmconfig_storage(&wmc);
+ }
- wfree(wmc->Name);
- wmc->Name = NULL;
- wfree(wmc->Exec);
- wmc->Exec = NULL;
- wfree(wmc->Category);
- wmc->Category = NULL;
- wmc->Flags = 0;
wfree(lastlabel);
lastlabel = wstrdup(label);
}
@@ -117,7 +114,7 @@ void parse_wmconfig(const char *file, void (*addWMMenuEntryCallback)(WMMenuEntry
else if (strcmp(key, "group") == 0)
wmc->Category = value;
else if (strcmp(key, "restart") == 0)
- wmc->Flags |= F_RESTART;
+ wmc->Restart = value;
else if (strcmp(key, "terminal") == 0)
wmc->Flags |= F_TERMINAL;
}
@@ -126,9 +123,10 @@ void parse_wmconfig(const char *file, void (*addWMMenuEntryCallback)(WMMenuEntry
fclose(fp);
- if (wmc_to_wm(&wmc, &wm))
+ if (wmc_to_wm(&wmc, &wm)) {
(*addWMMenuEntryCallback)(wm);
-
+ init_wmconfig_storage(&wmc);
+ }
}
/* get a line allocating label, key and value as necessary */
@@ -181,11 +179,52 @@ static void parse_wmconfig_line(char **label, char **key, char **value, char *li
*value = wstrndup(p + kstart, kend - kstart);
}
+/* normalize and convert one wmconfig-format entry to wm format */
static Bool wmc_to_wm(WMConfigMenuEntry **wmc, WMMenuEntry **wm)
{
- if (!*wmc || !(*wmc)->Name)
+ char *p;
+ size_t slen;
+
+ /* only Exec is mandatory */
+ if (!*wmc || !(*wmc)->Exec || !*(*wmc)->Exec)
return False;
+ /* normalize Exec: wmconfig tends to stuck an ampersand
+ * at the end of everything, which we don't need */
+ slen = strlen((*wmc)->Exec) - 1;
+ p = (*wmc)->Exec;
+ while (slen > 0 && (isspace(*(p + slen)) || *(p + slen) == '&'))
+ *(p + slen--) = '\0';
+
+ /* if there's no Name, use the first word of Exec; still better
+ * than nothing. i realize it's highly arguable whether `xterm' from
+ * `xterm -e "ssh dev push-to-prod"' is helpful or not, but since
+ * the alternative is to completely lose the entry, i opt for this.
+ * you could just fix the descriptor file to have a label <G> */
+ if (!(*wmc)->Name) {
+ (*wmc)->Name = wstrdup((*wmc)->Exec);
+ p = strchr((*wmc)->Name, ' ');
+ if (p)
+ *p = '\0';
+ }
+
+ /* if there's no Category, use "Applications"; apparently "no category"
+ * can manifest both as no `group' descriptor at all, or a group
+ * descriptor of "" */
+ if (!(*wmc)->Category || !*(*wmc)->Category)
+ (*wmc)->Category = wstrdup("Applications");
+
+ /* the `restart' type is used for restart, restart other
+ * wm and quit current wm too. separate these cases. */
+ if ((*wmc)->Restart) {
+ if (strcmp((*wmc)->Restart, "restart") == 0)
+ (*wmc)->Flags |= F_RESTART_SELF;
+ else if (strcmp((*wmc)->Restart, "quit") == 0)
+ (*wmc)->Flags |= F_QUIT;
+ else
+ (*wmc)->Flags |= F_RESTART_OTHER;
+ }
+
(*wm)->Name = (*wmc)->Name;
(*wm)->CmdLine = (*wmc)->Exec;
(*wm)->SubMenu = (*wmc)->Category;
@@ -193,3 +232,18 @@ static Bool wmc_to_wm(WMConfigMenuEntry **wmc, WMMenuEntry **wm)
return True;
}
+
+static void init_wmconfig_storage(WMConfigMenuEntry **wmc)
+{
+ if ((*wmc)->Category)
+ wfree((*wmc)->Category);
+ (*wmc)->Category = NULL;
+ if ((*wmc)->Name)
+ wfree((*wmc)->Name);
+ (*wmc)->Name = NULL;
+ if ((*wmc)->Restart)
+ wfree((*wmc)->Restart);
+ (*wmc)->Restart = NULL;
+ (*wmc)->Flags = 0;
+}
+
diff --git a/util/wmmenugen_parse_xdg.c b/util/wmmenugen_parse_xdg.c
index 0ee23f8..e19c0a2 100644
--- a/util/wmmenugen_parse_xdg.c
+++ b/util/wmmenugen_parse_xdg.c
@@ -467,3 +467,4 @@ static Bool compare_matchlevel(int *current_level, const char *found_locale)
return False;
}
+
--
1.7.0.4