commit - cb7621af57ac2abad12fa61893d00199daebdd29
commit + 8b2b06b5122892c74e4dd58772be73ea2fd2933b
blob - 362ed324bf60c6a99a1d6f2c6ab318910bbaf212
blob + f2687041ed034ffc3566a0168819e0ec26fc5c1c
--- iri.c
+++ iri.c
}
static inline int
-remove_dot_segments(struct iri *iri)
+remove_dot_segments(struct iri *i)
{
- char *p, *q, *buf, *s;
+ char *p, *q, *buf;
ptrdiff_t bufsize;
- buf = p = q = iri->iri_path;
- bufsize = sizeof(iri->iri_path);
-
+ buf = p = q = i->iri_path;
+ bufsize = sizeof(i->iri_path);
while (*p && (q - buf < bufsize)) {
- /* A */
- if (!strncmp(p, "../", 3)) {
- p += 3;
- continue;
- }
- if (!strncmp(p, "./", 2)) {
+ if (p[0] == '/' && p[1] == '.' &&
+ (p[2] == '/' || p[2] == '\0')) {
p += 2;
- continue;
- }
- /* B */
- if (!strncmp(p, "/./", 3)) {
- *q++ = '/';
- p += 3;
- continue;
- }
- if (!strcmp(p, "/.")) {
- *q++ = '/';
- p += 2;
- break;
- }
- /* C */
- if (p[0] == '/' && p[1] == '.' && p[2] == '.' &&
+ if (*p != '/')
+ *q++ = '/';
+ } else if (p[0] == '/' && p[1] == '.' && p[2] == '.' &&
(p[3] == '/' || p[3] == '\0')) {
p += 3;
- while (q != buf && *--q != '/')
+ while (q > buf && *--q != '/')
continue;
- *q++ = '/';
- continue;
- }
- /* D */
- if (!strcmp(p, ".")) {
- p++;
- break;
- }
- if (!strcmp(p, "..")) {
- p += 2;
- break;
- }
- /* E */
- s = strchr(p + 1, '/');
- while (*p && p != s && (q - buf < bufsize))
+ if (*p != '/' && (q > buf && q[-1] != '/'))
+ *q++ = '/';
+ } else
*q++ = *p++;
}
-
- if (*p == '\0' && (q - buf < bufsize)) {
+ if ((*p == '\0') && (q - buf < bufsize)) {
*q = '\0';
return (0);
}