-
Notifications
You must be signed in to change notification settings - Fork 35
Description
Hi, there is a potential bug with how httpGetDateTime handles dates in far (but not super distant) future.
This bug was reproduced on 881de11.
Description
Both httpGetDateString and httpGetDateTime operate on a time_t value (8 bytes on modern systems). However, parsing a date near the 2^32-1 boundary (e.g. Sun, 07 Feb 2106 06:28:15 GMT) causes a rounding error which leads httpGetDateTime to produce incorrect results.
I believe the cause is due to use of int internally, hence the arithmetic wraps around and is the cast to time_t which sign extends.
POC
The following testcase demonstrates the bug:
testcase.cpp
#include <cstdio>
#include <ctime>
#include <cassert>
extern "C" {
#include "/fuzz/src/cups/http.h"
}
int main(){
char buf[64];
printf("sizeof(time_t): %zu\n", sizeof(time_t));
time_t t = (time_t)4294967295ULL; // Sun, 07 Feb 2106 06:28:15 GMT (2^32-1)
printf("t: %zu\n", t);
if (!httpGetDateString(t, buf, sizeof(buf))) return 0; // formatting succeeded in testing
printf("buf: %s\n", buf);
time_t parsed = httpGetDateTime(buf);
printf("parsed: %zu\n", parsed);
assert(parsed == t);
return 0;
}
stdout
sizeof(time_t): 8
t: 4294967295
buf: Sun, 07 Feb 2106 06:28:15 GMT
parsed: 18446744073709551615
test: /fuzz/testcase.cpp:16: int main(): Assertion `parsed == t' failed.
Steps to Reproduce
The crash was triaged with the following Dockerfile:
Dockerfile
# Ubuntu 22.04 with some packages pre-installed
FROM hgarrereyn/stitch_repro_base@sha256:3ae94cdb7bf2660f4941dc523fe48cd2555049f6fb7d17577f5efd32a40fdd2c
RUN git clone https://github.com/OpenPrinting/libcups.git /fuzz/src && \
cd /fuzz/src && \
git checkout 881de116d71c695f125bf2d47acc3a988b9afaee && \
git submodule update --init --remote --recursive
ENV LD_LIBRARY_PATH=/fuzz/install/lib
ENV ASAN_OPTIONS=hard_rss_limit_mb=1024:detect_leaks=0
RUN echo '#!/bin/bash\nexec clang-17 -fsanitize=address -O0 "$@"' > /usr/local/bin/clang_wrapper && \
chmod +x /usr/local/bin/clang_wrapper && \
echo '#!/bin/bash\nexec clang++-17 -fsanitize=address -O0 "$@"' > /usr/local/bin/clang_wrapper++ && \
chmod +x /usr/local/bin/clang_wrapper++
# Install build dependencies
RUN apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y --no-install-recommends \
pkg-config \
libavahi-client-dev \
libnss-mdns \
libssl-dev \
zlib1g-dev \
libpng-dev \
ca-certificates \
make \
&& rm -rf /var/lib/apt/lists/*
# Provide a dummy pdfio pkg-config file so configure doesn't try to build the embedded submodule
# We won't build the tools that require PDFio, only the libcups library.
RUN mkdir -p /usr/local/lib/pkgconfig && \
printf "prefix=/usr/local\nexec_prefix=\${prefix}\nlibdir=\${exec_prefix}/lib\nincludedir=\${prefix}/include\n\nName: pdfio\nDescription: Dummy PDFio for building libcups library only\nVersion: 1.6.0\nLibs: \nCflags: \n" > /usr/local/lib/pkgconfig/pdfio.pc
# Build and install libcups (static only) into /fuzz/install
WORKDIR /fuzz/src
ENV CC=clang_wrapper CXX=clang_wrapper++
RUN ./configure --prefix=/fuzz/install --disable-shared --enable-static --with-tls=openssl --disable-dbus
# Build only the library (skip tools that may need external PDFio)
RUN make -j"$(nproc)" DIRS=cups && make -j"$(nproc)" DIRS=cups installBuild Command
clang++-17 -fsanitize=address -g -O0 -o /fuzz/test /fuzz/testcase.cpp -I/fuzz/src/cups -I/fuzz/install/include/cups -L/fuzz/install/lib -lcups3 -lavahi-client -lavahi-common -lssl -lcrypto -lz -lpthread -lm && /fuzz/testReproduce
- Copy
Dockerfileandtestcase.cppinto a local folder. - Build the repro image:
docker build . -t repro --platform=linux/amd64- Compile and run the testcase in the image:
docker run \
-it --rm \
--platform linux/amd64 \
--mount type=bind,source="testcase.cpp",target=/fuzz/testcase.cpp \
repro \
bash -c "clang++-17 -fsanitize=address -g -O0 -o /fuzz/test /fuzz/testcase.cpp -I/fuzz/src/cups -I/fuzz/install/include/cups -L/fuzz/install/lib -lcups3 -lavahi-client -lavahi-common -lssl -lcrypto -lz -lpthread -lm && /fuzz/test"Additional Info
This testcase was discovered by STITCH, an autonomous fuzzing system. All reports are reviewed manually (by a human) before submission.