* [PATCH 1/2] add git-quote: shell and C quoting tool
@ 2006-07-16 22:27 Alex Riesen
2006-07-24 5:49 ` Junio C Hamano
0 siblings, 1 reply; 3+ messages in thread
From: Alex Riesen @ 2006-07-16 22:27 UTC (permalink / raw)
To: git; +Cc: Junio C Hamano
Signed-off-by: Alex Riesen <raa.lkml@gmail.com>
---
As git-stripspace, it may ne useful for something. As an example, the
next patch converts git-bisect.sh to use of this tool.
In case anyone asks why isn't it a standalone tool nor is it put into
git-stripspace: I don't know. Maybe it should be.
Makefile | 3 +-
builtin-quote.c | 102 +++++++++++++++++++++++++++++++++++++++++++++++++++++++
builtin.h | 2 +
git.c | 1 +
4 files changed, 107 insertions(+), 1 deletions(-)
diff --git a/Makefile b/Makefile
index 01fb9cf..9fcbf3b 100644
--- a/Makefile
+++ b/Makefile
@@ -234,7 +234,8 @@ BUILTIN_OBJS = \
builtin-apply.o builtin-show-branch.o builtin-diff-files.o \
builtin-diff-index.o builtin-diff-stages.o builtin-diff-tree.o \
builtin-cat-file.o builtin-mailsplit.o builtin-stripspace.o \
- builtin-update-ref.o builtin-fmt-merge-msg.o builtin-prune.o
+ builtin-update-ref.o builtin-fmt-merge-msg.o builtin-prune.o \
+ builtin-quote.o
GITLIBS = $(LIB_FILE) $(XDIFF_LIB)
LIBS = $(GITLIBS) -lz
diff --git a/builtin-quote.c b/builtin-quote.c
new file mode 100644
index 0000000..cbd822d
--- /dev/null
+++ b/builtin-quote.c
@@ -0,0 +1,102 @@
+/*
+ * "git quote" builtin command
+ *
+ * DOES NOT QUOTE \0 (truncates lines at it)
+ */
+#include "cache.h"
+#include "builtin.h"
+#include "quote.h"
+
+enum {SHELL_QUOTE, C_QUOTE};
+static int style = SHELL_QUOTE,
+ use_stdin = 0;
+static const char *separator = NULL; /* default is space */
+static unsigned sep_len = 0;
+
+static const char builtin_quote_usage[] =
+"git-quote [--c] [--sep=<c-quoted> | -z] ( [--stdin] | [--] ... )";
+
+static void print_quoted(const char *text)
+{
+ switch (style)
+ {
+ case SHELL_QUOTE:
+ sq_quote_print(stdout, text);
+ break;
+ case C_QUOTE:
+ quote_c_style(text, NULL, stdout, 0);
+ break;
+ }
+ fwrite(separator, 1, sep_len, stdout);
+}
+
+int cmd_quote(int argc, const char **argv, char **envp)
+{
+ int i;
+ for (i = 1; i < argc; i++) {
+ const char *arg = argv[i];
+
+ if (arg[0] != '-')
+ break;
+ if (!strcmp(arg, "--")) {
+ i++;
+ break;
+ }
+ if (!strcmp(arg, "--stdin")) {
+ use_stdin = 1;
+ if ( !separator ) {
+ separator = "\n";
+ sep_len = 1;
+ }
+ break;
+ }
+ if (!strcmp(arg, "--c")) {
+ style = C_QUOTE;
+ continue;
+ }
+ if (!strcmp(arg, "-z")) {
+ separator = "";
+ sep_len = 1;
+ continue;
+ }
+ if (!strncmp(arg, "--sep=", 6)) {
+ const char *end;
+ char *tmp;
+ arg += 6;
+ if ('"' == *arg)
+ tmp = strdup(arg);
+ else {
+ size_t l = strlen(arg);
+ tmp = malloc(l + 3);
+ sprintf(tmp, "\"%s\"", arg);
+ }
+ separator = unquote_c_style(tmp, &end);
+ sep_len = strlen(separator);
+ /* this will leak if multiple --sep= given */
+ continue;
+ }
+ die(builtin_quote_usage);
+ }
+ if (!separator) {
+ sep_len = 1;
+ separator = "\x20";
+ }
+ if (use_stdin) {
+ size_t size = BUFSIZ;
+ char *buf = xmalloc(size);
+ int ch, pos = 0;
+ while (EOF != (ch = fgetc(stdin))) {
+ if (pos == size)
+ buf = xrealloc(buf, size <<= 1);
+ buf[pos++] = ch;
+ if ('\n' == ch) {
+ buf[--pos] = '\0';
+ pos = 0;
+ print_quoted(buf);
+ }
+ }
+ } else
+ for (; argv[i]; ++i)
+ print_quoted(argv[i]);
+ return 0;
+}
diff --git a/builtin.h b/builtin.h
index 5339d86..9bd522e 100644
--- a/builtin.h
+++ b/builtin.h
@@ -64,4 +64,6 @@ extern int mailinfo(FILE *in, FILE *out,
extern int cmd_stripspace(int argc, const char **argv, char **envp);
extern void stripspace(FILE *in, FILE *out);
+
+extern int cmd_quote(int argc, const char **argv, char **envp);
#endif
diff --git a/git.c b/git.c
index ee5a0e8..f94d25a 100644
--- a/git.c
+++ b/git.c
@@ -202,6 +202,7 @@ static void handle_internal_command(int
{ "update-ref", cmd_update_ref },
{ "fmt-merge-msg", cmd_fmt_merge_msg },
{ "prune", cmd_prune },
+ { "quote", cmd_quote },
};
int i;
--
1.4.1.gb944
^ permalink raw reply related [flat|nested] 3+ messages in thread
* Re: [PATCH 1/2] add git-quote: shell and C quoting tool
2006-07-16 22:27 [PATCH 1/2] add git-quote: shell and C quoting tool Alex Riesen
@ 2006-07-24 5:49 ` Junio C Hamano
2006-07-24 23:12 ` Alex Riesen
0 siblings, 1 reply; 3+ messages in thread
From: Junio C Hamano @ 2006-07-24 5:49 UTC (permalink / raw)
To: Alex Riesen; +Cc: git
fork0@t-online.de (Alex Riesen) writes:
> In case anyone asks why isn't it a standalone tool nor is it put into
> git-stripspace: I don't know. Maybe it should be.
This organization is fine by me.
* unquote?
* doc?
> +enum {SHELL_QUOTE, C_QUOTE};
> +static int style = SHELL_QUOTE,
> + use_stdin = 0;
Shouldn't style be of type which is that unnamed enum?
> +static const char *separator = NULL; /* default is space */
> +static unsigned sep_len = 0;
It is not clear if this is separator of input side or output
side (after reading the code it becomes somewhat obvious that
you are talking about output separator), and if the default is
space wouldn't it make more sense to set that here?
> +static const char builtin_quote_usage[] =
> +"git-quote [--c] [--sep=<c-quoted> | -z] ( [--stdin] | [--] ... )";
> +
> +static void print_quoted(const char *text)
> +{
> + switch (style)
> + {
> + case SHELL_QUOTE:
> + sq_quote_print(stdout, text);
> + break;
> + case C_QUOTE:
> + quote_c_style(text, NULL, stdout, 0);
> + break;
> + }
Not a big deal but aren't these going to write out things quoted
when they do not need to? To help scripts, it might be worth
adding "check if this needs quoting" interface perhaps?
> +int cmd_quote(int argc, const char **argv, char **envp)
> +{
> + int i;
> + for (i = 1; i < argc; i++) {
> + const char *arg = argv[i];
> +
> + if (arg[0] != '-')
> + break;
> + if (!strcmp(arg, "--")) {
> + i++;
> + break;
> + }
> + if (!strcmp(arg, "--stdin")) {
> + use_stdin = 1;
> + if ( !separator ) {
> + separator = "\n";
> + sep_len = 1;
> + }
> + break;
> + }
> + if (!strcmp(arg, "--c")) {
Perhaps "--c-style" with "-c" as a shorthand, (and
"--shell-style" with "-s" to complement)?
> + style = C_QUOTE;
> + continue;
> + }
> + if (!strcmp(arg, "-z")) {
> + separator = "";
> + sep_len = 1;
> + continue;
> + }
Is it plausible that somebody might want to feed you NUL
terminated sequence as input (iow you might want to give them
choice of separator on the input side)?
> + if (!strncmp(arg, "--sep=", 6)) {
Perhaps "--separator" (or "--output-separator") with whatever
shorthand is handy?
> + const char *end;
> + char *tmp;
> + arg += 6;
> + if ('"' == *arg)
> + tmp = strdup(arg);
> + else {
> + size_t l = strlen(arg);
> + tmp = malloc(l + 3);
> + sprintf(tmp, "\"%s\"", arg);
> + }
> + separator = unquote_c_style(tmp, &end);
> + sep_len = strlen(separator);
If the parameter is a malformed c-quoted string, you would dump
core here.
> + /* this will leak if multiple --sep= given */
> + continue;
> + }
> + die(builtin_quote_usage);
> + }
> + if (!separator) {
> + sep_len = 1;
> + separator = "\x20";
Any reason you needed to spell it in hex? Is this trying to
be portable to EBCDIC (or trying to prevent the code to be
ported there)? I dunno.
> + }
> + if (use_stdin) {
> + size_t size = BUFSIZ;
> + char *buf = xmalloc(size);
> + int ch, pos = 0;
> + while (EOF != (ch = fgetc(stdin))) {
> + if (pos == size)
> + buf = xrealloc(buf, size <<= 1);
> + buf[pos++] = ch;
> + if ('\n' == ch) {
> + buf[--pos] = '\0';
> + pos = 0;
> + print_quoted(buf);
> + }
> + }
Looks similar to strbuf.c::read_line() loop...
^ permalink raw reply [flat|nested] 3+ messages in thread
* Re: [PATCH 1/2] add git-quote: shell and C quoting tool
2006-07-24 5:49 ` Junio C Hamano
@ 2006-07-24 23:12 ` Alex Riesen
0 siblings, 0 replies; 3+ messages in thread
From: Alex Riesen @ 2006-07-24 23:12 UTC (permalink / raw)
To: Junio C Hamano; +Cc: git
Junio C Hamano, Mon, Jul 24, 2006 07:49:53 +0200:
> > In case anyone asks why isn't it a standalone tool nor is it put into
> > git-stripspace: I don't know. Maybe it should be.
>
> This organization is fine by me.
>
> * unquote?
Not done yet. I actually never expected it to be used for unquoting,
being naturally unquoted by bash. C-quoting was done just because it
was so simple to do. I have no idea where could that be used.
> * doc?
Done. Sorry for missing that.
> > +enum {SHELL_QUOTE, C_QUOTE};
> > +static int style = SHELL_QUOTE,
> > + use_stdin = 0;
>
> Shouldn't style be of type which is that unnamed enum?
It should. Done.
> > +static const char *separator = NULL; /* default is space */
> > +static unsigned sep_len = 0;
>
> It is not clear if this is separator of input side or output
> side (after reading the code it becomes somewhat obvious that
> you are talking about output separator), and if the default is
> space wouldn't it make more sense to set that here?
Right. It is out_separator now.
> > +static const char builtin_quote_usage[] =
> > +"git-quote [--c] [--sep=<c-quoted> | -z] ( [--stdin] | [--] ... )";
> > +
> > +static void print_quoted(const char *text)
> > +{
> > + switch (style)
> > + {
> > + case SHELL_QUOTE:
> > + sq_quote_print(stdout, text);
> > + break;
> > + case C_QUOTE:
> > + quote_c_style(text, NULL, stdout, 0);
> > + break;
> > + }
>
> Not a big deal but aren't these going to write out things quoted
> when they do not need to? To help scripts, it might be worth
> adding "check if this needs quoting" interface perhaps?
Not done yet. "--no-overquote"?
> > + if (!strcmp(arg, "--c")) {
>
> Perhaps "--c-style" with "-c" as a shorthand, (and
> "--shell-style" with "-s" to complement)?
Done. --sh-style.
> > + style = C_QUOTE;
> > + continue;
> > + }
> > + if (!strcmp(arg, "-z")) {
> > + separator = "";
> > + sep_len = 1;
> > + continue;
> > + }
>
> Is it plausible that somebody might want to feed you NUL
> terminated sequence as input (iow you might want to give them
> choice of separator on the input side)?
Done. -z sets both separators to NUL, --in-separator=<c-style> defines
by its first character the input separator. I.e.:
$ find | git quote -z --in-separator='\n'
'a'\0'b'\0''
which is not all that useful...
> > + if (!strncmp(arg, "--sep=", 6)) {
>
> Perhaps "--separator" (or "--output-separator") with whatever
> shorthand is handy?
--out-separator. No idea of a shortcut, though
> > + separator = unquote_c_style(tmp, &end);
> > + sep_len = strlen(separator);
>
> If the parameter is a malformed c-quoted string, you would dump
> core here.
Oops. Fixed.
> > + if (!separator) {
> > + sep_len = 1;
> > + separator = "\x20";
>
> Any reason you needed to spell it in hex? Is this trying to
> be portable to EBCDIC (or trying to prevent the code to be
> ported there)? I dunno.
Visibility. I have dificulty seeing spaces and tabs.
I changed it anyway, maybe that's just me.
> > + while (EOF != (ch = fgetc(stdin))) {
>
> Looks similar to strbuf.c::read_line() loop...
>
Indeed. Replaced.
I attach the updated patch here, because it is obviously is not quite
finished yet and I probably wont have enough time over the week. So
maybe someone takes over. Or it'll be taken as is, that happens too.
Signed-off-by: Alex Riesen <raa.lkml@gmail.com>
---
diff --git a/Documentation/git-quote.txt b/Documentation/git-quote.txt
new file mode 100644
index 0000000..98b2859
--- /dev/null
+++ b/Documentation/git-quote.txt
@@ -0,0 +1,70 @@
+git-quote(1)
+============
+
+NAME
+----
+git-quote - Quote given text according to Shell or C rules
+
+
+SYNOPSIS
+--------
+'git-quote' [-c] [-s] [-s] [--out-separator=<c-quoted>]
+ [--in-separator=<c-quoted>] [-z] [--] ...
+'git-quote' ... --stdin < <stream>
+
+DESCRIPTION
+-----------
+Quote the lines according to the given rules, which can be Shell backslash
+quoting (every line is enclosed in single ticks, backslash and single tick
+quoted specially) or a C quoting (use double ticks and backslash-prefixed
+symbols).
+
+The separator options are handled in the order they are given, so one
+can save some typing by giving "-z" first, and overriding input or
+output separator as needed.
+
+OPTIONS
+-------
+-c|--c-style::
+ Select C-style quoting
+
+-s|--sh-style::
+ Select Shell-style quoting. This is default.
+
+--out-separator=<c-quoted>::
+ Specify the separator between the output elements. If the separator
+ have to contain special characters, they must be quoted according
+ to C quoting rules (double ticks are not essential).
+ The ASCII space is default output separator.
+
+--in-separator=<c-quoted>::
+ Specify the separator between the input elements. Only the
+ first character of <c-quoted> is used.
+ Used only if --stdin is also given. The default is LF.
+
+-z::
+ Separate the elements on output and expect elements separated
+ on input with NUL character.
+ Used only if --stdin is also given.
+
+--stdin::
+ Specify that the elements have to be read from stdin.
+ This option ends command line parsing.
+ Also, if there were no output separator set by previous
+ --out-separator or -z, this option will set it to LF.
+
+<stream>::
+ Byte stream to act on.
+
+Author
+------
+Written by Alex Riesen <raa.lkml@gmail.com>
+
+Documentation
+--------------
+Documentation by Alex Riesen.
+
+GIT
+---
+Part of the gitlink:git[7] suite
+
diff --git a/Makefile b/Makefile
index 3e085df..4df2951 100644
--- a/Makefile
+++ b/Makefile
@@ -246,7 +246,8 @@ BUILTIN_OBJS = \
builtin-apply.o builtin-show-branch.o builtin-diff-files.o \
builtin-diff-index.o builtin-diff-stages.o builtin-diff-tree.o \
builtin-cat-file.o builtin-mailsplit.o builtin-stripspace.o \
- builtin-update-ref.o builtin-fmt-merge-msg.o builtin-prune.o
+ builtin-update-ref.o builtin-fmt-merge-msg.o builtin-prune.o \
+ builtin-quote.o
GITLIBS = $(LIB_FILE) $(XDIFF_LIB)
LIBS = $(GITLIBS) -lz
diff --git a/builtin-quote.c b/builtin-quote.c
new file mode 100644
index 0000000..d9d4b00
--- /dev/null
+++ b/builtin-quote.c
@@ -0,0 +1,123 @@
+/*
+ * "git quote" builtin command
+ *
+ * DOES NOT QUOTE \0 (truncates lines at it)
+ */
+#include "cache.h"
+#include "builtin.h"
+#include "strbuf.h"
+#include "quote.h"
+
+static enum {SHELL_QUOTE, C_QUOTE} style = SHELL_QUOTE;
+static int use_stdin = 0;
+static const char *out_separator = NULL; /* default is space */
+static unsigned out_separator_len = 0;
+
+static const char builtin_quote_usage[] =
+"git-quote [-c | -s] [--out-separator=<c-quoted> | -z] ( [--stdin] | [--] ... )";
+
+static void print_quoted(const char *text)
+{
+ switch (style)
+ {
+ case SHELL_QUOTE:
+ sq_quote_print(stdout, text);
+ break;
+ case C_QUOTE:
+ quote_c_style(text, NULL, stdout, 0);
+ break;
+ }
+ fwrite(out_separator, 1, out_separator_len, stdout);
+}
+
+static char *unquote_c_arg(const char *arg)
+{
+ const char *end;
+ char *tmp;
+ char *result;
+ if ('"' == *arg)
+ tmp = strdup(arg);
+ else {
+ size_t l = strlen(arg);
+ tmp = malloc(l + 3);
+ sprintf(tmp, "\"%s\"", arg);
+ }
+ result = unquote_c_style(tmp, &end);
+ free(tmp);
+ return result;
+}
+
+int cmd_quote(int argc, const char **argv, char **envp)
+{
+ int in_separator = '\n';
+ int i;
+ for (i = 1; i < argc; i++) {
+ const char *arg = argv[i];
+
+ if (arg[0] != '-')
+ break;
+ if (!strcmp(arg, "--")) {
+ i++;
+ break;
+ }
+ if (!strcmp(arg, "--stdin")) {
+ use_stdin = 1;
+ if ( !out_separator ) {
+ out_separator = "\n";
+ out_separator_len = 1;
+ }
+ break;
+ }
+ if (!strcmp(arg, "--c-style") || !strcmp(arg, "-c")) {
+ style = C_QUOTE;
+ continue;
+ }
+ if (!strcmp(arg, "--sh-style") || !strcmp(arg, "-s")) {
+ style = SHELL_QUOTE;
+ continue;
+ }
+ if (!strcmp(arg, "-z")) {
+ in_separator = 0;
+ out_separator = "";
+ out_separator_len = 1;
+ continue;
+ }
+ if (!strncmp(arg, "--out-separator=", 16)) {
+ arg += 16;
+ out_separator = unquote_c_arg(arg);
+ if (!out_separator)
+ die("malformed separator '%s'", arg);
+ out_separator_len = strlen(out_separator);
+ /* this will leak if multiple --sep= given */
+ continue;
+ }
+ if (!strncmp(arg, "--in-separator=", 15)) {
+ char *sep;
+ arg += 15;
+ sep = unquote_c_arg(arg);
+ if (!sep || !*sep)
+ die("malformed separator '%s'", arg);
+ in_separator = *sep;
+ free(sep);
+ continue;
+ }
+ die(builtin_quote_usage);
+ }
+ if (!out_separator) {
+ out_separator_len = 1;
+ out_separator = " ";
+ }
+ if (use_stdin) {
+ struct strbuf line;
+ strbuf_init(&line);
+
+ while (!line.eof) {
+ read_line(&line, stdin, in_separator);
+ if (line.len)
+ print_quoted(line.buf);
+ }
+ } else
+ for (; argv[i]; ++i)
+ print_quoted(argv[i]);
+ return 0;
+}
diff --git a/builtin.h b/builtin.h
index 5339d86..9bd522e 100644
--- a/builtin.h
+++ b/builtin.h
@@ -64,4 +64,6 @@ extern int mailinfo(FILE *in, FILE *out,
extern int cmd_stripspace(int argc, const char **argv, char **envp);
extern void stripspace(FILE *in, FILE *out);
+
+extern int cmd_quote(int argc, const char **argv, char **envp);
#endif
diff --git a/git.c b/git.c
index ee5a0e8..f94d25a 100644
--- a/git.c
+++ b/git.c
@@ -202,6 +202,7 @@ static void handle_internal_command(int
{ "update-ref", cmd_update_ref },
{ "fmt-merge-msg", cmd_fmt_merge_msg },
{ "prune", cmd_prune },
+ { "quote", cmd_quote },
};
int i;
^ permalink raw reply related [flat|nested] 3+ messages in thread
end of thread, other threads:[~2006-07-24 23:13 UTC | newest]
Thread overview: 3+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2006-07-16 22:27 [PATCH 1/2] add git-quote: shell and C quoting tool Alex Riesen
2006-07-24 5:49 ` Junio C Hamano
2006-07-24 23:12 ` Alex Riesen
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox