diff options
author | Taru Karttunen <taruti@taruti.net> | 2011-03-30 15:46:40 +0300 |
---|---|---|
committer | Taru Karttunen <taruti@taruti.net> | 2011-03-30 15:46:40 +0300 |
commit | e5888a1ffdae813d7575f5fb02275c6bb07e5199 (patch) | |
tree | d8d51eac403f07814b9e936eed0c9a79195e2450 /sys/src/cmd/abaco/urls.c |
Import sources from 2011-03-30 iso image
Diffstat (limited to 'sys/src/cmd/abaco/urls.c')
-rwxr-xr-x | sys/src/cmd/abaco/urls.c | 230 |
1 files changed, 230 insertions, 0 deletions
diff --git a/sys/src/cmd/abaco/urls.c b/sys/src/cmd/abaco/urls.c new file mode 100755 index 000000000..9386cb164 --- /dev/null +++ b/sys/src/cmd/abaco/urls.c @@ -0,0 +1,230 @@ +#include <u.h> +#include <libc.h> +#include <draw.h> +#include <memdraw.h> +#include <thread.h> +#include <cursor.h> +#include <mouse.h> +#include <keyboard.h> +#include <frame.h> +#include <plumb.h> +#include <html.h> +#include "dat.h" +#include "fns.h" + +Url * +urlalloc(Runestr *src, Runestr *post, int m) +{ + Url *u; + + u = emalloc(sizeof(Url)); + copyrunestr(&u->src, src); + if(m==HPost) + copyrunestr(&u->post, post); + u->method = m; + incref(u); + return u; +} + +void +urlfree(Url *u) +{ + if(u && decref(u)==0){ + closerunestr(&u->src); + closerunestr(&u->act); + closerunestr(&u->post); + closerunestr(&u->ctype); + free(u); + } +} + +Url * +urldup(Url *a) +{ + Url *b; + + b = emalloc(sizeof(Url)); + b->method = a->method; + copyrunestr(&b->src, &a->src); + copyrunestr(&b->act, &a->act); + copyrunestr(&b->post, &a->post); + copyrunestr(&b->ctype, &a->ctype); + return b; +} + +static +Runestr +getattr(int conn, char *s) +{ + char buf[BUFSIZE]; + int fd, n; + + snprint(buf, sizeof(buf), "%s/%d/%s", webmountpt, conn, s); + fd = open(buf, OREAD); + if(fd < 0) + error("can't open attr file"); + + n = read(fd, buf, sizeof(buf)-1); + if(n < 0) + error("can't read"); + + close(fd); + buf[n] = '\0'; + return (Runestr){runesmprint("%s", buf), n}; +} + +int +urlopen(Url *u) +{ + char buf[BUFSIZE]; + int cfd, fd, conn, n; + + snprint(buf, sizeof(buf), "%s/clone", webmountpt); + cfd = open(buf, ORDWR); + if(cfd < 0) + error("can't open clone file"); + + n = read(cfd, buf, sizeof(buf)-1); + if(n <= 0) + error("reading clone"); + + buf[n] = '\0'; + conn = atoi(buf); + + snprint(buf, sizeof(buf), "url %S", u->src.r); + if(write(cfd, buf, strlen(buf)) < 0){ +// fprint(2, "write: %s: %r\n", buf); + Err: + close(cfd); + return -1; + } + if(u->method==HPost && u->post.r != nil){ + snprint(buf, sizeof(buf), "%s/%d/postbody", webmountpt, conn); + fd = open(buf, OWRITE); + if(fd < 0){ +// fprint(2, "urlopen: bad query: %s: %r\n", buf); + goto Err; + } + snprint(buf, sizeof(buf), "%S", u->post.r); + if(write(fd, buf, strlen(buf)) < 0) + fprint(2, "urlopen: bad query: %s: %r\n", buf); + + close(fd); + } + snprint(buf, sizeof(buf), "%s/%d/body", webmountpt, conn); + fd = open(buf, OREAD); + if(fd < 0){ +// fprint(2, "open: %S: %r\n", u->src.r); + goto Err; + } + u->ctype = getattr(conn, "contenttype"); + u->act = getattr(conn, "parsed/url"); + if(u->act.nr == 0) + copyrunestr(&u->act, &u->src); + close(cfd); + return fd; +} + +void +urlcanon(Rune *name){ + Rune *s, *t; + Rune **comp, **p, **q; + int rooted; + + name = runestrchr(name, L'/')+2; + rooted=name[0]==L'/'; + /* + * Break the name into a list of components + */ + comp=emalloc(runestrlen(name)*sizeof(char *)); + p=comp; + *p++=name; + for(s=name;;s++){ + if(*s==L'/'){ + *p++=s+1; + *s='\0'; + } + else if(*s=='\0') + break; + } + *p=0; + /* + * go through the component list, deleting components that are empty (except + * the last component) or ., and any .. and its non-.. predecessor. + */ + p=q=comp; + while(*p){ + if(runestrcmp(*p, L"")==0 && p[1]!=0 + || runestrcmp(*p, L".")==0) + p++; + else if(runestrcmp(*p, L"..")==0 && q!=comp && runestrcmp(q[-1], L"..")!=0){ + --q; + p++; + } + else + *q++=*p++; + } + *q=0; + /* + * rebuild the path name + */ + s=name; + if(rooted) *s++='/'; + for(p=comp;*p;p++){ + t=*p; + while(*t) *s++=*t++; + if(p[1]!=0) *s++='/'; + } + *s='\0'; + free(comp); +} + +/* this is a HACK */ +Rune * +urlcombine(Rune *b, Rune *u) +{ + Rune *p, *q, *sep, *s; + Rune endrune[] = { L'?', L'#' }; + int i, restore; + + if(u == nil) + error("urlcombine: u == nil"); + + if(validurl(u)) + return erunestrdup(u); + + if(b==nil || !validurl(b)) + error("urlcombine: b==nil || !validurl(b)"); + + if(runestrncmp(u, L"//", 2) == 0){ + q = runestrchr(b, L':'); + return runesmprint("%.*S:%S", (int)(q-b), b, u); + } + p = runestrstr(b, L"://")+3; + sep = L""; + q = nil; + if(*u ==L'/') + q = runestrchr(p, L'/'); + else if(*u==L'#' || *u==L'?'){ + for(i=0; i<nelem(endrune); i++) + if(q = runestrchr(p, endrune[i])) + break; + }else{ + sep = L"/"; + restore = 0; + s = runestrchr(p, L'?'); + if(s != nil){ + *s = '\0'; + restore = 1; + } + q = runestrrchr(p, L'/'); + if(restore) + *s = L'?'; + } + if(q == nil) + p = runesmprint("%S%S%S", b, sep, u); + else + p = runesmprint("%.*S%S%S", (int)(q-b), b, sep, u); + urlcanon(p); + return p; +} |