From 1604c0fe0e5ce74538555c19a307ad38d0fca358 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 10 Jul 2018 10:14:24 -0400 Subject: [PATCH 1/7] Add the compatibility definition for getdelim.c from netbsd. We shouldn't actually need this code nearly anywhere we build: getdelim is POSIX, and mingw provides it. --- LICENSE | 30 +++++++++++++++++ src/ext/getdelim.c | 82 ++++++++++++++++++++++++++++++++++++++++++++++ src/ext/include.am | 2 +- 3 files changed, 113 insertions(+), 1 deletion(-) create mode 100644 src/ext/getdelim.c diff --git a/LICENSE b/LICENSE index 057ae57652..9e2709aea6 100644 --- a/LICENSE +++ b/LICENSE @@ -155,6 +155,36 @@ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +=============================================================================== +getdelim.c is distributed under this license: + + Copyright (c) 2011 The NetBSD Foundation, Inc. + All rights reserved. + + This code is derived from software contributed to The NetBSD Foundation + by Christos Zoulas. + + Redistribution and use in source and binary forms, with or without + modification, are permitted provided that the following conditions + are met: + 1. Redistributions of source code must retain the above copyright + notice, this list of conditions and the following disclaimer. + 2. Redistributions in binary form must reproduce the above copyright + notice, this list of conditions and the following disclaimer in the + documentation and/or other materials provided with the distribution. + + THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS + ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS + BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + POSSIBILITY OF SUCH DAMAGE. + =============================================================================== src/config/geoip is licensed under the following license: diff --git a/src/ext/getdelim.c b/src/ext/getdelim.c new file mode 100644 index 0000000000..60df7e1b64 --- /dev/null +++ b/src/ext/getdelim.c @@ -0,0 +1,82 @@ +/* $NetBSD: getdelim.c,v 1.2 2015/12/25 20:12:46 joerg Exp $ */ +/* NetBSD-src: getline.c,v 1.2 2014/09/16 17:23:50 christos Exp */ + +/*- + * Copyright (c) 2011 The NetBSD Foundation, Inc. + * All rights reserved. + * + * This code is derived from software contributed to The NetBSD Foundation + * by Christos Zoulas. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS + * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#include +#include +#include + +#if !HAVE_GETDELIM + +ssize_t +getdelim(char **buf, size_t *bufsiz, int delimiter, FILE *fp) +{ + char *ptr, *eptr; + + + if (*buf == NULL || *bufsiz == 0) { + *bufsiz = BUFSIZ; + if ((*buf = malloc(*bufsiz)) == NULL) + return -1; + } + + for (ptr = *buf, eptr = *buf + *bufsiz;;) { + int c = fgetc(fp); + if (c == -1) { + if (feof(fp)) { + ssize_t diff = (ssize_t)(ptr - *buf); + if (diff != 0) { + *ptr = '\0'; + return diff; + } + } + return -1; + } + *ptr++ = c; + if (c == delimiter) { + *ptr = '\0'; + return ptr - *buf; + } + if (ptr + 2 >= eptr) { + char *nbuf; + size_t nbufsiz = *bufsiz * 2; + ssize_t d = ptr - *buf; + if ((nbuf = realloc(*buf, nbufsiz)) == NULL) + return -1; + *buf = nbuf; + *bufsiz = nbufsiz; + eptr = nbuf + nbufsiz; + ptr = nbuf + d; + } + } +} + +#endif diff --git a/src/ext/include.am b/src/ext/include.am index 7ec2e43312..6bdce2d79e 100644 --- a/src/ext/include.am +++ b/src/ext/include.am @@ -10,6 +10,7 @@ EXTHEADERS = \ src/ext/tor_readpassphrase.h \ src/ext/strlcat.c \ src/ext/strlcpy.c \ + src/ext/getdelim.c \ src/ext/tinytest_macros.h \ src/ext/tor_queue.h \ src/ext/siphash.h \ @@ -173,4 +174,3 @@ EXTRA_DIST += \ src/ext/timeouts/Makefile \ src/ext/timeouts/Rules.shrc \ src/ext/timeouts/test-timeout.c - From b04d719c1067dd1cf9b48295f1d0e7ed5adb7255 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 10 Jul 2018 10:23:29 -0400 Subject: [PATCH 2/7] Integrate getdelim() and getline() support into Tor. --- configure.ac | 2 ++ src/ext/getdelim.c | 16 ++++++---------- src/lib/fs/.may_include | 3 +++ src/lib/fs/files.c | 4 ++++ src/lib/fs/files.h | 34 ++++++++++++++++++++++++++++++++++ 5 files changed, 49 insertions(+), 10 deletions(-) diff --git a/configure.ac b/configure.ac index 296591f025..ff03cf10e9 100644 --- a/configure.ac +++ b/configure.ac @@ -585,7 +585,9 @@ AC_CHECK_FUNCS( ftime \ get_current_dir_name \ getaddrinfo \ + getdelim \ getifaddrs \ + getline \ getpass \ getrlimit \ gettimeofday \ diff --git a/src/ext/getdelim.c b/src/ext/getdelim.c index 60df7e1b64..8254103ff9 100644 --- a/src/ext/getdelim.c +++ b/src/ext/getdelim.c @@ -30,21 +30,19 @@ * POSSIBILITY OF SUCH DAMAGE. */ -#include -#include -#include - -#if !HAVE_GETDELIM +#ifndef BUFSIZ +#define BUFSIZ 512 +#endif ssize_t -getdelim(char **buf, size_t *bufsiz, int delimiter, FILE *fp) +compat_getdelim_(char **buf, size_t *bufsiz, int delimiter, FILE *fp) { char *ptr, *eptr; if (*buf == NULL || *bufsiz == 0) { *bufsiz = BUFSIZ; - if ((*buf = malloc(*bufsiz)) == NULL) + if ((*buf = raw_malloc(*bufsiz)) == NULL) return -1; } @@ -69,7 +67,7 @@ getdelim(char **buf, size_t *bufsiz, int delimiter, FILE *fp) char *nbuf; size_t nbufsiz = *bufsiz * 2; ssize_t d = ptr - *buf; - if ((nbuf = realloc(*buf, nbufsiz)) == NULL) + if ((nbuf = raw_realloc(*buf, nbufsiz)) == NULL) return -1; *buf = nbuf; *bufsiz = nbufsiz; @@ -78,5 +76,3 @@ getdelim(char **buf, size_t *bufsiz, int delimiter, FILE *fp) } } } - -#endif diff --git a/src/lib/fs/.may_include b/src/lib/fs/.may_include index 6c9ce6ca04..b1e49fc891 100644 --- a/src/lib/fs/.may_include +++ b/src/lib/fs/.may_include @@ -1,4 +1,7 @@ orconfig.h + +ext/getdelim.c + lib/cc/*.h lib/container/*.h lib/encoding/*.h diff --git a/src/lib/fs/files.c b/src/lib/fs/files.c index 4e0a398baa..e93d36d86d 100644 --- a/src/lib/fs/files.c +++ b/src/lib/fs/files.c @@ -715,3 +715,7 @@ read_file_to_str, (const char *filename, int flags, struct stat *stat_out)) return string; } + +#if !defined(HAVE_GETDELIM) || defined(TOR_UNIT_TESTS) +#include "ext/getdelim.c" +#endif diff --git a/src/lib/fs/files.h b/src/lib/fs/files.h index 5a12eb8215..d219e3cf05 100644 --- a/src/lib/fs/files.h +++ b/src/lib/fs/files.h @@ -103,4 +103,38 @@ char *read_file_to_str_until_eof(int fd, size_t max_bytes_to_read, size_t *sz_out) ATTR_MALLOC; +#if !defined(HAVE_GETDELIM) || defined(TOR_UNIT_TESTS) +ssize_t compat_getdelim_(char **lineptr, size_t *n, int delim, FILE *stream); +#endif + +#ifdef HAVE_GETDELIM +/** + * Cross-platform wrapper for getdelim(): behaves as the POSIX-standard + * getdelim() function. + * + * Note that this function will use the libc memory allocator -- so any memory + * passed to this function must come from raw_malloc(), and must be freed by + * raw_free() -- don't use tor_malloc() and tor_free() with this. + */ +#define tor_getdelim(lineptr, n, delim, stream) \ + getdelim((lineptr), (n), (delim), (stream)) +#else +#define tor_getdelim(lineptr, n, delim, stream) \ + compat_getdelim_((lineptr), (n), (delim), (stream)) +#endif + +#ifdef HAVE_GETLINE +/** + * Cross-platform wrapper for getline(): behaves as the POSIX-standard + * getline() function. + * + * See tor_getdelim() for usage notes. + */ +#define tor_getline(lineptr, n, stream) \ + getline((lineptr), (n), (stream)) +#else +#define tor_getline(lineptr, n, stream) \ + tor_getdelim((lineptr), (n), '\n', (stream)) +#endif + #endif From 6574d4bd27471c30da934c4d8b82ecbe2b3eab7e Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 10 Jul 2018 10:26:22 -0400 Subject: [PATCH 3/7] Refactor dirserv_read_measured_bandwidths to have a single exit point --- src/feature/dircache/dirserv.c | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) diff --git a/src/feature/dircache/dirserv.c b/src/feature/dircache/dirserv.c index c5286b0cbf..50869c2b96 100644 --- a/src/feature/dircache/dirserv.c +++ b/src/feature/dircache/dirserv.c @@ -2616,6 +2616,7 @@ dirserv_read_measured_bandwidths(const char *from_file, * if there are additional header lines, as introduced in Bandwidth List spec * version 1.1.0 */ int line_is_after_headers = 0; + int rv = -1; /* Initialise line, so that we can't possibly run off the end. */ memset(line, 0, sizeof(line)); @@ -2623,21 +2624,19 @@ dirserv_read_measured_bandwidths(const char *from_file, if (fp == NULL) { log_warn(LD_CONFIG, "Can't open bandwidth file at configured location: %s", from_file); - return -1; + goto err; } /* If fgets fails, line is either unmodified, or indeterminate. */ if (!fgets(line, sizeof(line), fp)) { log_warn(LD_DIRSERV, "Empty bandwidth file"); - fclose(fp); - return -1; + goto err; } if (!strlen(line) || line[strlen(line)-1] != '\n') { log_warn(LD_DIRSERV, "Long or truncated time in bandwidth file: %s", escaped(line)); - fclose(fp); - return -1; + goto err; } line[strlen(line)-1] = '\0'; @@ -2645,16 +2644,14 @@ dirserv_read_measured_bandwidths(const char *from_file, if (!ok) { log_warn(LD_DIRSERV, "Non-integer time in bandwidth file: %s", escaped(line)); - fclose(fp); - return -1; + goto err; } now = time(NULL); if ((now - file_time) > MAX_MEASUREMENT_AGE) { log_warn(LD_DIRSERV, "Bandwidth measurement file stale. Age: %u", (unsigned)(time(NULL) - file_time)); - fclose(fp); - return -1; + goto err; } if (routerstatuses) @@ -2679,11 +2676,15 @@ dirserv_read_measured_bandwidths(const char *from_file, /* Now would be a nice time to clean the cache, too */ dirserv_expire_measured_bw_cache(now); - fclose(fp); log_info(LD_DIRSERV, "Bandwidth measurement file successfully read. " "Applied %d measurements.", applied_lines); - return 0; + rv = 0; + + err: + if (fp) + fclose(fp); + return rv; } /** As dirserv_get_routerdescs(), but instead of getting signed_descriptor_t From 951d59d706f116cbfa3d3700d9b342a736a571b2 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 10 Jul 2018 10:32:09 -0400 Subject: [PATCH 4/7] Use tor_getline() in dirserv.c to remove its upper line limit. Closes ticket 26223. --- changes/bug26223 | 3 +++ src/feature/dircache/dirserv.c | 10 ++++++---- 2 files changed, 9 insertions(+), 4 deletions(-) create mode 100644 changes/bug26223 diff --git a/changes/bug26223 b/changes/bug26223 new file mode 100644 index 0000000000..e17b0529e3 --- /dev/null +++ b/changes/bug26223 @@ -0,0 +1,3 @@ + o Minor features (directory authority): + - There is no longer an artificial upper limit on the length of bandwidth + lines. Closes ticket 26223. diff --git a/src/feature/dircache/dirserv.c b/src/feature/dircache/dirserv.c index 50869c2b96..57de6ab8ed 100644 --- a/src/feature/dircache/dirserv.c +++ b/src/feature/dircache/dirserv.c @@ -2606,7 +2606,6 @@ int dirserv_read_measured_bandwidths(const char *from_file, smartlist_t *routerstatuses) { - char line[512]; FILE *fp = tor_fopen_cloexec(from_file, "r"); int applied_lines = 0; time_t file_time, now; @@ -2617,9 +2616,10 @@ dirserv_read_measured_bandwidths(const char *from_file, * version 1.1.0 */ int line_is_after_headers = 0; int rv = -1; + char *line = NULL; + size_t n = 0; /* Initialise line, so that we can't possibly run off the end. */ - memset(line, 0, sizeof(line)); if (fp == NULL) { log_warn(LD_CONFIG, "Can't open bandwidth file at configured location: %s", @@ -2628,7 +2628,7 @@ dirserv_read_measured_bandwidths(const char *from_file, } /* If fgets fails, line is either unmodified, or indeterminate. */ - if (!fgets(line, sizeof(line), fp)) { + if (tor_getline(&line,&n,fp) <= 0) { log_warn(LD_DIRSERV, "Empty bandwidth file"); goto err; } @@ -2659,7 +2659,7 @@ dirserv_read_measured_bandwidths(const char *from_file, while (!feof(fp)) { measured_bw_line_t parsed_line; - if (fgets(line, sizeof(line), fp) && strlen(line)) { + if (tor_getline(&line, &n, fp) >= 0) { if (measured_bw_line_parse(&parsed_line, line, line_is_after_headers) != -1) { /* This condition will be true when the first complete valid bw line @@ -2682,6 +2682,8 @@ dirserv_read_measured_bandwidths(const char *from_file, rv = 0; err: + if (line) + raw_free(line); if (fp) fclose(fp); return rv; From c4dd38e625a105a5d5d29242a8531da9677c98d8 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 10 Jul 2018 20:15:23 -0400 Subject: [PATCH 5/7] Tabify lists in configure.ac --- configure.ac | 200 +++++++++++++++++++++++++-------------------------- 1 file changed, 100 insertions(+), 100 deletions(-) diff --git a/configure.ac b/configure.ac index ff03cf10e9..532476672a 100644 --- a/configure.ac +++ b/configure.ac @@ -572,60 +572,60 @@ AM_CONDITIONAL(THREADS_WIN32, test "$bwin32" = "true") AM_CONDITIONAL(THREADS_PTHREADS, test "$bwin32" = "false") AC_CHECK_FUNCS( - _NSGetEnviron \ + _NSGetEnviron \ RtlSecureZeroMemory \ SecureZeroMemory \ - accept4 \ - backtrace \ - backtrace_symbols_fd \ + accept4 \ + backtrace \ + backtrace_symbols_fd \ eventfd \ explicit_bzero \ timingsafe_memcmp \ - flock \ - ftime \ - get_current_dir_name \ - getaddrinfo \ + flock \ + ftime \ + get_current_dir_name \ + getaddrinfo \ getdelim \ - getifaddrs \ + getifaddrs \ getline \ - getpass \ - getrlimit \ - gettimeofday \ - gmtime_r \ + getpass \ + getrlimit \ + gettimeofday \ + gmtime_r \ gnu_get_libc_version \ htonll \ - inet_aton \ - ioctl \ - issetugid \ - llround \ - localtime_r \ - lround \ + inet_aton \ + ioctl \ + issetugid \ + llround \ + localtime_r \ + lround \ mach_approximate_time \ - memmem \ - memset_s \ - mmap \ + memmem \ + memset_s \ + mmap \ pipe \ pipe2 \ - prctl \ + prctl \ readpassphrase \ - rint \ - sigaction \ - socketpair \ + rint \ + sigaction \ + socketpair \ statvfs \ - strncasecmp \ - strcasecmp \ - strlcat \ - strlcpy \ + strncasecmp \ + strcasecmp \ + strlcat \ + strlcpy \ strnlen \ - strptime \ - strtok_r \ - strtoull \ - sysconf \ + strptime \ + strtok_r \ + strtoull \ + sysconf \ sysctl \ truncate \ - uname \ + uname \ usleep \ - vasprintf \ + vasprintf \ _vscprintf ) @@ -1367,57 +1367,57 @@ dnl Make sure to enable support for large off_t if available. AC_SYS_LARGEFILE AC_CHECK_HEADERS([errno.h \ - fcntl.h \ - signal.h \ - string.h \ - sys/capability.h \ - sys/fcntl.h \ - sys/stat.h \ - sys/time.h \ - sys/types.h \ - time.h \ - unistd.h \ - arpa/inet.h \ - crt_externs.h \ - execinfo.h \ - gnu/libc-version.h \ - grp.h \ - ifaddrs.h \ - inttypes.h \ - limits.h \ - linux/types.h \ - machine/limits.h \ - malloc.h \ - malloc/malloc.h \ - malloc_np.h \ - netdb.h \ - netinet/in.h \ - netinet/in6.h \ - pwd.h \ - readpassphrase.h \ - stdatomic.h \ - sys/eventfd.h \ - sys/file.h \ - sys/ioctl.h \ - sys/limits.h \ - sys/mman.h \ - sys/param.h \ - sys/prctl.h \ + fcntl.h \ + signal.h \ + string.h \ + sys/capability.h \ + sys/fcntl.h \ + sys/stat.h \ + sys/time.h \ + sys/types.h \ + time.h \ + unistd.h \ + arpa/inet.h \ + crt_externs.h \ + execinfo.h \ + gnu/libc-version.h \ + grp.h \ + ifaddrs.h \ + inttypes.h \ + limits.h \ + linux/types.h \ + machine/limits.h \ + malloc.h \ + malloc/malloc.h \ + malloc_np.h \ + netdb.h \ + netinet/in.h \ + netinet/in6.h \ + pwd.h \ + readpassphrase.h \ + stdatomic.h \ + sys/eventfd.h \ + sys/file.h \ + sys/ioctl.h \ + sys/limits.h \ + sys/mman.h \ + sys/param.h \ + sys/prctl.h \ sys/random.h \ - sys/resource.h \ - sys/select.h \ - sys/socket.h \ - sys/statvfs.h \ - sys/syscall.h \ - sys/sysctl.h \ - sys/syslimits.h \ - sys/time.h \ - sys/types.h \ - sys/un.h \ - sys/utime.h \ - sys/wait.h \ - syslog.h \ - utime.h]) + sys/resource.h \ + sys/select.h \ + sys/socket.h \ + sys/statvfs.h \ + sys/syscall.h \ + sys/sysctl.h \ + sys/syslimits.h \ + sys/time.h \ + sys/types.h \ + sys/un.h \ + sys/utime.h \ + sys/wait.h \ + syslog.h \ + utime.h]) AC_CHECK_HEADERS(sys/param.h) @@ -2271,20 +2271,20 @@ fi CPPFLAGS="$CPPFLAGS $TOR_CPPFLAGS_libevent $TOR_CPPFLAGS_openssl $TOR_CPPFLAGS_zlib" AC_CONFIG_FILES([ - Doxyfile - Makefile - config.rust - link_rust.sh - contrib/dist/suse/tor.sh - contrib/operator-tools/tor.logrotate - contrib/dist/tor.sh - contrib/dist/torctl - contrib/dist/tor.service - src/config/torrc.sample - src/config/torrc.minimal - src/rust/.cargo/config - scripts/maint/checkOptionDocs.pl - scripts/maint/updateVersions.pl + Doxyfile + Makefile + config.rust + link_rust.sh + contrib/dist/suse/tor.sh + contrib/operator-tools/tor.logrotate + contrib/dist/tor.sh + contrib/dist/torctl + contrib/dist/tor.service + src/config/torrc.sample + src/config/torrc.minimal + src/rust/.cargo/config + scripts/maint/checkOptionDocs.pl + scripts/maint/updateVersions.pl ]) if test "x$asciidoc" = "xtrue" && test "$ASCIIDOC" = "none"; then From 391ef5e42cc79982a28aaaf22e9f9b255f6910d3 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 10 Jul 2018 20:16:37 -0400 Subject: [PATCH 6/7] Explain why we use raw_free with getdelim result. --- src/feature/dircache/dirserv.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/feature/dircache/dirserv.c b/src/feature/dircache/dirserv.c index 57de6ab8ed..1500467ec0 100644 --- a/src/feature/dircache/dirserv.c +++ b/src/feature/dircache/dirserv.c @@ -2682,8 +2682,10 @@ dirserv_read_measured_bandwidths(const char *from_file, rv = 0; err: - if (line) + if (line) { + // we need to raw_free this buffer because we got it from tor_getdelim() raw_free(line); + } if (fp) fclose(fp); return rv; From c90961a9233e7287605886585503ee94d13a4592 Mon Sep 17 00:00:00 2001 From: Nick Mathewson Date: Tue, 10 Jul 2018 20:18:20 -0400 Subject: [PATCH 7/7] Document compat_getdelim_. --- src/lib/fs/files.h | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/lib/fs/files.h b/src/lib/fs/files.h index d219e3cf05..2ee1b20149 100644 --- a/src/lib/fs/files.h +++ b/src/lib/fs/files.h @@ -104,6 +104,9 @@ char *read_file_to_str_until_eof(int fd, size_t max_bytes_to_read, ATTR_MALLOC; #if !defined(HAVE_GETDELIM) || defined(TOR_UNIT_TESTS) +/** Internal back-end function to implement getdelim(): only exists when + * Tor is built for unit tests, or when Tor is built on an operating system + * without its own getdelim(). */ ssize_t compat_getdelim_(char **lineptr, size_t *n, int delim, FILE *stream); #endif @@ -112,6 +115,8 @@ ssize_t compat_getdelim_(char **lineptr, size_t *n, int delim, FILE *stream); * Cross-platform wrapper for getdelim(): behaves as the POSIX-standard * getdelim() function. * + * See `getdelim(3)` for more information. + * * Note that this function will use the libc memory allocator -- so any memory * passed to this function must come from raw_malloc(), and must be freed by * raw_free() -- don't use tor_malloc() and tor_free() with this.