tpercent encode characters in path names - stagit - [fork] customized build of … | |
git clone git://src.adamsgaard.dk/stagit | |
Log | |
Files | |
Refs | |
README | |
LICENSE | |
--- | |
commit 5b88f7cee4ac2e79072fd7c31e5dafbdfd527faa | |
parent 937dd3bc3e623be46b4795afc71aa28134919911 | |
Author: Hiltjo Posthuma <[email protected]> | |
Date: Tue, 16 Nov 2021 14:16:46 +0100 | |
percent encode characters in path names | |
Paths could contain characters like # (fragment), '?', control-characters, etc. | |
Diffstat: | |
M stagit-index.c | 24 +++++++++++++++++++++++- | |
M stagit.c | 32 ++++++++++++++++++++++++++---… | |
2 files changed, 50 insertions(+), 6 deletions(-) | |
--- | |
diff --git a/stagit-index.c b/stagit-index.c | |
t@@ -30,6 +30,28 @@ joinpath(char *buf, size_t bufsiz, const char *path, const … | |
path, path[0] && path[strlen(path) - 1] != '/' ? "/" :… | |
} | |
+/* Percent-encode, see RFC3986 section 2.1. */ | |
+void | |
+percentencode(FILE *fp, const char *s, size_t len) | |
+{ | |
+ static char tab[] = "0123456789ABCDEF"; | |
+ unsigned char uc; | |
+ size_t i; | |
+ | |
+ for (i = 0; *s && i < len; s++, i++) { | |
+ uc = *s; | |
+ /* NOTE: do not encode '/' for paths */ | |
+ if (uc < '/' || uc >= 127 || (uc >= ':' && uc <= '@') || | |
+ uc == '[' || uc == ']') { | |
+ putc('%', fp); | |
+ putc(tab[(uc >> 4) & 0x0f], fp); | |
+ putc(tab[uc & 0x0f], fp); | |
+ } else { | |
+ putc(uc, fp); | |
+ } | |
+ } | |
+} | |
+ | |
/* Escape characters below as HTML 2.0 / XML 1.0. */ | |
void | |
xmlencode(FILE *fp, const char *s, size_t len) | |
t@@ -123,7 +145,7 @@ writelog(FILE *fp) | |
*p = '\0'; | |
fputs("<tr><td><a href=\"", fp); | |
- xmlencode(fp, stripped_name, strlen(stripped_name)); | |
+ percentencode(fp, stripped_name, strlen(stripped_name)); | |
fputs("/log.html\">", fp); | |
xmlencode(fp, stripped_name, strlen(stripped_name)); | |
fputs("</a></td><td>", fp); | |
diff --git a/stagit.c b/stagit.c | |
t@@ -362,6 +362,28 @@ efopen(const char *filename, const char *flags) | |
return fp; | |
} | |
+/* Percent-encode, see RFC3986 section 2.1. */ | |
+void | |
+percentencode(FILE *fp, const char *s, size_t len) | |
+{ | |
+ static char tab[] = "0123456789ABCDEF"; | |
+ unsigned char uc; | |
+ size_t i; | |
+ | |
+ for (i = 0; *s && i < len; s++, i++) { | |
+ uc = *s; | |
+ /* NOTE: do not encode '/' for paths */ | |
+ if (uc < '/' || uc >= 127 || (uc >= ':' && uc <= '@') || | |
+ uc == '[' || uc == ']') { | |
+ putc('%', fp); | |
+ putc(tab[(uc >> 4) & 0x0f], fp); | |
+ putc(tab[uc & 0x0f], fp); | |
+ } else { | |
+ putc(uc, fp); | |
+ } | |
+ } | |
+} | |
+ | |
/* Escape characters below as HTML 2.0 / XML 1.0. */ | |
void | |
xmlencode(FILE *fp, const char *s, size_t len) | |
t@@ -500,7 +522,7 @@ writeheader(FILE *fp, const char *title) | |
fputs("</span></td></tr>", fp); | |
if (cloneurl[0]) { | |
fputs("<tr class=\"url\"><td></td><td>git clone <a href=\"", f… | |
- xmlencode(fp, cloneurl, strlen(cloneurl)); | |
+ xmlencode(fp, cloneurl, strlen(cloneurl)); /* not percent-enco… | |
fputs("\">", fp); | |
xmlencode(fp, cloneurl, strlen(cloneurl)); | |
fputs("</a>", fp); | |
t@@ -583,7 +605,7 @@ printcommit(FILE *fp, struct commitinfo *ci) | |
fputs("<b>Author:</b> ", fp); | |
xmlencode(fp, ci->author->name, strlen(ci->author->name)); | |
fputs(" <<a href=\"mailto:", fp); | |
- xmlencode(fp, ci->author->email, strlen(ci->author->email)); | |
+ xmlencode(fp, ci->author->email, strlen(ci->author->email)); /… | |
fputs("\">", fp); | |
xmlencode(fp, ci->author->email, strlen(ci->author->email)); | |
fputs("</a>>\n<b>Date:</b> ", fp); | |
t@@ -678,11 +700,11 @@ printshowfile(FILE *fp, struct commitinfo *ci) | |
patch = ci->deltas[i]->patch; | |
delta = git_patch_get_delta(patch); | |
fprintf(fp, "<b>diff --git a/<a id=\"h%zu\" href=\"%sfile/", i… | |
- xmlencode(fp, delta->old_file.path, strlen(delta->old_file.pat… | |
+ percentencode(fp, delta->old_file.path, strlen(delta->old_file… | |
fputs(".html\">", fp); | |
xmlencode(fp, delta->old_file.path, strlen(delta->old_file.pat… | |
fprintf(fp, "</a> b/<a href=\"%sfile/", relpath); | |
- xmlencode(fp, delta->new_file.path, strlen(delta->new_file.pat… | |
+ percentencode(fp, delta->new_file.path, strlen(delta->new_file… | |
fprintf(fp, ".html\">"); | |
xmlencode(fp, delta->new_file.path, strlen(delta->new_file.pat… | |
fprintf(fp, "</a></b>\n"); | |
t@@ -1050,7 +1072,7 @@ writefilestree(FILE *fp, git_tree *tree, const char *pat… | |
fputs("<tr><td>", fp); | |
fputs(filemode(git_tree_entry_filemode(entry)), fp); | |
fprintf(fp, "</td><td><a href=\"%s", relpath); | |
- xmlencode(fp, filepath, strlen(filepath)); | |
+ percentencode(fp, filepath, strlen(filepath)); | |
fputs("\">", fp); | |
xmlencode(fp, entrypath, strlen(entrypath)); | |
fputs("</a></td><td class=\"num\" align=\"right\">", f… |