]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
[master] portability fixes for map files
authorEvan Hunt <each@isc.org>
Mon, 17 Jun 2013 16:09:43 +0000 (09:09 -0700)
committerEvan Hunt <each@isc.org>
Mon, 17 Jun 2013 16:09:43 +0000 (09:09 -0700)
3598. [cleanup] Improved portability of map file code. [RT #33820]

12 files changed:
CHANGES
lib/dns/include/dns/rbt.h
lib/dns/journal.c
lib/dns/rbt.c
lib/dns/rbtdb.c
lib/dns/tests/rbt_test.c
lib/isc/include/isc/stdio.h
lib/isc/unix/errno2result.c
lib/isc/unix/stdio.c
lib/isc/win32/errno2result.c
lib/isc/win32/libisc.def
lib/isc/win32/stdio.c

diff --git a/CHANGES b/CHANGES
index 44e6cdda4191cb97949d486e86568572f5e98e5f..b0c45a3bdd8c64e4c8076592d8b5a2ba5eaea906 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -1,3 +1,5 @@
+3598.  [cleanup]       Improved portability of map file code. [RT #33820]
+
 3597.  [bug]           Ensure automatic-resigning heaps are reconstructed
                        when loading zones in map format. [RT #33381]
 
index 7433d90872d7845c0ce384b7ae6a26d97b66829b..9158be6e2a741e896f7d81007b4e45acc473c01f 100644 (file)
@@ -153,7 +153,7 @@ typedef isc_result_t (*dns_rbtfindcallback_t)(dns_rbtnode_t *node,
 
 typedef isc_result_t (*dns_rbtdatawriter_t)(FILE *file,
                                            unsigned char *data,
-                                           isc_uint32_t version,
+                                           void *arg,
                                            isc_uint64_t *crc);
 
 typedef isc_result_t (*dns_rbtdatafixer_t)(dns_rbtnode_t *rbtnode,
@@ -689,8 +689,8 @@ dns_rbt_destroy2(dns_rbt_t **rbtp, unsigned int quantum);
  * \li  ISC_R_QUOTA if 'quantum' nodes have been destroyed.
  */
 
-long
-dns_rbt_serialize_align(long target);
+off_t
+dns_rbt_serialize_align(off_t target);
 /*%<
  * Align the provided integer to a pointer-size boundary.
  * This should be used if, during serialization of data to a will-be
@@ -700,7 +700,7 @@ dns_rbt_serialize_align(long target);
 isc_result_t
 dns_rbt_serialize_tree(FILE *file, dns_rbt_t *rbt,
                       dns_rbtdatawriter_t datawriter,
-                      isc_uint32_t serial, long *offset);
+                      void *writer_arg, off_t *offset);
 /*%<
  * Write out the RBT structure and its data to a file.
  *
index 022a3e280f83292db0a73d6aa69b91d4b6a8d06b..05878e119e00652a08bb83ffa40fdd356ce700df 100644 (file)
@@ -387,7 +387,8 @@ journal_header_encode(journal_header_t *cooked, journal_rawheader_t *raw) {
 static isc_result_t
 journal_seek(dns_journal_t *j, isc_uint32_t offset) {
        isc_result_t result;
-       result = isc_stdio_seek(j->fp, (long)offset, SEEK_SET);
+
+       result = isc_stdio_seek(j->fp, (off_t)offset, SEEK_SET);
        if (result != ISC_R_SUCCESS) {
                isc_log_write(JOURNAL_COMMON_LOGARGS, ISC_LOG_ERROR,
                              "%s: seek: %s", j->filename,
index bd70f5279fecbadbf518f53ae44142174110e8f1..9ce5acaa52b222aad300cea1d8b4618351a8acf8 100644 (file)
@@ -156,7 +156,7 @@ serialize_node(FILE *file, dns_rbtnode_t *node, uintptr_t left,
 
 static isc_result_t
 serialize_nodes(FILE *file, dns_rbtnode_t *node, uintptr_t parent,
-               dns_rbtdatawriter_t datawriter, isc_uint32_t serial,
+               dns_rbtdatawriter_t datawriter, void *writer_arg,
                uintptr_t *where, isc_uint64_t *crc);
 /*
  * The following functions allow you to get the actual address of a pointer
@@ -420,7 +420,7 @@ write_header(FILE *file, dns_rbt_t *rbt, isc_uint64_t first_node_offset,
 {
        file_header_t header;
        isc_result_t result;
-       long location;
+       off_t location;
 
        if (FILE_VERSION[0] == '\0') {
                memset(FILE_VERSION, 0, sizeof(FILE_VERSION));
@@ -445,9 +445,7 @@ write_header(FILE *file, dns_rbt_t *rbt, isc_uint64_t first_node_offset,
 
        header.crc = crc;
 
-       location = ftell(file);
-       if (location < 0)
-               return (ISC_R_FAILURE);
+       CHECK(isc_stdio_tell(file, &location));
        location = dns_rbt_serialize_align(location);
        CHECK(isc_stdio_seek(file, location, SEEK_SET));
        CHECK(isc_stdio_write(&header, 1, sizeof(file_header_t), file, NULL));
@@ -466,7 +464,7 @@ serialize_node(FILE *file, dns_rbtnode_t *node, uintptr_t left,
               uintptr_t data, isc_uint64_t *crc)
 {
        dns_rbtnode_t temp_node;
-       long file_position;
+       off_t file_position;
        unsigned char *node_data;
        size_t datasize;
        isc_result_t result;
@@ -476,10 +474,7 @@ serialize_node(FILE *file, dns_rbtnode_t *node, uintptr_t left,
 
        INSIST(node != NULL);
 
-       file_position = ftell(file);
-       if (file_position < 0)
-               return (ISC_R_FAILURE);
-
+       CHECK(isc_stdio_tell(file, &file_position));
        file_position = dns_rbt_serialize_align(file_position);
        CHECK(isc_stdio_seek(file, file_position, SEEK_SET));
 
@@ -546,12 +541,11 @@ serialize_node(FILE *file, dns_rbtnode_t *node, uintptr_t left,
 
 static isc_result_t
 serialize_nodes(FILE *file, dns_rbtnode_t *node, uintptr_t parent,
-               dns_rbtdatawriter_t datawriter, isc_uint32_t serial,
+               dns_rbtdatawriter_t datawriter, void *writer_arg,
                uintptr_t *where, isc_uint64_t *crc)
 {
        uintptr_t left = 0, right = 0, down = 0, data = 0;
-       long location = 0;
-       long offset_adjust;
+       off_t location = 0, offset_adjust;
        isc_result_t result;
 
        if (node == NULL) {
@@ -561,14 +555,9 @@ serialize_nodes(FILE *file, dns_rbtnode_t *node, uintptr_t parent,
        }
 
        /* Reserve space for current node. */
-       location = ftell(file);
-       if (location < 0)
-               return (ISC_R_FAILURE);
+       CHECK(isc_stdio_tell(file, &location));
        location = dns_rbt_serialize_align(location);
        CHECK(isc_stdio_seek(file, location, SEEK_SET));
-       location = ftell(file);
-       if (location < 0)
-               return (ISC_R_FAILURE);
 
        offset_adjust = dns_rbt_serialize_align(location + NODE_SIZE(node));
        CHECK(isc_stdio_seek(file, offset_adjust, SEEK_SET));
@@ -580,28 +569,21 @@ serialize_nodes(FILE *file, dns_rbtnode_t *node, uintptr_t parent,
         * will break the way the crc hash is computed.
         */
        CHECK(serialize_nodes(file, getleft(node, NULL), location,
-                             datawriter, serial, &left, crc));
+                             datawriter, writer_arg, &left, crc));
        CHECK(serialize_nodes(file, getright(node, NULL), location,
-                             datawriter, serial, &right, crc));
+                             datawriter, writer_arg, &right, crc));
        CHECK(serialize_nodes(file, getdown(node, NULL), location,
-                             datawriter, serial, &down, crc));
+                             datawriter, writer_arg, &down, crc));
 
        if (node->data != NULL) {
-               long ret;
+               off_t ret;
 
-               ret = ftell(file);
-               if (ret < 0)
-                       return (ISC_R_FAILURE);
+               CHECK(isc_stdio_tell(file, &ret));
                ret = dns_rbt_serialize_align(ret);
-
                CHECK(isc_stdio_seek(file, ret, SEEK_SET));
-
-               ret = ftell(file);
-               if (ret < 0)
-                       return (ISC_R_FAILURE);
                data = ret;
 
-               datawriter(file, node->data, serial, crc);
+               datawriter(file, node->data, writer_arg, crc);
        }
 
        /* Seek back to reserved space. */
@@ -614,15 +596,15 @@ serialize_nodes(FILE *file, dns_rbtnode_t *node, uintptr_t parent,
        CHECK(isc_stdio_seek(file, 0, SEEK_END));
 
        if (where != NULL)
-               *where = location;
+               *where = (uintptr_t) location;
 
  cleanup:
        return (result);
 }
 
-long
-dns_rbt_serialize_align(long target) {
-       long offset = target % 8;
+off_t
+dns_rbt_serialize_align(off_t target) {
+       off_t offset = target % 8;
 
        if (offset == 0)
                return (target);
@@ -633,10 +615,10 @@ dns_rbt_serialize_align(long target) {
 isc_result_t
 dns_rbt_serialize_tree(FILE *file, dns_rbt_t *rbt,
                       dns_rbtdatawriter_t datawriter,
-                      isc_uint32_t serial, long *offset)
+                      void *writer_arg, off_t *offset)
 {
        isc_result_t result;
-       long header_position, node_position, end_position;
+       off_t header_position, node_position, end_position;
        isc_uint64_t crc;
 
        REQUIRE(file != NULL);
@@ -645,24 +627,17 @@ dns_rbt_serialize_tree(FILE *file, dns_rbt_t *rbt,
 
        isc_crc64_init(&crc);
 
-       header_position = ftell(file);
-       if (header_position < 0)
-               return (ISC_R_FAILURE);
+       CHECK(isc_stdio_tell(file, &header_position));
 
        /* Write dummy header */
        CHECK(dns_rbt_zero_header(file));
 
        /* Serialize nodes */
-       node_position = ftell(file);
-       if (node_position < 0)
-               return (ISC_R_FAILURE);
-
+       CHECK(isc_stdio_tell(file, &node_position));
        CHECK(serialize_nodes(file, rbt->root, 0, datawriter,
-                             serial, NULL, &crc));
-       end_position = ftell(file);
-       if (end_position < 0)
-               return (ISC_R_FAILURE);
+                             writer_arg, NULL, &crc));
 
+       CHECK(isc_stdio_tell(file, &end_position));
        if (node_position == end_position) {
                CHECK(isc_stdio_seek(file, header_position, SEEK_SET));
                *offset = 0;
index b0a153b482d012d4f765dc193d70cf31d0697621..728b3da96f6caae957e879016841c08544a45006 100644 (file)
@@ -511,7 +511,7 @@ struct dns_rbtdb {
         * Base values for the mmap() code.
         */
        void *                          mmap_location;
-       isc_uint64_t                    mmap_size;
+       size_t                          mmap_size;
 
        /* Locked by tree_lock. */
        dns_rbt_t *                     tree;
@@ -1107,7 +1107,8 @@ free_rbtdb(dns_rbtdb_t *rbtdb, isc_boolean_t log, isc_event_t *event) {
        isc_mem_detach(&rbtdb->hmctx);
 
        if (rbtdb->mmap_location != NULL)
-         isc_file_munmap(rbtdb->mmap_location, (size_t) rbtdb->mmap_size);
+               isc_file_munmap(rbtdb->mmap_location,
+                               (size_t) rbtdb->mmap_size);
 
        isc_mem_putanddetach(&rbtdb->common.mctx, rbtdb, sizeof(*rbtdb));
        isc_ondestroy_notify(&ondest, rbtdb);
@@ -7093,12 +7094,12 @@ deserialize(void *arg, FILE *f, off_t offset) {
        header = (rbtdb_file_header_t *)(base + offset);
 
        rbtdb->mmap_location = base;
-       rbtdb->mmap_size = filesize;
+       rbtdb->mmap_size = (size_t) filesize;
        rbtdb->origin_node = NULL;
 
        if (header->tree != 0) {
                result = dns_rbt_deserialize_tree(base, filesize,
-                                                 (size_t) header->tree,
+                                                 (off_t) header->tree,
                                                  rbtdb->common.mctx,
                                                  delete_callback, rbtdb,
                                                  rbt_datafixer, rbtdb,
@@ -7118,7 +7119,7 @@ deserialize(void *arg, FILE *f, off_t offset) {
 
        if (header->nsec != 0) {
                result = dns_rbt_deserialize_tree(base, filesize,
-                                                 (size_t) header->nsec,
+                                                 (off_t) header->nsec,
                                                  rbtdb->common.mctx,
                                                  delete_callback, rbtdb,
                                                  rbt_datafixer, rbtdb,
@@ -7134,7 +7135,7 @@ deserialize(void *arg, FILE *f, off_t offset) {
 
        if (header->nsec3 != 0) {
                result = dns_rbt_deserialize_tree(base, filesize,
-                                                 (size_t) header->nsec3,
+                                                 (off_t) header->nsec3,
                                                  rbtdb->common.mctx,
                                                  delete_callback, rbtdb,
                                                  rbt_datafixer, rbtdb,
@@ -7241,18 +7242,24 @@ endload(dns_db_t *db, dns_rdatacallbacks_t *callbacks) {
  * by the void *data pointer in the dns_rbtnode
  */
 static isc_result_t
-rbt_datawriter(FILE *rbtfile, unsigned char *data, isc_uint32_t serial,
+rbt_datawriter(FILE *rbtfile, unsigned char *data, void *arg,
               isc_uint64_t *crc)
 {
+       rbtdb_version_t *version = (rbtdb_version_t *) arg;
+       rbtdb_serial_t serial;
        rdatasetheader_t newheader;
        rdatasetheader_t *header = (rdatasetheader_t *) data, *next;
-       size_t where, size, cooked;
+       off_t where, cooked;
+       size_t size;
        unsigned char *p;
-       isc_result_t result;
-       static const char pad[sizeof(char *)];
+       isc_result_t result = ISC_R_SUCCESS;
+       char pad[sizeof(char *)];
 
        REQUIRE(rbtfile != NULL);
        REQUIRE(data != NULL);
+       REQUIRE(version != NULL);
+
+       serial = version->serial;
 
        for (; header != NULL; header = next) {
                next = header->next;
@@ -7268,7 +7275,7 @@ rbt_datawriter(FILE *rbtfile, unsigned char *data, isc_uint32_t serial,
                if (header == NULL)
                        continue;
 
-               where = ftell(rbtfile);
+               CHECK(isc_stdio_tell(rbtfile, &where));
                size = dns_rdataslab_size((unsigned char *) header,
                                          sizeof(rdatasetheader_t));
 
@@ -7298,30 +7305,26 @@ rbt_datawriter(FILE *rbtfile, unsigned char *data, isc_uint32_t serial,
 #endif
                isc_crc64_update(crc, (unsigned char *) &newheader,
                                 sizeof(rdatasetheader_t));
-               result = isc_stdio_write(&newheader,
-                                        sizeof(rdatasetheader_t), 1,
-                                        rbtfile, NULL);
-               if (result != ISC_R_SUCCESS)
-                       return (result);
+               CHECK(isc_stdio_write(&newheader, sizeof(rdatasetheader_t), 1,
+                                     rbtfile, NULL));
 
                isc_crc64_update(crc, p + sizeof(rdatasetheader_t),
                                 size - sizeof(rdatasetheader_t));
-               result = isc_stdio_write(p + sizeof(rdatasetheader_t),
-                            size - sizeof(rdatasetheader_t), 1, rbtfile, NULL);
-               if (result != ISC_R_SUCCESS)
-                       return (result);
+               CHECK(isc_stdio_write(p + sizeof(rdatasetheader_t),
+                                     size - sizeof(rdatasetheader_t), 1,
+                                     rbtfile, NULL));
                /*
                 * Pad to force alignment.
                 */
-               if (cooked != size) {
-                       result = isc_stdio_write(pad, cooked - size, 1,
-                                                rbtfile, NULL);
-                       if (result != ISC_R_SUCCESS)
-                               return (result);
+               if (size != (size_t) cooked) {
+                       memset(pad, 0, sizeof(pad));
+                       CHECK(isc_stdio_write(pad, cooked - size, 1,
+                                             rbtfile, NULL));
                }
        }
 
-       return (ISC_R_SUCCESS);
+ failure:
+       return (result);
 }
 
 /*
@@ -7348,8 +7351,8 @@ rbtdb_zero_header(FILE *rbtfile) {
  * itself that should be stored here.
  */
 static isc_result_t
-rbtdb_write_header(FILE *rbtfile, long tree_location, long nsec_location,
-                  long nsec3_location)
+rbtdb_write_header(FILE *rbtfile, off_t tree_location, off_t nsec_location,
+                  off_t nsec3_location)
 {
        rbtdb_file_header_t header;
        isc_result_t result;
@@ -7365,9 +7368,9 @@ rbtdb_write_header(FILE *rbtfile, long tree_location, long nsec_location,
        memcpy(header.version2, FILE_VERSION, sizeof(header.version2));
        header.ptrsize = (isc_uint32_t) sizeof(void *);
        header.bigendian = (1 == htonl(1)) ? 1 : 0;
-       header.tree = tree_location;
-       header.nsec = nsec_location;
-       header.nsec3 = nsec3_location;
+       header.tree = (isc_uint64_t) tree_location;
+       header.nsec = (isc_uint64_t) nsec_location;
+       header.nsec3 = (isc_uint64_t) nsec3_location;
        result = isc_stdio_write(&header, 1, sizeof(rbtdb_file_header_t),
                              rbtfile, NULL);
        fflush(rbtfile);
@@ -7380,10 +7383,7 @@ serialize(dns_db_t *db, dns_dbversion_t *ver, FILE *rbtfile) {
        rbtdb_version_t *version = (rbtdb_version_t *) ver;
        dns_rbtdb_t *rbtdb;
        isc_result_t result;
-       long tree_location;
-       long nsec_location;
-       long nsec3_location;
-       long header_location;
+       off_t tree_location, nsec_location, nsec3_location, header_location;
 
        rbtdb = (dns_rbtdb_t *)db;
 
@@ -7405,20 +7405,14 @@ serialize(dns_db_t *db, dns_dbversion_t *ver, FILE *rbtfile) {
         * NOTE: need to do something better with the return codes, &= will
         * not work.
         */
-       header_location = ftell(rbtfile);
-       if (header_location < 0)
-               return (ISC_R_FAILURE);
-
+       CHECK(isc_stdio_tell(rbtfile, &header_location));
        CHECK(rbtdb_zero_header(rbtfile));
        CHECK(dns_rbt_serialize_tree(rbtfile, rbtdb->tree, rbt_datawriter,
-                                    (isc_uint32_t) version->serial,
-                                    &tree_location));
+                                    version, &tree_location));
        CHECK(dns_rbt_serialize_tree(rbtfile, rbtdb->nsec, rbt_datawriter,
-                                    (isc_uint32_t) version->serial,
-                                    &nsec_location));
+                                    version, &nsec_location));
        CHECK(dns_rbt_serialize_tree(rbtfile, rbtdb->nsec3, rbt_datawriter,
-                                    (isc_uint32_t) version->serial,
-                                    &nsec3_location));
+                                    version, &nsec3_location));
 
        CHECK(isc_stdio_seek(rbtfile, header_location, SEEK_SET));
        CHECK(rbtdb_write_header(rbtfile, tree_location, nsec_location,
index 01fab10da7f2df43e51befe95ed4cdaba3a91b81..2ab2425c489a7a27dabc40236f0b79c539f8f79f 100644 (file)
@@ -46,6 +46,7 @@
 #include <isc/os.h>
 #include <isc/string.h>
 #include <isc/socket.h>
+#include <isc/stdio.h>
 #include <isc/task.h>
 #include <isc/timer.h>
 #include <isc/util.h>
@@ -106,20 +107,25 @@ delete_data(void *data, void *arg) {
 }
 
 static isc_result_t
-write_data(FILE *file, unsigned char *datap, isc_uint32_t serial,
-          isc_uint64_t *crc) {
+write_data(FILE *file, unsigned char *datap, void *arg, isc_uint64_t *crc) {
+       isc_result_t result;
        size_t ret = 0;
        data_holder_t *data = (data_holder_t *)datap;
        data_holder_t temp;
-       uintptr_t where = ftell(file);
+       off_t where;
 
-       UNUSED(serial);
+       UNUSED(arg);
 
+       REQUIRE(file != NULL);
        REQUIRE(crc != NULL);
        REQUIRE(data != NULL);
        REQUIRE((data->len == 0 && data->data == NULL) ||
                (data->len != 0 && data->data != NULL));
 
+       result = isc_stdio_tell(file, &where);
+       if (result != ISC_R_SUCCESS)
+               return (result);
+
        temp = *data;
        temp.data = (data->len == 0
                     ? NULL
@@ -332,7 +338,8 @@ ATF_TC_BODY(serialize, tc) {
        printf("serialization begins.\n");
        rbtfile = fopen("./zone.bin", "w+b");
        ATF_REQUIRE(rbtfile != NULL);
-       result = dns_rbt_serialize_tree(rbtfile, rbt, write_data, 0, &offset);
+       result = dns_rbt_serialize_tree(rbtfile, rbt, write_data, NULL,
+                                       &offset);
        ATF_REQUIRE(result == ISC_R_SUCCESS);
        dns_rbt_destroy(&rbt);
 
@@ -400,7 +407,8 @@ ATF_TC_BODY(deserialize_corrupt, tc) {
        add_test_data(mctx, rbt);
        rbtfile = fopen("./zone.bin", "w+b");
        ATF_REQUIRE(rbtfile != NULL);
-       result = dns_rbt_serialize_tree(rbtfile, rbt, write_data, 0, &offset);
+       result = dns_rbt_serialize_tree(rbtfile, rbt, write_data, NULL,
+                                       &offset);
        ATF_REQUIRE(result == ISC_R_SUCCESS);
        dns_rbt_destroy(&rbt);
 
index 1a7ae642d5eba2e8903dbf39ad304e460003e129..2cade512b6cac6f31ad9480a92df38c0eed75d60 100644 (file)
@@ -48,7 +48,11 @@ isc_stdio_close(FILE *f);
 
 /*% Seek */
 isc_result_t
-isc_stdio_seek(FILE *f, long offset, int whence);
+isc_stdio_seek(FILE *f, off_t offset, int whence);
+
+/*% Tell */
+isc_result_t
+isc_stdio_tell(FILE *f, off_t *offsetp);
 
 /*% Read */
 isc_result_t
index f20aa295ca9c2c3b278c0af829028d99232e0b8b..2fc1953be47b7c79ce04c28cfc2aba719a384bba 100644 (file)
@@ -58,6 +58,10 @@ isc___errno2result(int posixerrno, const char *file, unsigned int line) {
        case ENFILE:
        case EMFILE:
                return (ISC_R_TOOMANYOPENFILES);
+#ifdef EOVERFLOW
+       case EOVERFLOW:
+               return (ISC_R_RANGE);
+#endif
        case EPIPE:
 #ifdef ECONNRESET
        case ECONNRESET:
index 360c8c644afc214bf8be70cdeb496dceaf9e5d11..6adfd701679d05426e69b3c53da2bf6e0ae5b68e 100644 (file)
@@ -24,6 +24,7 @@
 
 #include <isc/stdio.h>
 #include <isc/stat.h>
+#include <isc/util.h>
 
 #include "errno2result.h"
 
@@ -50,16 +51,30 @@ isc_stdio_close(FILE *f) {
 }
 
 isc_result_t
-isc_stdio_seek(FILE *f, long offset, int whence) {
+isc_stdio_seek(FILE *f, off_t offset, int whence) {
        int r;
 
-       r = fseek(f, offset, whence);
+       r = fseeko(f, offset, whence);
        if (r == 0)
                return (ISC_R_SUCCESS);
        else
                return (isc__errno2result(errno));
 }
 
+isc_result_t
+isc_stdio_tell(FILE *f, off_t *offsetp) {
+       off_t r;
+
+       REQUIRE(offsetp != NULL);
+
+       r = ftello(f);
+       if (r >= 0) {
+               *offsetp = r;
+               return (ISC_R_SUCCESS);
+       } else
+               return (isc__errno2result(errno));
+}
+
 isc_result_t
 isc_stdio_read(void *ptr, size_t size, size_t nmemb, FILE *f, size_t *nret) {
        isc_result_t result = ISC_R_SUCCESS;
index c3d54d632e8dbfbe4763932fc05773d8920062ba..2ff09e542e563df389f640e3477be6ad616fc453 100644 (file)
@@ -57,6 +57,10 @@ isc__errno2resultx(int posixerrno, const char *file, int line) {
                return (ISC_R_IOERROR);
        case ENOMEM:
                return (ISC_R_NOMEMORY);
+#ifdef EOVERFLOW
+       case EOVERFLOW:
+               return (ISC_R_RANGE);
+#endif
        case ENFILE:
        case EMFILE:
        case WSAEMFILE:
index 02dd93d94146830ddbe74c2d43baf1fbffb71e1e..7f3cb62e18625aef7491febae642156a5d561663 100644 (file)
@@ -512,6 +512,7 @@ isc_stdio_open
 isc_stdio_read
 isc_stdio_seek
 isc_stdio_sync
+isc_stdio_tell
 isc_stdio_write
 isc_stdtime_get
 isc_string_append
index 427a8e1e1872dd31711345dccfe55217cb4b0c48..7ff233fee337f7703ef7fdd81fdb0dacc480a4ae 100644 (file)
@@ -23,6 +23,7 @@
 #include <errno.h>
 
 #include <isc/stdio.h>
+#include <isc/util.h>
 
 #include "errno2result.h"
 
@@ -49,16 +50,30 @@ isc_stdio_close(FILE *f) {
 }
 
 isc_result_t
-isc_stdio_seek(FILE *f, long offset, int whence) {
+isc_stdio_seek(FILE *f, off_t offset, int whence) {
        int r;
 
-       r = fseek(f, offset, whence);
+       r = fseeko(f, offset, whence);
        if (r == 0)
                return (ISC_R_SUCCESS);
        else
                return (isc__errno2result(errno));
 }
 
+isc_result_t
+isc_stdio_tell(FILE *f, off_t *offsetp) {
+       off_t r;
+
+       REQUIRE(offsetp != NULL);
+
+       r = ftello(f);
+       if (r >= 0) {
+               *offsetp = r;
+               return (ISC_R_SUCCESS);
+       } else
+               return (isc__errno2result(errno));
+}
+
 isc_result_t
 isc_stdio_read(void *ptr, size_t size, size_t nmemb, FILE *f, size_t *nret) {
        isc_result_t result = ISC_R_SUCCESS;