--- a/src/server/util/io.c Wed May 22 13:27:31 2013 +0200 +++ b/src/server/util/io.c Wed May 22 15:05:06 2013 +0200 @@ -48,10 +48,10 @@ }; IOStream net_io_funcs = { - net_stream_write, - net_stream_writev, - net_stream_read, - net_stream_sendfile + (io_write_f)net_stream_write, + (io_writev_f)net_stream_writev, + (io_read_f)net_stream_read, + (io_sendfile_f)net_stream_sendfile }; @@ -81,34 +81,60 @@ st->fd = fd; st->max_read = 0; st->rd = 0; + st->chunkedenc = 0; + st->buffered = 0; return (IOStream*)st; } -ssize_t net_stream_write(IOStream *st, void *buf, size_t nbytes) { - return write(((NetIOStream*)st)->fd, buf, nbytes); -} - -ssize_t net_stream_writev(IOStream *st, struct iovec *iovec, int iovcnt) { - return writev(((NetIOStream*)st)->fd, iovec, iovcnt); +ssize_t net_stream_write(NetIOStream *st, void *buf, size_t nbytes) { + if(st->chunkedenc) { + // TODO: on some plattforms iov_len is smaller than size_t + struct iovec io[2]; + char chunk_len[16]; + io[0].iov_base = chunk_len; + io[0].iov_len = snprintf(chunk_len, 16, "\n%x\r\n", nbytes); + io[1].iov_base = buf; + io[1].iov_len = nbytes; + ssize_t r = writev(st->fd, io, 2); + return r - io[0].iov_len; + } else { + return write(st->fd, buf, nbytes); + } } -ssize_t net_stream_read(IOStream *st, void *buf, size_t nbytes) { - NetIOStream *n = (NetIOStream*)st; - if(n->max_read != 0 && n->rd >= n->max_read) { +ssize_t net_stream_writev(NetIOStream *st, struct iovec *iovec, int iovcnt) { + if(st->chunkedenc) { + struct iovec *io = calloc(iovcnt + 1, sizeof(struct iovec)); + char chunk_len[16]; + io[0].iov_base = chunk_len; + size_t len = 0; + for(int i=0;i<iovcnt;i++) { + len += iovec[i].iov_len; + } + io[0].iov_len = snprintf(chunk_len, 16, "\n%x\r\n", len); + memcpy(io + 1, iovec, iovcnt * sizeof(struct iovec)); + ssize_t r = writev(st->fd, io, iovcnt + 1); + return r - io[0].iov_len; + } else { + return writev(st->fd, iovec, iovcnt); + } +} + +ssize_t net_stream_read(NetIOStream *st, void *buf, size_t nbytes) { + if(st->max_read != 0 && st->rd >= st->max_read) { return 0; } - ssize_t r = read(n->fd, buf, nbytes); - n->rd += r; + ssize_t r = read(st->fd, buf, nbytes); + st->rd += r; return r; } -ssize_t net_stream_sendfile(IOStream *st, sendfiledata *sfd) { - NetIOStream *io = (NetIOStream*)st; +ssize_t net_stream_sendfile(NetIOStream *st, sendfiledata *sfd) { // TODO: header and trailer ssize_t ret = 0; off_t fileoffset = sfd->offset; if(sfd->fd->fd != -1) { - ret = sendfile(io->fd, sfd->fd->fd, &fileoffset, sfd->len); + ret = sendfile(st->fd, sfd->fd->fd, &fileoffset, sfd->len); } else { // TODO: regular copy fprintf(stderr, "sendfile not implemented for SYS_FILE\n");