ssize_t do_sendfilev(int sock, char *dir, int nfiles, int chunk_size) { int i; size_t xferred; sfv_list_t *s; struct sendfilevec *vec, *v; s = find_sfv_list(dir); assert(s); if (chunk_size != 0) return (do_sendfilev_chunked(s, sock, chunk_size)); if ((vec = alloca(nfiles * sizeof (struct sendfilevec))) == 0) { perror("calloc"); return (-1); } v = vec; bzero(vec, nfiles * sizeof (struct sendfilevec)); for (i = 0; i < nfiles; i++) { int r = select_file(s); v->sfv_fd = s->flist[r].fd; v->sfv_len = s->flist[r].size; v++; } return (sendfilev(sock, vec, nfiles, &xferred)); }
/* Open all readable files in the dir 'dir' and get their sizes */ int sendfile_init(char *dir) { int count = 0; struct file_list *flist; struct file_list *fl; sfv_list_t *s; if ((s = find_sfv_list(dir)) != NULL) return (0); bzero(&fhead, sizeof (fhead)); if (ftw(dir, add_file, 1000) != 0) { perror("find(ftw):"); return (-1); } /* Now walk the file_list_t list and count entries */ flist = fhead.next; for (fl = fhead.next; fl; fl = fl->next) count++; assert(count); if ((s = calloc(1, sizeof (sfv_list_t))) == NULL) { perror("calloc"); return (-1); } if ((s->flist = calloc(count, sizeof (struct file_list))) == NULL) { perror("calloc"); return (-1); } s->nfiles = count; flist = s->flist; (void) strlcpy(s->dir, dir, sizeof (s->dir)); for (fl = fhead.next; fl; fl = fl->next) { (void) memcpy(flist, fl, sizeof (file_list_t)); flist++; } if (sfv_list) { s->next = sfv_list->next; sfv_list->next = s; } else { sfv_list = s; } return (0); }
int main(int argc, char *argv[]) { int i; sfv_list_t *s; srand(gethrtime()); sendfilev_init(argv[1]); sendfilev_init(argv[1]); s = find_sfv_list(argv[1]); assert(s); for (i = 0; i < 10; i++) select_file(s); return (0); }
ssize_t do_sendfile(int sock, char *dir, int chunk_size) { off_t off = 0; sfv_list_t *s; s = find_sfv_list(dir); assert(s); int r = select_file(s); if (chunk_size == 0) return (sendfile(sock, s->flist[r].fd, &off, s->flist[r].size)); else { int size = 0; int n; while (size < s->flist[r].size) { if ((n = sendfile(sock, s->flist[r].fd, &off, s->flist[r].size)) < 0) return (n); size += n; } return (size); } }
ssize_t do_sendfile(int sock, char *dir, int chunk_size) { #if defined(UPERF_FREEBSD) || defined(UPERF_DARWIN) off_t len; #endif off_t off = 0; sfv_list_t *s; s = find_sfv_list(dir); assert(s); int r = select_file(s); if (chunk_size == 0) { #if defined(UPERF_FREEBSD) || defined(UPERF_DARWIN) #if defined(UPERF_FREEBSD) len = 0; if (sendfile(s->flist[r].fd, sock, off, s->flist[r].size, NULL, &len, 0) < 0) { #else len = s->flist[r].size; if (sendfile(s->flist[r].fd, sock, off, &len, NULL, 0) < 0) { #endif return (-1); } else { return (len); } #else return (sendfile(sock, s->flist[r].fd, &off, s->flist[r].size)); #endif } else { #if defined(UPERF_FREEBSD) || defined(UPERF_DARWIN) while (off < s->flist[r].size) { #if defined(UPERF_FREEBSD) len = 0; if (sendfile(s->flist[r].fd, sock, off, chunk_size, NULL, &len, 0) < 0) { #else len = chunk_size; if (sendfile(s->flist[r].fd, sock, off, &len, NULL, 0) < 0) { #endif return (-1); } off += len; } #else while (off < s->flist[r].size) { if (sendfile(sock, s->flist[r].fd, &off, chunk_size) < 0) { return (-1); } } #endif return (s->flist[r].size); } } #ifdef MAIN int main(int argc, char *argv[]) { int i; sfv_list_t *s; srand(gethrtime()); sendfilev_init(argv[1]); sendfilev_init(argv[1]); s = find_sfv_list(argv[1]); assert(s); for (i = 0; i < 10; i++) select_file(s); return (0); }