From c9de6c53dcf3eb1071c7999c8accc43ef2b3f458 Mon Sep 17 00:00:00 2001 From: Mark Adler Date: Sun, 24 Jan 2021 22:00:00 -0800 Subject: [PATCH] Portability improvements. Avoid many bogus warnings across versions of gcc. Work around missing definitions on some systems. Fix some printf format types. --- pigz.c | 77 ++++++++++++++++++++----------------- try.h | 6 +-- zopfli/src/zopfli/cache.c | 2 +- zopfli/src/zopfli/deflate.c | 13 ++++--- 4 files changed, 53 insertions(+), 45 deletions(-) diff --git a/pigz.c b/pigz.c index 7430e1e..6ec3a82 100644 --- a/pigz.c +++ b/pigz.c @@ -333,7 +333,7 @@ // Portability defines. #define _FILE_OFFSET_BITS 64 // Use large file functions #define _LARGE_FILES // Same thing for AIX -#define _POSIX_C_SOURCE 200809L // For MinGW +#define _XOPEN_SOURCE 700 // For POSIX 2008 // Included headers and what is expected from each. #include // fflush(), fprintf(), fputs(), getchar(), putc(), @@ -874,10 +874,10 @@ local void log_dump(void) { ; log_free(); if (mem_track.num || mem_track.size) - complain("memory leak: %lu allocs of %lu bytes total", + complain("memory leak: %zu allocs of %zu bytes total", mem_track.num, mem_track.size); if (mem_track.max) - fprintf(stderr, "%lu bytes of memory used in %lu allocs\n", + fprintf(stderr, "%zu bytes of memory used in %zu allocs\n", mem_track.max, mem_track.tot); } @@ -993,7 +993,7 @@ local size_t writen(int desc, void const *buf, size_t len) { size_t left = len; while (left) { - size_t const max = SIZE_MAX >> 1; // max ssize_t + size_t const max = SSIZE_MAX; ssize_t ret = write(desc, next, left > max ? max : left); if (ret < 1) throw(errno, "write error on %s (%s)", g.outf, strerror(errno)); @@ -1668,26 +1668,32 @@ local void compress_thread(void *dummy) { size_t len; // remaining bytes to compress/check #if ZLIB_VERNUM >= 0x1260 int bits; // deflate pending bits -#endif -#ifndef NOZOPFLI - struct space *temp = NULL; // temporary space for zopfli input #endif int ret; // zlib return code - z_stream strm; // deflate stream ball_t err; // error information from throw() (void)dummy; try { - // initialize the deflate stream for this thread - strm.zfree = ZFREE; - strm.zalloc = ZALLOC; - strm.opaque = OPAQUE; - ret = deflateInit2(&strm, 6, Z_DEFLATED, -15, 8, Z_DEFAULT_STRATEGY); - if (ret == Z_MEM_ERROR) - throw(ENOMEM, "not enough memory"); - if (ret != Z_OK) - throw(EINVAL, "internal error"); + z_stream strm; // deflate stream +#ifndef NOZOPFLI + struct space *temp = NULL; + // get temporary space for zopfli input + if (g.level > 9) + temp = get_space(&out_pool); + else +#endif + { + // initialize the deflate stream for this thread + strm.zfree = ZFREE; + strm.zalloc = ZALLOC; + strm.opaque = OPAQUE; + ret = deflateInit2(&strm, 6, Z_DEFLATED, -15, 8, Z_DEFAULT_STRATEGY); + if (ret == Z_MEM_ERROR) + throw(ENOMEM, "not enough memory"); + if (ret != Z_OK) + throw(EINVAL, "internal error"); + } // keep looking for work for (;;) { @@ -1714,11 +1720,8 @@ local void compress_thread(void *dummy) { (void)deflateParams(&strm, g.level, Z_DEFAULT_STRATEGY); #ifndef NOZOPFLI } - else { - if (temp == NULL) - temp = get_space(&out_pool); + else temp->len = 0; - } #endif // set dictionary if provided, release that input or dictionary @@ -1912,11 +1915,15 @@ local void compress_thread(void *dummy) { } // found job with seq == -1 -- return to join + release(compress_have); #ifndef NOZOPFLI - drop_space(temp); + if (g.level > 9) + drop_space(temp); + else #endif - release(compress_have); - (void)deflateEnd(&strm); + { + (void)deflateEnd(&strm); + } } catch (err) { THREADABORT(err); @@ -3078,7 +3085,7 @@ local void show_info(int method, unsigned long check, length_t len, int cont) { strncpy(tag, "<...>", max + 1); else if (g.hname == NULL) { n = strlen(g.inf) - compressed_suffix(g.inf); - strncpy(tag, g.inf, n > max + 1 ? max + 1 : n); + memcpy(tag, g.inf, n > max + 1 ? max + 1 : n); if (strcmp(g.inf + n, ".tgz") == 0 && n < max + 1) strncpy(tag + n, ".tar", max + 1 - n); } @@ -3802,37 +3809,33 @@ local char *justname(char *path) { return p == NULL ? path : p + 1; } -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wunused-result" - // Copy file attributes, from -> to, as best we can. This is best effort, so no // errors are reported. The mode bits, including suid, sgid, and the sticky bit // are copied (if allowed), the owner's user id and group id are copied (again // if allowed), and the access and modify times are copied. -local void copymeta(char *from, char *to) { +local int copymeta(char *from, char *to) { struct stat st; struct timeval times[2]; // get all of from's Unix meta data, return if not a regular file if (stat(from, &st) != 0 || (st.st_mode & S_IFMT) != S_IFREG) - return; + return -4; // set to's mode bits, ignore errors - (void)chmod(to, st.st_mode & 07777); + int ret = chmod(to, st.st_mode & 07777); // copy owner's user and group, ignore errors - (void)chown(to, st.st_uid, st.st_gid); + ret += chown(to, st.st_uid, st.st_gid); // copy access and modify times, ignore errors times[0].tv_sec = st.st_atime; times[0].tv_usec = 0; times[1].tv_sec = st.st_mtime; times[1].tv_usec = 0; - (void)utimes(to, times); + ret += utimes(to, times); + return ret; } -#pragma GCC diagnostic pop - // Set the access and modify times of fd to t. local void touch(char *path, time_t t) { struct timeval times[2]; @@ -4430,6 +4433,7 @@ local int option(char *arg) { puts("Subject to the terms of the zlib license."); puts("No warranty is provided or implied."); exit(0); + break; // avoid warning case 'M': g.headis |= 0xa; break; case 'N': g.headis = 0xf; break; #ifndef NOZOPFLI @@ -4443,13 +4447,16 @@ local int option(char *arg) { if (g.verbosity > 1) printf("zlib %s\n", zlibVersion()); exit(0); + break; // avoid warning case 'Y': g.sync = 1; break; case 'Z': throw(EINVAL, "invalid option: LZW output not supported: %s", bad); + break; // avoid warning case 'a': throw(EINVAL, "invalid option: no ascii conversion: %s", bad); + break; // avoid warning case 'b': get = 1; break; case 'c': g.pipeout = 1; break; case 'd': if (!g.decode) g.headis >>= 2; g.decode = 1; break; diff --git a/try.h b/try.h index 03289dd..3009f7d 100644 --- a/try.h +++ b/try.h @@ -304,8 +304,8 @@ struct try_s_ { # define try_stack_ ((try_t_ *)pthread_getspecific(try_key_)) # define try_stack_set_(next) \ do { \ - int try_ret_ = pthread_setspecific(try_key_, next); \ - assert(try_ret_ == 0 && "try: pthread_setspecific() failed"); \ + assert(pthread_setspecific(try_key_, next) == 0 && \ + "try: pthread_setspecific() failed"); \ } while (0) #else /* !PTHREAD_ONCE_INIT */ extern try_t_ *try_stack_; @@ -320,7 +320,7 @@ struct try_s_ { #define TRY_TRY_ \ do { \ try_t_ try_this_; \ - int try_pushed_ = 1; \ + volatile int try_pushed_ = 1; \ try_this_.ball.code = 0; \ try_this_.ball.free = 0; \ try_this_.ball.why = NULL; \ diff --git a/zopfli/src/zopfli/cache.c b/zopfli/src/zopfli/cache.c index f5559c3..e5934df 100644 --- a/zopfli/src/zopfli/cache.c +++ b/zopfli/src/zopfli/cache.c @@ -33,7 +33,7 @@ void ZopfliInitCache(size_t blocksize, ZopfliLongestMatchCache* lmc) { lmc->sublen = (unsigned char*)malloc(ZOPFLI_CACHE_LENGTH * 3 * blocksize); if(lmc->sublen == NULL) { fprintf(stderr, - "Error: Out of memory. Tried allocating %lu bytes of memory.\n", + "Error: Out of memory. Tried allocating %zu bytes of memory.\n", ZOPFLI_CACHE_LENGTH * 3 * blocksize); exit (EXIT_FAILURE); } diff --git a/zopfli/src/zopfli/deflate.c b/zopfli/src/zopfli/deflate.c index abe7360..f7b62e4 100644 --- a/zopfli/src/zopfli/deflate.c +++ b/zopfli/src/zopfli/deflate.c @@ -431,22 +431,23 @@ Changes the population counts in a way that the consequent Huffman tree compression, especially its rle-part, will be more likely to compress this data more efficiently. length contains the size of the histogram. */ -void OptimizeHuffmanForRle(int length, size_t* counts) { - int i, k, stride; +void OptimizeHuffmanForRle(unsigned length, size_t* counts) { + unsigned i; + int k, stride; size_t symbol, sum, limit; int* good_for_rle; /* 1) We don't want to touch the trailing zeros. We may break the rules of the format by adding more data in the distance codes. */ - for (; length >= 0; --length) { - if (length == 0) { - return; - } + for (; length > 0; --length) { if (counts[length - 1] != 0) { /* Now counts[0..length - 1] does not have trailing zeros. */ break; } } + if (length == 0) { + return; + } /* 2) Let's mark all population counts that already can be encoded with an rle code.*/ good_for_rle = (int*)malloc(length * sizeof(int));