From f93476ebd32559634d23e630a18cbbf8c53c34bb Mon Sep 17 00:00:00 2001 From: Alex Young Date: Thu, 27 Feb 2014 16:04:25 +0000 Subject: [PATCH] Replace off64_t with uint64_t where it makes sense to do so. It looks like off64_t was propagated through the code from the return type of lseek64(), which isn't appropriate in many of the places we're using it. --- src/common/ioutil.c | 8 +++++++- src/common/ioutil.h | 2 +- src/common/mirror.c | 6 +++--- src/common/mode.c | 10 +++++++--- src/common/readwrite.c | 16 +++++++++------- src/common/readwrite.h | 12 ++++++------ src/common/serve.h | 5 ++--- src/proxy/proxy.c | 10 +++++----- src/proxy/proxy.h | 3 +-- 9 files changed, 41 insertions(+), 31 deletions(-) diff --git a/src/common/ioutil.c b/src/common/ioutil.c index b63f2a0..d709a0c 100644 --- a/src/common/ioutil.c +++ b/src/common/ioutil.c @@ -76,8 +76,14 @@ int build_allocation_map(struct bitset * allocation_map, int fd) } -int open_and_mmap(const char* filename, int* out_fd, off64_t *out_size, void **out_map) +int open_and_mmap(const char* filename, int* out_fd, uint64_t *out_size, void **out_map) { + /* + * size and out_size are intentionally of different types. + * lseek64() uses off64_t to signal errors in the sign bit. + * Since we check for these errors before trying to assign to + * *out_size, we know *out_size can never go negative. + */ off64_t size; /* O_DIRECT should not be used with mmap() */ diff --git a/src/common/ioutil.h b/src/common/ioutil.h index 9a7c969..da69452 100644 --- a/src/common/ioutil.h +++ b/src/common/ioutil.h @@ -65,7 +65,7 @@ int read_lines_until_blankline(int fd, int max_line_length, char ***lines); * ''out_size'' and the address of the mmap in ''out_map''. If anything goes * wrong, returns -1 setting errno, otherwise 0. */ -int open_and_mmap( const char* filename, int* out_fd, off64_t *out_size, void **out_map); +int open_and_mmap( const char* filename, int* out_fd, uint64_t* out_size, void **out_map); /** Check to see whether the given file descriptor is closed. diff --git a/src/common/mirror.c b/src/common/mirror.c index 646e4c0..d9cac1f 100644 --- a/src/common/mirror.c +++ b/src/common/mirror.c @@ -139,7 +139,7 @@ enum mirror_state mirror_get_state( struct mirror * mirror ) void mirror_init( struct mirror * mirror, const char * filename ) { int map_fd; - off64_t size; + uint64_t size; NULLCHECK( mirror ); NULLCHECK( filename ); @@ -270,7 +270,7 @@ void mirror_cleanup( struct server * serve, } -int mirror_connect( struct mirror * mirror, off64_t local_size ) +int mirror_connect( struct mirror * mirror, uint64_t local_size ) { struct sockaddr * connect_from = NULL; int connected = 0; @@ -292,7 +292,7 @@ int mirror_connect( struct mirror * mirror, off64_t local_size ) "Select failed." ); if( FD_ISSET( mirror->client, &fds ) ){ - off64_t remote_size; + uint64_t remote_size; if ( socket_nbd_read_hello( mirror->client, &remote_size ) ) { if( remote_size == local_size ){ connected = 1; diff --git a/src/common/mode.c b/src/common/mode.c index 732091c..47dbffc 100644 --- a/src/common/mode.c +++ b/src/common/mode.c @@ -573,7 +573,10 @@ void params_readwrite( parse_port( s_port, &out->connect_to.v4 ); - out->from = atol(s_from); + long signed_from = atol(s_from); + FATAL_IF_NEGATIVE( signed_from, + "Can't read from a negative offset %d.", signed_from); + out->from = signed_from; if (write_not_read) { if (s_length_or_filename[0]-48 < 10) { @@ -585,9 +588,10 @@ void params_readwrite( s_length_or_filename, O_RDONLY); FATAL_IF_NEGATIVE(out->data_fd, "Couldn't open %s", s_length_or_filename); - out->len = lseek64(out->data_fd, 0, SEEK_END); - FATAL_IF_NEGATIVE(out->len, + off64_t signed_len = lseek64(out->data_fd, 0, SEEK_END); + FATAL_IF_NEGATIVE(signed_len, "Couldn't find length of %s", s_length_or_filename); + out->len = signed_len; FATAL_IF_NEGATIVE( lseek64(out->data_fd, 0, SEEK_SET), "Couldn't rewind %s", s_length_or_filename diff --git a/src/common/readwrite.c b/src/common/readwrite.c index bb348d3..cf065e5 100644 --- a/src/common/readwrite.c +++ b/src/common/readwrite.c @@ -41,7 +41,7 @@ int socket_connect(struct sockaddr* to, struct sockaddr* from) return fd; } -int nbd_check_hello( struct nbd_init_raw* init_raw, off64_t* out_size ) +int nbd_check_hello( struct nbd_init_raw* init_raw, uint64_t* out_size ) { if ( strncmp( init_raw->passwd, INIT_PASSWD, 8 ) != 0 ) { warn( "wrong passwd" ); @@ -62,7 +62,7 @@ fail: } -int socket_nbd_read_hello( int fd, off64_t* out_size ) +int socket_nbd_read_hello( int fd, uint64_t* out_size ) { struct nbd_init_raw init_raw; @@ -101,7 +101,7 @@ int socket_nbd_write_hello(int fd, off64_t out_size) return 1; } -void fill_request(struct nbd_request *request, int type, off64_t from, int len) +void fill_request(struct nbd_request *request, int type, uint64_t from, uint32_t len) { request->magic = htobe32(REQUEST_MAGIC); request->type = htobe32(type); @@ -150,7 +150,7 @@ void wait_for_data( int fd, int timeout_secs ) } -void socket_nbd_read(int fd, off64_t from, int len, int out_fd, void* out_buf, int timeout_secs) +void socket_nbd_read(int fd, uint64_t from, uint32_t len, int out_fd, void* out_buf, int timeout_secs) { struct nbd_request request; struct nbd_reply reply; @@ -174,7 +174,7 @@ void socket_nbd_read(int fd, off64_t from, int len, int out_fd, void* out_buf, i } } -void socket_nbd_write(int fd, off64_t from, int len, int in_fd, void* in_buf, int timeout_secs) +void socket_nbd_write(int fd, uint64_t from, uint32_t len, int in_fd, void* in_buf, int timeout_secs) { struct nbd_request request; struct nbd_reply reply; @@ -214,10 +214,12 @@ int socket_nbd_disconnect( int fd ) } #define CHECK_RANGE(error_type) { \ - off64_t size;\ + uint64_t size;\ int success = socket_nbd_read_hello(params->client, &size); \ if ( success ) {\ - if (params->from < 0 || (params->from + params->len) > size) {\ + uint64_t endpoint = params->from + params->len; \ + if (endpoint > size || \ + endpoint < params->from ) { /* this happens on overflow */ \ fatal(error_type \ " request %d+%d is out of range given size %d", \ params->from, params->len, size\ diff --git a/src/common/readwrite.h b/src/common/readwrite.h index 155edd7..04b12c6 100644 --- a/src/common/readwrite.h +++ b/src/common/readwrite.h @@ -7,17 +7,17 @@ #include "nbdtypes.h" int socket_connect(struct sockaddr* to, struct sockaddr* from); -int socket_nbd_read_hello(int fd, off64_t * size); -int socket_nbd_write_hello(int fd, off64_t size); -void socket_nbd_read(int fd, off64_t from, int len, int out_fd, void* out_buf, int timeout_secs); -void socket_nbd_write(int fd, off64_t from, int len, int out_fd, void* out_buf, int timeout_secs); +int socket_nbd_read_hello(int fd, uint64_t* size); +int socket_nbd_write_hello(int fd, uint64_t size); +void socket_nbd_read(int fd, uint64_t from, uint32_t len, int out_fd, void* out_buf, int timeout_secs); +void socket_nbd_write(int fd, uint64_t from, uint32_t len, int out_fd, void* out_buf, int timeout_secs); int socket_nbd_disconnect( int fd ); /* as you can see, we're slowly accumulating code that should really be in an * NBD library */ -void nbd_hello_to_buf( struct nbd_init_raw* buf, off64_t out_size ); -int nbd_check_hello( struct nbd_init_raw* init_raw, off64_t* out_size ); +void nbd_hello_to_buf( struct nbd_init_raw* buf, uint64_t out_size ); +int nbd_check_hello( struct nbd_init_raw* init_raw, uint64_t* out_size ); #endif diff --git a/src/common/serve.h b/src/common/serve.h index 9b90cbc..5d04e14 100644 --- a/src/common/serve.h +++ b/src/common/serve.h @@ -155,9 +155,8 @@ struct mode_readwrite_params { union mysockaddr connect_to; union mysockaddr connect_from; - /* FIXME: these should be uint64_t and uint32_t respectively */ - off64_t from; - off64_t len; + uint64_t from; + uint32_t len; int data_fd; int client; diff --git a/src/proxy/proxy.c b/src/proxy/proxy.c index 16d853a..58213be 100644 --- a/src/proxy/proxy.c +++ b/src/proxy/proxy.c @@ -103,7 +103,7 @@ void proxy_destroy( struct proxier* proxy ) } /* Shared between our two different connect_to_upstream paths */ -void proxy_finish_connect_to_upstream( struct proxier *proxy, off64_t size ); +void proxy_finish_connect_to_upstream( struct proxier *proxy, uint64_t size ); /* Try to establish a connection to our upstream server. Return 1 on success, * 0 on failure. this is a blocking call that returns a non-blocking socket. @@ -116,7 +116,7 @@ int proxy_connect_to_upstream( struct proxier* proxy ) } int fd = socket_connect( &proxy->connect_to.generic, connect_from ); - off64_t size = 0; + uint64_t size = 0; if ( -1 == fd ) { return 0; @@ -188,7 +188,7 @@ error: return; } -void proxy_finish_connect_to_upstream( struct proxier *proxy, off64_t size ) { +void proxy_finish_connect_to_upstream( struct proxier *proxy, uint64_t size ) { if ( proxy->upstream_size == 0 ) { info( "Size of upstream image is %"PRIu64" bytes", size ); @@ -358,7 +358,7 @@ int proxy_prefetch_for_request( struct proxier* proxy, int state ) req->len <= prefetch_size( proxy->prefetch ) && is_read && prefetch_start < prefetch_end && - prefetch_end <= (uint64_t)proxy->upstream_size; /* FIXME: we shouldn't need a cast - upstream_size should be uint64_t */ + prefetch_end <= proxy->upstream_size; /* We pull the request out of the proxy struct, rewrite the * request size, and write it back. @@ -512,7 +512,7 @@ int proxy_read_init_from_upstream( struct proxier* proxy, int state ) } if ( proxy->init.needle == proxy->init.size ) { - off64_t upstream_size; + uint64_t upstream_size; if ( !nbd_check_hello( (struct nbd_init_raw*) proxy->init.buf, &upstream_size ) ) { warn( "Upstream sent invalid init" ); goto disconnect; diff --git a/src/proxy/proxy.h b/src/proxy/proxy.h index d99e0bd..22d10c5 100644 --- a/src/proxy/proxy.h +++ b/src/proxy/proxy.h @@ -48,8 +48,7 @@ struct proxier { int upstream_fd; /* This is the size we advertise to the downstream server */ - /* FIXME: should be uint64_t */ - off64_t upstream_size; + uint64_t upstream_size; /* We transform the raw request header into here */ struct nbd_request req_hdr;