URI:
       tdownload.c - plan9port - [fork] Plan 9 from user space
  HTML git clone git://src.adamsgaard.dk/plan9port
   DIR Log
   DIR Files
   DIR Refs
   DIR README
   DIR LICENSE
       ---
       tdownload.c (1671B)
       ---
            1 #include "a.h"
            2 
            3 typedef struct DEntry DEntry;
            4 struct DEntry
            5 {
            6         CEntry ce;
            7         HTTPHeader hdr;
            8         char *tmpfile;
            9         int fd;
           10 };
           11 
           12 static void
           13 dfree(CEntry *ce)
           14 {
           15         DEntry *d;
           16 
           17         d = (DEntry*)ce;
           18         if(d->tmpfile){
           19                 remove(d->tmpfile);
           20                 free(d->tmpfile);
           21                 close(d->fd);
           22         }
           23 }
           24 
           25 static Cache *downloadcache;
           26 
           27 static char*
           28 parseurl(char *url, char **path)
           29 {
           30         char *host, *p;
           31         int len;
           32 
           33         if(memcmp(url, "http://", 7) != 0)
           34                 return nil;
           35         p = strchr(url+7, '/');
           36         if(p == nil)
           37                 p = url+strlen(url);
           38         len = p - (url+7);
           39         host = emalloc(len+1);
           40         memmove(host, url+7, len);
           41         host[len] = 0;
           42         if(*p == 0)
           43                 p = "/";
           44         *path = p;
           45         return host;
           46 }
           47 
           48 int
           49 download(char *url, HTTPHeader *hdr)
           50 {
           51         DEntry *d;
           52         char *host, *path;
           53         char buf[] = "/var/tmp/smugfs.XXXXXX";
           54         char *req;
           55         int fd;
           56         Fmt fmt;
           57 
           58         if(downloadcache == nil)
           59                 downloadcache = newcache(sizeof(DEntry), 128, dfree);
           60 
           61         host = parseurl(url, &path);
           62         if(host == nil)
           63                 return -1;
           64 
           65         d = (DEntry*)cachelookup(downloadcache, url, 1);
           66         if(d->tmpfile){
           67                 free(host);
           68                 *hdr = d->hdr;
           69                 return dup(d->fd, -1);
           70         }
           71         d->fd = -1;  // paranoia
           72 
           73         if((fd = opentemp(buf, ORDWR|ORCLOSE)) < 0){
           74                 free(host);
           75                 return -1;
           76         }
           77 
           78         fmtstrinit(&fmt);
           79         fmtprint(&fmt, "GET %s HTTP/1.0\r\n", path);
           80         fmtprint(&fmt, "Host: %s\r\n", host);
           81         fmtprint(&fmt, "User-Agent: " USER_AGENT "\r\n");
           82         fmtprint(&fmt, "\r\n");
           83         req = fmtstrflush(&fmt);
           84 
           85         fprint(2, "Get %s\n", url);
           86 
           87         if(httptofile(&http, host, req, hdr, fd) < 0){
           88                 free(host);
           89                 free(req);
           90                 return -1;
           91         }
           92         free(host);
           93         free(req);
           94         d->tmpfile = estrdup(buf);
           95         d->fd = dup(fd, -1);
           96         d->hdr = *hdr;
           97         return fd;
           98 }
           99 
          100 void
          101 downloadflush(char *substr)
          102 {
          103         if(downloadcache)
          104                 cacheflush(downloadcache, substr);
          105 }