Merge pull request #1469 from AFLplusplus/dev

push to stable
This commit is contained in:
van Hauser 2022-07-15 10:12:35 +02:00 committed by GitHub
commit c57988e672
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
118 changed files with 2436 additions and 1466 deletions

View File

@ -19,40 +19,22 @@ import subprocess
import sys
import os
import re
import shutil
# string_re = re.compile('(\\"(\\\\.|[^"\\\\])*\\")') # future use
with open(".clang-format") as f:
fmt = f.read()
CLANG_FORMAT_BIN = os.getenv("CLANG_FORMAT_BIN")
if CLANG_FORMAT_BIN is None:
o = 0
try:
p = subprocess.Popen(["clang-format-11", "--version"], stdout=subprocess.PIPE)
o, _ = p.communicate()
o = str(o, "utf-8")
o = re.sub(r".*ersion ", "", o)
# o = o[len("clang-format version "):].strip()
o = o[: o.find(".")]
o = int(o)
except:
print("clang-format-11 is needed. Aborted.")
exit(1)
# if o < 7:
# if subprocess.call(['which', 'clang-format-7'], stdout=subprocess.PIPE) == 0:
# CLANG_FORMAT_BIN = 'clang-format-7'
# elif subprocess.call(['which', 'clang-format-8'], stdout=subprocess.PIPE) == 0:
# CLANG_FORMAT_BIN = 'clang-format-8'
# elif subprocess.call(['which', 'clang-format-9'], stdout=subprocess.PIPE) == 0:
# CLANG_FORMAT_BIN = 'clang-format-9'
# elif subprocess.call(['which', 'clang-format-11'], stdout=subprocess.PIPE) == 0:
# CLANG_FORMAT_BIN = 'clang-format-11'
# else:
# print ("clang-format 7 or above is needed. Aborted.")
# exit(1)
else:
CLANG_FORMAT_BIN = "clang-format-11"
CURRENT_LLVM = os.getenv('LLVM_VERSION', 14)
CLANG_FORMAT_BIN = os.getenv("CLANG_FORMAT_BIN", "")
if shutil.which(CLANG_FORMAT_BIN) is None:
CLANG_FORMAT_BIN = f"clang-format-{CURRENT_LLVM}"
if shutil.which(CLANG_FORMAT_BIN) is None:
print(f"[!] clang-format-{CURRENT_LLVM} is needed. Aborted.")
exit(1)
COLUMN_LIMIT = 80
for line in fmt.split("\n"):

View File

@ -1,65 +1,75 @@
!/coresight_mode
*.dSYM
*.o
*.pyc
*.so
.sync_tmp
.test
.test2
.sync_tmp
*.o
*.so
*.pyc
*.dSYM
as
ld
in
out
core*
.git
.dockerignore
.github
CITATION.cff
CONTRIBUTING.md
Changelog.md
Dockerfile
LICENSE
TODO.md
afl-analyze
afl-as
afl-clang
afl-clang\+\+
afl-clang-fast
afl-clang-fast\+\+
afl-clang-lto
afl-clang-lto\+\+
afl-fuzz
afl-g\+\+
afl-gcc
afl-gcc-fast
afl-g\+\+-fast
afl-gotcpu
afl-ld
afl-ld-lto
afl-qemu-trace
afl-showmap
afl-tmin
afl-analyze.8
afl-as
afl-as.8
afl-clang-fast\+\+.8
afl-clang
afl-clang-fast
afl-clang-fast.8
afl-clang-fast\+\+
afl-clang-fast\+\+.8
afl-clang-lto
afl-clang-lto.8
afl-clang-lto\+\+
afl-clang-lto\+\+.8
afl-clang\+\+
afl-cmin.8
afl-cmin.bash.8
afl-fuzz
afl-fuzz.8
afl-gcc.8
afl-gcc-fast.8
afl-g\+\+
afl-g\+\+-fast
afl-g\+\+-fast.8
afl-gcc
afl-gcc-fast
afl-gcc-fast.8
afl-gcc.8
afl-gotcpu
afl-gotcpu.8
afl-ld
afl-ld-lto
afl-plot.8
afl-qemu-trace
afl-showmap
afl-showmap.8
afl-system-config.8
afl-tmin
afl-tmin.8
afl-whatsup.8
as
core*
examples/afl_frida/afl-frida
examples/afl_frida/frida-gum-example.c
examples/afl_frida/frida-gum.h
examples/afl_frida/libtestinstr.so
examples/afl_network_proxy/afl-network-client
examples/afl_network_proxy/afl-network-server
in
ld
out
qemu_mode/libcompcov/compcovtest
qemu_mode/qemu-*
test/unittests/unit_hash
test/unittests/unit_list
test/unittests/unit_maybe_alloc
test/unittests/unit_preallocable
test/unittests/unit_rand
unicorn_mode/samples/*/\.test-*
unicorn_mode/samples/*/output
unicorn_mode/unicornafl
test/unittests/unit_maybe_alloc
test/unittests/unit_preallocable
test/unittests/unit_list
test/unittests/unit_rand
test/unittests/unit_hash
examples/afl_network_proxy/afl-network-server
examples/afl_network_proxy/afl-network-client
examples/afl_frida/afl-frida
examples/afl_frida/libtestinstr.so
examples/afl_frida/frida-gum-example.c
examples/afl_frida/frida-gum.h

View File

@ -1,49 +0,0 @@
name: Publish Docker Images
on:
push:
branches:
- stable
- dev
tags:
- '*'
jobs:
push_to_registry:
name: Push Docker images to Dockerhub
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@master
- name: Set up QEMU
uses: docker/setup-qemu-action@v2
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v2
- name: Login to Dockerhub
uses: docker/login-action@v2
with:
username: ${{ secrets.DOCKER_USERNAME }}
password: ${{ secrets.DOCKER_TOKEN }}
- name: Publish dev as dev to docker.io registry
uses: docker/build-push-action@v3
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
tags: aflplusplus/aflplusplus:${{ github.ref_name }}
if: ${{ github.ref_name == 'dev' }}
- name: Publish stable as stable and latest to docker.io registry
uses: docker/build-push-action@v3
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
tags: aflplusplus/aflplusplus:${{ github.ref_name }},aflplusplus/aflplusplus:latest
if: ${{ github.ref_name == 'stable' }}
- name: Publish tagged release to docker.io registry
uses: docker/build-push-action@v3
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
tags: aflplusplus/aflplusplus:${{ github.ref_name }}
if: ${{ github.ref_type == 'tag' }}

View File

@ -2,13 +2,16 @@ name: CI
on:
push:
branches: [ stable, dev ]
branches:
- stable
- dev
pull_request:
branches: [ stable, dev ]
branches:
- dev # No need for stable-pull-request, as that equals dev-push
jobs:
linux:
runs-on: '${{ matrix.os }}'
runs-on: "${{ matrix.os }}"
strategy:
matrix:
os: [ubuntu-22.04, ubuntu-20.04, ubuntu-18.04]
@ -16,7 +19,7 @@ jobs:
AFL_SKIP_CPUFREQ: 1
AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES: 1
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
- name: debug
run: apt-cache search plugin-dev | grep gcc-; echo; apt-cache search clang-format- | grep clang-format-
- name: update
@ -38,9 +41,9 @@ jobs:
AFL_SKIP_CPUFREQ: 1
AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES: 1
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
- name: install
run: brew install make gcc
run: brew install make gcc llvm
- name: fix install
run: cd /usr/local/bin; ln -s gcc-11 gcc; ln -s g++-11 g++; which gcc; gcc -v
- name: build

33
.github/workflows/code-format.yml vendored Normal file
View File

@ -0,0 +1,33 @@
name: Formatting
on:
push:
branches:
- stable
- dev
pull_request:
branches:
- dev # No need for stable-pull-request, as that equals dev-push
jobs:
code-format-check:
name: Check code format
if: ${{ 'false' == 'true' }} # Disable the job
runs-on: ubuntu-22.04
container: docker.io/aflplusplus/aflplusplus:dev
steps:
- name: Checkout
uses: actions/checkout@v3
- name: Format
run: |
git config --global --add safe.directory /__w/AFLplusplus/AFLplusplus
apt-get update
apt-get install -y clang-format-${LLVM_VERSION}
make code-format
- name: Check if code needed formatting
run: |
git --no-pager -c color.ui=always diff HEAD
if ! git diff HEAD --quiet; then
echo "[!] Please run 'make code-format' and push its changes."
exit 1
fi

View File

@ -2,31 +2,32 @@ name: "CodeQL"
on:
push:
branches: [ stable, dev ]
branches:
- stable
- dev
pull_request:
branches: [ stable, dev ]
branches:
- dev # No need for stable-pull-request, as that equals dev-push
jobs:
analyze:
name: Analyze
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
language: [ 'cpp' ]
container: # We use a previous image as it's expected to have all the dependencies
image: docker.io/aflplusplus/aflplusplus:dev
steps:
- name: Checkout repository
uses: actions/checkout@v2
- name: Initialize CodeQL
uses: github/codeql-action/init@v1
with:
languages: ${{ matrix.language }}
- name: Autobuild
uses: github/codeql-action/autobuild@v1
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v1
- name: Fix for using external repo in container build # https://github.com/actions/checkout/issues/760
run: git config --global --add safe.directory /__w/AFLplusplus/AFLplusplus
- name: Checkout
uses: actions/checkout@v3
- name: Initialize CodeQL
uses: github/codeql-action/init@v2
with:
languages: cpp, python
- name: Build AFLplusplus # Rebuild because CodeQL needs to monitor the build process
env:
CC: gcc # These are symlinked to the version used in the container build
CXX: g++
run: make -i all # Best effort using -i
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v2

75
.github/workflows/container.yml vendored Normal file
View File

@ -0,0 +1,75 @@
name: Container
on:
push:
branches:
- stable
- dev
tags:
- "*"
pull_request:
branches:
- dev # No need for stable-pull-request, as that equals dev-push
jobs:
build-and-test-amd64:
name: Test amd64 image
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v3
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v2
- name: Build amd64
uses: docker/build-push-action@v3
with:
context: .
tags: aflplusplus:test-amd64
load: true
cache-to: type=gha,mode=max
build-args: |
TEST_BUILD=1
- name: Test amd64
run: >
docker run --rm aflplusplus:test-amd64 bash -c "
apt-get update &&
apt-get install -y libcmocka-dev &&
make -i tests
"
push:
name: Push amd64 and arm64 images
runs-on: ubuntu-latest
needs:
- build-and-test-amd64
if: ${{ github.event_name == 'push' && github.repository == 'AFLplusplus/AFLplusplus' }}
steps:
- name: Checkout
uses: actions/checkout@v3
- name: Set up QEMU
uses: docker/setup-qemu-action@v2
with:
platforms: arm64
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v2
- name: Login to docker.io
uses: docker/login-action@v2
with:
username: ${{ secrets.DOCKER_USERNAME }}
password: ${{ secrets.DOCKER_TOKEN }}
- name: Set tags to push
id: push-tags
run: |
PUSH_TAGS=docker.io/aflplusplus/aflplusplus:${GITHUB_REF_NAME}
if [ "${GITHUB_REF_NAME}" = "stable" ]; then
PUSH_TAGS=${PUSH_TAGS},docker.io/aflplusplus/aflplusplus:latest
fi
export PUSH_TAGS
echo "::set-output name=PUSH_TAGS::${PUSH_TAGS}"
- name: Push to docker.io registry
uses: docker/build-push-action@v3
with:
context: .
platforms: linux/amd64,linux/arm64
push: true
tags: ${{ steps.push-tags.outputs.PUSH_TAGS }}
cache-from: type=gha

View File

@ -2,9 +2,12 @@ name: Rust Custom Mutators
on:
push:
branches: [ stable, dev ]
branches:
- stable
- dev
pull_request:
branches: [ stable, dev ]
branches:
- dev # No need for stable-pull-request, as that equals dev-push
jobs:
test:
@ -17,7 +20,7 @@ jobs:
matrix:
os: [ubuntu-22.04, ubuntu-20.04]
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v3
- name: Install Rust Toolchain
uses: actions-rs/toolchain@v1
with:
@ -27,4 +30,4 @@ jobs:
- name: Run General Tests
run: cargo test
- name: Run Tests for afl_internals feature flag
run: cd custom_mutator && cargo test --features=afl_internals
run: cd custom_mutator && cargo test --features=afl_internals

View File

@ -1,81 +1,88 @@
#
# This Dockerfile for AFLplusplus uses Ubuntu 22.04 jammy and
# installs LLVM 14 for afl-clang-lto support :-)
# installs LLVM 14 for afl-clang-lto support.
#
# GCC 11 is used instead of 12 because genhtml for afl-cov doesn't like it.
#
FROM ubuntu:22.04 AS aflplusplus
LABEL "maintainer"="afl++ team <afl@aflplus.plus>"
LABEL "about"="AFLplusplus docker image"
LABEL "about"="AFLplusplus container image"
ARG DEBIAN_FRONTEND=noninteractive
env NO_ARCH_OPT 1
RUN apt-get update && \
apt-get -y install --no-install-suggests --no-install-recommends \
automake \
cmake \
meson \
ninja-build \
bison flex \
build-essential \
git \
python3 python3-dev python3-setuptools python-is-python3 \
libtool libtool-bin \
libglib2.0-dev \
wget vim jupp nano bash-completion less \
apt-utils apt-transport-https ca-certificates gnupg dialog \
libpixman-1-dev \
gnuplot-nox \
&& rm -rf /var/lib/apt/lists/*
# TODO: reactivate in timely manner
#RUN echo "deb http://apt.llvm.org/jammy/ llvm-toolchain-jammy-15 main" >> /etc/apt/sources.list && \
# wget -qO - https://apt.llvm.org/llvm-snapshot.gpg.key | apt-key add -
RUN echo "deb http://ppa.launchpad.net/ubuntu-toolchain-r/test/ubuntu jammy main" >> /etc/apt/sources.list && \
apt-key adv --recv-keys --keyserver keyserver.ubuntu.com 1E9377A2BA9EF27F
ENV NO_ARCH_OPT=1
ENV IS_DOCKER=1
RUN apt-get update && apt-get full-upgrade -y && \
apt-get -y install --no-install-suggests --no-install-recommends \
gcc-12 g++-12 gcc-12-plugin-dev gdb lcov \
clang-14 clang-tools-14 libc++1-14 libc++-14-dev \
libc++abi1-14 libc++abi-14-dev libclang1-14 libclang-14-dev \
libclang-common-14-dev libclang-cpp14 libclang-cpp14-dev liblld-14 \
liblld-14-dev liblldb-14 liblldb-14-dev libllvm14 libomp-14-dev \
libomp5-14 lld-14 lldb-14 llvm-14 llvm-14-dev llvm-14-runtime llvm-14-tools
apt-get install -y --no-install-recommends wget ca-certificates && \
rm -rf /var/lib/apt/lists/*
# arm64 doesn't have gcc-multilib, and it's only used for -m32 support on x86
ARG TARGETPLATFORM
RUN [ "$TARGETPLATFORM" = "linux/amd64" ] && \
apt-get -y install --no-install-suggests --no-install-recommends \
gcc-10-multilib gcc-multilib || true
ENV LLVM_VERSION=14
ENV GCC_VERSION=11
RUN rm -rf /var/lib/apt/lists/*
RUN echo "deb [signed-by=/etc/apt/keyrings/llvm-snapshot.gpg.key] http://apt.llvm.org/jammy/ llvm-toolchain-jammy-${LLVM_VERSION} main" > /etc/apt/sources.list.d/llvm.list && \
wget -qO /etc/apt/keyrings/llvm-snapshot.gpg.key https://apt.llvm.org/llvm-snapshot.gpg.key
RUN update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-12 0
RUN update-alternatives --install /usr/bin/g++ g++ /usr/bin/g++-12 0
RUN apt-get update && \
apt-get -y install --no-install-recommends \
make cmake automake meson ninja-build bison flex \
git xz-utils bzip2 wget jupp nano bash-completion less vim joe ssh psmisc \
python3 python3-dev python3-setuptools python-is-python3 \
libtool libtool-bin libglib2.0-dev \
apt-utils apt-transport-https gnupg dialog \
gnuplot-nox libpixman-1-dev \
gcc-${GCC_VERSION} g++-${GCC_VERSION} gcc-${GCC_VERSION}-plugin-dev gdb lcov \
clang-${LLVM_VERSION} clang-tools-${LLVM_VERSION} libc++1-${LLVM_VERSION} \
libc++-${LLVM_VERSION}-dev libc++abi1-${LLVM_VERSION} libc++abi-${LLVM_VERSION}-dev \
libclang1-${LLVM_VERSION} libclang-${LLVM_VERSION}-dev \
libclang-common-${LLVM_VERSION}-dev libclang-cpp${LLVM_VERSION} \
libclang-cpp${LLVM_VERSION}-dev liblld-${LLVM_VERSION} \
liblld-${LLVM_VERSION}-dev liblldb-${LLVM_VERSION} liblldb-${LLVM_VERSION}-dev \
libllvm${LLVM_VERSION} libomp-${LLVM_VERSION}-dev libomp5-${LLVM_VERSION} \
lld-${LLVM_VERSION} lldb-${LLVM_VERSION} llvm-${LLVM_VERSION} \
llvm-${LLVM_VERSION}-dev llvm-${LLVM_VERSION}-runtime llvm-${LLVM_VERSION}-tools \
$([ "$(dpkg --print-architecture)" = "amd64" ] && echo gcc-${GCC_VERSION}-multilib gcc-multilib) \
$([ "$(dpkg --print-architecture)" = "arm64" ] && echo libcapstone-dev) && \
rm -rf /var/lib/apt/lists/*
# gcc-multilib is only used for -m32 support on x86
# libcapstone-dev is used for coresight_mode on arm64
ENV LLVM_CONFIG=llvm-config-14
RUN update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-${GCC_VERSION} 0 && \
update-alternatives --install /usr/bin/g++ g++ /usr/bin/g++-${GCC_VERSION} 0 && \
update-alternatives --install /usr/bin/clang clang /usr/bin/clang-${LLVM_VERSION} 0 && \
update-alternatives --install /usr/bin/clang++ clang++ /usr/bin/clang++-${LLVM_VERSION} 0
RUN wget -qO- https://sh.rustup.rs | CARGO_HOME=/etc/cargo sh -s -- -y -q --no-modify-path
ENV PATH=$PATH:/etc/cargo/bin
ENV LLVM_CONFIG=llvm-config-${LLVM_VERSION}
ENV AFL_SKIP_CPUFREQ=1
ENV AFL_TRY_AFFINITY=1
ENV AFL_I_DONT_CARE_ABOUT_MISSING_CRASHES=1
RUN git clone --depth=1 https://github.com/vanhauser-thc/afl-cov /afl-cov
RUN cd /afl-cov && make install && cd ..
RUN git clone --depth=1 https://github.com/vanhauser-thc/afl-cov && \
(cd afl-cov && make install) && rm -rf afl-cov
# Build currently broken
ENV NO_CORESIGHT=1
ENV NO_UNICORN_ARM64=1
COPY . /AFLplusplus
WORKDIR /AFLplusplus
COPY . .
RUN export CC=gcc-12 && export CXX=g++-12 && make clean && \
make distrib && make install && make clean
ARG CC=gcc-$GCC_VERSION
ARG CXX=g++-$GCC_VERSION
RUN sh -c 'echo set encoding=utf-8 > /root/.vimrc'
RUN echo '. /etc/bash_completion' >> ~/.bashrc
RUN echo 'alias joe="joe --wordwrap --joe_state -nobackup"' >> ~/.bashrc
RUN echo "export PS1='"'[afl++ \h] \w$(__git_ps1) \$ '"'" >> ~/.bashrc
ENV IS_DOCKER="1"
# Used in CI to prevent a 'make clean' which would remove the binaries to be tested
ARG TEST_BUILD
# Disabled as there are now better alternatives
#COPY --from=aflplusplus/afl-dyninst /usr/local/lib/libdyninstAPI_RT.so /usr/local/lib/libdyninstAPI_RT.so
#COPY --from=aflplusplus/afl-dyninst /afl-dyninst/libAflDyninst.so /usr/local/lib/libAflDyninst.so
RUN sed -i.bak 's/^ -/ /g' GNUmakefile && \
make clean && make distrib && \
([ "${TEST_BUILD}" ] || (make install && make clean)) && \
mv GNUmakefile.bak GNUmakefile
RUN echo "set encoding=utf-8" > /root/.vimrc && \
echo ". /etc/bash_completion" >> ~/.bashrc && \
echo 'alias joe="joe --wordwrap --joe_state -nobackup"' >> ~/.bashrc && \
echo "export PS1='"'[afl++ \h] \w$(__git_ps1) \$ '"'" >> ~/.bashrc

View File

@ -312,7 +312,7 @@ all: test_x86 test_shm test_python ready $(PROGS) afl-as llvm gcc_plugin test_bu
.PHONY: llvm
llvm:
-$(MAKE) -j4 -f GNUmakefile.llvm
-$(MAKE) -j$(nproc) -f GNUmakefile.llvm
@test -e afl-cc || { echo "[-] Compiling afl-cc failed. You seem not to have a working compiler." ; exit 1; }
.PHONY: gcc_plugin
@ -572,7 +572,7 @@ clean:
-$(MAKE) -f GNUmakefile.gcc_plugin clean
-$(MAKE) -C utils/libdislocator clean
-$(MAKE) -C utils/libtokencap clean
$(MAKE) -C utils/aflpp_driver clean
-$(MAKE) -C utils/aflpp_driver clean
-$(MAKE) -C utils/afl_network_proxy clean
-$(MAKE) -C utils/socket_fuzzing clean
-$(MAKE) -C utils/argv_fuzzing clean
@ -610,7 +610,7 @@ endif
.PHONY: distrib
distrib: all
-$(MAKE) -j4 -f GNUmakefile.llvm
-$(MAKE) -j$(nproc) -f GNUmakefile.llvm
ifneq "$(SYS)" "Darwin"
-$(MAKE) -f GNUmakefile.gcc_plugin
endif
@ -623,15 +623,23 @@ endif
-$(MAKE) -C frida_mode
ifneq "$(SYS)" "Darwin"
ifeq "$(ARCH)" "aarch64"
ifndef NO_CORESIGHT
-$(MAKE) -C coresight_mode
endif
endif
ifeq "$(SYS)" "Linux"
ifndef NO_NYX
ifndef NO_NYX
-cd nyx_mode && ./build_nyx_support.sh
endif
endif
endif
-cd qemu_mode && sh ./build_qemu_support.sh
ifeq "$(ARCH)" "aarch64"
ifndef NO_UNICORN_ARM64
-cd unicorn_mode && unset CFLAGS && sh ./build_unicorn_support.sh
endif
else
-cd unicorn_mode && unset CFLAGS && sh ./build_unicorn_support.sh
endif
endif
.PHONY: binary-only
@ -645,7 +653,9 @@ binary-only: test_shm test_python ready $(PROGS)
-$(MAKE) -C frida_mode
ifneq "$(SYS)" "Darwin"
ifeq "$(ARCH)" "aarch64"
ifndef NO_CORESIGHT
-$(MAKE) -C coresight_mode
endif
endif
ifeq "$(SYS)" "Linux"
ifndef NO_NYX
@ -653,12 +663,18 @@ ifndef NO_NYX
endif
endif
-cd qemu_mode && sh ./build_qemu_support.sh
ifeq "$(ARCH)" "aarch64"
ifndef NO_UNICORN_ARM64
-cd unicorn_mode && unset CFLAGS && sh ./build_unicorn_support.sh
endif
else
-cd unicorn_mode && unset CFLAGS && sh ./build_unicorn_support.sh
endif
endif
.PHONY: source-only
source-only: all
-$(MAKE) -j4 -f GNUmakefile.llvm
-$(MAKE) -j$(nproc) -f GNUmakefile.llvm
ifneq "$(SYS)" "Darwin"
-$(MAKE) -f GNUmakefile.gcc_plugin
endif

View File

@ -100,7 +100,9 @@ ifeq "$(SYS)" "SunOS"
endif
PROGS = ./afl-gcc-pass.so ./afl-compiler-rt.o ./afl-compiler-rt-32.o ./afl-compiler-rt-64.o
PASSES = ./afl-gcc-pass.so ./afl-gcc-cmplog-pass.so ./afl-gcc-cmptrs-pass.so
PROGS = $(PASSES) ./afl-compiler-rt.o ./afl-compiler-rt-32.o ./afl-compiler-rt-64.o
.PHONY: all
all: test_shm test_deps $(PROGS) test_build all_done
@ -141,6 +143,8 @@ afl-common.o: ./src/afl-common.c
@printf "[*] Building 64-bit variant of the runtime (-m64)... "
@$(CC) $(CFLAGS_SAFE) $(CPPFLAGS) -O3 -Wno-unused-result -m64 -fPIC -c $< -o $@ 2>/dev/null; if [ "$$?" = "0" ]; then echo "success!"; else echo "failed (that's fine)"; fi
$(PASSES): instrumentation/afl-gcc-common.h
./afl-gcc-pass.so: instrumentation/afl-gcc-pass.so.cc | test_deps
$(CXX) $(CXXEFLAGS) $(PLUGIN_FLAGS) -shared $< -o $@
ln -sf afl-cc afl-gcc-fast
@ -148,6 +152,12 @@ afl-common.o: ./src/afl-common.c
ln -sf afl-cc.8 afl-gcc-fast.8
ln -sf afl-cc.8 afl-g++-fast.8
./afl-gcc-cmplog-pass.so: instrumentation/afl-gcc-cmplog-pass.so.cc | test_deps
$(CXX) $(CXXEFLAGS) $(PLUGIN_FLAGS) -shared $< -o $@
./afl-gcc-cmptrs-pass.so: instrumentation/afl-gcc-cmptrs-pass.so.cc | test_deps
$(CXX) $(CXXEFLAGS) $(PLUGIN_FLAGS) -shared $< -o $@
.PHONY: test_build
test_build: $(PROGS)
@echo "[*] Testing the CC wrapper and instrumentation output..."
@ -190,6 +200,8 @@ install: all
ln -sf afl-c++ $${DESTDIR}$(BIN_PATH)/afl-g++-fast
ln -sf afl-compiler-rt.o $${DESTDIR}$(HELPER_PATH)/afl-gcc-rt.o
install -m 755 ./afl-gcc-pass.so $${DESTDIR}$(HELPER_PATH)
install -m 755 ./afl-gcc-cmplog-pass.so $${DESTDIR}$(HELPER_PATH)
install -m 755 ./afl-gcc-cmptrs-pass.so $${DESTDIR}$(HELPER_PATH)
install -m 644 -T instrumentation/README.gcc_plugin.md $${DESTDIR}$(DOC_PATH)/README.gcc_plugin.md
.PHONY: clean

View File

@ -534,7 +534,6 @@ BEGIN {
}
}
close(sortedKeys)
print ""
print "[+] Found "tuple_count" unique tuples across "in_count" files."
if (out_count == 1) {

View File

@ -54,7 +54,7 @@ $(GLIBC_LDSO): | $(GLIBC_NAME).tar.xz
$(MAKE) install
$(GLIBC_NAME).tar.xz:
wget -O $@ $(GLIBC_URL_BASE)/$@
wget -qO $@ $(GLIBC_URL_BASE)/$@
clean:
$(MAKE) -C $(CS_TRACE) clean

View File

@ -128,7 +128,7 @@ git pull >/dev/null 2>&1
sh -c 'git stash && git stash drop' 1>/dev/null 2>/dev/null
git checkout "$GRAMMAR_VERSION" || exit 1
echo "[*] Downloading antlr..."
wget -c https://www.antlr.org/download/antlr-4.8-complete.jar
wget -q https://www.antlr.org/download/antlr-4.8-complete.jar
cd ..
echo

View File

@ -8,6 +8,13 @@
Want to stay in the loop on major new features? Join our mailing list by
sending a mail to <afl-users+subscribe@googlegroups.com>.
### Version ++4.02a (dev)
- gcc_plugin:
- Adacore submitted CMPLOG support to the gcc_plugin! :-)
- llvm_mode:
- laf cmp splitting fixed for more comparison types
### Version ++4.01c (release)
- fixed */build_...sh scripts to work outside of git
- new custom_mutator: libafl with token fuzzing :)

View File

@ -21,12 +21,12 @@ development state of AFL++.
If you want to build AFL++ yourself, you have many options. The easiest choice
is to build and install everything:
NOTE: depending on your Debian/Ubuntu/Kali/... version replease `-12` with
NOTE: depending on your Debian/Ubuntu/Kali/... version release `-12` with
whatever llvm version is available!
```shell
sudo apt-get update
sudo apt-get install -y build-essential python3-dev automake cmake git flex bison libglib2.0-dev libpixman-1-dev python3-setuptools
sudo apt-get install -y build-essential python3-dev automake cmake git flex bison libglib2.0-dev libpixman-1-dev python3-setuptools cargo libgtk-3-dev
# try to install llvm 12 and install the distro default if that fails
sudo apt-get install -y lld-12 llvm-12 llvm-12-dev clang-12 || sudo apt-get install -y lld llvm llvm-dev clang
sudo apt-get install -y gcc-$(gcc --version|head -n1|sed 's/\..*//'|sed 's/.* //')-plugin-dev libstdc++-$(gcc --version|head -n1|sed 's/\..*//'|sed 's/.* //')-dev
@ -148,7 +148,7 @@ and definitely don't look POSIX-compliant. This means two things:
environment before starting afl-fuzz.
User emulation mode of QEMU does not appear to be supported on MacOS X, so
black-box instrumentation mode (`-Q`) will not work. However, Frida mode (`-O`)
black-box instrumentation mode (`-Q`) will not work. However, FRIDA mode (`-O`)
works on both x86 and arm64 MacOS boxes.
MacOS X supports SYSV shared memory used by AFL's instrumentation, but the

View File

@ -160,6 +160,8 @@ Available options:
Setting `AFL_LLVM_CMPLOG=1` during compilation will tell afl-clang-fast to
produce a CmpLog binary.
For afl-gcc-fast, set `AFL_GCC_CMPLOG=1` instead.
For more information, see
[instrumentation/README.cmplog.md](../instrumentation/README.cmplog.md).
@ -460,7 +462,7 @@ checks or alter some of the more exotic semantics of the tool:
some basic stats. This behavior is also automatically triggered when the
output from afl-fuzz is redirected to a file or to a pipe.
- In QEMU mode (-Q) and Frida mode (-O), `AFL_PATH` will be searched for
- In QEMU mode (-Q) and FRIDA mode (-O), `AFL_PATH` will be searched for
afl-qemu-trace and afl-frida-trace.so.
- If you are using persistent mode (you should, see
@ -553,10 +555,10 @@ checks or alter some of the more exotic semantics of the tool:
in the target binary
- If you need an early forkserver in your target because of early
constructors in your target you can set `AFL_EARLY_FORKSERVER`.
constructors in your target, you can set `AFL_EARLY_FORKSERVER`.
Note that this is not a compile time option but a runtime option :-)
- set `AFL_PIZZA_MODE` to 1 to enable the April 1st stats menu, set to 0
- Set `AFL_PIZZA_MODE` to 1 to enable the April 1st stats menu, set to 0
to disable although it is 1st of April.
## 5) Settings for afl-qemu-trace

View File

@ -12,7 +12,7 @@ QEMU 5.1 with laf-intel and Redqueen, FRIDA mode, unicorn mode, gcc plugin, full
| NeverZero [B] | x86[_64] | x(1) | x | x | x | x | | |
| Persistent Mode [C] | | x | x | x86[_64]/arm64 | x86[_64]/arm[64] | x | | |
| LAF-Intel / CompCov [D] | | x | | | x86[_64]/arm[64] | x86[_64]/arm[64] | x86[_64] | |
| CmpLog [E] | | x | | x86[_64]/arm64 | x86[_64]/arm[64] | | | |
| CmpLog [E] | | x | x | x86[_64]/arm64 | x86[_64]/arm[64] | | | |
| Selective Instrumentation [F] | | x | x | x | x | | | |
| Non-Colliding Coverage [G] | | x(4) | | | (x)(5) | | | |
| Ngram prev_loc Coverage [H] | | x(6) | | | | | | |

View File

@ -838,9 +838,10 @@ Here are some of the most important caveats for AFL++:
- There is no direct support for fuzzing network services, background daemons,
or interactive apps that require UI interaction to work. You may need to make
simple code changes to make them behave in a more traditional way. Preeny or libdesock may
offer a relatively simple option, too - see:
[https://github.com/zardus/preeny](https://github.com/zardus/preeny) or [https://github.com/fkie-cad/libdesock](https://github.com/fkie-cad/libdesock)
simple code changes to make them behave in a more traditional way. Preeny or
libdesock may offer a relatively simple option, too - see:
[https://github.com/zardus/preeny](https://github.com/zardus/preeny) or
[https://github.com/fkie-cad/libdesock](https://github.com/fkie-cad/libdesock)
Some useful tips for modifying network-based services can be also found at:
[https://www.fastly.com/blog/how-to-fuzz-server-american-fuzzy-lop](https://www.fastly.com/blog/how-to-fuzz-server-american-fuzzy-lop)

View File

@ -19,18 +19,18 @@ Mentor: vanhauser-thc
## WASM Instrumentation
Currently, AFL++ can be used for source code fuzzing and traditional binaries.
With the rise of WASM as a compile target, however, a novel way of instrumentation
needs to be implemented for binaries compiled to Webassembly. This can either be
done by inserting instrumentation directly into the WASM AST, or by patching
feedback into a WASM VM of choice, similar to the current Unicorn
With the rise of WASM as a compile target, however, a novel way of
instrumentation needs to be implemented for binaries compiled to Webassembly.
This can either be done by inserting instrumentation directly into the WASM AST,
or by patching feedback into a WASM VM of choice, similar to the current Unicorn
instrumentation.
Mentor: any
## Support other programming languages
Other programming languages also use llvm hence they could be (easily?) supported
for fuzzing, e.g., mono, swift, go, kotlin native, fortran, ...
Other programming languages also use llvm hence they could be (easily?)
supported for fuzzing, e.g., mono, swift, go, kotlin native, fortran, ...
GCC also supports: Objective-C, Fortran, Ada, Go, and D (according to
[Gcc homepage](https://gcc.gnu.org/))

View File

@ -1,11 +1,13 @@
# Tools that help fuzzing with AFL++
Speeding up fuzzing:
## Speeding up fuzzing
* [libfiowrapper](https://github.com/marekzmyslowski/libfiowrapper) - if the
function you want to fuzz requires loading a file, this allows using the
shared memory test case feature :-) - recommended.
Minimization of test cases:
## Minimization of test cases
* [afl-pytmin](https://github.com/ilsani/afl-pytmin) - a wrapper for afl-tmin
that tries to speed up the process of minimization of a single test case by
using many CPU cores.
@ -14,7 +16,8 @@ Minimization of test cases:
* [halfempty](https://github.com/googleprojectzero/halfempty) - is a fast
utility for minimizing test cases by Tavis Ormandy based on parallelization.
Distributed execution:
## Distributed execution
* [disfuzz-afl](https://github.com/MartijnB/disfuzz-afl) - distributed fuzzing
for AFL.
* [AFLDFF](https://github.com/quantumvm/AFLDFF) - AFL distributed fuzzing
@ -26,7 +29,8 @@ Distributed execution:
* [afl-in-the-cloud](https://github.com/abhisek/afl-in-the-cloud) - another
script for running AFL in AWS.
Deployment, management, monitoring, reporting
## Deployment, management, monitoring, reporting
* [afl-utils](https://gitlab.com/rc0r/afl-utils) - a set of utilities for
automatic processing/analysis of crashes and reducing the number of test
cases.
@ -44,7 +48,8 @@ Deployment, management, monitoring, reporting
* [afl-extras](https://github.com/fekir/afl-extras) - shell scripts to
parallelize afl-tmin, startup, and data collection.
Crash processing
## Crash processing
* [AFLTriage](https://github.com/quic/AFLTriage) -
triage crashing input files using gdb.
* [afl-crash-analyzer](https://github.com/floyd-fuh/afl-crash-analyzer) -

View File

@ -33,6 +33,7 @@ structure is), these links have you covered (some are outdated though):
[https://github.com/adrian-rt/superion-mutator](https://github.com/adrian-rt/superion-mutator)
## Video Tutorials
* [Install AFL++ Ubuntu](https://www.youtube.com/watch?v=5dCvhkbi3RA)
* [[Fuzzing with AFLplusplus] Installing AFLPlusplus and fuzzing a simple C program](https://www.youtube.com/watch?v=9wRVo0kYSlc)
* [[Fuzzing with AFLplusplus] How to fuzz a binary with no source code on Linux in persistent mode](https://www.youtube.com/watch?v=LGPJdEO02p4)

View File

@ -116,7 +116,7 @@ ifndef OS
$(error "Operating system unsupported")
endif
GUM_DEVKIT_VERSION=15.1.22
GUM_DEVKIT_VERSION=15.1.27
GUM_DEVKIT_FILENAME=frida-gumjs-devkit-$(GUM_DEVKIT_VERSION)-$(OS)-$(ARCH).tar.xz
GUM_DEVKIT_URL="https://github.com/frida/frida/releases/download/$(GUM_DEVKIT_VERSION)/$(GUM_DEVKIT_FILENAME)"
@ -275,7 +275,7 @@ endif
else
$(GUM_DEVKIT_TARBALL): | $(FRIDA_BUILD_DIR)
wget -O $@ $(GUM_DEVKIT_URL) || curl -L -o $@ $(GUM_DEVKIT_URL)
wget -qO $@ $(GUM_DEVKIT_URL) || curl -L -o $@ $(GUM_DEVKIT_URL)
$(GUM_DEVIT_LIBRARY): $(GUM_DEVKIT_TARBALL)
tar Jxvfm $(GUM_DEVKIT_TARBALL) -C $(FRIDA_BUILD_DIR)

View File

@ -5,13 +5,13 @@
#include "config.h"
extern char * instrument_debug_filename;
extern char * instrument_coverage_filename;
extern char *instrument_debug_filename;
extern char *instrument_coverage_filename;
extern gboolean instrument_tracing;
extern gboolean instrument_optimize;
extern gboolean instrument_unique;
extern guint64 instrument_hash_zero;
extern char * instrument_coverage_unstable_filename;
extern char *instrument_coverage_unstable_filename;
extern gboolean instrument_coverage_insn;
extern gboolean instrument_use_fixed_seed;
@ -35,9 +35,9 @@ GumStalkerTransformer *instrument_get_transformer(void);
gboolean instrument_is_coverage_optimize_supported(void);
void instrument_coverage_optimize_init(void);
void instrument_coverage_optimize(const cs_insn * instr,
void instrument_coverage_optimize(const cs_insn *instr,
GumStalkerOutput *output);
void instrument_coverage_optimize_insn(const cs_insn * instr,
void instrument_coverage_optimize_insn(const cs_insn *instr,
GumStalkerOutput *output);
void instrument_debug_config(void);

View File

@ -13,7 +13,7 @@ typedef void (*afl_persistent_hook_fn)(api_regs *regs, uint64_t guest_base,
extern int __afl_persistent_loop(unsigned int max_cnt);
extern unsigned int * __afl_fuzz_len;
extern unsigned int *__afl_fuzz_len;
extern unsigned char *__afl_fuzz_ptr;
extern guint64 persistent_start;

View File

@ -401,9 +401,9 @@ enum {
typedef void (*seccomp_child_func_t)(int event_fd, void *ctx);
typedef void (*seccomp_filter_callback_t)(struct seccomp_notif * req,
typedef void (*seccomp_filter_callback_t)(struct seccomp_notif *req,
struct seccomp_notif_resp *resp,
GumReturnAddressArray * frames);
GumReturnAddressArray *frames);
void seccomp_atomic_set(volatile bool *ptr, bool val);
bool seccomp_atomic_try_set(volatile bool *ptr, bool val);

View File

@ -43,7 +43,7 @@ typedef struct {
G_DECLARE_FINAL_TYPE(GumAflStalkerStats, gum_afl_stalker_stats, GUM,
AFL_STALKER_STATS, GObject)
extern char * stats_filename;
extern char *stats_filename;
extern guint64 stats_interval;
void stats_config(void);

View File

@ -30,7 +30,7 @@ void asan_init(void) {
static gboolean asan_exclude_module(const GumModuleDetails *details,
gpointer user_data) {
gchar * symbol_name = (gchar *)user_data;
gchar *symbol_name = (gchar *)user_data;
GumAddress address;
address = gum_module_find_export_by_name(details->name, symbol_name);

View File

@ -22,8 +22,8 @@ asan_storeN_t asan_storeN = NULL;
static void asan_callout(GumCpuContext *ctx, gpointer user_data) {
asan_ctx_t * asan_ctx = (asan_ctx_t *)user_data;
cs_arm64_op * operand = &asan_ctx->operand;
asan_ctx_t *asan_ctx = (asan_ctx_t *)user_data;
cs_arm64_op *operand = &asan_ctx->operand;
arm64_op_mem *mem = &operand->mem;
gsize base = 0;
gsize index = 0;
@ -59,7 +59,7 @@ void asan_instrument(const cs_insn *instr, GumStalkerIterator *iterator) {
cs_arm64 arm64 = instr->detail->arm64;
cs_arm64_op *operand;
asan_ctx_t * ctx;
asan_ctx_t *ctx;
if (!asan_initialized) return;

View File

@ -17,7 +17,7 @@ static void asan_callout(GumCpuContext *ctx, gpointer user_data) {
UNUSED_PARAMETER(user_data);
cs_x86_op * operand = (cs_x86_op *)user_data;
cs_x86_op *operand = (cs_x86_op *)user_data;
x86_op_mem *mem = &operand->mem;
gsize base = 0;
gsize index = 0;
@ -48,9 +48,9 @@ void asan_instrument(const cs_insn *instr, GumStalkerIterator *iterator) {
UNUSED_PARAMETER(iterator);
cs_x86 x86 = instr->detail->x86;
cs_x86_op * operand;
cs_x86_op *operand;
x86_op_mem *mem;
cs_x86_op * ctx;
cs_x86_op *ctx;
if (!asan_initialized) return;

View File

@ -17,7 +17,7 @@ static void asan_callout(GumCpuContext *ctx, gpointer user_data) {
UNUSED_PARAMETER(user_data);
cs_x86_op * operand = (cs_x86_op *)user_data;
cs_x86_op *operand = (cs_x86_op *)user_data;
x86_op_mem *mem = &operand->mem;
gsize base = 0;
gsize index = 0;
@ -48,9 +48,9 @@ void asan_instrument(const cs_insn *instr, GumStalkerIterator *iterator) {
UNUSED_PARAMETER(iterator);
cs_x86 x86 = instr->detail->x86;
cs_x86_op * operand;
cs_x86_op *operand;
x86_op_mem *mem;
cs_x86_op * ctx;
cs_x86_op *ctx;
if (!asan_initialized) return;

View File

@ -13,9 +13,9 @@
#define MAX_MEMFD_SIZE (64UL << 10)
extern struct cmp_map *__afl_cmp_map;
static GArray * cmplog_ranges = NULL;
static GHashTable * hash_yes = NULL;
static GHashTable * hash_no = NULL;
static GArray *cmplog_ranges = NULL;
static GHashTable *hash_yes = NULL;
static GHashTable *hash_no = NULL;
static long page_size = 0;
static long page_offset_mask = 0;
@ -24,7 +24,7 @@ static long page_mask = 0;
static gboolean cmplog_range(const GumRangeDetails *details,
gpointer user_data) {
GArray * cmplog_ranges = (GArray *)user_data;
GArray *cmplog_ranges = (GArray *)user_data;
GumMemoryRange range = *details->range;
g_array_append_val(cmplog_ranges, range);
return TRUE;
@ -118,7 +118,7 @@ gboolean cmplog_test_addr(guint64 addr, size_t size) {
if (g_hash_table_contains(hash_yes, GSIZE_TO_POINTER(addr))) { return true; }
if (g_hash_table_contains(hash_no, GSIZE_TO_POINTER(addr))) { return false; }
void * page_addr = GSIZE_TO_POINTER(addr & page_mask);
void *page_addr = GSIZE_TO_POINTER(addr & page_mask);
size_t page_offset = addr & page_offset_mask;
/* If it spans a page, then bail */

View File

@ -148,7 +148,7 @@ static void cmplog_call_callout(GumCpuContext *context, gpointer user_data) {
}
static void cmplog_instrument_put_operand(cmplog_ctx_t *ctx,
cs_arm64_op * operand) {
cs_arm64_op *operand) {
ctx->type = operand->type;
switch (operand->type) {
@ -169,7 +169,7 @@ static void cmplog_instrument_put_operand(cmplog_ctx_t *ctx,
}
static void cmplog_instrument_call(const cs_insn * instr,
static void cmplog_instrument_call(const cs_insn *instr,
GumStalkerIterator *iterator) {
cs_arm64 arm64 = instr->detail->arm64;
@ -247,8 +247,8 @@ static void cmplog_cmp_sub_callout(GumCpuContext *context, gpointer user_data) {
}
static void cmplog_instrument_cmp_sub_put_callout(GumStalkerIterator *iterator,
cs_arm64_op * operand1,
cs_arm64_op * operand2,
cs_arm64_op *operand1,
cs_arm64_op *operand2,
size_t size) {
cmplog_pair_ctx_t *ctx = g_malloc(sizeof(cmplog_pair_ctx_t));
@ -263,7 +263,7 @@ static void cmplog_instrument_cmp_sub_put_callout(GumStalkerIterator *iterator,
}
static void cmplog_instrument_cmp_sub(const cs_insn * instr,
static void cmplog_instrument_cmp_sub(const cs_insn *instr,
GumStalkerIterator *iterator) {
cs_arm64 arm64 = instr->detail->arm64;

View File

@ -141,7 +141,7 @@ static void cmplog_call_callout(GumCpuContext *context, gpointer user_data) {
}
static void cmplog_instrument_put_operand(cmplog_ctx_t *ctx,
cs_x86_op * operand) {
cs_x86_op *operand) {
ctx->type = operand->type;
ctx->size = operand->size;
@ -163,7 +163,7 @@ static void cmplog_instrument_put_operand(cmplog_ctx_t *ctx,
}
static void cmplog_instrument_call(const cs_insn * instr,
static void cmplog_instrument_call(const cs_insn *instr,
GumStalkerIterator *iterator) {
cs_x86 x86 = instr->detail->x86;
@ -230,7 +230,7 @@ static void cmplog_cmp_sub_callout(GumCpuContext *context, gpointer user_data) {
}
static void cmplog_instrument_cmp_sub_put_callout(GumStalkerIterator *iterator,
cs_x86_op * operand1,
cs_x86_op *operand1,
cs_x86_op *operand2) {
cmplog_pair_ctx_t *ctx = g_malloc(sizeof(cmplog_pair_ctx_t));
@ -244,7 +244,7 @@ static void cmplog_instrument_cmp_sub_put_callout(GumStalkerIterator *iterator,
}
static void cmplog_instrument_cmp_sub(const cs_insn * instr,
static void cmplog_instrument_cmp_sub(const cs_insn *instr,
GumStalkerIterator *iterator) {
cs_x86 x86 = instr->detail->x86;

View File

@ -146,7 +146,7 @@ static void cmplog_call_callout(GumCpuContext *context, gpointer user_data) {
}
static void cmplog_instrument_put_operand(cmplog_ctx_t *ctx,
cs_x86_op * operand) {
cs_x86_op *operand) {
ctx->type = operand->type;
ctx->size = operand->size;
@ -168,7 +168,7 @@ static void cmplog_instrument_put_operand(cmplog_ctx_t *ctx,
}
static void cmplog_instrument_call(const cs_insn * instr,
static void cmplog_instrument_call(const cs_insn *instr,
GumStalkerIterator *iterator) {
cs_x86 x86 = instr->detail->x86;
@ -238,7 +238,7 @@ static void cmplog_cmp_sub_callout(GumCpuContext *context, gpointer user_data) {
}
static void cmplog_instrument_cmp_sub_put_callout(GumStalkerIterator *iterator,
cs_x86_op * operand1,
cs_x86_op *operand1,
cs_x86_op *operand2) {
cmplog_pair_ctx_t *ctx = g_malloc(sizeof(cmplog_pair_ctx_t));
@ -252,7 +252,7 @@ static void cmplog_instrument_cmp_sub_put_callout(GumStalkerIterator *iterator,
}
static void cmplog_instrument_cmp_sub(const cs_insn * instr,
static void cmplog_instrument_cmp_sub(const cs_insn *instr,
GumStalkerIterator *iterator) {
cs_x86 x86 = instr->detail->x86;

View File

@ -28,14 +28,14 @@ guint64 instrument_hash_seed = 0;
gboolean instrument_use_fixed_seed = FALSE;
guint64 instrument_fixed_seed = 0;
char * instrument_coverage_unstable_filename = NULL;
char *instrument_coverage_unstable_filename = NULL;
gboolean instrument_coverage_insn = FALSE;
static GumStalkerTransformer *transformer = NULL;
static GumAddress previous_rip = 0;
static GumAddress previous_end = 0;
static u8 * edges_notified = NULL;
static u8 *edges_notified = NULL;
__thread guint64 instrument_previous_pc;
__thread guint64 *instrument_previous_pc_addr = NULL;
@ -149,7 +149,7 @@ __attribute__((hot)) static void on_basic_block(GumCpuContext *context,
}
static void instrument_basic_block(GumStalkerIterator *iterator,
GumStalkerOutput * output,
GumStalkerOutput *output,
gpointer user_data) {
UNUSED_PARAMETER(user_data);
@ -157,7 +157,7 @@ static void instrument_basic_block(GumStalkerIterator *iterator,
const cs_insn *instr;
gboolean begin = TRUE;
gboolean excluded;
block_ctx_t * ctx = NULL;
block_ctx_t *ctx = NULL;
while (gum_stalker_iterator_next(iterator, &instr)) {

View File

@ -14,7 +14,7 @@ gboolean instrument_is_coverage_optimize_supported(void) {
}
void instrument_coverage_optimize(const cs_insn * instr,
void instrument_coverage_optimize(const cs_insn *instr,
GumStalkerOutput *output) {
UNUSED_PARAMETER(instr);
@ -23,7 +23,7 @@ void instrument_coverage_optimize(const cs_insn * instr,
}
void instrument_coverage_optimize_insn(const cs_insn * instr,
void instrument_coverage_optimize_insn(const cs_insn *instr,
GumStalkerOutput *output) {
UNUSED_PARAMETER(instr);

View File

@ -159,8 +159,8 @@ static gboolean instrument_is_deterministic(const cs_insn *from_insn) {
static void instrument_coverage_switch(GumStalkerObserver *self,
gpointer from_address,
gpointer start_address,
const cs_insn * from_insn,
gpointer * target) {
const cs_insn *from_insn,
gpointer *target) {
UNUSED_PARAMETER(self);
UNUSED_PARAMETER(from_address);
@ -218,7 +218,7 @@ static void instrument_coverage_suppress_init(void) {
if (initialized) { return; }
initialized = true;
GumStalkerObserver * observer = stalker_get_observer();
GumStalkerObserver *observer = stalker_get_observer();
GumStalkerObserverInterface *iface = GUM_STALKER_OBSERVER_GET_IFACE(observer);
iface->switch_callback = instrument_coverage_switch;
@ -257,7 +257,7 @@ static void instrument_patch_ardp(guint32 *patch, GumAddress insn,
}
void instrument_coverage_optimize(const cs_insn * instr,
void instrument_coverage_optimize(const cs_insn *instr,
GumStalkerOutput *output) {
afl_log_code code = {0};
@ -345,7 +345,7 @@ void instrument_coverage_optimize(const cs_insn * instr,
}
void instrument_coverage_optimize_insn(const cs_insn * instr,
void instrument_coverage_optimize_insn(const cs_insn *instr,
GumStalkerOutput *output) {
UNUSED_PARAMETER(instr);

View File

@ -17,7 +17,7 @@ static int unstable_coverage_fd = -1;
static int unstable_coverage_pipes[2] = {-1, -1};
static uint64_t normal_coverage_last_start = 0;
static gchar * unstable_coverage_fuzzer_stats = NULL;
static gchar *unstable_coverage_fuzzer_stats = NULL;
typedef struct {
@ -68,7 +68,7 @@ typedef struct {
static gboolean coverage_range(const GumRangeDetails *details,
gpointer user_data) {
GArray * coverage_ranges = (GArray *)user_data;
GArray *coverage_ranges = (GArray *)user_data;
coverage_range_t coverage = {0};
if (details->file == NULL) { return TRUE; }
@ -210,8 +210,8 @@ static GArray *coverage_get_modules(void) {
static void instrument_coverage_mark(void *key, void *value, void *user_data) {
UNUSED_PARAMETER(key);
coverage_mark_ctx_t * ctx = (coverage_mark_ctx_t *)user_data;
GArray * coverage_modules = ctx->modules;
coverage_mark_ctx_t *ctx = (coverage_mark_ctx_t *)user_data;
GArray *coverage_modules = ctx->modules;
normal_coverage_data_t *val = (normal_coverage_data_t *)value;
guint i;
@ -289,9 +289,9 @@ static void coverage_write_modules(int fd, GArray *coverage_modules) {
coverage_format(fd, "%016" G_GINT64_MODIFIER "X, ", module->base_address);
coverage_format(fd, "%016" G_GINT64_MODIFIER "X, ", module->limit);
/* entry */
coverage_format(fd, "%016" G_GINT64_MODIFIER "X, ", 0);
coverage_format(fd, "%016" G_GINT64_MODIFIER "X, ", 0UL);
/* checksum */
coverage_format(fd, "%016" G_GINT64_MODIFIER "X, ", 0);
coverage_format(fd, "%016" G_GINT64_MODIFIER "X, ", 0UL);
/* timestamp */
coverage_format(fd, "%08" G_GINT32_MODIFIER "X, ", 0);
coverage_format(fd, "%s\n", module->path);
@ -426,7 +426,7 @@ static void instrument_coverage_normal_run() {
static GArray *instrument_coverage_unstable_read_unstable_ids(void) {
gchar * contents = NULL;
gchar *contents = NULL;
gsize length = 0;
GArray *unstable_edge_ids =
g_array_sized_new(false, false, sizeof(gpointer), 100);
@ -533,7 +533,7 @@ static GHashTable *instrument_collect_unstable_blocks(
while (g_hash_table_iter_next(&iter, NULL, &value)) {
unstable_coverage_data_t *unstable = (unstable_coverage_data_t *)value;
normal_coverage_data_t * from =
normal_coverage_data_t *from =
gum_malloc0(sizeof(normal_coverage_data_t));
normal_coverage_data_t *to = gum_malloc0(sizeof(normal_coverage_data_t));
from->start = unstable->from;

View File

@ -66,7 +66,7 @@ static void instrument_disasm(guint8 *start, guint8 *end,
instrument_debug("\t0x%" G_GINT64_MODIFIER "x\t* 0x%016" G_GSIZE_MODIFIER
"x\n",
curr, *(size_t *)curr);
(uint64_t)curr, *(size_t *)curr);
len += sizeof(size_t);
continue;

View File

@ -174,13 +174,13 @@ void instrument_coverage_optimize_init(void) {
static void instrument_coverage_switch(GumStalkerObserver *self,
gpointer from_address,
gpointer start_address,
const cs_insn * from_insn,
gpointer * target) {
const cs_insn *from_insn,
gpointer *target) {
UNUSED_PARAMETER(self);
UNUSED_PARAMETER(from_address);
cs_x86 * x86;
cs_x86 *x86;
cs_x86_op *op;
if (from_insn == NULL) { return; }
@ -230,7 +230,7 @@ static void instrument_coverage_suppress_init(void) {
if (initialized) { return; }
initialized = true;
GumStalkerObserver * observer = stalker_get_observer();
GumStalkerObserver *observer = stalker_get_observer();
GumStalkerObserverInterface *iface = GUM_STALKER_OBSERVER_GET_IFACE(observer);
iface->switch_callback = instrument_coverage_switch;
@ -333,7 +333,7 @@ static void instrument_coverage_write(GumAddress address,
}
void instrument_coverage_optimize(const cs_insn * instr,
void instrument_coverage_optimize(const cs_insn *instr,
GumStalkerOutput *output) {
GumX86Writer *cw = output->writer.x86;
@ -364,7 +364,7 @@ void instrument_coverage_optimize(const cs_insn * instr,
}
void instrument_coverage_optimize_insn(const cs_insn * instr,
void instrument_coverage_optimize_insn(const cs_insn *instr,
GumStalkerOutput *output) {
GumX86Writer *cw = output->writer.x86;

View File

@ -105,11 +105,11 @@ static gboolean instrument_cache_relocate(GumAddress old_pc, GumAddress new_pc,
}
static void instrument_cache_rewrite_branch_insn(const cs_insn * instr,
static void instrument_cache_rewrite_branch_insn(const cs_insn *instr,
GumStalkerOutput *output) {
GumX86Writer *cw = output->writer.x86;
cs_x86 * x86 = &instr->detail->x86;
cs_x86 *x86 = &instr->detail->x86;
guint8 modified[sizeof(instr->bytes)] = {0};
guint8 offset = 0;
guint8 skip = 0;
@ -225,8 +225,8 @@ static void instrument_cache_rewrite_branch_insn(const cs_insn * instr,
} else {
GumAddress target = instr->address + old_offset;
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RAX, target);
gum_x86_writer_put_mov_reg_reg_ptr(cw, GUM_REG_RAX, GUM_REG_RAX);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RAX, target);
gum_x86_writer_put_mov_reg_reg_ptr(cw, GUM_X86_RAX, GUM_X86_RAX);
return;
}
@ -249,29 +249,29 @@ static void instrument_cache_rewrite_branch_insn(const cs_insn * instr,
static void instrument_cache_write_push_frame(GumX86Writer *cw) {
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_XSP, -(GUM_RED_ZONE_SIZE + (1 * sizeof(gpointer))),
GUM_REG_XAX);
cw, GUM_X86_XSP, -(GUM_RED_ZONE_SIZE + (1 * sizeof(gpointer))),
GUM_X86_XAX);
gum_x86_writer_put_lahf(cw);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_XSP, -(GUM_RED_ZONE_SIZE + (2 * sizeof(gpointer))),
GUM_REG_XAX);
cw, GUM_X86_XSP, -(GUM_RED_ZONE_SIZE + (2 * sizeof(gpointer))),
GUM_X86_XAX);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_XSP, -(GUM_RED_ZONE_SIZE + (3 * sizeof(gpointer))),
GUM_REG_XBX);
cw, GUM_X86_XSP, -(GUM_RED_ZONE_SIZE + (3 * sizeof(gpointer))),
GUM_X86_XBX);
}
static void instrument_cache_write_pop_frame(GumX86Writer *cw) {
gum_x86_writer_put_mov_reg_reg_offset_ptr(
cw, GUM_REG_XBX, GUM_REG_XSP,
cw, GUM_X86_XBX, GUM_X86_XSP,
-(GUM_RED_ZONE_SIZE + (3 * sizeof(gpointer))));
gum_x86_writer_put_mov_reg_reg_offset_ptr(
cw, GUM_REG_XAX, GUM_REG_XSP,
cw, GUM_X86_XAX, GUM_X86_XSP,
-(GUM_RED_ZONE_SIZE + (2 * sizeof(gpointer))));
gum_x86_writer_put_sahf(cw);
gum_x86_writer_put_mov_reg_reg_offset_ptr(
cw, GUM_REG_XAX, GUM_REG_XSP,
cw, GUM_X86_XAX, GUM_X86_XSP,
-(GUM_RED_ZONE_SIZE + (1 * sizeof(gpointer))));
}
@ -281,21 +281,21 @@ static void instrument_cache_write_lookup(GumX86Writer *cw) {
/* &map_base[GPOINTER_TO_SIZE(addr) & MAP_MASK]; */
gsize mask = (instrument_cache_size / sizeof(gpointer)) - 1;
gum_x86_writer_put_mov_reg_u64(cw, GUM_REG_XBX, mask);
gum_x86_writer_put_and_reg_reg(cw, GUM_REG_XAX, GUM_REG_XBX);
gum_x86_writer_put_shl_reg_u8(cw, GUM_REG_XAX, util_log2(sizeof(gpointer)));
gum_x86_writer_put_mov_reg_u64(cw, GUM_REG_XBX, GPOINTER_TO_SIZE(map_base));
gum_x86_writer_put_add_reg_reg(cw, GUM_REG_XAX, GUM_REG_XBX);
gum_x86_writer_put_mov_reg_u64(cw, GUM_X86_XBX, mask);
gum_x86_writer_put_and_reg_reg(cw, GUM_X86_XAX, GUM_X86_XBX);
gum_x86_writer_put_shl_reg_u8(cw, GUM_X86_XAX, util_log2(sizeof(gpointer)));
gum_x86_writer_put_mov_reg_u64(cw, GUM_X86_XBX, GPOINTER_TO_SIZE(map_base));
gum_x86_writer_put_add_reg_reg(cw, GUM_X86_XAX, GUM_X86_XBX);
/* Read the return address lookup */
gum_x86_writer_put_mov_reg_reg_ptr(cw, GUM_REG_XAX, GUM_REG_XAX);
gum_x86_writer_put_mov_reg_reg_ptr(cw, GUM_X86_XAX, GUM_X86_XAX);
}
void instrument_cache_jmp_call(const cs_insn *instr, GumStalkerOutput *output) {
GumX86Writer *cw = output->writer.x86;
cs_x86 * x86 = &instr->detail->x86;
cs_x86 *x86 = &instr->detail->x86;
if (x86->op_count != 1) { FFATAL("Unexpected operand count"); }
@ -315,7 +315,7 @@ void instrument_cache_jmp_call(const cs_insn *instr, GumStalkerOutput *output) {
* red-zone.
*/
gum_x86_writer_put_mov_reg_reg_offset_ptr(
cw, GUM_REG_XAX, GUM_REG_XSP,
cw, GUM_X86_XAX, GUM_X86_XSP,
-(GUM_RED_ZONE_SIZE + (1 * sizeof(gpointer))));
instrument_cache_rewrite_branch_insn(instr, output);
@ -323,33 +323,33 @@ void instrument_cache_jmp_call(const cs_insn *instr, GumStalkerOutput *output) {
instrument_cache_write_lookup(cw);
/* Test if its set*/
gum_x86_writer_put_cmp_reg_i32(cw, GUM_REG_XAX, INVALID);
gum_x86_writer_put_cmp_reg_i32(cw, GUM_X86_XAX, INVALID);
gum_x86_writer_put_jcc_short_label(cw, X86_INS_JLE, null, GUM_UNLIKELY);
/* If it's set, then stash the address beyond the red-zone */
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_XSP, -(GUM_RED_ZONE_SIZE + (4 * sizeof(gpointer))),
GUM_REG_XAX);
cw, GUM_X86_XSP, -(GUM_RED_ZONE_SIZE + (4 * sizeof(gpointer))),
GUM_X86_XAX);
if (instr->id == X86_INS_JMP) {
instrument_cache_write_pop_frame(cw);
gum_x86_writer_put_jmp_reg_offset_ptr(
cw, GUM_REG_XSP, -(GUM_RED_ZONE_SIZE + (4 * sizeof(gpointer))));
cw, GUM_X86_XSP, -(GUM_RED_ZONE_SIZE + (4 * sizeof(gpointer))));
} else {
gum_x86_writer_put_mov_reg_address(
cw, GUM_REG_XAX, GUM_ADDRESS(instr->address + instr->size));
gum_x86_writer_put_mov_reg_offset_ptr_reg(cw, GUM_REG_XSP,
-sizeof(gpointer), GUM_REG_XAX);
cw, GUM_X86_XAX, GUM_ADDRESS(instr->address + instr->size));
gum_x86_writer_put_mov_reg_offset_ptr_reg(cw, GUM_X86_XSP,
-sizeof(gpointer), GUM_X86_XAX);
instrument_cache_write_pop_frame(cw);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_XSP, GUM_REG_XSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_XSP, GUM_X86_XSP,
-sizeof(gpointer));
gum_x86_writer_put_jmp_reg_offset_ptr(
cw, GUM_REG_XSP, -(GUM_RED_ZONE_SIZE + ((4 - 1) * sizeof(gpointer))));
cw, GUM_X86_XSP, -(GUM_RED_ZONE_SIZE + ((4 - 1) * sizeof(gpointer))));
}
@ -362,7 +362,7 @@ void instrument_cache_jmp_call(const cs_insn *instr, GumStalkerOutput *output) {
void instrument_cache_ret(const cs_insn *instr, GumStalkerOutput *output) {
GumX86Writer *cw = output->writer.x86;
cs_x86 * x86 = &instr->detail->x86;
cs_x86 *x86 = &instr->detail->x86;
guint16 n = 0;
if (x86->op_count != 0) {
@ -381,16 +381,16 @@ void instrument_cache_ret(const cs_insn *instr, GumStalkerOutput *output) {
instrument_cache_write_push_frame(cw);
gum_x86_writer_put_mov_reg_reg_ptr(cw, GUM_REG_XAX, GUM_REG_XSP);
gum_x86_writer_put_mov_reg_reg_ptr(cw, GUM_X86_XAX, GUM_X86_XSP);
instrument_cache_write_lookup(cw);
/* Test if its set*/
gum_x86_writer_put_cmp_reg_i32(cw, GUM_REG_XAX, INVALID);
gum_x86_writer_put_cmp_reg_i32(cw, GUM_X86_XAX, INVALID);
gum_x86_writer_put_jcc_short_label(cw, X86_INS_JLE, null, GUM_UNLIKELY);
/* If it's set, then overwrite our return address and return */
gum_x86_writer_put_mov_reg_ptr_reg(cw, GUM_REG_XSP, GUM_REG_XAX);
gum_x86_writer_put_mov_reg_ptr_reg(cw, GUM_X86_XSP, GUM_X86_XAX);
instrument_cache_write_pop_frame(cw);
if (n == 0) {

View File

@ -86,14 +86,14 @@ gboolean instrument_is_coverage_optimize_supported(void) {
static void instrument_coverage_switch(GumStalkerObserver *self,
gpointer from_address,
gpointer start_address,
const cs_insn * from_insn,
gpointer * target) {
const cs_insn *from_insn,
gpointer *target) {
UNUSED_PARAMETER(self);
UNUSED_PARAMETER(from_address);
UNUSED_PARAMETER(start_address);
cs_x86 * x86;
cs_x86 *x86;
cs_x86_op *op;
if (from_insn == NULL) { return; }
@ -136,7 +136,7 @@ static void instrument_coverage_suppress_init(void) {
if (initialized) { return; }
initialized = true;
GumStalkerObserver * observer = stalker_get_observer();
GumStalkerObserver *observer = stalker_get_observer();
GumStalkerObserverInterface *iface = GUM_STALKER_OBSERVER_GET_IFACE(observer);
iface->switch_callback = instrument_coverage_switch;
@ -149,7 +149,7 @@ static void instrument_coverage_suppress_init(void) {
}
void instrument_coverage_optimize(const cs_insn * instr,
void instrument_coverage_optimize(const cs_insn *instr,
GumStalkerOutput *output) {
afl_log_code code = {0};
@ -223,7 +223,7 @@ void instrument_coverage_optimize(const cs_insn * instr,
}
void instrument_coverage_optimize_insn(const cs_insn * instr,
void instrument_coverage_optimize_insn(const cs_insn *instr,
GumStalkerOutput *output) {
UNUSED_PARAMETER(instr);

View File

@ -7,16 +7,16 @@ gboolean js_done = FALSE;
js_api_stalker_callback_t js_user_callback = NULL;
js_main_hook_t js_main_hook = NULL;
static char * js_script = NULL;
static gchar * filename = "afl.js";
static gchar * contents;
static GumScriptBackend * backend;
static GCancellable * cancellable = NULL;
static GError * error = NULL;
static GumScript * script;
static char *js_script = NULL;
static gchar *filename = "afl.js";
static gchar *contents;
static GumScriptBackend *backend;
static GCancellable *cancellable = NULL;
static GError *error = NULL;
static GumScript *script;
static GumScriptScheduler *scheduler;
static GMainContext * context;
static GMainLoop * main_loop;
static GMainContext *context;
static GMainLoop *main_loop;
static void js_msg(GumScript *script, const gchar *message, GBytes *data,
gpointer user_data) {

View File

@ -69,8 +69,8 @@ static void lib_read_text_section(lib_details_t *lib_details, Elf_Ehdr *hdr) {
Elf_Addr preferred_base;
Elf_Shdr *shdr;
Elf_Shdr *shstrtab;
char * shstr;
char * section_name;
char *shstr;
char *section_name;
Elf_Shdr *curr;
char text_name[] = ".text";

View File

@ -16,9 +16,9 @@ static gboolean lib_get_main_module(const GumModuleDetails *details,
gpointer user_data) {
GumDarwinModule **ret = (GumDarwinModule **)user_data;
GumDarwinModule * module = gum_darwin_module_new_from_memory(
details->path, mach_task_self(), details->range->base_address,
GUM_DARWIN_MODULE_FLAGS_NONE, NULL);
GumDarwinModule *module = gum_darwin_module_new_from_memory(
details->path, mach_task_self(), details->range->base_address,
GUM_DARWIN_MODULE_FLAGS_NONE, NULL);
FVERBOSE("Found main module: %s", module->name);

View File

@ -92,7 +92,7 @@ static void embedded_init(void) {
static void afl_print_cmdline(void) {
#if defined(__linux__)
char * buffer = g_malloc0(PROC_MAX);
char *buffer = g_malloc0(PROC_MAX);
gchar *fname = g_strdup_printf("/proc/%d/cmdline", getppid());
int fd = open(fname, O_RDONLY);
@ -144,7 +144,7 @@ static void afl_print_cmdline(void) {
static void afl_print_env(void) {
char * buffer = g_malloc0(PROC_MAX);
char *buffer = g_malloc0(PROC_MAX);
gchar *fname = g_strdup_printf("/proc/%d/environ", getppid());
int fd = open(fname, O_RDONLY);

View File

@ -31,7 +31,7 @@ typedef struct {
gboolean found_range(const GumRangeDetails *details, gpointer user_data) {
gum_range_t range = {0};
GArray * ranges = (GArray *)user_data;
GArray *ranges = (GArray *)user_data;
range.range = *details->range;
range.protection = details->protection;
@ -45,9 +45,9 @@ gboolean found_range(const GumRangeDetails *details, gpointer user_data) {
#if defined(__linux__) && !defined(__ANDROID__)
static int on_dlclose(void *handle) {
GArray * ranges = NULL;
GArray *ranges = NULL;
struct link_map *lm = NULL;
gum_range_t * range = NULL;
gum_range_t *range = NULL;
GumAddress base;
GumAddress limit;
gpointer mem;

View File

@ -24,7 +24,7 @@ gboolean persistent_is_supported(void) {
}
static void instrument_persitent_save_regs(GumArm64Writer * cw,
static void instrument_persitent_save_regs(GumArm64Writer *cw,
persistent_ctx_t *regs) {
GumAddress regs_address = GUM_ADDRESS(regs);
@ -105,18 +105,13 @@ static void instrument_persitent_save_regs(GumArm64Writer * cw,
offsetof(persistent_ctx_t, rflags));
/* Q */
gum_arm64_writer_put_stp_reg_reg_reg_offset(
cw, ARM64_REG_Q0, ARM64_REG_Q1, ARM64_REG_X0,
offsetof(GumCpuContext, q[0]), GUM_INDEX_SIGNED_OFFSET);
gum_arm64_writer_put_stp_reg_reg_reg_offset(
cw, ARM64_REG_Q2, ARM64_REG_Q3, ARM64_REG_X0,
offsetof(GumCpuContext, q[16]), GUM_INDEX_SIGNED_OFFSET);
gum_arm64_writer_put_stp_reg_reg_reg_offset(
cw, ARM64_REG_Q4, ARM64_REG_Q5, ARM64_REG_X0,
offsetof(GumCpuContext, q[32]), GUM_INDEX_SIGNED_OFFSET);
gum_arm64_writer_put_stp_reg_reg_reg_offset(
cw, ARM64_REG_Q6, ARM64_REG_Q7, ARM64_REG_X0,
offsetof(GumCpuContext, q[48]), GUM_INDEX_SIGNED_OFFSET);
for (int i = 0; i < 16; i++) {
gum_arm64_writer_put_stp_reg_reg_reg_offset(
cw, ARM64_REG_Q0 + (i * 2), ARM64_REG_Q0 + (i * 2) + 1, ARM64_REG_X0,
offsetof(GumCpuContext, v[i]), GUM_INDEX_SIGNED_OFFSET);
}
/* x0 & x1 */
gum_arm64_writer_put_ldp_reg_reg_reg_offset(cw, ARM64_REG_X2, ARM64_REG_X3,
@ -136,7 +131,7 @@ static void instrument_persitent_save_regs(GumArm64Writer * cw,
}
static void instrument_persitent_restore_regs(GumArm64Writer * cw,
static void instrument_persitent_restore_regs(GumArm64Writer *cw,
persistent_ctx_t *regs) {
GumAddress regs_address = GUM_ADDRESS(regs);
@ -201,18 +196,14 @@ static void instrument_persitent_restore_regs(GumArm64Writer * cw,
offsetof(persistent_ctx_t, rflags));
gum_arm64_writer_put_instruction(cw, msr_nzcv_x1);
gum_arm64_writer_put_ldp_reg_reg_reg_offset(
cw, ARM64_REG_Q0, ARM64_REG_Q1, ARM64_REG_X0,
offsetof(GumCpuContext, q[0]), GUM_INDEX_SIGNED_OFFSET);
gum_arm64_writer_put_ldp_reg_reg_reg_offset(
cw, ARM64_REG_Q2, ARM64_REG_Q3, ARM64_REG_X0,
offsetof(GumCpuContext, q[16]), GUM_INDEX_SIGNED_OFFSET);
gum_arm64_writer_put_ldp_reg_reg_reg_offset(
cw, ARM64_REG_Q4, ARM64_REG_Q5, ARM64_REG_X0,
offsetof(GumCpuContext, q[32]), GUM_INDEX_SIGNED_OFFSET);
gum_arm64_writer_put_ldp_reg_reg_reg_offset(
cw, ARM64_REG_Q6, ARM64_REG_Q7, ARM64_REG_X0,
offsetof(GumCpuContext, q[48]), GUM_INDEX_SIGNED_OFFSET);
/* Q */
for (int i = 0; i < 16; i++) {
gum_arm64_writer_put_ldp_reg_reg_reg_offset(
cw, ARM64_REG_Q0 + (i * 2), ARM64_REG_Q0 + (i * 2) + 1, ARM64_REG_X0,
offsetof(GumCpuContext, v[i]), GUM_INDEX_SIGNED_OFFSET);
}
/* x2 & x3 */
gum_arm64_writer_put_ldp_reg_reg_reg_offset(
@ -258,7 +249,7 @@ static void instrument_afl_persistent_loop(GumArm64Writer *cw) {
}
static void persistent_prologue_hook(GumArm64Writer * cw,
static void persistent_prologue_hook(GumArm64Writer *cw,
persistent_ctx_t *regs) {
if (persistent_hook == NULL) return;

View File

@ -25,148 +25,148 @@ gboolean persistent_is_supported(void) {
}
static void instrument_persitent_save_regs(GumX86Writer * cw,
static void instrument_persitent_save_regs(GumX86Writer *cw,
persistent_ctx_t *regs) {
GumAddress regs_address = GUM_ADDRESS(regs);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
-(GUM_RED_ZONE_SIZE));
/* Should be pushing FPU here, but meh */
gum_x86_writer_put_pushfx(cw);
gum_x86_writer_put_push_reg(cw, GUM_REG_RAX);
gum_x86_writer_put_push_reg(cw, GUM_X86_RAX);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RAX, regs_address);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RAX, regs_address);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rbx), GUM_REG_RBX);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rbx), GUM_X86_RBX);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rcx), GUM_REG_RCX);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rcx), GUM_X86_RCX);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rdx), GUM_REG_RDX);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rdx), GUM_X86_RDX);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rdi), GUM_REG_RDI);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rdi), GUM_X86_RDI);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rsi), GUM_REG_RSI);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rsi), GUM_X86_RSI);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rbp), GUM_REG_RBP);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rbp), GUM_X86_RBP);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r8), GUM_REG_R8);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r8), GUM_X86_R8);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r9), GUM_REG_R9);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r9), GUM_X86_R9);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r10), GUM_REG_R10);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r10), GUM_X86_R10);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r11), GUM_REG_R11);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r11), GUM_X86_R11);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r12), GUM_REG_R12);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r12), GUM_X86_R12);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r13), GUM_REG_R13);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r13), GUM_X86_R13);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r14), GUM_REG_R14);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r14), GUM_X86_R14);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, r15), GUM_REG_R15);
cw, GUM_X86_RAX, offsetof(GumCpuContext, r15), GUM_X86_R15);
/* Store RIP */
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RBX,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RBX,
GUM_ADDRESS(persistent_start));
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rip), GUM_REG_RBX);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rip), GUM_X86_RBX);
/* Store adjusted RSP */
gum_x86_writer_put_mov_reg_reg(cw, GUM_REG_RBX, GUM_REG_RSP);
gum_x86_writer_put_mov_reg_reg(cw, GUM_X86_RBX, GUM_X86_RSP);
/* RED_ZONE + Saved flags, RAX, alignment */
gum_x86_writer_put_add_reg_imm(cw, GUM_REG_RBX,
gum_x86_writer_put_add_reg_imm(cw, GUM_X86_RBX,
GUM_RED_ZONE_SIZE + (0x8 * 2));
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rsp), GUM_REG_RBX);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rsp), GUM_X86_RBX);
/* Save the flags */
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RBX, GUM_REG_RSP, 0x8);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RBX, GUM_X86_RSP, 0x8);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(persistent_ctx_t, rflags), GUM_REG_RBX);
cw, GUM_X86_RAX, offsetof(persistent_ctx_t, rflags), GUM_X86_RBX);
/* Save the RAX */
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RBX, GUM_REG_RSP, 0x0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RBX, GUM_X86_RSP, 0x0);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_RAX, offsetof(GumCpuContext, rax), GUM_REG_RBX);
cw, GUM_X86_RAX, offsetof(GumCpuContext, rax), GUM_X86_RBX);
/* Pop the saved values */
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP, 0x10);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP, 0x10);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
(GUM_RED_ZONE_SIZE));
}
static void instrument_persitent_restore_regs(GumX86Writer * cw,
static void instrument_persitent_restore_regs(GumX86Writer *cw,
persistent_ctx_t *regs) {
GumAddress regs_address = GUM_ADDRESS(regs);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RAX, regs_address);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RAX, regs_address);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RCX, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RCX, GUM_X86_RAX,
offsetof(GumCpuContext, rcx));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RDX, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RDX, GUM_X86_RAX,
offsetof(GumCpuContext, rdx));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RDI, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RDI, GUM_X86_RAX,
offsetof(GumCpuContext, rdi));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RSI, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RSI, GUM_X86_RAX,
offsetof(GumCpuContext, rsi));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RBP, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RBP, GUM_X86_RAX,
offsetof(GumCpuContext, rbp));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R8, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R8, GUM_X86_RAX,
offsetof(GumCpuContext, r8));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R9, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R9, GUM_X86_RAX,
offsetof(GumCpuContext, r9));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R10, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R10, GUM_X86_RAX,
offsetof(GumCpuContext, r10));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R11, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R11, GUM_X86_RAX,
offsetof(GumCpuContext, r11));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R12, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R12, GUM_X86_RAX,
offsetof(GumCpuContext, r12));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R13, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R13, GUM_X86_RAX,
offsetof(GumCpuContext, r13));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R14, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R14, GUM_X86_RAX,
offsetof(GumCpuContext, r14));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_R15, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_R15, GUM_X86_RAX,
offsetof(GumCpuContext, r15));
/* Don't restore RIP */
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RSP, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RSP, GUM_X86_RAX,
offsetof(GumCpuContext, rsp));
/* Restore RBX, RAX & Flags */
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
-(GUM_RED_ZONE_SIZE));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RBX, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RBX, GUM_X86_RAX,
offsetof(GumCpuContext, rbx));
gum_x86_writer_put_push_reg(cw, GUM_REG_RBX);
gum_x86_writer_put_push_reg(cw, GUM_X86_RBX);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RBX, GUM_REG_RAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RBX, GUM_X86_RAX,
offsetof(GumCpuContext, rax));
gum_x86_writer_put_push_reg(cw, GUM_REG_RBX);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RBX, GUM_REG_RAX,
gum_x86_writer_put_push_reg(cw, GUM_X86_RBX);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RBX, GUM_X86_RAX,
offsetof(persistent_ctx_t, rflags));
gum_x86_writer_put_push_reg(cw, GUM_REG_RBX);
gum_x86_writer_put_push_reg(cw, GUM_X86_RBX);
gum_x86_writer_put_popfx(cw);
gum_x86_writer_put_pop_reg(cw, GUM_REG_RAX);
gum_x86_writer_put_pop_reg(cw, GUM_REG_RBX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_RAX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_RBX);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
(GUM_RED_ZONE_SIZE));
}
static void instrument_exit(GumX86Writer *cw) {
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RAX, GUM_ADDRESS(_exit));
gum_x86_writer_put_mov_reg_u32(cw, GUM_REG_RDI, 0);
gum_x86_writer_put_call_reg(cw, GUM_REG_RAX);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RAX, GUM_ADDRESS(_exit));
gum_x86_writer_put_mov_reg_u32(cw, GUM_X86_RDI, 0);
gum_x86_writer_put_call_reg(cw, GUM_X86_RAX);
}
@ -186,13 +186,13 @@ static int instrument_afl_persistent_loop_func(void) {
static void instrument_afl_persistent_loop(GumX86Writer *cw) {
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
-(GUM_RED_ZONE_SIZE));
gum_x86_writer_put_call_address_with_arguments(
cw, GUM_CALL_CAPI, GUM_ADDRESS(instrument_afl_persistent_loop_func), 0);
gum_x86_writer_put_test_reg_reg(cw, GUM_REG_RAX, GUM_REG_RAX);
gum_x86_writer_put_test_reg_reg(cw, GUM_X86_RAX, GUM_X86_RAX);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
(GUM_RED_ZONE_SIZE));
}
@ -200,26 +200,26 @@ static void instrument_afl_persistent_loop(GumX86Writer *cw) {
static void persistent_prologue_hook(GumX86Writer *cw, persistent_ctx_t *regs) {
if (persistent_hook == NULL) return;
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
-(GUM_RED_ZONE_SIZE));
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RDX,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RDX,
GUM_ADDRESS(&__afl_fuzz_len));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RDX, GUM_REG_RDX, 0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RDX, GUM_REG_RDX, 0);
gum_x86_writer_put_mov_reg_u64(cw, GUM_REG_RDI, 0xffffffff);
gum_x86_writer_put_and_reg_reg(cw, GUM_REG_RDX, GUM_REG_RDI);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RDX, GUM_X86_RDX, 0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RDX, GUM_X86_RDX, 0);
gum_x86_writer_put_mov_reg_u64(cw, GUM_X86_RDI, 0xffffffff);
gum_x86_writer_put_and_reg_reg(cw, GUM_X86_RDX, GUM_X86_RDI);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RSI,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RSI,
GUM_ADDRESS(&__afl_fuzz_ptr));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RSI, GUM_REG_RSI, 0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RSI, GUM_X86_RSI, 0);
gum_x86_writer_put_call_address_with_arguments(
cw, GUM_CALL_CAPI, GUM_ADDRESS(persistent_hook), 3, GUM_ARG_ADDRESS,
GUM_ADDRESS(&regs->ctx), GUM_ARG_REGISTER, GUM_REG_RSI, GUM_ARG_REGISTER,
GUM_REG_RDX);
GUM_ADDRESS(&regs->ctx), GUM_ARG_REGISTER, GUM_X86_RSI, GUM_ARG_REGISTER,
GUM_X86_RDX);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
(GUM_RED_ZONE_SIZE));
}
@ -228,23 +228,23 @@ static void instrument_persitent_save_ret(GumX86Writer *cw) {
/* Stack usage by this function */
gssize offset = GUM_RED_ZONE_SIZE + (3 * 8);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
-(GUM_RED_ZONE_SIZE));
gum_x86_writer_put_pushfx(cw);
gum_x86_writer_put_push_reg(cw, GUM_REG_RAX);
gum_x86_writer_put_push_reg(cw, GUM_REG_RBX);
gum_x86_writer_put_push_reg(cw, GUM_X86_RAX);
gum_x86_writer_put_push_reg(cw, GUM_X86_RBX);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_RBX, GUM_REG_RSP,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_RBX, GUM_X86_RSP,
offset);
gum_x86_writer_put_mov_reg_ptr_reg(cw, GUM_REG_RAX, GUM_REG_RBX);
gum_x86_writer_put_mov_reg_ptr_reg(cw, GUM_X86_RAX, GUM_X86_RBX);
gum_x86_writer_put_pop_reg(cw, GUM_REG_RBX);
gum_x86_writer_put_pop_reg(cw, GUM_REG_RAX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_RBX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_RAX);
gum_x86_writer_put_popfx(cw);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP,
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP,
(GUM_RED_ZONE_SIZE));
}
@ -278,7 +278,7 @@ void persistent_prologue_arch(GumStalkerOutput *output) {
FVERBOSE("Persistent loop reached");
/* Pop the return value */
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP, 8);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP, 8);
instrument_persitent_save_regs(cw, &saved_regs);
@ -326,13 +326,13 @@ void persistent_epilogue_arch(GumStalkerOutput *output) {
/* The stack should be aligned when we re-enter our loop */
gconstpointer zero = cw->code + 1;
gum_x86_writer_put_test_reg_u32(cw, GUM_REG_RSP, 0xF);
gum_x86_writer_put_test_reg_u32(cw, GUM_X86_RSP, 0xF);
gum_x86_writer_put_jcc_near_label(cw, X86_INS_JE, zero, GUM_NO_HINT);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_RSP, GUM_REG_RSP, -8);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_RSP, GUM_X86_RSP, -8);
gum_x86_writer_put_label(cw, zero);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_RAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_jmp_reg_ptr(cw, GUM_REG_RAX);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_RAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_jmp_reg_ptr(cw, GUM_X86_RAX);
}

View File

@ -25,105 +25,105 @@ gboolean persistent_is_supported(void) {
}
static void instrument_persitent_save_regs(GumX86Writer * cw,
static void instrument_persitent_save_regs(GumX86Writer *cw,
persistent_ctx_t *regs) {
GumAddress regs_address = GUM_ADDRESS(regs);
/* Should be pushing FPU here, but meh */
gum_x86_writer_put_pushfx(cw);
gum_x86_writer_put_push_reg(cw, GUM_REG_EAX);
gum_x86_writer_put_push_reg(cw, GUM_X86_EAX);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_EAX, regs_address);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_EAX, regs_address);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, ebx), GUM_REG_EBX);
cw, GUM_X86_EAX, offsetof(GumCpuContext, ebx), GUM_X86_EBX);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, ecx), GUM_REG_ECX);
cw, GUM_X86_EAX, offsetof(GumCpuContext, ecx), GUM_X86_ECX);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, edx), GUM_REG_EDX);
cw, GUM_X86_EAX, offsetof(GumCpuContext, edx), GUM_X86_EDX);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, edi), GUM_REG_EDI);
cw, GUM_X86_EAX, offsetof(GumCpuContext, edi), GUM_X86_EDI);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, esi), GUM_REG_ESI);
cw, GUM_X86_EAX, offsetof(GumCpuContext, esi), GUM_X86_ESI);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, ebp), GUM_REG_EBP);
cw, GUM_X86_EAX, offsetof(GumCpuContext, ebp), GUM_X86_EBP);
/* Store RIP */
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_EBX,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_EBX,
GUM_ADDRESS(persistent_start));
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, eip), GUM_REG_EBX);
cw, GUM_X86_EAX, offsetof(GumCpuContext, eip), GUM_X86_EBX);
/* Store adjusted RSP */
gum_x86_writer_put_mov_reg_reg(cw, GUM_REG_EBX, GUM_REG_ESP);
gum_x86_writer_put_mov_reg_reg(cw, GUM_X86_EBX, GUM_X86_ESP);
/* RED_ZONE + Saved flags, RAX */
gum_x86_writer_put_add_reg_imm(cw, GUM_REG_EBX, (0x4 * 2));
gum_x86_writer_put_add_reg_imm(cw, GUM_X86_EBX, (0x4 * 2));
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, esp), GUM_REG_EBX);
cw, GUM_X86_EAX, offsetof(GumCpuContext, esp), GUM_X86_EBX);
/* Save the flags */
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EBX, GUM_REG_ESP, 0x4);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EBX, GUM_X86_ESP, 0x4);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(persistent_ctx_t, eflags), GUM_REG_EBX);
cw, GUM_X86_EAX, offsetof(persistent_ctx_t, eflags), GUM_X86_EBX);
/* Save the RAX */
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EBX, GUM_REG_ESP, 0x0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EBX, GUM_X86_ESP, 0x0);
gum_x86_writer_put_mov_reg_offset_ptr_reg(
cw, GUM_REG_EAX, offsetof(GumCpuContext, eax), GUM_REG_EBX);
cw, GUM_X86_EAX, offsetof(GumCpuContext, eax), GUM_X86_EBX);
/* Pop the saved values */
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_ESP, GUM_REG_ESP, 0x8);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_ESP, GUM_X86_ESP, 0x8);
}
static void instrument_persitent_restore_regs(GumX86Writer * cw,
static void instrument_persitent_restore_regs(GumX86Writer *cw,
persistent_ctx_t *regs) {
GumAddress regs_address = GUM_ADDRESS(regs);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_EAX, regs_address);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_EAX, regs_address);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_ECX, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_ECX, GUM_X86_EAX,
offsetof(GumCpuContext, ecx));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EDX, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EDX, GUM_X86_EAX,
offsetof(GumCpuContext, edx));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EDI, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EDI, GUM_X86_EAX,
offsetof(GumCpuContext, edi));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_ESI, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_ESI, GUM_X86_EAX,
offsetof(GumCpuContext, esi));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EBP, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EBP, GUM_X86_EAX,
offsetof(GumCpuContext, ebp));
/* Don't restore RIP */
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_ESP, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_ESP, GUM_X86_EAX,
offsetof(GumCpuContext, esp));
/* Restore RBX, RAX & Flags */
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EBX, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EBX, GUM_X86_EAX,
offsetof(GumCpuContext, ebx));
gum_x86_writer_put_push_reg(cw, GUM_REG_EBX);
gum_x86_writer_put_push_reg(cw, GUM_X86_EBX);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EBX, GUM_REG_EAX,
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EBX, GUM_X86_EAX,
offsetof(GumCpuContext, eax));
gum_x86_writer_put_push_reg(cw, GUM_REG_EBX);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EBX, GUM_REG_EAX,
gum_x86_writer_put_push_reg(cw, GUM_X86_EBX);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EBX, GUM_X86_EAX,
offsetof(persistent_ctx_t, eflags));
gum_x86_writer_put_push_reg(cw, GUM_REG_EBX);
gum_x86_writer_put_push_reg(cw, GUM_X86_EBX);
gum_x86_writer_put_popfx(cw);
gum_x86_writer_put_pop_reg(cw, GUM_REG_EAX);
gum_x86_writer_put_pop_reg(cw, GUM_REG_EBX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_EAX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_EBX);
}
static void instrument_exit(GumX86Writer *cw) {
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_EAX, GUM_ADDRESS(_exit));
gum_x86_writer_put_mov_reg_u32(cw, GUM_REG_EDI, 0);
gum_x86_writer_put_push_reg(cw, GUM_REG_EDI);
gum_x86_writer_put_call_reg(cw, GUM_REG_EAX);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_EAX, GUM_ADDRESS(_exit));
gum_x86_writer_put_mov_reg_u32(cw, GUM_X86_EDI, 0);
gum_x86_writer_put_push_reg(cw, GUM_X86_EDI);
gum_x86_writer_put_call_reg(cw, GUM_X86_EAX);
}
@ -145,7 +145,7 @@ static void instrument_afl_persistent_loop(GumX86Writer *cw) {
gum_x86_writer_put_call_address_with_arguments(
cw, GUM_CALL_CAPI, GUM_ADDRESS(instrument_afl_persistent_loop_func), 0);
gum_x86_writer_put_test_reg_reg(cw, GUM_REG_EAX, GUM_REG_EAX);
gum_x86_writer_put_test_reg_reg(cw, GUM_X86_EAX, GUM_X86_EAX);
}
@ -153,20 +153,20 @@ static void persistent_prologue_hook(GumX86Writer *cw, persistent_ctx_t *regs) {
if (persistent_hook == NULL) return;
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_ECX,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_ECX,
GUM_ADDRESS(&__afl_fuzz_len));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_ECX, GUM_REG_ECX, 0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_ECX, GUM_REG_ECX, 0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_ECX, GUM_X86_ECX, 0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_ECX, GUM_X86_ECX, 0);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_EDX,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_EDX,
GUM_ADDRESS(&__afl_fuzz_ptr));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EDX, GUM_REG_EDX, 0);
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EDX, GUM_X86_EDX, 0);
/* Base address is 64-bits (hence two zero arguments) */
gum_x86_writer_put_call_address_with_arguments(
cw, GUM_CALL_CAPI, GUM_ADDRESS(persistent_hook), 3, GUM_ARG_ADDRESS,
GUM_ADDRESS(&regs->ctx), GUM_ARG_REGISTER, GUM_REG_EDX, GUM_ARG_REGISTER,
GUM_REG_ECX);
GUM_ADDRESS(&regs->ctx), GUM_ARG_REGISTER, GUM_X86_EDX, GUM_ARG_REGISTER,
GUM_X86_ECX);
}
@ -176,16 +176,16 @@ static void instrument_persitent_save_ret(GumX86Writer *cw) {
gssize offset = (3 * 4);
gum_x86_writer_put_pushfx(cw);
gum_x86_writer_put_push_reg(cw, GUM_REG_EAX);
gum_x86_writer_put_push_reg(cw, GUM_REG_EBX);
gum_x86_writer_put_push_reg(cw, GUM_X86_EAX);
gum_x86_writer_put_push_reg(cw, GUM_X86_EBX);
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_EAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_REG_EBX, GUM_REG_ESP,
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_EAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_mov_reg_reg_offset_ptr(cw, GUM_X86_EBX, GUM_X86_ESP,
offset);
gum_x86_writer_put_mov_reg_ptr_reg(cw, GUM_REG_EAX, GUM_REG_EBX);
gum_x86_writer_put_mov_reg_ptr_reg(cw, GUM_X86_EAX, GUM_X86_EBX);
gum_x86_writer_put_pop_reg(cw, GUM_REG_EBX);
gum_x86_writer_put_pop_reg(cw, GUM_REG_EAX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_EBX);
gum_x86_writer_put_pop_reg(cw, GUM_X86_EAX);
gum_x86_writer_put_popfx(cw);
}
@ -219,7 +219,7 @@ void persistent_prologue_arch(GumStalkerOutput *output) {
FVERBOSE("Persistent loop reached");
/* Pop the return value */
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_REG_ESP, GUM_REG_ESP, 4);
gum_x86_writer_put_lea_reg_reg_offset(cw, GUM_X86_ESP, GUM_X86_ESP, 4);
instrument_persitent_save_regs(cw, &saved_regs);
@ -263,8 +263,8 @@ void persistent_epilogue_arch(GumStalkerOutput *output) {
if (persistent_debug) { gum_x86_writer_put_breakpoint(cw); }
gum_x86_writer_put_mov_reg_address(cw, GUM_REG_EAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_jmp_reg_ptr(cw, GUM_REG_EAX);
gum_x86_writer_put_mov_reg_address(cw, GUM_X86_EAX, GUM_ADDRESS(&saved_ret));
gum_x86_writer_put_jmp_reg_ptr(cw, GUM_X86_EAX);
}

View File

@ -19,7 +19,7 @@
typedef struct {
size_t count;
void * entry[PREFETCH_ENTRIES];
void *entry[PREFETCH_ENTRIES];
guint8 backpatch_data[BP_SIZE];
gsize backpatch_size;
@ -173,7 +173,7 @@ static void prefetch_read_blocks(void) {
static void prefetch_read_patches(void) {
gsize offset = 0;
GumStalker * stalker = stalker_get();
GumStalker *stalker = stalker_get();
GumBackpatch *backpatch = NULL;
for (gsize remaining = prefetch_data->backpatch_size - offset;
@ -319,7 +319,7 @@ void prefetch_init(void) {
if (!prefetch_backpatch) { return; }
GumStalkerObserver * observer = stalker_get_observer();
GumStalkerObserver *observer = stalker_get_observer();
GumStalkerObserverInterface *iface = GUM_STALKER_OBSERVER_GET_IFACE(observer);
iface->notify_backpatch = gum_afl_stalker_backpatcher_notify;

View File

@ -9,7 +9,7 @@
typedef struct {
gchar * suffix;
gchar *suffix;
GumMemoryRange *range;
gboolean done;
@ -135,7 +135,7 @@ static gboolean convert_name_token_for_module(const GumModuleDetails *details,
static void convert_name_token(gchar *token, GumMemoryRange *range) {
gchar * suffix = g_strconcat("/", token, NULL);
gchar *suffix = g_strconcat("/", token, NULL);
convert_name_ctx_t ctx = {.suffix = suffix, .range = range, .done = false};
gum_process_enumerate_modules(convert_name_token_for_module, &ctx);
@ -235,7 +235,7 @@ static void print_ranges(char *key, GArray *ranges) {
static gboolean collect_module_ranges_callback(const GumRangeDetails *details,
gpointer user_data) {
GArray * ranges = (GArray *)user_data;
GArray *ranges = (GArray *)user_data;
GumMemoryRange range = *details->range;
g_array_append_val(ranges, range);
return TRUE;
@ -292,12 +292,12 @@ void ranges_add_exclude(GumMemoryRange *range) {
static GArray *collect_ranges(char *env_key) {
char * env_val;
gchar ** tokens;
char *env_val;
gchar **tokens;
int token_count;
GumMemoryRange range;
int i;
GArray * result;
GArray *result;
result = g_array_new(false, false, sizeof(GumMemoryRange));
@ -330,7 +330,7 @@ static GArray *collect_ranges(char *env_key) {
static GArray *collect_libs_ranges(void) {
GArray * result;
GArray *result;
GumMemoryRange range;
result = g_array_new(false, false, sizeof(GumMemoryRange));
@ -422,7 +422,7 @@ static gboolean intersect_range(GumMemoryRange *rr, GumMemoryRange *ra,
static GArray *intersect_ranges(GArray *a, GArray *b) {
GArray * result;
GArray *result;
GumMemoryRange *ra;
GumMemoryRange *rb;
GumMemoryRange ri;
@ -452,7 +452,7 @@ static GArray *intersect_ranges(GArray *a, GArray *b) {
static GArray *subtract_ranges(GArray *a, GArray *b) {
GArray * result;
GArray *result;
GumMemoryRange *ra;
GumAddress ral;
GumMemoryRange *rb;
@ -528,7 +528,7 @@ static GArray *subtract_ranges(GArray *a, GArray *b) {
static GArray *merge_ranges(GArray *a) {
GArray * result;
GArray *result;
GumMemoryRange rp;
GumMemoryRange *r;
@ -585,11 +585,11 @@ void ranges_config(void) {
void ranges_init(void) {
GumMemoryRange ri;
GArray * step1;
GArray * step2;
GArray * step3;
GArray * step4;
GArray * step5;
GArray *step1;
GArray *step2;
GArray *step3;
GArray *step4;
GArray *step5;
FOKF(cBLU "Ranges" cRST " - " cGRN "instrument jit:" cYEL " [%c]",
ranges_inst_jit ? 'X' : ' ');
@ -669,7 +669,7 @@ gboolean range_is_excluded(GumAddress address) {
void ranges_exclude() {
GumMemoryRange *r;
GumStalker * stalker = stalker_get();
GumStalker *stalker = stalker_get();
FVERBOSE("Excluding ranges");

View File

@ -8,9 +8,9 @@
#include "seccomp.h"
#include "util.h"
static void seccomp_callback_filter(struct seccomp_notif * req,
static void seccomp_callback_filter(struct seccomp_notif *req,
struct seccomp_notif_resp *resp,
GumReturnAddressArray * frames) {
GumReturnAddressArray *frames) {
GumDebugSymbolDetails details = {0};
if (req->data.nr == SYS_OPENAT) {
@ -54,7 +54,7 @@ static void seccomp_callback_filter(struct seccomp_notif * req,
free(syms);
#else
void **syms = (void **)__builtin_frame_address(0);
void * framep = __builtin_frame_address(1);
void *framep = __builtin_frame_address(1);
int i = 0;
syms = framep;

View File

@ -21,7 +21,7 @@ typedef struct {
seccomp_child_func_t func;
int event_fd;
void * ctx;
void *ctx;
} seccomp_child_func_ctx_t;

View File

@ -129,7 +129,7 @@ static volatile bool seccomp_filter_child_done = false;
static pid_t seccomp_filter_child = -1;
static GumCpuContext seccomp_filter_cpu_context = {0};
static GumReturnAddressArray seccomp_filter_frames = {.len = 0, .items = {0}};
static GumBacktracer * seccomp_filter_backtracer = NULL;
static GumBacktracer *seccomp_filter_backtracer = NULL;
static void seccomp_filter_child_handler(int sig, siginfo_t *info,
void *ucontext) {
@ -209,7 +209,7 @@ int seccomp_filter_install(pid_t child) {
void seccomp_filter_run(int fd, seccomp_filter_callback_t callback) {
struct seccomp_notif * req = NULL;
struct seccomp_notif *req = NULL;
struct seccomp_notif_resp *resp = NULL;
struct seccomp_notif_sizes sizes;

View File

@ -59,9 +59,9 @@ void seccomp_socket_send(int sockfd, int fd) {
struct iovec iov = {.iov_base = &data, .iov_len = sizeof(data)};
union cmsg control_msg = {.hdr = {
.cmsg_len = CMSG_LEN(sizeof(int)),
.cmsg_level = SOL_SOCKET,
.cmsg_type = SCM_RIGHTS,
.cmsg_len = CMSG_LEN(sizeof(int)),
.cmsg_level = SOL_SOCKET,
.cmsg_type = SCM_RIGHTS,
}};

View File

@ -74,7 +74,7 @@ static gboolean stalker_exclude_self(const GumRangeDetails *details,
gpointer user_data) {
UNUSED_PARAMETER(user_data);
gchar * name;
gchar *name;
gboolean found;
GumStalker *stalker;
if (details->file == NULL) { return TRUE; }

View File

@ -16,7 +16,7 @@
#define MICRO_TO_SEC 1000000
char * stats_filename = NULL;
char *stats_filename = NULL;
guint64 stats_interval = 0;
static guint64 stats_interval_us = 0;
static int stats_fd = -1;
@ -41,8 +41,8 @@ void stats_write(void) {
stats_data->curr.stats_time = current_time;
GDateTime *date_time = g_date_time_new_now_local();
char * date_string = g_date_time_format(date_time, "%Y-%m-%d");
char * time_string = g_date_time_format(date_time, "%H:%M:%S");
char *date_string = g_date_time_format(date_time, "%Y-%m-%d");
char *time_string = g_date_time_format(date_time, "%H:%M:%S");
guint elapsed = (stats_data->curr.stats_time - stats_data->prev.stats_time) /
MICRO_TO_SEC;

View File

@ -248,7 +248,7 @@ void stats_write_arch(stats_data_t *data) {
static x86_op_type stats_get_operand_type(const cs_insn *instr) {
cs_x86 * x86 = &instr->detail->x86;
cs_x86 *x86 = &instr->detail->x86;
cs_x86_op *operand;
if (x86->op_count != 1) {
@ -266,7 +266,7 @@ static x86_op_type stats_get_operand_type(const cs_insn *instr) {
static void stats_collect_call_imm_excluded_arch(const cs_insn *instr) {
cs_x86 * x86 = &instr->detail->x86;
cs_x86 *x86 = &instr->detail->x86;
cs_x86_op *operand = &x86->operands[0];
if (range_is_excluded(GUM_ADDRESS(operand->imm))) {

View File

@ -188,7 +188,7 @@ struct queue_entry {
u8 *testcase_buf; /* The testcase buffer, if loaded. */
u8 * cmplog_colorinput; /* the result buf of colorization */
u8 *cmplog_colorinput; /* the result buf of colorization */
struct tainted *taint; /* Taint information from CmpLog */
struct queue_entry *mother; /* queue entry this based on */
@ -341,18 +341,18 @@ typedef struct py_mutator {
PyObject *py_module;
PyObject *py_functions[PY_FUNC_COUNT];
void * afl_state;
void * py_data;
void *afl_state;
void *py_data;
u8 * fuzz_buf;
u8 *fuzz_buf;
size_t fuzz_size;
Py_buffer post_process_buf;
u8 * trim_buf;
u8 *trim_buf;
size_t trim_size;
u8 * havoc_buf;
u8 *havoc_buf;
size_t havoc_size;
} py_mutator_t;
@ -361,13 +361,13 @@ typedef struct py_mutator {
typedef struct MOpt_globals {
u64 * finds;
u64 * finds_v2;
u64 * cycles;
u64 * cycles_v2;
u64 * cycles_v3;
u64 *finds;
u64 *finds_v2;
u64 *cycles;
u64 *cycles_v2;
u64 *cycles_v3;
u32 is_pilot_mode;
u64 * pTime;
u64 *pTime;
u64 period;
char *havoc_stagename;
char *splice_stageformat;
@ -406,7 +406,7 @@ struct afl_pass_stat {
struct foreign_sync {
u8 * dir;
u8 *dir;
time_t mtime;
};
@ -418,7 +418,7 @@ typedef struct afl_state {
afl_forkserver_t fsrv;
sharedmem_t shm;
sharedmem_t * shm_fuzz;
sharedmem_t *shm_fuzz;
afl_env_vars_t afl_env;
char **argv; /* argv if needed */
@ -529,7 +529,7 @@ typedef struct afl_state {
*virgin_crash; /* Bits we haven't seen in crashes */
double *alias_probability; /* alias weighted probabilities */
u32 * alias_table; /* alias weighted random lookup table */
u32 *alias_table; /* alias weighted random lookup table */
u32 active_items; /* enabled entries in the queue */
u8 *var_bytes; /* Bytes that appear to be variable */
@ -643,7 +643,7 @@ typedef struct afl_state {
/* CmpLog */
char * cmplog_binary;
char *cmplog_binary;
afl_forkserver_t cmplog_fsrv; /* cmplog has its own little forkserver */
/* Custom mutators */
@ -658,7 +658,7 @@ typedef struct afl_state {
u8 cmplog_enable_arith, cmplog_enable_transform;
struct afl_pass_stat *pass_stats;
struct cmp_map * orig_cmp_map;
struct cmp_map *orig_cmp_map;
u8 describe_op_buf_256[256]; /* describe_op will use this to return a string
up to 256 */
@ -690,9 +690,9 @@ typedef struct afl_state {
u64 statsd_last_send_ms;
struct sockaddr_in statsd_server;
int statsd_sock;
char * statsd_tags_flavor;
char * statsd_tags_format;
char * statsd_metric_format;
char *statsd_tags_flavor;
char *statsd_tags_format;
char *statsd_metric_format;
int statsd_metric_format_type;
double stats_avg_exec;
@ -770,9 +770,9 @@ typedef struct afl_state {
struct custom_mutator {
const char *name;
char * name_short;
void * dh;
u8 * post_process_buf;
char *name_short;
void *dh;
u8 *post_process_buf;
u8 stacked_custom_prob, stacked_custom;
void *data; /* custom mutator data ptr */

View File

@ -49,7 +49,7 @@ void argv_cpy_free(char **argv);
char **get_cs_argv(u8 *own_loc, u8 **target_path_p, int argc, char **argv);
char **get_qemu_argv(u8 *own_loc, u8 **target_path_p, int argc, char **argv);
char **get_wine_argv(u8 *own_loc, u8 **target_path_p, int argc, char **argv);
char * get_afl_env(char *env);
char *get_afl_env(char *env);
/* Extract env vars from input string and set them using setenv()
For use with AFL_TARGET_ENV, ... */

View File

@ -26,7 +26,7 @@
/* Version string: */
// c = release, a = volatile github dev, e = experimental branch
#define VERSION "++4.01c"
#define VERSION "++4.02a"
/******************************************************
* *

View File

@ -192,7 +192,7 @@ static inline const char *colorfilter(const char *x) {
if (likely(disabled)) return x;
static char monochromestring[4096];
char * d = monochromestring;
char *d = monochromestring;
int in_seq = 0;
while (*x) {

View File

@ -150,7 +150,7 @@ typedef struct afl_forkserver {
#ifdef AFL_PERSISTENT_RECORD
u32 persistent_record_idx; /* persistent replay cache ptr */
u32 persistent_record_cnt; /* persistent replay counter */
u8 * persistent_record_dir;
u8 *persistent_record_dir;
u8 **persistent_record_data;
u32 *persistent_record_len;
s32 persistent_record_pid;
@ -168,14 +168,14 @@ typedef struct afl_forkserver {
#ifdef __linux__
nyx_plugin_handler_t *nyx_handlers;
char * out_dir_path; /* path to the output directory */
char *out_dir_path; /* path to the output directory */
u8 nyx_mode; /* if running in nyx mode or not */
bool nyx_parent; /* create initial snapshot */
bool nyx_standalone; /* don't serialize the snapshot */
void * nyx_runner; /* nyx runner object */
void *nyx_runner; /* nyx runner object */
u32 nyx_id; /* nyx runner id (0 -> master) */
u32 nyx_bind_cpu_id; /* nyx runner cpu id */
char * nyx_aux_string;
char *nyx_aux_string;
#endif
} afl_forkserver_t;

View File

@ -43,7 +43,7 @@ typedef struct list_element {
struct list_element *prev;
struct list_element *next;
void * data;
void *data;
} element_t;
@ -102,7 +102,7 @@ static inline void list_append(list_t *list, void *el) {
#define LIST_FOREACH(list, type, block) \
do { \
\
list_t * li = (list); \
list_t *li = (list); \
element_t *head = get_head((li)); \
element_t *el_box = (head)->next; \
if (!el_box) FATAL("foreach over uninitialized list"); \

View File

@ -56,7 +56,7 @@ typedef struct sharedmem {
} sharedmem_t;
u8 * afl_shm_init(sharedmem_t *, size_t, unsigned char non_instrumented_mode);
u8 *afl_shm_init(sharedmem_t *, size_t, unsigned char non_instrumented_mode);
void afl_shm_deinit(sharedmem_t *);
#endif

View File

@ -510,7 +510,7 @@ XXH_PUBLIC_API XXH_errorcode XXH32_freeState(XXH32_state_t *statePtr);
* @pre
* @p dst_state and @p src_state must not be `NULL` and must not overlap.
*/
XXH_PUBLIC_API void XXH32_copyState(XXH32_state_t * dst_state,
XXH_PUBLIC_API void XXH32_copyState(XXH32_state_t *dst_state,
const XXH32_state_t *src_state);
/*!
@ -742,10 +742,10 @@ XXH_PUBLIC_API XXH64_hash_t XXH64(const void *input, size_t length,
*
* @see XXH64_state_s for details.
*/
typedef struct XXH64_state_s XXH64_state_t; /* incomplete type */
typedef struct XXH64_state_s XXH64_state_t; /* incomplete type */
XXH_PUBLIC_API XXH64_state_t *XXH64_createState(void);
XXH_PUBLIC_API XXH_errorcode XXH64_freeState(XXH64_state_t *statePtr);
XXH_PUBLIC_API void XXH64_copyState(XXH64_state_t * dst_state,
XXH_PUBLIC_API void XXH64_copyState(XXH64_state_t *dst_state,
const XXH64_state_t *src_state);
XXH_PUBLIC_API XXH_errorcode XXH64_reset(XXH64_state_t *statePtr,
@ -870,10 +870,10 @@ XXH_PUBLIC_API XXH64_hash_t XXH3_64bits_withSecret(const void *data, size_t len,
*
* @see XXH3_state_s for details.
*/
typedef struct XXH3_state_s XXH3_state_t;
typedef struct XXH3_state_s XXH3_state_t;
XXH_PUBLIC_API XXH3_state_t *XXH3_createState(void);
XXH_PUBLIC_API XXH_errorcode XXH3_freeState(XXH3_state_t *statePtr);
XXH_PUBLIC_API void XXH3_copyState(XXH3_state_t * dst_state,
XXH_PUBLIC_API void XXH3_copyState(XXH3_state_t *dst_state,
const XXH3_state_t *src_state);
/*
@ -902,7 +902,7 @@ XXH_PUBLIC_API XXH_errorcode XXH3_64bits_reset_withSecret(
XXH3_state_t *statePtr, const void *secret, size_t secretSize);
XXH_PUBLIC_API XXH_errorcode XXH3_64bits_update(XXH3_state_t *statePtr,
const void * input,
const void *input,
size_t length);
XXH_PUBLIC_API XXH64_hash_t XXH3_64bits_digest(const XXH3_state_t *statePtr);
@ -955,7 +955,7 @@ XXH_PUBLIC_API XXH_errorcode XXH3_128bits_reset_withSecret(
XXH3_state_t *statePtr, const void *secret, size_t secretSize);
XXH_PUBLIC_API XXH_errorcode XXH3_128bits_update(XXH3_state_t *statePtr,
const void * input,
const void *input,
size_t length);
XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_digest(const XXH3_state_t *statePtr);
@ -1229,7 +1229,7 @@ struct XXH3_state_s {
* `secretBuffer`. When customSeedSize > 0, supplying NULL as customSeed is
* undefined behavior.
*/
XXH_PUBLIC_API void XXH3_generateSecret(void * secretBuffer,
XXH_PUBLIC_API void XXH3_generateSecret(void *secretBuffer,
const void *customSeed,
size_t customSeedSize);
@ -1951,7 +1951,7 @@ static xxh_u32 XXH_readBE32(const void *ptr) {
#endif
XXH_FORCE_INLINE xxh_u32 XXH_readLE32_align(const void * ptr,
XXH_FORCE_INLINE xxh_u32 XXH_readLE32_align(const void *ptr,
XXH_alignment align) {
if (align == XXH_unaligned) {
@ -2317,7 +2317,7 @@ XXH_PUBLIC_API XXH_errorcode XXH32_freeState(XXH32_state_t *statePtr) {
}
/*! @ingroup xxh32_family */
XXH_PUBLIC_API void XXH32_copyState(XXH32_state_t * dstState,
XXH_PUBLIC_API void XXH32_copyState(XXH32_state_t *dstState,
const XXH32_state_t *srcState) {
memcpy(dstState, srcState, sizeof(*dstState));
@ -2355,7 +2355,7 @@ XXH_PUBLIC_API XXH_errorcode XXH32_update(XXH32_state_t *state,
{
const xxh_u8 * p = (const xxh_u8 *)input;
const xxh_u8 *p = (const xxh_u8 *)input;
const xxh_u8 *const bEnd = p + len;
state->total_len_32 += (XXH32_hash_t)len;
@ -2625,7 +2625,7 @@ static xxh_u64 XXH_readBE64(const void *ptr) {
#endif
XXH_FORCE_INLINE xxh_u64 XXH_readLE64_align(const void * ptr,
XXH_FORCE_INLINE xxh_u64 XXH_readLE64_align(const void *ptr,
XXH_alignment align) {
if (align == XXH_unaligned)
@ -2852,7 +2852,7 @@ XXH_PUBLIC_API XXH_errorcode XXH64_freeState(XXH64_state_t *statePtr) {
}
/*! @ingroup xxh64_family */
XXH_PUBLIC_API void XXH64_copyState(XXH64_state_t * dstState,
XXH_PUBLIC_API void XXH64_copyState(XXH64_state_t *dstState,
const XXH64_state_t *srcState) {
memcpy(dstState, srcState, sizeof(*dstState));
@ -2890,7 +2890,7 @@ XXH_PUBLIC_API XXH_errorcode XXH64_update(XXH64_state_t *state,
{
const xxh_u8 * p = (const xxh_u8 *)input;
const xxh_u8 *p = (const xxh_u8 *)input;
const xxh_u8 *const bEnd = p + len;
state->total_len += len;
@ -4268,7 +4268,7 @@ XXH_FORCE_INLINE XXH_TARGET_AVX512 void XXH3_initCustomSecret_avx512(
union {
const __m512i *cp;
void * p;
void *p;
} remote_const_void;
@ -4385,7 +4385,7 @@ XXH_FORCE_INLINE XXH_TARGET_AVX2 void XXH3_initCustomSecret_avx2(
(xxh_i64)(0U - seed64), (xxh_i64)seed64);
const __m256i *const src = (const __m256i *)((const void *)XXH3_kSecret);
__m256i * dest = (__m256i *)customSecret;
__m256i *dest = (__m256i *)customSecret;
#if defined(__GNUC__) || defined(__clang__)
/*
@ -4519,7 +4519,7 @@ XXH_FORCE_INLINE XXH_TARGET_SSE2 void XXH3_initCustomSecret_sse2(
int i;
const void *const src16 = XXH3_kSecret;
__m128i * dst16 = (__m128i *)customSecret;
__m128i *dst16 = (__m128i *)customSecret;
#if defined(__GNUC__) || defined(__clang__)
/*
* On GCC & Clang, marking 'dest' as modified will cause the compiler:
@ -4594,7 +4594,7 @@ XXH_FORCE_INLINE void XXH3_scrambleAcc_neon(void *XXH_RESTRICT acc,
{
uint64x2_t * xacc = (uint64x2_t *)acc;
uint64x2_t *xacc = (uint64x2_t *)acc;
uint8_t const *xsecret = (uint8_t const *)secret;
uint32x2_t prime = vdup_n_u32(XXH_PRIME32_1);
@ -5106,7 +5106,7 @@ XXH_FORCE_INLINE XXH64_hash_t XXH3_hashLong_64b_withSeed_internal(
/*
* It's important for performance that XXH3_hashLong is not inlined.
*/
XXH_NO_INLINE XXH64_hash_t XXH3_hashLong_64b_withSeed(const void * input,
XXH_NO_INLINE XXH64_hash_t XXH3_hashLong_64b_withSeed(const void *input,
size_t len,
XXH64_hash_t seed,
const xxh_u8 *secret,
@ -5277,7 +5277,7 @@ XXH_PUBLIC_API XXH_errorcode XXH3_freeState(XXH3_state_t *statePtr) {
}
/*! @ingroup xxh3_family */
XXH_PUBLIC_API void XXH3_copyState(XXH3_state_t * dst_state,
XXH_PUBLIC_API void XXH3_copyState(XXH3_state_t *dst_state,
const XXH3_state_t *src_state) {
memcpy(dst_state, src_state, sizeof(*dst_state));
@ -5482,8 +5482,8 @@ XXH_PUBLIC_API XXH_errorcode XXH3_64bits_update(XXH3_state_t *state,
}
XXH_FORCE_INLINE void XXH3_digest_long(XXH64_hash_t * acc,
const XXH3_state_t * state,
XXH_FORCE_INLINE void XXH3_digest_long(XXH64_hash_t *acc,
const XXH3_state_t *state,
const unsigned char *secret) {
/*
@ -5545,7 +5545,7 @@ XXH_PUBLIC_API XXH64_hash_t XXH3_64bits_digest(const XXH3_state_t *state) {
#define XXH_MIN(x, y) (((x) > (y)) ? (y) : (x))
/*! @ingroup xxh3_family */
XXH_PUBLIC_API void XXH3_generateSecret(void * secretBuffer,
XXH_PUBLIC_API void XXH3_generateSecret(void *secretBuffer,
const void *customSeed,
size_t customSeedSize) {
@ -6081,7 +6081,7 @@ XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_withSecret(const void *input,
}
/*! @ingroup xxh3_family */
XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_withSeed(const void * input,
XXH_PUBLIC_API XXH128_hash_t XXH3_128bits_withSeed(const void *input,
size_t len,
XXH64_hash_t seed) {
@ -6142,7 +6142,7 @@ XXH_PUBLIC_API XXH_errorcode XXH3_128bits_reset_withSeed(XXH3_state_t *statePtr,
/*! @ingroup xxh3_family */
XXH_PUBLIC_API XXH_errorcode XXH3_128bits_update(XXH3_state_t *state,
const void * input,
const void *input,
size_t len) {
return XXH3_update(state, (const xxh_u8 *)input, len, XXH3_accumulate_512,

View File

@ -99,4 +99,11 @@ See
## 6) Bonus feature #3: selective instrumentation
It can be more effective to fuzzing to only instrument parts of the code. For
details, see [README.instrument_list.md](README.instrument_list.md).
details, see [README.instrument_list.md](README.instrument_list.md).
## 7) Bonus feature #4: CMPLOG
The gcc_plugin also support CMPLOG/Redqueen, just set `AFL_GCC_CMPLOG` before
instrumenting the target.
Read more about this in the llvm document.

View File

@ -182,7 +182,7 @@ class ModuleSanitizerCoverageLTO
private:
void instrumentFunction(Function &F, DomTreeCallback DTCallback,
PostDomTreeCallback PDTCallback);
void InjectCoverageForIndirectCalls(Function & F,
void InjectCoverageForIndirectCalls(Function &F,
ArrayRef<Instruction *> IndirCalls);
bool InjectCoverage(Function &F, ArrayRef<BasicBlock *> AllBlocks,
bool IsLeafFunc = true);
@ -211,10 +211,10 @@ class ModuleSanitizerCoverageLTO
FunctionCallee SanCovTracePC /*, SanCovTracePCGuard*/;
Type *IntptrTy, *IntptrPtrTy, *Int64Ty, *Int64PtrTy, *Int32Ty, *Int32PtrTy,
*Int16Ty, *Int8Ty, *Int8PtrTy, *Int1Ty, *Int1PtrTy;
Module * CurModule;
Module *CurModule;
std::string CurModuleUniqueId;
Triple TargetTriple;
LLVMContext * C;
LLVMContext *C;
const DataLayout *DL;
GlobalVariable *FunctionGuardArray; // for trace-pc-guard.
@ -235,20 +235,20 @@ class ModuleSanitizerCoverageLTO
uint32_t unhandled = 0;
uint32_t select_cnt = 0;
uint64_t map_addr = 0;
const char * skip_nozero = NULL;
const char * use_threadsafe_counters = nullptr;
const char *skip_nozero = NULL;
const char *use_threadsafe_counters = nullptr;
std::vector<BasicBlock *> BlockList;
DenseMap<Value *, std::string *> valueMap;
std::vector<std::string> dictionary;
IntegerType * Int8Tyi = NULL;
IntegerType * Int32Tyi = NULL;
IntegerType * Int64Tyi = NULL;
ConstantInt * Zero = NULL;
ConstantInt * One = NULL;
LLVMContext * Ct = NULL;
Module * Mo = NULL;
GlobalVariable * AFLMapPtr = NULL;
Value * MapPtrFixed = NULL;
IntegerType *Int8Tyi = NULL;
IntegerType *Int32Tyi = NULL;
IntegerType *Int64Tyi = NULL;
ConstantInt *Zero = NULL;
ConstantInt *One = NULL;
LLVMContext *Ct = NULL;
Module *Mo = NULL;
GlobalVariable *AFLMapPtr = NULL;
Value *MapPtrFixed = NULL;
std::ofstream dFile;
size_t found = 0;
// afl++ END
@ -330,12 +330,12 @@ llvmGetPassPluginInfo() {
}
PreservedAnalyses ModuleSanitizerCoverageLTO::run(Module & M,
PreservedAnalyses ModuleSanitizerCoverageLTO::run(Module &M,
ModuleAnalysisManager &MAM) {
ModuleSanitizerCoverageLTO ModuleSancov(Options);
auto &FAM = MAM.getResult<FunctionAnalysisManagerModuleProxy>(M).getManager();
auto DTCallback = [&FAM](Function &F) -> const DominatorTree * {
auto DTCallback = [&FAM](Function &F) -> const DominatorTree *{
return &FAM.getResult<DominatorTreeAnalysis>(F);
@ -380,7 +380,7 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
FunctionPCsArray = nullptr;
IntptrTy = Type::getIntNTy(*C, DL->getPointerSizeInBits());
IntptrPtrTy = PointerType::getUnqual(IntptrTy);
Type * VoidTy = Type::getVoidTy(*C);
Type *VoidTy = Type::getVoidTy(*C);
IRBuilder<> IRB(*C);
Int64PtrTy = PointerType::getUnqual(IRB.getInt64Ty());
Int32PtrTy = PointerType::getUnqual(IRB.getInt32Ty());
@ -393,7 +393,7 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
Int1Ty = IRB.getInt1Ty();
/* afl++ START */
char * ptr;
char *ptr;
LLVMContext &Ctx = M.getContext();
Ct = &Ctx;
Int8Tyi = IntegerType::getInt8Ty(Ctx);
@ -499,11 +499,11 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
for (auto &IN : BB) {
CallInst *callInst = nullptr;
CmpInst * cmpInst = nullptr;
CmpInst *cmpInst = nullptr;
if ((cmpInst = dyn_cast<CmpInst>(&IN))) {
Value * op = cmpInst->getOperand(1);
Value *op = cmpInst->getOperand(1);
ConstantInt *ilen = dyn_cast<ConstantInt>(op);
if (ilen && ilen->uge(0xffffffffffffffff) == false) {
@ -759,7 +759,7 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
if (HasStr2 == true) {
Value * op2 = callInst->getArgOperand(2);
Value *op2 = callInst->getArgOperand(2);
ConstantInt *ilen = dyn_cast<ConstantInt>(op2);
if (ilen) {
@ -866,7 +866,7 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
if (isMemcmp || isStrncmp || isStrncasecmp) {
Value * op2 = callInst->getArgOperand(2);
Value *op2 = callInst->getArgOperand(2);
ConstantInt *ilen = dyn_cast<ConstantInt>(op2);
if (ilen) {
@ -921,7 +921,7 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
std::string outstring;
fprintf(stderr, "%s: length %zu/%zu \"", FuncName.c_str(), optLen,
thestring.length());
for (uint8_t i = 0; i < thestring.length(); i++) {
for (uint16_t i = 0; i < (uint16_t)thestring.length(); i++) {
uint8_t c = thestring[i];
if (c <= 32 || c >= 127)
@ -1017,7 +1017,7 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
GlobalVariable *AFLMapAddrFixed = new GlobalVariable(
M, Int64Tyi, true, GlobalValue::ExternalLinkage, 0, "__afl_map_addr");
ConstantInt *MapAddr = ConstantInt::get(Int64Tyi, map_addr);
StoreInst * StoreMapAddr = IRB.CreateStore(MapAddr, AFLMapAddrFixed);
StoreInst *StoreMapAddr = IRB.CreateStore(MapAddr, AFLMapAddrFixed);
ModuleSanitizerCoverageLTO::SetNoSanitizeMetadata(StoreMapAddr);
}
@ -1032,7 +1032,7 @@ bool ModuleSanitizerCoverageLTO::instrumentModule(
new GlobalVariable(M, Int32Tyi, true, GlobalValue::ExternalLinkage, 0,
"__afl_final_loc");
ConstantInt *const_loc = ConstantInt::get(Int32Tyi, write_loc);
StoreInst * StoreFinalLoc = IRB.CreateStore(const_loc, AFLFinalLoc);
StoreInst *StoreFinalLoc = IRB.CreateStore(const_loc, AFLFinalLoc);
ModuleSanitizerCoverageLTO::SetNoSanitizeMetadata(StoreFinalLoc);
}
@ -1159,7 +1159,7 @@ static bool isFullDominator(const BasicBlock *BB, const DominatorTree *DT) {
}
// True if block has predecessors and it postdominates all of them.
static bool isFullPostDominator(const BasicBlock * BB,
static bool isFullPostDominator(const BasicBlock *BB,
const PostDominatorTree *PDT) {
if (pred_begin(BB) == pred_end(BB)) return false;
@ -1175,8 +1175,8 @@ static bool isFullPostDominator(const BasicBlock * BB,
}
static bool shouldInstrumentBlock(const Function &F, const BasicBlock *BB,
const DominatorTree * DT,
const PostDominatorTree * PDT,
const DominatorTree *DT,
const PostDominatorTree *PDT,
const SanitizerCoverageOptions &Options) {
// Don't insert coverage for blocks containing nothing but unreachable: we
@ -1246,7 +1246,7 @@ void ModuleSanitizerCoverageLTO::instrumentFunction(
SmallVector<Instruction *, 8> IndirCalls;
SmallVector<BasicBlock *, 16> BlocksToInstrument;
const DominatorTree * DT = DTCallback(F);
const DominatorTree *DT = DTCallback(F);
const PostDominatorTree *PDT = PDTCallback(F);
bool IsLeafFunc = true;
uint32_t skip_next = 0;
@ -1294,8 +1294,8 @@ void ModuleSanitizerCoverageLTO::instrumentFunction(
if (!skip_next && (selectInst = dyn_cast<SelectInst>(&IN))) {
uint32_t vector_cnt = 0;
Value * condition = selectInst->getCondition();
Value * result;
Value *condition = selectInst->getCondition();
Value *result;
auto t = condition->getType();
IRBuilder<> IRB(selectInst->getNextNode());
@ -1451,8 +1451,8 @@ GlobalVariable *ModuleSanitizerCoverageLTO::CreateFunctionLocalArrayInSection(
ArrayType *ArrayTy = ArrayType::get(Ty, NumElements);
auto Array = new GlobalVariable(
*CurModule, ArrayTy, false, GlobalVariable::PrivateLinkage,
Constant::getNullValue(ArrayTy), "__sancov_gen_");
*CurModule, ArrayTy, false, GlobalVariable::PrivateLinkage,
Constant::getNullValue(ArrayTy), "__sancov_gen_");
#if LLVM_VERSION_MAJOR >= 13
if (TargetTriple.supportsCOMDAT() &&
@ -1584,8 +1584,8 @@ void ModuleSanitizerCoverageLTO::InjectCoverageForIndirectCalls(
for (auto I : IndirCalls) {
IRBuilder<> IRB(I);
CallBase & CB = cast<CallBase>(*I);
Value * Callee = CB.getCalledOperand();
CallBase &CB = cast<CallBase>(*I);
Value *Callee = CB.getCalledOperand();
if (isa<InlineAsm>(Callee)) continue;
IRB.CreateCall(SanCovTracePCIndir, IRB.CreatePointerCast(Callee, IntptrTy));
@ -1593,7 +1593,7 @@ void ModuleSanitizerCoverageLTO::InjectCoverageForIndirectCalls(
}
void ModuleSanitizerCoverageLTO::InjectCoverageAtBlock(Function & F,
void ModuleSanitizerCoverageLTO::InjectCoverageAtBlock(Function &F,
BasicBlock &BB,
size_t Idx,
bool IsLeafFunc) {

View File

@ -142,14 +142,14 @@ class ModuleSanitizerCoverageAFL
private:
void instrumentFunction(Function &F, DomTreeCallback DTCallback,
PostDomTreeCallback PDTCallback);
void InjectCoverageForIndirectCalls(Function & F,
void InjectCoverageForIndirectCalls(Function &F,
ArrayRef<Instruction *> IndirCalls);
void InjectTraceForCmp(Function &F, ArrayRef<Instruction *> CmpTraceTargets);
void InjectTraceForDiv(Function & F,
void InjectTraceForDiv(Function &F,
ArrayRef<BinaryOperator *> DivTraceTargets);
void InjectTraceForGep(Function & F,
void InjectTraceForGep(Function &F,
ArrayRef<GetElementPtrInst *> GepTraceTargets);
void InjectTraceForSwitch(Function & F,
void InjectTraceForSwitch(Function &F,
ArrayRef<Instruction *> SwitchTraceTargets);
bool InjectCoverage(Function &F, ArrayRef<BasicBlock *> AllBlocks,
bool IsLeafFunc = true);
@ -187,10 +187,10 @@ class ModuleSanitizerCoverageAFL
GlobalVariable *SanCovLowestStack;
Type *IntptrTy, *IntptrPtrTy, *Int64Ty, *Int64PtrTy, *Int32Ty, *Int32PtrTy,
*Int16Ty, *Int8Ty, *Int8PtrTy, *Int1Ty, *Int1PtrTy;
Module * CurModule;
Module *CurModule;
std::string CurModuleUniqueId;
Triple TargetTriple;
LLVMContext * C;
LLVMContext *C;
const DataLayout *DL;
GlobalVariable *FunctionGuardArray; // for trace-pc-guard.
@ -204,8 +204,8 @@ class ModuleSanitizerCoverageAFL
uint32_t instr = 0, selects = 0, unhandled = 0;
GlobalVariable *AFLMapPtr = NULL;
ConstantInt * One = NULL;
ConstantInt * Zero = NULL;
ConstantInt *One = NULL;
ConstantInt *Zero = NULL;
};
@ -287,12 +287,12 @@ llvmGetPassPluginInfo() {
#endif
PreservedAnalyses ModuleSanitizerCoverageAFL::run(Module & M,
PreservedAnalyses ModuleSanitizerCoverageAFL::run(Module &M,
ModuleAnalysisManager &MAM) {
ModuleSanitizerCoverageAFL ModuleSancov(Options);
auto &FAM = MAM.getResult<FunctionAnalysisManagerModuleProxy>(M).getManager();
auto DTCallback = [&FAM](Function &F) -> const DominatorTree * {
auto DTCallback = [&FAM](Function &F) -> const DominatorTree *{
return &FAM.getResult<DominatorTreeAnalysis>(F);
@ -433,7 +433,7 @@ bool ModuleSanitizerCoverageAFL::instrumentModule(
FunctionPCsArray = nullptr;
IntptrTy = Type::getIntNTy(*C, DL->getPointerSizeInBits());
IntptrPtrTy = PointerType::getUnqual(IntptrTy);
Type * VoidTy = Type::getVoidTy(*C);
Type *VoidTy = Type::getVoidTy(*C);
IRBuilder<> IRB(*C);
Int64PtrTy = PointerType::getUnqual(IRB.getInt64Ty());
Int32PtrTy = PointerType::getUnqual(IRB.getInt32Ty());
@ -612,8 +612,8 @@ bool isFullPostDominator(const BasicBlock *BB, const PostDominatorTree *PDT) {
}
bool shouldInstrumentBlock(const Function &F, const BasicBlock *BB,
const DominatorTree * DT,
const PostDominatorTree * PDT,
const DominatorTree *DT,
const PostDominatorTree *PDT,
const SanitizerCoverageOptions &Options) {
// Don't insert coverage for blocks containing nothing but unreachable: we
@ -704,7 +704,7 @@ void ModuleSanitizerCoverageAFL::instrumentFunction(
SmallVector<BinaryOperator *, 8> DivTraceTargets;
SmallVector<GetElementPtrInst *, 8> GepTraceTargets;
const DominatorTree * DT = DTCallback(F);
const DominatorTree *DT = DTCallback(F);
const PostDominatorTree *PDT = PDTCallback(F);
bool IsLeafFunc = true;
@ -761,8 +761,8 @@ GlobalVariable *ModuleSanitizerCoverageAFL::CreateFunctionLocalArrayInSection(
ArrayType *ArrayTy = ArrayType::get(Ty, NumElements);
auto Array = new GlobalVariable(
*CurModule, ArrayTy, false, GlobalVariable::PrivateLinkage,
Constant::getNullValue(ArrayTy), "__sancov_gen_");
*CurModule, ArrayTy, false, GlobalVariable::PrivateLinkage,
Constant::getNullValue(ArrayTy), "__sancov_gen_");
#if LLVM_VERSION_MAJOR >= 13
if (TargetTriple.supportsCOMDAT() &&
@ -971,8 +971,8 @@ bool ModuleSanitizerCoverageAFL::InjectCoverage(
if (!skip_next && (selectInst = dyn_cast<SelectInst>(&IN))) {
uint32_t vector_cnt = 0;
Value * condition = selectInst->getCondition();
Value * result;
Value *condition = selectInst->getCondition();
Value *result;
auto t = condition->getType();
IRBuilder<> IRB(selectInst->getNextNode());
@ -1113,7 +1113,7 @@ bool ModuleSanitizerCoverageAFL::InjectCoverage(
/* Get CurLoc */
LoadInst *CurLoc = nullptr;
Value * MapPtrIdx = nullptr;
Value *MapPtrIdx = nullptr;
/* Load counter for CurLoc */
if (!vector_cnt) {
@ -1212,8 +1212,8 @@ void ModuleSanitizerCoverageAFL::InjectCoverageForIndirectCalls(
for (auto I : IndirCalls) {
IRBuilder<> IRB(I);
CallBase & CB = cast<CallBase>(*I);
Value * Callee = CB.getCalledOperand();
CallBase &CB = cast<CallBase>(*I);
Value *Callee = CB.getCalledOperand();
if (isa<InlineAsm>(Callee)) continue;
IRB.CreateCall(SanCovTracePCIndir, IRB.CreatePointerCast(Callee, IntptrTy));
@ -1234,7 +1234,7 @@ void ModuleSanitizerCoverageAFL::InjectTraceForSwitch(
IRBuilder<> IRB(I);
SmallVector<Constant *, 16> Initializers;
Value * Cond = SI->getCondition();
Value *Cond = SI->getCondition();
if (Cond->getType()->getScalarSizeInBits() >
Int64Ty->getScalarSizeInBits())
continue;
@ -1282,7 +1282,7 @@ void ModuleSanitizerCoverageAFL::InjectTraceForDiv(
for (auto BO : DivTraceTargets) {
IRBuilder<> IRB(BO);
Value * A1 = BO->getOperand(1);
Value *A1 = BO->getOperand(1);
if (isa<ConstantInt>(A1)) continue;
if (!A1->getType()->isIntegerTy()) continue;
uint64_t TypeSize = DL->getTypeStoreSizeInBits(A1->getType());
@ -1319,8 +1319,8 @@ void ModuleSanitizerCoverageAFL::InjectTraceForCmp(
if (ICmpInst *ICMP = dyn_cast<ICmpInst>(I)) {
IRBuilder<> IRB(ICMP);
Value * A0 = ICMP->getOperand(0);
Value * A1 = ICMP->getOperand(1);
Value *A0 = ICMP->getOperand(0);
Value *A1 = ICMP->getOperand(1);
if (!A0->getType()->isIntegerTy()) continue;
uint64_t TypeSize = DL->getTypeStoreSizeInBits(A0->getType());
int CallbackIdx = TypeSize == 8 ? 0
@ -1353,7 +1353,7 @@ void ModuleSanitizerCoverageAFL::InjectTraceForCmp(
}
void ModuleSanitizerCoverageAFL::InjectCoverageAtBlock(Function & F,
void ModuleSanitizerCoverageAFL::InjectCoverageAtBlock(Function &F,
BasicBlock &BB,
size_t Idx,
bool IsLeafFunc) {
@ -1472,7 +1472,7 @@ void ModuleSanitizerCoverageAFL::InjectCoverageAtBlock(Function & F,
if (Options.StackDepth && IsEntryBB && !IsLeafFunc) {
// Check stack depth. If it's the deepest so far, record it.
Module * M = F.getParent();
Module *M = F.getParent();
Function *GetFrameAddr = Intrinsic::getDeclaration(
M, Intrinsic::frameaddress,
IRB.getInt8PtrTy(M->getDataLayout().getAllocaAddrSpace()));

View File

@ -92,11 +92,11 @@ static u8 __afl_area_initial[MAP_INITIAL_SIZE];
static u8 *__afl_area_ptr_dummy = __afl_area_initial;
static u8 *__afl_area_ptr_backup = __afl_area_initial;
u8 * __afl_area_ptr = __afl_area_initial;
u8 * __afl_dictionary;
u8 * __afl_fuzz_ptr;
u8 *__afl_area_ptr = __afl_area_initial;
u8 *__afl_dictionary;
u8 *__afl_fuzz_ptr;
static u32 __afl_fuzz_len_dummy;
u32 * __afl_fuzz_len = &__afl_fuzz_len_dummy;
u32 *__afl_fuzz_len = &__afl_fuzz_len_dummy;
u32 __afl_final_loc;
u32 __afl_map_size = MAP_SIZE;
@ -399,7 +399,7 @@ static void __afl_map_shm(void) {
}
#ifdef USEMMAP
const char * shm_file_path = id_str;
const char *shm_file_path = id_str;
int shm_fd = -1;
unsigned char *shm_base = NULL;
@ -450,11 +450,11 @@ static void __afl_map_shm(void) {
if (__afl_map_size && __afl_map_size > MAP_SIZE) {
u8 *map_env = (u8 *)getenv("AFL_MAP_SIZE");
if (!map_env || atoi((char *)map_env) < MAP_SIZE) {
u8 *map_env = (u8 *)getenv("AFL_MAP_SIZE");
if (!map_env || atoi((char *)map_env) < MAP_SIZE) {
send_forkserver_error(FS_ERROR_MAP_SIZE);
_exit(1);
send_forkserver_error(FS_ERROR_MAP_SIZE);
_exit(1);
}
@ -466,13 +466,13 @@ static void __afl_map_shm(void) {
if (!__afl_area_ptr || __afl_area_ptr == (void *)-1) {
if (__afl_map_addr)
if (__afl_map_addr)
send_forkserver_error(FS_ERROR_MAP_ADDR);
else
send_forkserver_error(FS_ERROR_SHMAT);
perror("shmat for map");
_exit(1);
_exit(1);
}
@ -583,7 +583,7 @@ static void __afl_map_shm(void) {
}
#ifdef USEMMAP
const char * shm_file_path = id_str;
const char *shm_file_path = id_str;
int shm_fd = -1;
struct cmp_map *shm_base = NULL;
@ -689,7 +689,7 @@ static void __afl_unmap_shm(void) {
void write_error_with_location(char *text, char *filename, int linenumber) {
u8 * o = getenv("__AFL_OUT_DIR");
u8 *o = getenv("__AFL_OUT_DIR");
char *e = strerror(errno);
if (o) {

View File

@ -0,0 +1,404 @@
/* GCC plugin for cmplog instrumentation of code for AFL++.
Copyright 2014-2019 Free Software Foundation, Inc
Copyright 2015, 2016 Google Inc. All rights reserved.
Copyright 2019-2020 AFLplusplus Project. All rights reserved.
Copyright 2019-2022 AdaCore
Written by Alexandre Oliva <oliva@adacore.com>, based on the AFL++
LLVM CmpLog pass by Andrea Fioraldi <andreafioraldi@gmail.com>, and
on the AFL GCC pass.
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "afl-gcc-common.h"
/* This plugin, being under the same license as GCC, satisfies the
"GPL-compatible Software" definition in the GCC RUNTIME LIBRARY
EXCEPTION, so it can be part of an "Eligible" "Compilation
Process". */
int plugin_is_GPL_compatible = 1;
namespace {
static const struct pass_data afl_cmplog_pass_data = {
.type = GIMPLE_PASS,
.name = "aflcmplog",
.optinfo_flags = OPTGROUP_NONE,
.tv_id = TV_NONE,
.properties_required = 0,
.properties_provided = 0,
.properties_destroyed = 0,
.todo_flags_start = 0,
.todo_flags_finish = (TODO_update_ssa | TODO_cleanup_cfg | TODO_verify_il |
TODO_rebuild_cgraph_edges),
};
struct afl_cmplog_pass : afl_base_pass {
afl_cmplog_pass(bool quiet)
: afl_base_pass(quiet, /*debug=*/false, afl_cmplog_pass_data),
t8u(),
cmplog_hooks() {
}
/* An unsigned 8-bit integral type. */
tree t8u;
/* Declarations for the various cmplog hook functions, allocated on demand..
[0] is for __cmplog_ins_hookN, that accepts non-power-of-2 sizes.
[n in 1..5] are for unsigned ints of 2^{n-1} bytes. */
tree cmplog_hooks[6];
tree cmplog_hook(unsigned i) {
tree t, fnt;
if (!t8u) {
if (BITS_PER_UNIT == 8)
t8u = unsigned_char_type_node;
else
t8u = build_nonstandard_integer_type(8, 1);
}
if (i <= ARRAY_SIZE(cmplog_hooks) && cmplog_hooks[i])
return cmplog_hooks[i];
switch (i) {
case 0:
#ifdef uint128_type_node
t = uint128_type_node;
#else
t = build_nonstandard_integer_type(128, 1);
#endif
fnt =
build_function_type_list(void_type_node, t, t, t8u, t8u, NULL_TREE);
t = cmplog_hooks[0] = build_fn_decl("__cmplog_ins_hookN", fnt);
break;
case 1:
t = t8u;
fnt = build_function_type_list(void_type_node, t, t, t8u, NULL_TREE);
t = cmplog_hooks[1] = build_fn_decl("__cmplog_ins_hook1", fnt);
break;
case 2:
t = uint16_type_node;
fnt = build_function_type_list(void_type_node, t, t, t8u, NULL_TREE);
t = cmplog_hooks[2] = build_fn_decl("__cmplog_ins_hook2", fnt);
break;
case 3:
t = uint32_type_node;
fnt = build_function_type_list(void_type_node, t, t, t8u, NULL_TREE);
t = cmplog_hooks[3] = build_fn_decl("__cmplog_ins_hook4", fnt);
break;
case 4:
t = uint64_type_node;
fnt = build_function_type_list(void_type_node, t, t, t8u, NULL_TREE);
t = cmplog_hooks[4] = build_fn_decl("__cmplog_ins_hook8", fnt);
break;
case 5:
#ifdef uint128_type_node
t = uint128_type_node;
#else
t = build_nonstandard_integer_type(128, 1);
#endif
fnt = build_function_type_list(void_type_node, t, t, t8u, NULL_TREE);
t = cmplog_hooks[5] = build_fn_decl("__cmplog_ins_hook16", fnt);
break;
default:
gcc_unreachable();
}
/* Mark the newly-created decl as non-throwing, so that we can
insert call within basic blocks. */
TREE_NOTHROW(t) = 1;
return t;
}
/* Insert a cmplog hook call before GSI for a CODE compare between
LHS and RHS. */
void insert_cmplog_call(gimple_stmt_iterator gsi, tree_code code, tree lhs,
tree rhs) {
gcc_checking_assert(TYPE_MAIN_VARIANT(TREE_TYPE(lhs)) ==
TYPE_MAIN_VARIANT(TREE_TYPE(rhs)));
tree fn;
bool pass_n = false;
/* Obtain the compare operand size as a constant. */
tree st = TREE_TYPE(lhs);
tree szt = TYPE_SIZE(st);
if (!tree_fits_uhwi_p(szt)) return;
unsigned HOST_WIDE_INT sz = tree_to_uhwi(szt);
/* Round it up. */
if (sz % 8) sz = (((sz - 1) / 8) + 1) * 8;
/* Select the hook function to call, based on the size. */
switch (sz) {
default:
fn = cmplog_hook(0);
pass_n = true;
break;
case 8:
fn = cmplog_hook(1);
break;
case 16:
fn = cmplog_hook(2);
break;
case 32:
fn = cmplog_hook(3);
break;
case 64:
fn = cmplog_hook(4);
break;
case 128:
fn = cmplog_hook(5);
break;
}
/* Set attr according to the compare operation. */
unsigned char attr = 0;
switch (code) {
case UNORDERED_EXPR:
case ORDERED_EXPR:
/* ??? */
/* Fallthrough. */
case NE_EXPR:
case LTGT_EXPR:
break;
case EQ_EXPR:
case UNEQ_EXPR:
attr += 1;
break;
case GT_EXPR:
case UNGT_EXPR:
attr += 2;
break;
case GE_EXPR:
case UNGE_EXPR:
attr += 3;
break;
case LT_EXPR:
case UNLT_EXPR:
attr += 4;
break;
case LE_EXPR:
case UNLE_EXPR:
attr += 5;
break;
default:
gcc_unreachable();
}
if (FLOAT_TYPE_P(TREE_TYPE(lhs))) {
attr += 8;
tree t = build_nonstandard_integer_type(sz, 1);
tree s = make_ssa_name(t);
gimple *g = gimple_build_assign(s, VIEW_CONVERT_EXPR,
build1(VIEW_CONVERT_EXPR, t, lhs));
lhs = s;
gsi_insert_before(&gsi, g, GSI_SAME_STMT);
s = make_ssa_name(t);
g = gimple_build_assign(s, VIEW_CONVERT_EXPR,
build1(VIEW_CONVERT_EXPR, t, rhs));
rhs = s;
gsi_insert_before(&gsi, g, GSI_SAME_STMT);
}
/* Convert the operands to the hook arg type, if needed. */
tree t = TREE_VALUE(TYPE_ARG_TYPES(TREE_TYPE(fn)));
lhs = fold_convert_loc(UNKNOWN_LOCATION, t, lhs);
if (!is_gimple_val(lhs)) {
tree s = make_ssa_name(t);
gimple *g = gimple_build_assign(s, lhs);
lhs = s;
gsi_insert_before(&gsi, g, GSI_SAME_STMT);
}
rhs = fold_convert_loc(UNKNOWN_LOCATION, t, rhs);
if (!is_gimple_val(rhs)) {
tree s = make_ssa_name(t);
gimple *g = gimple_build_assign(s, rhs);
rhs = s;
gsi_insert_before(&gsi, g, GSI_SAME_STMT);
}
/* Insert the call. */
tree att = build_int_cst(t8u, attr);
gimple *call;
if (pass_n)
call = gimple_build_call(fn, 4, lhs, rhs, att,
build_int_cst(t8u, sz / 8 - 1));
else
call = gimple_build_call(fn, 3, lhs, rhs, att);
gsi_insert_before(&gsi, call, GSI_SAME_STMT);
}
virtual unsigned int execute(function *fn) {
if (!isInInstrumentList(fn)) return 0;
basic_block bb;
FOR_EACH_BB_FN(bb, fn) {
/* A GIMPLE_COND or GIMPLE_SWITCH will always be the last stmt
in a BB. */
gimple_stmt_iterator gsi = gsi_last_bb(bb);
if (gsi_end_p(gsi)) continue;
gimple *stmt = gsi_stmt(gsi);
if (gimple_code(stmt) == GIMPLE_COND) {
tree_code code = gimple_cond_code(stmt);
tree lhs = gimple_cond_lhs(stmt);
tree rhs = gimple_cond_rhs(stmt);
insert_cmplog_call(gsi, code, lhs, rhs);
} else if (gimple_code(stmt) == GIMPLE_SWITCH) {
gswitch *sw = as_a<gswitch *>(stmt);
tree lhs = gimple_switch_index(sw);
for (int i = 0, e = gimple_switch_num_labels(sw); i < e; i++) {
tree clx = gimple_switch_label(sw, i);
tree rhsl = CASE_LOW(clx);
/* Default case labels exprs don't have a CASE_LOW. */
if (!rhsl) continue;
tree rhsh = CASE_HIGH(clx);
/* If there is a CASE_HIGH, issue range compares. */
if (rhsh) {
insert_cmplog_call(gsi, GE_EXPR, lhs, rhsl);
insert_cmplog_call(gsi, LE_EXPR, lhs, rhsh);
}
/* Otherwise, use a single equality compare. */
else
insert_cmplog_call(gsi, EQ_EXPR, lhs, rhsl);
}
} else
continue;
}
return 0;
}
};
static struct plugin_info afl_cmplog_plugin = {
.version = "20220420",
.help = G_("AFL gcc cmplog plugin\n\
\n\
Set AFL_QUIET in the environment to silence it.\n\
"),
};
} // namespace
/* This is the function GCC calls when loading a plugin. Initialize
and register further callbacks. */
int plugin_init(struct plugin_name_args *info,
struct plugin_gcc_version *version) {
if (!plugin_default_version_check(version, &gcc_version))
FATAL(G_("GCC and plugin have incompatible versions, expected GCC %s, "
"is %s"),
gcc_version.basever, version->basever);
/* Show a banner. */
bool quiet = false;
if (isatty(2) && !getenv("AFL_QUIET"))
SAYF(cCYA "afl-gcc-cmplog-pass " cBRI VERSION cRST
" by <oliva@adacore.com>\n");
else
quiet = true;
const char *name = info->base_name;
register_callback(name, PLUGIN_INFO, NULL, &afl_cmplog_plugin);
afl_cmplog_pass *aflp = new afl_cmplog_pass(quiet);
struct register_pass_info pass_info = {
.pass = aflp,
.reference_pass_name = "ssa",
.ref_pass_instance_number = 1,
.pos_op = PASS_POS_INSERT_AFTER,
};
register_callback(name, PLUGIN_PASS_MANAGER_SETUP, NULL, &pass_info);
return 0;
}

View File

@ -0,0 +1,366 @@
/* GCC plugin for cmplog routines instrumentation of code for AFL++.
Copyright 2014-2019 Free Software Foundation, Inc
Copyright 2015, 2016 Google Inc. All rights reserved.
Copyright 2019-2020 AFLplusplus Project. All rights reserved.
Copyright 2019-2022 AdaCore
Written by Alexandre Oliva <oliva@adacore.com>, based on the AFL++
LLVM CmpLog Routines pass by Andrea Fioraldi
<andreafioraldi@gmail.com>, and on the AFL GCC CmpLog pass.
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "afl-gcc-common.h"
/* This plugin, being under the same license as GCC, satisfies the
"GPL-compatible Software" definition in the GCC RUNTIME LIBRARY
EXCEPTION, so it can be part of an "Eligible" "Compilation
Process". */
int plugin_is_GPL_compatible = 1;
namespace {
static const struct pass_data afl_cmptrs_pass_data = {
.type = GIMPLE_PASS,
.name = "aflcmptrs",
.optinfo_flags = OPTGROUP_NONE,
.tv_id = TV_NONE,
.properties_required = 0,
.properties_provided = 0,
.properties_destroyed = 0,
.todo_flags_start = 0,
.todo_flags_finish = (TODO_update_ssa | TODO_cleanup_cfg | TODO_verify_il |
TODO_rebuild_cgraph_edges),
};
struct afl_cmptrs_pass : afl_base_pass {
afl_cmptrs_pass(bool quiet)
: afl_base_pass(quiet, /*debug=*/false, afl_cmptrs_pass_data),
tp8u(),
cmptrs_hooks() {
}
/* A pointer type to a unsigned 8-bit integral type. */
tree tp8u;
/* Declarations for the various cmptrs hook functions, allocated on
demand.. [0] is for compares between any pointers, [1] is for
compares between G++ std::string, [2] is for compares between G++
std::string and GCC C strings, [3] and [4] are analogous to [1]
and [2] but for LLVM C++ strings. */
tree cmptrs_hooks[5];
tree cmptrs_hook(unsigned i) {
if (!tp8u) {
tree t8u;
if (BITS_PER_UNIT == 8)
t8u = unsigned_char_type_node;
else
t8u = build_nonstandard_integer_type(8, 1);
tp8u = build_pointer_type(t8u);
}
if (i <= ARRAY_SIZE(cmptrs_hooks) && cmptrs_hooks[i])
return cmptrs_hooks[i];
const char *n = NULL;
switch (i) {
case 0:
n = "__cmplog_rtn_hook";
break;
case 1:
n = "__cmplog_rtn_gcc_stdstring_stdstring";
break;
case 2:
n = "__cmplog_rtn_gcc_stdstring_cstring";
break;
case 3:
n = "__cmplog_rtn_llvm_stdstring_stdstring";
break;
case 4:
n = "__cmplog_rtn_llvm_stdstring_cstring";
break;
default:
gcc_unreachable();
}
tree fnt = build_function_type_list(void_type_node, tp8u, tp8u, NULL_TREE);
tree t = cmptrs_hooks[i] = build_fn_decl(n, fnt);
/* Mark the newly-created decl as non-throwing, so that we can
insert call within basic blocks. */
TREE_NOTHROW(t) = 1;
return t;
}
/* Return true if T is the char* type. */
bool is_c_string(tree t) {
return (POINTER_TYPE_P(t) &&
TYPE_MAIN_VARIANT(TREE_TYPE(t)) == char_type_node);
}
/* Return true if T is an indirect std::string type. The LLVM pass
tests portions of the mangled name of the callee. We could do
that in GCC too, but computing the mangled name may cause
template instantiations and get symbols defined that could
otherwise be considered unused. We check for compatible layout,
and class, namespace, and field names. These have been unchanged
since at least GCC 7, probably longer, up to GCC 11. Odds are
that, if it were to change in significant ways, mangling would
also change to flag the incompatibility, and we'd have to use a
different hook anyway. */
bool is_gxx_std_string(tree t) {
/* We need a pointer or reference type. */
if (!POINTER_TYPE_P(t)) return false;
/* Get to the pointed-to type. */
t = TREE_TYPE(t);
if (!t) return false;
/* Select the main variant, so that can compare types with pointers. */
t = TYPE_MAIN_VARIANT(t);
/* We expect it to be a record type. */
if (TREE_CODE(t) != RECORD_TYPE) return false;
/* The type of the template is basic_string. */
if (strcmp(IDENTIFIER_POINTER(TYPE_IDENTIFIER(t)), "basic_string") != 0)
return false;
/* It's declared in an internal namespace named __cxx11. */
tree c = DECL_CONTEXT(TYPE_NAME(t));
if (!c || TREE_CODE(c) != NAMESPACE_DECL ||
strcmp(IDENTIFIER_POINTER(DECL_NAME(c)), "__cxx11") != 0)
return false;
/* The __cxx11 namespace is a member of namespace std. */
c = DECL_CONTEXT(c);
if (!c || TREE_CODE(c) != NAMESPACE_DECL ||
strcmp(IDENTIFIER_POINTER(DECL_NAME(c)), "std") != 0)
return false;
/* And the std namespace is in the global namespace. */
c = DECL_CONTEXT(c);
if (c && TREE_CODE(c) != TRANSLATION_UNIT_DECL) return false;
/* Check that the first nonstatic data member of the record type
is named _M_dataplus. */
for (c = TYPE_FIELDS(t); c; c = DECL_CHAIN(c))
if (TREE_CODE(c) == FIELD_DECL) break;
if (!c || !integer_zerop(DECL_FIELD_BIT_OFFSET(c)) ||
strcmp(IDENTIFIER_POINTER(DECL_NAME(c)), "_M_dataplus") != 0)
return false;
/* Check that the second nonstatic data member of the record type
is named _M_string_length. */
tree f2;
for (f2 = DECL_CHAIN(c); f2; f2 = DECL_CHAIN(f2))
if (TREE_CODE(f2) == FIELD_DECL) break;
if (!f2 /* No need to check this field's offset. */
|| strcmp(IDENTIFIER_POINTER(DECL_NAME(f2)), "_M_string_length") != 0)
return false;
/* The type of the second data member is size_t. */
if (!TREE_TYPE(f2) || TYPE_MAIN_VARIANT(TREE_TYPE(f2)) != size_type_node)
return false;
/* Now go back to the first data member. Its type should be a
record type named _Alloc_hider. */
c = TREE_TYPE(c);
if (!c || TREE_CODE(c) != RECORD_TYPE ||
strcmp(IDENTIFIER_POINTER(TYPE_IDENTIFIER(c)), "_Alloc_hider") != 0)
return false;
/* And its first data member is named _M_p. */
for (c = TYPE_FIELDS(c); c; c = DECL_CHAIN(c))
if (TREE_CODE(c) == FIELD_DECL) break;
if (!c || !integer_zerop(DECL_FIELD_BIT_OFFSET(c)) ||
strcmp(IDENTIFIER_POINTER(DECL_NAME(c)), "_M_p") != 0)
return false;
/* For the basic_string<char> type we're interested in, the type
of the data member is the C string type. */
if (!is_c_string(TREE_TYPE(c))) return false;
/* This might not be the real thing, but the bits that matter for
the hook are there. */
return true;
}
/* ??? This is not implemented. What would the point be of
recognizing LLVM's string type in GCC? */
bool is_llvm_std_string(tree t) {
return false;
}
virtual unsigned int execute(function *fn) {
if (!isInInstrumentList(fn)) return 0;
basic_block bb;
FOR_EACH_BB_FN(bb, fn) {
for (gimple_stmt_iterator gsi = gsi_after_labels(bb); !gsi_end_p(gsi);
gsi_next(&gsi)) {
gimple *stmt = gsi_stmt(gsi);
/* We're only interested in GIMPLE_CALLs. */
if (gimple_code(stmt) != GIMPLE_CALL) continue;
if (gimple_call_num_args(stmt) < 2) continue;
gcall *c = as_a<gcall *>(stmt);
tree callee_type = gimple_call_fntype(c);
if (!callee_type || !TYPE_ARG_TYPES(callee_type) ||
!TREE_CHAIN(TYPE_ARG_TYPES(callee_type)))
continue;
tree arg_type[2] = {
TYPE_MAIN_VARIANT(TREE_VALUE(TYPE_ARG_TYPES(callee_type))),
TYPE_MAIN_VARIANT(
TREE_VALUE(TREE_CHAIN(TYPE_ARG_TYPES(callee_type))))};
tree fn = NULL;
/* Callee arglist starts with two GCC std::string arguments. */
if (arg_type[0] == arg_type[1] && is_gxx_std_string(arg_type[0]))
fn = cmptrs_hook(1);
/* Callee arglist starts with GCC std::string and C string. */
else if (is_gxx_std_string(arg_type[0]) && is_c_string(arg_type[1]))
fn = cmptrs_hook(2);
/* Callee arglist starts with two LLVM std::string arguments. */
else if (arg_type[0] == arg_type[1] && is_llvm_std_string(arg_type[0]))
fn = cmptrs_hook(3);
/* Callee arglist starts with LLVM std::string and C string. */
else if (is_llvm_std_string(arg_type[0]) && is_c_string(arg_type[1]))
fn = cmptrs_hook(4);
/* Callee arglist starts with two pointers to the same type,
and callee returns a value. */
else if (arg_type[0] == arg_type[1] && POINTER_TYPE_P(arg_type[0]) &&
(TYPE_MAIN_VARIANT(gimple_call_return_type(c)) !=
void_type_node))
fn = cmptrs_hook(0);
else
continue;
tree arg[2] = {gimple_call_arg(c, 0), gimple_call_arg(c, 1)};
for (unsigned i = 0; i < ARRAY_SIZE(arg); i++) {
tree c = fold_convert_loc(UNKNOWN_LOCATION, tp8u, arg[i]);
if (!is_gimple_val(c)) {
tree s = make_ssa_name(tp8u);
gimple *g = gimple_build_assign(s, c);
c = s;
gsi_insert_before(&gsi, g, GSI_SAME_STMT);
}
arg[i] = c;
}
gimple *call = gimple_build_call(fn, 2, arg[0], arg[1]);
gsi_insert_before(&gsi, call, GSI_SAME_STMT);
}
}
return 0;
}
};
static struct plugin_info afl_cmptrs_plugin = {
.version = "20220420",
.help = G_("AFL gcc cmptrs plugin\n\
\n\
Set AFL_QUIET in the environment to silence it.\n\
"),
};
} // namespace
/* This is the function GCC calls when loading a plugin. Initialize
and register further callbacks. */
int plugin_init(struct plugin_name_args *info,
struct plugin_gcc_version *version) {
if (!plugin_default_version_check(version, &gcc_version))
FATAL(G_("GCC and plugin have incompatible versions, expected GCC %s, "
"is %s"),
gcc_version.basever, version->basever);
/* Show a banner. */
bool quiet = false;
if (isatty(2) && !getenv("AFL_QUIET"))
SAYF(cCYA "afl-gcc-cmptrs-pass " cBRI VERSION cRST
" by <oliva@adacore.com>\n");
else
quiet = true;
const char *name = info->base_name;
register_callback(name, PLUGIN_INFO, NULL, &afl_cmptrs_plugin);
afl_cmptrs_pass *aflp = new afl_cmptrs_pass(quiet);
struct register_pass_info pass_info = {
.pass = aflp,
.reference_pass_name = "ssa",
.ref_pass_instance_number = 1,
.pos_op = PASS_POS_INSERT_AFTER,
};
register_callback(name, PLUGIN_PASS_MANAGER_SETUP, NULL, &pass_info);
return 0;
}

View File

@ -0,0 +1,500 @@
/* GCC plugin common infrastructure for AFL++ instrumentation passes.
Copyright 2014-2019 Free Software Foundation, Inc
Copyright 2015, 2016 Google Inc. All rights reserved.
Copyright 2019-2022 AdaCore
Written by Alexandre Oliva <oliva@adacore.com>, based on the AFL++
GCC plugin.
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "../include/config.h"
#include "../include/debug.h"
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#ifdef likely
#undef likely
#endif
#ifdef unlikely
#undef unlikely
#endif
#include <list>
#include <string>
#include <fstream>
#include <algorithm>
#include <fnmatch.h>
#include <gcc-plugin.h>
#include <plugin-version.h>
#include <toplev.h>
#include <tree-pass.h>
#include <context.h>
#include <tree.h>
#include <gimplify.h>
#include <basic-block.h>
#include <tree-ssa-alias.h>
#include <gimple-expr.h>
#include <gimple.h>
#include <gimple-iterator.h>
#include <stringpool.h>
#include <gimple-ssa.h>
#if (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__) >= \
60200 /* >= version 6.2.0 */
#include <tree-vrp.h>
#endif
#include <tree-ssanames.h>
#include <tree-phinodes.h>
#include <ssa-iterators.h>
#include <intl.h>
namespace {
struct afl_base_pass : gimple_opt_pass {
afl_base_pass(bool quiet, bool debug, struct pass_data const &pd)
: gimple_opt_pass(pd, g), be_quiet(quiet), debug(debug) {
initInstrumentList();
}
/* Are we outputting to a non-terminal, or running with AFL_QUIET
set? */
const bool be_quiet;
/* Are we running with AFL_DEBUG set? */
const bool debug;
#define report_fatal_error(msg) BADF(msg)
std::list<std::string> allowListFiles;
std::list<std::string> allowListFunctions;
std::list<std::string> denyListFiles;
std::list<std::string> denyListFunctions;
/* Note: this ignore check is also called in isInInstrumentList() */
bool isIgnoreFunction(function *F) {
// Starting from "LLVMFuzzer" these are functions used in libfuzzer based
// fuzzing campaign installations, e.g. oss-fuzz
static constexpr const char *ignoreList[] = {
"asan.",
"llvm.",
"sancov.",
"__ubsan_",
"ign.",
"__afl_",
"_fini",
"__libc_csu",
"__asan",
"__msan",
"__cmplog",
"__sancov",
"msan.",
"LLVMFuzzerM",
"LLVMFuzzerC",
"LLVMFuzzerI",
"__decide_deferred",
"maybe_duplicate_stderr",
"discard_output",
"close_stdout",
"dup_and_close_stderr",
"maybe_close_fd_mask",
"ExecuteFilesOnyByOne"
};
const char *name = IDENTIFIER_POINTER(DECL_NAME(F->decl));
int len = IDENTIFIER_LENGTH(DECL_NAME(F->decl));
for (auto const &ignoreListFunc : ignoreList) {
if (strncmp(name, ignoreListFunc, len) == 0) { return true; }
}
return false;
}
void initInstrumentList() {
char *allowlist = getenv("AFL_GCC_ALLOWLIST");
if (!allowlist) allowlist = getenv("AFL_GCC_INSTRUMENT_FILE");
if (!allowlist) allowlist = getenv("AFL_GCC_WHITELIST");
if (!allowlist) allowlist = getenv("AFL_LLVM_ALLOWLIST");
if (!allowlist) allowlist = getenv("AFL_LLVM_INSTRUMENT_FILE");
if (!allowlist) allowlist = getenv("AFL_LLVM_WHITELIST");
char *denylist = getenv("AFL_GCC_DENYLIST");
if (!denylist) denylist = getenv("AFL_GCC_BLOCKLIST");
if (!denylist) denylist = getenv("AFL_LLVM_DENYLIST");
if (!denylist) denylist = getenv("AFL_LLVM_BLOCKLIST");
if (allowlist && denylist)
FATAL(
"You can only specify either AFL_GCC_ALLOWLIST or AFL_GCC_DENYLIST "
"but not both!");
if (allowlist) {
std::string line;
std::ifstream fileStream;
fileStream.open(allowlist);
if (!fileStream) report_fatal_error("Unable to open AFL_GCC_ALLOWLIST");
getline(fileStream, line);
while (fileStream) {
int is_file = -1;
std::size_t npos;
std::string original_line = line;
line.erase(std::remove_if(line.begin(), line.end(), ::isspace),
line.end());
// remove # and following
if ((npos = line.find("#")) != std::string::npos)
line = line.substr(0, npos);
if (line.compare(0, 4, "fun:") == 0) {
is_file = 0;
line = line.substr(4);
} else if (line.compare(0, 9, "function:") == 0) {
is_file = 0;
line = line.substr(9);
} else if (line.compare(0, 4, "src:") == 0) {
is_file = 1;
line = line.substr(4);
} else if (line.compare(0, 7, "source:") == 0) {
is_file = 1;
line = line.substr(7);
}
if (line.find(":") != std::string::npos) {
FATAL("invalid line in AFL_GCC_ALLOWLIST: %s", original_line.c_str());
}
if (line.length() > 0) {
// if the entry contains / or . it must be a file
if (is_file == -1)
if (line.find("/") != std::string::npos ||
line.find(".") != std::string::npos)
is_file = 1;
// otherwise it is a function
if (is_file == 1)
allowListFiles.push_back(line);
else
allowListFunctions.push_back(line);
}
getline(fileStream, line);
}
if (debug)
DEBUGF("loaded allowlist with %zu file and %zu function entries\n",
allowListFiles.size(), allowListFunctions.size());
}
if (denylist) {
std::string line;
std::ifstream fileStream;
fileStream.open(denylist);
if (!fileStream) report_fatal_error("Unable to open AFL_GCC_DENYLIST");
getline(fileStream, line);
while (fileStream) {
int is_file = -1;
std::size_t npos;
std::string original_line = line;
line.erase(std::remove_if(line.begin(), line.end(), ::isspace),
line.end());
// remove # and following
if ((npos = line.find("#")) != std::string::npos)
line = line.substr(0, npos);
if (line.compare(0, 4, "fun:") == 0) {
is_file = 0;
line = line.substr(4);
} else if (line.compare(0, 9, "function:") == 0) {
is_file = 0;
line = line.substr(9);
} else if (line.compare(0, 4, "src:") == 0) {
is_file = 1;
line = line.substr(4);
} else if (line.compare(0, 7, "source:") == 0) {
is_file = 1;
line = line.substr(7);
}
if (line.find(":") != std::string::npos) {
FATAL("invalid line in AFL_GCC_DENYLIST: %s", original_line.c_str());
}
if (line.length() > 0) {
// if the entry contains / or . it must be a file
if (is_file == -1)
if (line.find("/") != std::string::npos ||
line.find(".") != std::string::npos)
is_file = 1;
// otherwise it is a function
if (is_file == 1)
denyListFiles.push_back(line);
else
denyListFunctions.push_back(line);
}
getline(fileStream, line);
}
if (debug)
DEBUGF("loaded denylist with %zu file and %zu function entries\n",
denyListFiles.size(), denyListFunctions.size());
}
}
/* Returns the source file name attached to the function declaration F. If
there is no source location information, returns an empty string. */
std::string getSourceName(function *F) {
return DECL_SOURCE_FILE(F->decl) ? DECL_SOURCE_FILE(F->decl) : "";
}
bool isInInstrumentList(function *F) {
bool return_default = true;
// is this a function with code? If it is external we don't instrument it
// anyway and it can't be in the instrument file list. Or if it is it is
// ignored.
if (isIgnoreFunction(F)) return false;
if (!denyListFiles.empty() || !denyListFunctions.empty()) {
if (!denyListFunctions.empty()) {
std::string instFunction = IDENTIFIER_POINTER(DECL_NAME(F->decl));
for (std::list<std::string>::iterator it = denyListFunctions.begin();
it != denyListFunctions.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (instFunction.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), instFunction.c_str(), 0) == 0) {
if (debug)
DEBUGF(
"Function %s is in the deny function list, not "
"instrumenting ... \n",
instFunction.c_str());
return false;
}
}
}
}
if (!denyListFiles.empty()) {
std::string source_file = getSourceName(F);
if (!source_file.empty()) {
for (std::list<std::string>::iterator it = denyListFiles.begin();
it != denyListFiles.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (source_file.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), source_file.c_str(), 0) == 0) {
return false;
}
}
}
} else {
// we could not find out the location. in this case we say it is not
// in the instrument file list
if (!be_quiet)
WARNF(
"No debug information found for function %s, will be "
"instrumented (recompile with -g -O[1-3]).",
IDENTIFIER_POINTER(DECL_NAME(F->decl)));
}
}
}
// if we do not have a instrument file list return true
if (!allowListFiles.empty() || !allowListFunctions.empty()) {
return_default = false;
if (!allowListFunctions.empty()) {
std::string instFunction = IDENTIFIER_POINTER(DECL_NAME(F->decl));
for (std::list<std::string>::iterator it = allowListFunctions.begin();
it != allowListFunctions.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (instFunction.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), instFunction.c_str(), 0) == 0) {
if (debug)
DEBUGF(
"Function %s is in the allow function list, instrumenting "
"... \n",
instFunction.c_str());
return true;
}
}
}
}
if (!allowListFiles.empty()) {
std::string source_file = getSourceName(F);
if (!source_file.empty()) {
for (std::list<std::string>::iterator it = allowListFiles.begin();
it != allowListFiles.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (source_file.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), source_file.c_str(), 0) == 0) {
if (debug)
DEBUGF(
"Function %s is in the allowlist (%s), instrumenting ... "
"\n",
IDENTIFIER_POINTER(DECL_NAME(F->decl)),
source_file.c_str());
return true;
}
}
}
} else {
// we could not find out the location. In this case we say it is not
// in the instrument file list
if (!be_quiet)
WARNF(
"No debug information found for function %s, will not be "
"instrumented (recompile with -g -O[1-3]).",
IDENTIFIER_POINTER(DECL_NAME(F->decl)));
return false;
}
}
}
return return_default;
}
};
} // namespace

View File

@ -124,50 +124,8 @@
entry edge for the entry block.
*/
#include "../include/config.h"
#include "../include/debug.h"
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#ifdef likely
#undef likely
#endif
#ifdef unlikely
#undef unlikely
#endif
#include <list>
#include <string>
#include <fstream>
#include <algorithm>
#include <fnmatch.h>
#include <gcc-plugin.h>
#include <plugin-version.h>
#include <toplev.h>
#include <tree-pass.h>
#include <context.h>
#include <tree.h>
#include <gimplify.h>
#include <basic-block.h>
#include <tree-ssa-alias.h>
#include <gimple-expr.h>
#include <gimple.h>
#include <gimple-iterator.h>
#include <stringpool.h>
#include <gimple-ssa.h>
#if (__GNUC__ * 10000 + __GNUC_MINOR__ * 100 + __GNUC_PATCHLEVEL__) >= \
60200 /* >= version 6.2.0 */
#include <tree-vrp.h>
#endif
#include <tree-ssanames.h>
#include <tree-phinodes.h>
#include <ssa-iterators.h>
#include <intl.h>
#include "afl-gcc-common.h"
#include "memmodel.h"
/* This plugin, being under the same license as GCC, satisfies the
"GPL-compatible Software" definition in the GCC RUNTIME LIBRARY
@ -191,12 +149,10 @@ static constexpr struct pass_data afl_pass_data = {
};
struct afl_pass : gimple_opt_pass {
struct afl_pass : afl_base_pass {
afl_pass(bool quiet, unsigned int ratio)
: gimple_opt_pass(afl_pass_data, g),
be_quiet(quiet),
debug(!!getenv("AFL_DEBUG")),
: afl_base_pass(quiet, !!getenv("AFL_DEBUG"), afl_pass_data),
inst_ratio(ratio),
#ifdef AFL_GCC_OUT_OF_LINE
out_of_line(!!(AFL_GCC_OUT_OF_LINE)),
@ -210,13 +166,6 @@ struct afl_pass : gimple_opt_pass {
}
/* Are we outputting to a non-terminal, or running with AFL_QUIET
set? */
const bool be_quiet;
/* Are we running with AFL_DEBUG set? */
const bool debug;
/* How likely (%) is a block to be instrumented? */
const unsigned int inst_ratio;
@ -297,21 +246,22 @@ struct afl_pass : gimple_opt_pass {
gimple_build_assign(ntry, POINTER_PLUS_EXPR, map_ptr, indx);
gimple_seq_add_stmt(&seq, idx_map);
/* Increment the counter in idx_map. */
tree memref = build2(MEM_REF, TREE_TYPE(TREE_TYPE(ntry)), ntry,
build_zero_cst(TREE_TYPE(ntry)));
if (blocks == 0)
cntr = create_tmp_var(TREE_TYPE(memref), ".afl_edge_count");
/* Load the count from the entry. */
auto load_cntr = gimple_build_assign(cntr, memref);
gimple_seq_add_stmt(&seq, load_cntr);
/* Prepare to add constant 1 to it. */
tree incrv = build_one_cst(TREE_TYPE(cntr));
tree incrv = build_one_cst(TREE_TYPE(TREE_TYPE(ntry)));
if (neverZero) {
/* Increment the counter in idx_map. */
tree memref = build2(MEM_REF, TREE_TYPE(TREE_TYPE(ntry)), ntry,
build_zero_cst(TREE_TYPE(ntry)));
if (blocks == 0)
cntr = create_tmp_var(TREE_TYPE(memref), ".afl_edge_count");
/* Load the count from the entry. */
auto load_cntr = gimple_build_assign(cntr, memref);
gimple_seq_add_stmt(&seq, load_cntr);
/* NeverZero: if count wrapped around to zero, advance to
one. */
if (blocks == 0) {
@ -348,16 +298,25 @@ struct afl_pass : gimple_opt_pass {
in xincr. */
incrv = xincr;
/* Add the increment (1 or the overflow bit) to count. */
auto incr_cntr = gimple_build_assign(cntr, PLUS_EXPR, cntr, incrv);
gimple_seq_add_stmt(&seq, incr_cntr);
/* Store count in the map entry. */
auto store_cntr = gimple_build_assign(unshare_expr(memref), cntr);
gimple_seq_add_stmt(&seq, store_cntr);
} else {
/* Use a serialized memory model. */
tree memmod = build_int_cst(integer_type_node, MEMMODEL_SEQ_CST);
tree fadd = builtin_decl_explicit(BUILT_IN_ATOMIC_FETCH_ADD_1);
auto incr_cntr = gimple_build_call(fadd, 3, ntry, incrv, memmod);
gimple_seq_add_stmt(&seq, incr_cntr);
}
/* Add the increment (1 or the overflow bit) to count. */
auto incr_cntr = gimple_build_assign(cntr, PLUS_EXPR, cntr, incrv);
gimple_seq_add_stmt(&seq, incr_cntr);
/* Store count in the map entry. */
auto store_cntr = gimple_build_assign(unshare_expr(memref), cntr);
gimple_seq_add_stmt(&seq, store_cntr);
/* Store bid >> 1 in __afl_prev_loc. */
auto shift_loc =
gimple_build_assign(ploc, build_int_cst(TREE_TYPE(ploc), bid >> 1));
@ -456,6 +415,8 @@ struct afl_pass : gimple_opt_pass {
thread-local variable. */
static inline tree get_afl_area_ptr_decl() {
/* If type changes, the size N in FETCH_ADD_<N> must be adjusted
in builtin calls above. */
tree type = build_pointer_type(unsigned_char_type_node);
tree decl = build_decl(BUILTINS_LOCATION, VAR_DECL,
get_identifier("__afl_area_ptr"), type);
@ -490,420 +451,11 @@ struct afl_pass : gimple_opt_pass {
}
#define report_fatal_error(msg) BADF(msg)
std::list<std::string> allowListFiles;
std::list<std::string> allowListFunctions;
std::list<std::string> denyListFiles;
std::list<std::string> denyListFunctions;
/* Note: this ignore check is also called in isInInstrumentList() */
bool isIgnoreFunction(function *F) {
// Starting from "LLVMFuzzer" these are functions used in libfuzzer based
// fuzzing campaign installations, e.g. oss-fuzz
static constexpr const char *ignoreList[] = {
"asan.",
"llvm.",
"sancov.",
"__ubsan_",
"ign.",
"__afl_",
"_fini",
"__libc_csu",
"__asan",
"__msan",
"__cmplog",
"__sancov",
"msan.",
"LLVMFuzzerM",
"LLVMFuzzerC",
"LLVMFuzzerI",
"__decide_deferred",
"maybe_duplicate_stderr",
"discard_output",
"close_stdout",
"dup_and_close_stderr",
"maybe_close_fd_mask",
"ExecuteFilesOnyByOne"
};
const char *name = IDENTIFIER_POINTER(DECL_NAME(F->decl));
int len = IDENTIFIER_LENGTH(DECL_NAME(F->decl));
for (auto const &ignoreListFunc : ignoreList) {
if (strncmp(name, ignoreListFunc, len) == 0) { return true; }
}
return false;
}
void initInstrumentList() {
char *allowlist = getenv("AFL_GCC_ALLOWLIST");
if (!allowlist) allowlist = getenv("AFL_GCC_INSTRUMENT_FILE");
if (!allowlist) allowlist = getenv("AFL_GCC_WHITELIST");
if (!allowlist) allowlist = getenv("AFL_LLVM_ALLOWLIST");
if (!allowlist) allowlist = getenv("AFL_LLVM_INSTRUMENT_FILE");
if (!allowlist) allowlist = getenv("AFL_LLVM_WHITELIST");
char *denylist = getenv("AFL_GCC_DENYLIST");
if (!denylist) denylist = getenv("AFL_GCC_BLOCKLIST");
if (!denylist) denylist = getenv("AFL_LLVM_DENYLIST");
if (!denylist) denylist = getenv("AFL_LLVM_BLOCKLIST");
if (allowlist && denylist)
FATAL(
"You can only specify either AFL_GCC_ALLOWLIST or AFL_GCC_DENYLIST "
"but not both!");
if (allowlist) {
std::string line;
std::ifstream fileStream;
fileStream.open(allowlist);
if (!fileStream) report_fatal_error("Unable to open AFL_GCC_ALLOWLIST");
getline(fileStream, line);
while (fileStream) {
int is_file = -1;
std::size_t npos;
std::string original_line = line;
line.erase(std::remove_if(line.begin(), line.end(), ::isspace),
line.end());
// remove # and following
if ((npos = line.find("#")) != std::string::npos)
line = line.substr(0, npos);
if (line.compare(0, 4, "fun:") == 0) {
is_file = 0;
line = line.substr(4);
} else if (line.compare(0, 9, "function:") == 0) {
is_file = 0;
line = line.substr(9);
} else if (line.compare(0, 4, "src:") == 0) {
is_file = 1;
line = line.substr(4);
} else if (line.compare(0, 7, "source:") == 0) {
is_file = 1;
line = line.substr(7);
}
if (line.find(":") != std::string::npos) {
FATAL("invalid line in AFL_GCC_ALLOWLIST: %s", original_line.c_str());
}
if (line.length() > 0) {
// if the entry contains / or . it must be a file
if (is_file == -1)
if (line.find("/") != std::string::npos ||
line.find(".") != std::string::npos)
is_file = 1;
// otherwise it is a function
if (is_file == 1)
allowListFiles.push_back(line);
else
allowListFunctions.push_back(line);
}
getline(fileStream, line);
}
if (debug)
DEBUGF("loaded allowlist with %zu file and %zu function entries\n",
allowListFiles.size(), allowListFunctions.size());
}
if (denylist) {
std::string line;
std::ifstream fileStream;
fileStream.open(denylist);
if (!fileStream) report_fatal_error("Unable to open AFL_GCC_DENYLIST");
getline(fileStream, line);
while (fileStream) {
int is_file = -1;
std::size_t npos;
std::string original_line = line;
line.erase(std::remove_if(line.begin(), line.end(), ::isspace),
line.end());
// remove # and following
if ((npos = line.find("#")) != std::string::npos)
line = line.substr(0, npos);
if (line.compare(0, 4, "fun:") == 0) {
is_file = 0;
line = line.substr(4);
} else if (line.compare(0, 9, "function:") == 0) {
is_file = 0;
line = line.substr(9);
} else if (line.compare(0, 4, "src:") == 0) {
is_file = 1;
line = line.substr(4);
} else if (line.compare(0, 7, "source:") == 0) {
is_file = 1;
line = line.substr(7);
}
if (line.find(":") != std::string::npos) {
FATAL("invalid line in AFL_GCC_DENYLIST: %s", original_line.c_str());
}
if (line.length() > 0) {
// if the entry contains / or . it must be a file
if (is_file == -1)
if (line.find("/") != std::string::npos ||
line.find(".") != std::string::npos)
is_file = 1;
// otherwise it is a function
if (is_file == 1)
denyListFiles.push_back(line);
else
denyListFunctions.push_back(line);
}
getline(fileStream, line);
}
if (debug)
DEBUGF("loaded denylist with %zu file and %zu function entries\n",
denyListFiles.size(), denyListFunctions.size());
}
}
/* Returns the source file name attached to the function declaration F. If
there is no source location information, returns an empty string. */
std::string getSourceName(function *F) {
return DECL_SOURCE_FILE(F->decl) ? DECL_SOURCE_FILE(F->decl) : "";
}
bool isInInstrumentList(function *F) {
bool return_default = true;
// is this a function with code? If it is external we don't instrument it
// anyway and it can't be in the instrument file list. Or if it is it is
// ignored.
if (isIgnoreFunction(F)) return false;
if (!denyListFiles.empty() || !denyListFunctions.empty()) {
if (!denyListFunctions.empty()) {
std::string instFunction = IDENTIFIER_POINTER(DECL_NAME(F->decl));
for (std::list<std::string>::iterator it = denyListFunctions.begin();
it != denyListFunctions.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (instFunction.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), instFunction.c_str(), 0) == 0) {
if (debug)
DEBUGF(
"Function %s is in the deny function list, not "
"instrumenting ... \n",
instFunction.c_str());
return false;
}
}
}
}
if (!denyListFiles.empty()) {
std::string source_file = getSourceName(F);
if (!source_file.empty()) {
for (std::list<std::string>::iterator it = denyListFiles.begin();
it != denyListFiles.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (source_file.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), source_file.c_str(), 0) == 0) {
return false;
}
}
}
} else {
// we could not find out the location. in this case we say it is not
// in the instrument file list
if (!be_quiet)
WARNF(
"No debug information found for function %s, will be "
"instrumented (recompile with -g -O[1-3]).",
IDENTIFIER_POINTER(DECL_NAME(F->decl)));
}
}
}
// if we do not have a instrument file list return true
if (!allowListFiles.empty() || !allowListFunctions.empty()) {
return_default = false;
if (!allowListFunctions.empty()) {
std::string instFunction = IDENTIFIER_POINTER(DECL_NAME(F->decl));
for (std::list<std::string>::iterator it = allowListFunctions.begin();
it != allowListFunctions.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (instFunction.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), instFunction.c_str(), 0) == 0) {
if (debug)
DEBUGF(
"Function %s is in the allow function list, instrumenting "
"... \n",
instFunction.c_str());
return true;
}
}
}
}
if (!allowListFiles.empty()) {
std::string source_file = getSourceName(F);
if (!source_file.empty()) {
for (std::list<std::string>::iterator it = allowListFiles.begin();
it != allowListFiles.end(); ++it) {
/* We don't check for filename equality here because
* filenames might actually be full paths. Instead we
* check that the actual filename ends in the filename
* specified in the list. We also allow UNIX-style pattern
* matching */
if (source_file.length() >= it->length()) {
if (fnmatch(("*" + *it).c_str(), source_file.c_str(), 0) == 0) {
if (debug)
DEBUGF(
"Function %s is in the allowlist (%s), instrumenting ... "
"\n",
IDENTIFIER_POINTER(DECL_NAME(F->decl)),
source_file.c_str());
return true;
}
}
}
} else {
// we could not find out the location. In this case we say it is not
// in the instrument file list
if (!be_quiet)
WARNF(
"No debug information found for function %s, will not be "
"instrumented (recompile with -g -O[1-3]).",
IDENTIFIER_POINTER(DECL_NAME(F->decl)));
return false;
}
}
}
return return_default;
}
};
static struct plugin_info afl_plugin = {
.version = "20220907",
.version = "20220420",
.help = G_("AFL gcc plugin\n\
\n\
Set AFL_QUIET in the environment to silence it.\n\
@ -920,7 +472,7 @@ Specify -frandom-seed for reproducible instrumentation.\n\
/* This is the function GCC calls when loading a plugin. Initialize
and register further callbacks. */
int plugin_init(struct plugin_name_args * info,
int plugin_init(struct plugin_name_args *info,
struct plugin_gcc_version *version) {
if (!plugin_default_version_check(version, &gcc_version))
@ -950,7 +502,7 @@ int plugin_init(struct plugin_name_args * info,
const char *name = info->base_name;
register_callback(name, PLUGIN_INFO, NULL, &afl_plugin);
afl_pass * aflp = new afl_pass(quiet, inst_ratio);
afl_pass *aflp = new afl_pass(quiet, inst_ratio);
struct register_pass_info pass_info = {
.pass = aflp,

View File

@ -181,7 +181,7 @@ bool AFLdict2filePass::runOnModule(Module &M) {
#endif
DenseMap<Value *, std::string *> valueMap;
char * ptr;
char *ptr;
int found = 0;
/* Show a banner */
@ -246,11 +246,11 @@ bool AFLdict2filePass::runOnModule(Module &M) {
for (auto &IN : BB) {
CallInst *callInst = nullptr;
CmpInst * cmpInst = nullptr;
CmpInst *cmpInst = nullptr;
if ((cmpInst = dyn_cast<CmpInst>(&IN))) {
Value * op = cmpInst->getOperand(1);
Value *op = cmpInst->getOperand(1);
ConstantInt *ilen = dyn_cast<ConstantInt>(op);
/* We skip > 64 bit integers. why? first because their value is
@ -518,7 +518,7 @@ bool AFLdict2filePass::runOnModule(Module &M) {
if (HasStr2 == true) {
Value * op2 = callInst->getArgOperand(2);
Value *op2 = callInst->getArgOperand(2);
ConstantInt *ilen = dyn_cast<ConstantInt>(op2);
if (ilen) {
@ -631,7 +631,7 @@ bool AFLdict2filePass::runOnModule(Module &M) {
if (isMemcmp || isStrncmp || isStrncasecmp) {
Value * op2 = callInst->getArgOperand(2);
Value *op2 = callInst->getArgOperand(2);
ConstantInt *ilen = dyn_cast<ConstantInt>(op2);
if (ilen) {

View File

@ -101,7 +101,7 @@ llvmGetPassPluginInfo() {
}
PreservedAnalyses AFLcheckIfInstrument::run(Module & M,
PreservedAnalyses AFLcheckIfInstrument::run(Module &M,
ModuleAnalysisManager &MAM) {
/* Show a banner */
@ -135,7 +135,7 @@ PreservedAnalyses AFLcheckIfInstrument::run(Module & M,
DEBUGF("function %s is NOT in the instrument file list\n",
F.getName().str().c_str());
auto & Ctx = F.getContext();
auto &Ctx = F.getContext();
AttributeList Attrs = F.getAttributes();
#if LLVM_VERSION_MAJOR >= 14
AttributeList NewAttrs = Attrs.addFnAttribute(Ctx, "skipinstrument");

View File

@ -251,7 +251,7 @@ bool AFLCoverage::runOnModule(Module &M) {
/* Decide instrumentation ratio */
char * inst_ratio_str = getenv("AFL_INST_RATIO");
char *inst_ratio_str = getenv("AFL_INST_RATIO");
unsigned int inst_ratio = 100;
if (inst_ratio_str) {
@ -486,7 +486,7 @@ bool AFLCoverage::runOnModule(Module &M) {
Constant *PrevLocShuffleMask = ConstantVector::get(PrevLocShuffle);
Constant * PrevCallerShuffleMask = NULL;
Constant *PrevCallerShuffleMask = NULL;
SmallVector<Constant *, 32> PrevCallerShuffle = {UndefValue::get(Int32Ty)};
if (ctx_k) {
@ -506,7 +506,7 @@ bool AFLCoverage::runOnModule(Module &M) {
// other constants we need
ConstantInt *One = ConstantInt::get(Int8Ty, 1);
Value * PrevCtx = NULL; // CTX sensitive coverage
Value *PrevCtx = NULL; // CTX sensitive coverage
LoadInst *PrevCaller = NULL; // K-CTX coverage
/* Instrument all the things! */

View File

@ -156,9 +156,9 @@ Iterator Unique(Iterator first, Iterator last) {
bool CmpLogInstructions::hookInstrs(Module &M) {
std::vector<Instruction *> icomps;
LLVMContext & C = M.getContext();
LLVMContext &C = M.getContext();
Type * VoidTy = Type::getVoidTy(C);
Type *VoidTy = Type::getVoidTy(C);
IntegerType *Int8Ty = IntegerType::getInt8Ty(C);
IntegerType *Int16Ty = IntegerType::getInt16Ty(C);
IntegerType *Int32Ty = IntegerType::getInt32Ty(C);
@ -338,7 +338,7 @@ bool CmpLogInstructions::hookInstrs(Module &M) {
IntegerType *intTyOp1 = NULL;
unsigned max_size = 0, cast_size = 0;
unsigned attr = 0, vector_cnt = 0, is_fp = 0;
CmpInst * cmpInst = dyn_cast<CmpInst>(selectcmpInst);
CmpInst *cmpInst = dyn_cast<CmpInst>(selectcmpInst);
if (!cmpInst) { continue; }
@ -666,7 +666,7 @@ bool CmpLogInstructions::hookInstrs(Module &M) {
}
#if LLVM_MAJOR >= 11 /* use new pass manager */
PreservedAnalyses CmpLogInstructions::run(Module & M,
PreservedAnalyses CmpLogInstructions::run(Module &M,
ModuleAnalysisManager &MAM) {
#else

View File

@ -506,8 +506,8 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
args.push_back(v1Pcasted);
args.push_back(v2Pcasted);
@ -537,10 +537,10 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value * v3Pbitcast = IRB.CreateBitCast(
v3P, IntegerType::get(C, v3P->getType()->getPrimitiveSizeInBits()));
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v3Pbitcast = IRB.CreateBitCast(
v3P, IntegerType::get(C, v3P->getType()->getPrimitiveSizeInBits()));
Value *v3Pcasted =
IRB.CreateIntCast(v3Pbitcast, IntegerType::get(C, 64), false);
args.push_back(v1Pcasted);
@ -572,8 +572,8 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
args.push_back(v1Pcasted);
args.push_back(v2Pcasted);
@ -603,10 +603,10 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value * v3Pbitcast = IRB.CreateBitCast(
v3P, IntegerType::get(C, v3P->getType()->getPrimitiveSizeInBits()));
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v3Pbitcast = IRB.CreateBitCast(
v3P, IntegerType::get(C, v3P->getType()->getPrimitiveSizeInBits()));
Value *v3Pcasted =
IRB.CreateIntCast(v3Pbitcast, IntegerType::get(C, 64), false);
args.push_back(v1Pcasted);
@ -638,8 +638,8 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
args.push_back(v1Pcasted);
args.push_back(v2Pcasted);
@ -668,8 +668,8 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
args.push_back(v1Pcasted);
args.push_back(v2Pcasted);
@ -698,8 +698,8 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
args.push_back(v1Pcasted);
args.push_back(v2Pcasted);
@ -728,8 +728,8 @@ bool CmpLogRoutines::hookRtns(Module &M) {
IRBuilder<> IRB(ThenTerm);
std::vector<Value *> args;
Value * v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value * v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
Value *v1Pcasted = IRB.CreatePointerCast(v1P, i8PtrTy);
Value *v2Pcasted = IRB.CreatePointerCast(v2P, i8PtrTy);
args.push_back(v1Pcasted);
args.push_back(v2Pcasted);

View File

@ -149,9 +149,9 @@ Iterator Unique(Iterator first, Iterator last) {
bool CmplogSwitches::hookInstrs(Module &M) {
std::vector<SwitchInst *> switches;
LLVMContext & C = M.getContext();
LLVMContext &C = M.getContext();
Type * VoidTy = Type::getVoidTy(C);
Type *VoidTy = Type::getVoidTy(C);
IntegerType *Int8Ty = IntegerType::getInt8Ty(C);
IntegerType *Int16Ty = IntegerType::getInt16Ty(C);
IntegerType *Int32Ty = IntegerType::getInt32Ty(C);
@ -270,7 +270,7 @@ bool CmplogSwitches::hookInstrs(Module &M) {
for (auto &SI : switches) {
Value * Val = SI->getCondition();
Value *Val = SI->getCondition();
unsigned int max_size = Val->getType()->getIntegerBitWidth(), cast_size;
unsigned char do_cast = 0;

View File

@ -168,10 +168,10 @@ bool CompareTransform::transformCmps(Module &M, const bool processStrcmp,
DenseMap<Value *, std::string *> valueMap;
std::vector<CallInst *> calls;
LLVMContext & C = M.getContext();
IntegerType * Int8Ty = IntegerType::getInt8Ty(C);
IntegerType * Int32Ty = IntegerType::getInt32Ty(C);
IntegerType * Int64Ty = IntegerType::getInt64Ty(C);
LLVMContext &C = M.getContext();
IntegerType *Int8Ty = IntegerType::getInt8Ty(C);
IntegerType *Int32Ty = IntegerType::getInt32Ty(C);
IntegerType *Int64Ty = IntegerType::getInt64Ty(C);
#if LLVM_VERSION_MAJOR >= 9
FunctionCallee tolowerFn;
@ -409,7 +409,7 @@ bool CompareTransform::transformCmps(Module &M, const bool processStrcmp,
/* check if third operand is a constant integer
* strlen("constStr") and sizeof() are treated as constant */
Value * op2 = callInst->getArgOperand(2);
Value *op2 = callInst->getArgOperand(2);
ConstantInt *ilen = dyn_cast<ConstantInt>(op2);
if (ilen) {
@ -449,7 +449,7 @@ bool CompareTransform::transformCmps(Module &M, const bool processStrcmp,
*Str2P = callInst->getArgOperand(1);
StringRef Str1, Str2, ConstStr;
std::string TmpConstStr;
Value * VarStr;
Value *VarStr;
bool HasStr1 = getConstantStringInfo(Str1P, Str1);
bool HasStr2 = getConstantStringInfo(Str2P, Str2);
uint64_t constStrLen, unrollLen, constSizedLen = 0;
@ -457,7 +457,7 @@ bool CompareTransform::transformCmps(Module &M, const bool processStrcmp,
bool isSizedcmp = false;
bool isCaseInsensitive = false;
bool needs_null = false;
Function * Callee = callInst->getCalledFunction();
Function *Callee = callInst->getCalledFunction();
if (Callee) {
@ -616,14 +616,14 @@ bool CompareTransform::transformCmps(Module &M, const bool processStrcmp,
for (uint64_t i = 0; i < unrollLen; i++) {
BasicBlock * cur_cmp_bb = next_cmp_bb, *cur_lenchk_bb = next_lenchk_bb;
BasicBlock *cur_cmp_bb = next_cmp_bb, *cur_lenchk_bb = next_lenchk_bb;
unsigned char c;
if (cur_lenchk_bb) {
IRBuilder<> cur_lenchk_IRB(&*(cur_lenchk_bb->getFirstInsertionPt()));
Value * icmp = cur_lenchk_IRB.CreateICmpEQ(
sizedValue, ConstantInt::get(sizedValue->getType(), i));
Value *icmp = cur_lenchk_IRB.CreateICmpEQ(
sizedValue, ConstantInt::get(sizedValue->getType(), i));
cur_lenchk_IRB.CreateCondBr(icmp, end_bb, cur_cmp_bb);
cur_lenchk_bb->getTerminator()->eraseFromParent();

View File

@ -230,9 +230,9 @@ char SplitComparesTransform::ID = 0;
/// FCMP instructions with predicate xGT or xLT and EQ
bool SplitComparesTransform::simplifyFPCompares(Module &M) {
LLVMContext & C = M.getContext();
LLVMContext &C = M.getContext();
std::vector<Instruction *> fcomps;
IntegerType * Int1Ty = IntegerType::getInt1Ty(C);
IntegerType *Int1Ty = IntegerType::getInt1Ty(C);
/* iterate over all functions, bbs and instruction and add
* all integer comparisons with >= and <= predicates to the icomps vector */
@ -362,8 +362,8 @@ bool SplitComparesTransform::simplifyFPCompares(Module &M) {
/// This function splits ICMP instructions with xGE or xLE predicates into two
/// ICMP instructions with predicate xGT or xLT and EQ
bool SplitComparesTransform::simplifyOrEqualsCompare(CmpInst * IcmpInst,
Module & M,
bool SplitComparesTransform::simplifyOrEqualsCompare(CmpInst *IcmpInst,
Module &M,
CmpWorklist &worklist) {
LLVMContext &C = M.getContext();
@ -498,7 +498,7 @@ bool SplitComparesTransform::simplifySignedCompare(CmpInst *IcmpInst, Module &M,
/* create a new basic block which is executed if the signedness bit is
* different */
CmpInst * icmp_inv_sig_cmp;
CmpInst *icmp_inv_sig_cmp;
BasicBlock *sign_bb =
BasicBlock::Create(C, "sign", end_bb->getParent(), end_bb);
if (pred == CmpInst::ICMP_SGT) {
@ -522,7 +522,7 @@ bool SplitComparesTransform::simplifySignedCompare(CmpInst *IcmpInst, Module &M,
BranchInst::Create(end_bb, sign_bb);
/* create a new bb which is executed if signedness is equal */
CmpInst * icmp_usign_cmp;
CmpInst *icmp_usign_cmp;
BasicBlock *middle_bb =
BasicBlock::Create(C, "injected", end_bb->getParent(), end_bb);
/* we can do a normal unsigned compare now */
@ -566,8 +566,17 @@ bool SplitComparesTransform::splitCompare(CmpInst *cmp_inst, Module &M,
case CmpInst::ICMP_NE:
case CmpInst::ICMP_UGT:
case CmpInst::ICMP_ULT:
case CmpInst::ICMP_UGE:
case CmpInst::ICMP_ULE:
case CmpInst::ICMP_SGT:
case CmpInst::ICMP_SLT:
case CmpInst::ICMP_SGE:
case CmpInst::ICMP_SLE:
break;
default:
if (!be_quiet)
fprintf(stderr, "Error: split-compare: Unsupported predicate (%u)\n",
pred);
// unsupported predicate!
return false;
@ -581,6 +590,8 @@ bool SplitComparesTransform::splitCompare(CmpInst *cmp_inst, Module &M,
if (!intTyOp0) {
// not an integer type
if (!be_quiet)
fprintf(stderr, "Error: split-compare: not an integer type\n");
return false;
}
@ -595,11 +606,11 @@ bool SplitComparesTransform::splitCompare(CmpInst *cmp_inst, Module &M,
LLVMContext &C = M.getContext();
IntegerType *Int1Ty = IntegerType::getInt1Ty(C);
BasicBlock * bb = cmp_inst->getParent();
BasicBlock *bb = cmp_inst->getParent();
IntegerType *OldIntType = IntegerType::get(C, bitw);
IntegerType *NewIntType = IntegerType::get(C, bitw / 2);
BasicBlock * end_bb = bb->splitBasicBlock(BasicBlock::iterator(cmp_inst));
CmpInst * icmp_high, *icmp_low;
BasicBlock *end_bb = bb->splitBasicBlock(BasicBlock::iterator(cmp_inst));
CmpInst *icmp_high, *icmp_low;
/* create the comparison of the top halves of the original operands */
Value *s_op0, *op0_high, *s_op1, *op1_high;
@ -629,7 +640,7 @@ bool SplitComparesTransform::splitCompare(CmpInst *cmp_inst, Module &M,
BasicBlock *cmp_low_bb =
BasicBlock::Create(C, "" /*"injected"*/, end_bb->getParent(), end_bb);
Value * op0_low, *op1_low;
Value *op0_low, *op1_low;
IRBuilder<> Builder(cmp_low_bb);
op0_low = Builder.CreateTrunc(op0, NewIntType);
@ -675,6 +686,12 @@ bool SplitComparesTransform::splitCompare(CmpInst *cmp_inst, Module &M,
}
case CmpInst::ICMP_SGE:
case CmpInst::ICMP_SLE:
case CmpInst::ICMP_SGT:
case CmpInst::ICMP_SLT:
case CmpInst::ICMP_UGE:
case CmpInst::ICMP_ULE:
case CmpInst::ICMP_UGT:
case CmpInst::ICMP_ULT: {
@ -684,10 +701,11 @@ bool SplitComparesTransform::splitCompare(CmpInst *cmp_inst, Module &M,
* if this is true we can go to the end if not we have to go to the
* bb which checks the lower half of the operands */
Instruction *op0_low, *op1_low;
CmpInst * icmp_inv_cmp = nullptr;
BasicBlock * inv_cmp_bb =
CmpInst *icmp_inv_cmp = nullptr;
BasicBlock *inv_cmp_bb =
BasicBlock::Create(C, "inv_cmp", end_bb->getParent(), end_bb);
if (pred == CmpInst::ICMP_UGT) {
if (pred == CmpInst::ICMP_UGT || pred == CmpInst::ICMP_SGT ||
pred == CmpInst::ICMP_UGE || pred == CmpInst::ICMP_SGE) {
icmp_inv_cmp = CmpInst::Create(Instruction::ICmp, CmpInst::ICMP_ULT,
op0_high, op1_high);
@ -729,6 +747,8 @@ bool SplitComparesTransform::splitCompare(CmpInst *cmp_inst, Module &M,
}
default:
if (!be_quiet)
fprintf(stderr, "Error: split-compare: should not happen\n");
return false;
}
@ -944,7 +964,7 @@ size_t SplitComparesTransform::splitFPCompares(Module &M) {
// BUG FIXME TODO: u64 does not work for > 64 bit ... e.g. 80 and 128 bit
if (sizeInBits > 64) { continue; }
IntegerType * intType = IntegerType::get(C, op_size);
IntegerType *intType = IntegerType::get(C, op_size);
const unsigned int precision = sizeInBits == 32 ? 24
: sizeInBits == 64 ? 53
: sizeInBits == 128 ? 113
@ -1052,8 +1072,8 @@ size_t SplitComparesTransform::splitFPCompares(Module &M) {
/*** now working in nonan_bb ***/
/* Treat -0.0 as equal to +0.0, that is for -0.0 make it +0.0 */
Instruction * b_op0, *b_op1;
Instruction * isMzero_op0, *isMzero_op1;
Instruction *b_op0, *b_op1;
Instruction *isMzero_op0, *isMzero_op1;
const unsigned long long MinusZero = 1UL << (sizeInBits - 1U);
const unsigned long long PlusZero = 0;
@ -1172,7 +1192,7 @@ size_t SplitComparesTransform::splitFPCompares(Module &M) {
/* compare the exponents of the operands */
Instruction *icmp_exponents_equal;
Instruction *icmp_exponent_result;
BasicBlock * signequal2_bb = signequal_bb;
BasicBlock *signequal2_bb = signequal_bb;
switch (FcmpInst->getPredicate()) {
case CmpInst::FCMP_UEQ:
@ -1342,8 +1362,8 @@ size_t SplitComparesTransform::splitFPCompares(Module &M) {
/* compare the fractions of the operands */
Instruction *icmp_fraction_result;
BasicBlock * middle2_bb = middle_bb;
PHINode * PN2 = nullptr;
BasicBlock *middle2_bb = middle_bb;
PHINode *PN2 = nullptr;
switch (FcmpInst->getPredicate()) {
case CmpInst::FCMP_UEQ:
@ -1484,7 +1504,7 @@ size_t SplitComparesTransform::splitFPCompares(Module &M) {
}
#if LLVM_MAJOR >= 11
PreservedAnalyses SplitComparesTransform::run(Module & M,
PreservedAnalyses SplitComparesTransform::run(Module &M,
ModuleAnalysisManager &MAM) {
#else

View File

@ -102,7 +102,7 @@ class SplitSwitchesTransform : public ModulePass {
struct CaseExpr {
ConstantInt *Val;
BasicBlock * BB;
BasicBlock *BB;
CaseExpr(ConstantInt *val = nullptr, BasicBlock *bb = nullptr)
: Val(val), BB(bb) {
@ -182,7 +182,7 @@ BasicBlock *SplitSwitchesTransform::switchConvert(
unsigned ValTypeBitWidth = Cases[0].Val->getBitWidth();
IntegerType *ValType =
IntegerType::get(OrigBlock->getContext(), ValTypeBitWidth);
IntegerType * ByteType = IntegerType::get(OrigBlock->getContext(), 8);
IntegerType *ByteType = IntegerType::get(OrigBlock->getContext(), 8);
unsigned BytesInValue = bytesChecked.size();
std::vector<uint8_t> setSizes;
std::vector<std::set<uint8_t> > byteSets(BytesInValue, std::set<uint8_t>());
@ -221,8 +221,8 @@ BasicBlock *SplitSwitchesTransform::switchConvert(
/* there are only smallestSize different bytes at index smallestIndex */
Instruction *Shift, *Trunc;
Function * F = OrigBlock->getParent();
BasicBlock * NewNode = BasicBlock::Create(Val->getContext(), "NodeBlock", F);
Function *F = OrigBlock->getParent();
BasicBlock *NewNode = BasicBlock::Create(Val->getContext(), "NodeBlock", F);
Shift = BinaryOperator::Create(Instruction::LShr, Val,
ConstantInt::get(ValType, smallestIndex * 8));
NewNode->getInstList().push_back(Shift);
@ -403,9 +403,9 @@ bool SplitSwitchesTransform::splitSwitches(Module &M) {
BasicBlock *CurBlock = SI->getParent();
BasicBlock *OrigBlock = CurBlock;
Function * F = CurBlock->getParent();
Function *F = CurBlock->getParent();
/* this is the value we are switching on */
Value * Val = SI->getCondition();
Value *Val = SI->getCondition();
BasicBlock *Default = SI->getDefaultDest();
unsigned bitw = Val->getType()->getIntegerBitWidth();
@ -445,7 +445,7 @@ bool SplitSwitchesTransform::splitSwitches(Module &M) {
* round up bytesChecked (in case getBitWidth() % 8 != 0) */
std::vector<bool> bytesChecked((7 + Cases[0].Val->getBitWidth()) / 8,
false);
BasicBlock * SwitchBlock =
BasicBlock *SwitchBlock =
switchConvert(Cases, bytesChecked, OrigBlock, NewDefault, Val, 0);
/* Branch to our shiny new if-then stuff... */
@ -483,7 +483,7 @@ bool SplitSwitchesTransform::splitSwitches(Module &M) {
}
#if LLVM_VERSION_MAJOR >= 11 /* use new pass manager */
PreservedAnalyses SplitSwitchesTransform::run(Module & M,
PreservedAnalyses SplitSwitchesTransform::run(Module &M,
ModuleAnalysisManager &MAM) {
#else

View File

@ -1,4 +1,7 @@
#!/bin/bash
set -e
echo "================================================="
echo " Nyx build script"
echo "================================================="
@ -6,14 +9,14 @@ echo
echo "[*] Performing basic sanity checks..."
if [ ! "`uname -s`" = "Linux" ]; then
if [ ! "$(uname -s)" = "Linux" ]; then
echo "[-] Error: Nyx mode is only available on Linux."
exit 0
fi
if [ ! "`uname -m`" = "x86_64" ]; then
if [ ! "$(uname -m)" = "x86_64" ]; then
echo "[-] Error: Nyx mode is only available on x86_64 (yet)."
exit 0
@ -22,10 +25,10 @@ fi
echo "[*] Making sure all Nyx is checked out"
git status 1>/dev/null 2>/dev/null
if [ $? -eq 0 ]; then
git submodule init || exit 1
if git status 1>/dev/null 2>&1; then
git submodule init
echo "[*] initializing QEMU-Nyx submodule"
git submodule update ./QEMU-Nyx 2>/dev/null # ignore errors
echo "[*] initializing packer submodule"
@ -47,32 +50,27 @@ test -e QEMU-Nyx/.git || { echo "[-] QEMU-Nyx not checked out, please install gi
echo "[*] checking packer init.cpio.gz ..."
if [ ! -f "packer/linux_initramfs/init.cpio.gz" ]; then
cd packer/linux_initramfs/
sh pack.sh || exit 1
cd ../../
(cd packer/linux_initramfs/ && sh pack.sh)
fi
echo "[*] Checking libnyx ..."
if [ ! -f "libnyx/libnyx/target/release/liblibnyx.a" ]; then
cd libnyx/libnyx
cargo build --release || exit 1
cd ../../
(cd libnyx/libnyx && cargo build --release)
fi
echo "[*] Checking QEMU-Nyx ..."
if [ ! -f "QEMU-Nyx/x86_64-softmmu/qemu-system-x86_64" ]; then
cd QEMU-Nyx/
./compile_qemu_nyx.sh static || exit 1
cd ..
if ! dpkg -s gtk3-devel > /dev/null 2>&1; then
echo "[-] Disabling GTK because gtk3-devel is not installed."
sed -i 's/--enable-gtk//g' QEMU-Nyx/compile_qemu_nyx.sh
fi
(cd QEMU-Nyx && ./compile_qemu_nyx.sh static)
fi
echo "[*] Checking libnyx.so ..."
if [ -f "libnyx/libnyx/target/release/liblibnyx.so" ]; then
cp -v libnyx/libnyx/target/release/liblibnyx.so ../libnyx.so || exit 1
else
echo "[ ] libnyx.so not found..."
exit 1
fi
cp libnyx/libnyx/target/release/liblibnyx.so ../libnyx.so
echo "[+] All done for nyx_mode, enjoy!"
exit 0

View File

@ -273,7 +273,7 @@ echo "[+] Configuration complete."
echo "[*] Attempting to build QEMU (fingers crossed!)..."
make -j `nproc` || exit 1
make -j$(nproc) || exit 1
echo "[+] Build process successful!"

View File

@ -139,7 +139,7 @@ static void __compcov_load(void) {
char *bin_name = getenv("AFL_COMPCOV_BINNAME");
procmaps_iterator *maps = pmparser_parse(-1);
procmaps_struct * maps_tmp = NULL;
procmaps_struct *maps_tmp = NULL;
while ((maps_tmp = pmparser_next(maps)) != NULL) {

View File

@ -32,8 +32,8 @@ implied warranty.
*/
typedef struct procmaps_struct {
void * addr_start; //< start address of the area
void * addr_end; //< end address
void *addr_start; //< start address of the area
void *addr_end; //< end address
unsigned long length; //< size of the range
char perm[5]; //< permissions rwxp

View File

@ -1390,7 +1390,7 @@ DLMALLOC_EXPORT void *mspace_memalign(mspace msp, size_t alignment,
*/
DLMALLOC_EXPORT void **mspace_independent_calloc(mspace msp, size_t n_elements,
size_t elem_size,
void * chunks[]);
void *chunks[]);
/*
mspace_independent_comalloc behaves as independent_comalloc, but
@ -1399,7 +1399,7 @@ DLMALLOC_EXPORT void **mspace_independent_calloc(mspace msp, size_t n_elements,
DLMALLOC_EXPORT void **mspace_independent_comalloc(mspace msp,
size_t n_elements,
size_t sizes[],
void * chunks[]);
void *chunks[]);
/*
mspace_footprint() returns the number of bytes obtained from the
@ -2607,7 +2607,7 @@ typedef struct malloc_tree_chunk *tbinptr; /* The type of bins of trees */
struct malloc_segment {
char * base; /* base address */
char *base; /* base address */
size_t size; /* allocated size */
struct malloc_segment *next; /* ptr to next segment */
flag_t sflags; /* mmap and extern flag */
@ -2723,7 +2723,7 @@ struct malloc_state {
binmap_t treemap;
size_t dvsize;
size_t topsize;
char * least_addr;
char *least_addr;
mchunkptr dv;
mchunkptr top;
size_t trim_check;
@ -2739,7 +2739,7 @@ struct malloc_state {
MLOCK_T mutex; /* locate lock among fields that rarely change */
#endif /* USE_LOCKS */
msegment seg;
void * extp; /* Unused but available for extensions */
void *extp; /* Unused but available for extensions */
size_t exts;
};
@ -3593,7 +3593,7 @@ static void do_check_tree(mstate m, tchunkptr t) {
/* Check all the chunks in a treebin. */
static void do_check_treebin(mstate m, bindex_t i) {
tbinptr * tb = treebin_at(m, i);
tbinptr *tb = treebin_at(m, i);
tchunkptr t = *tb;
int empty = (m->treemap & (1U << i)) == 0;
if (t == 0) assert(empty);
@ -3886,11 +3886,7 @@ static void internal_malloc_stats(mstate m) {
mark_smallmap(M, I); \
else if (RTCHECK(ok_address(M, B->fd))) \
F = B->fd; \
else { \
\
CORRUPTION_ERROR_ACTION(M); \
\
} \
else { CORRUPTION_ERROR_ACTION(M); } \
B->fd = P; \
F->bk = P; \
P->fd = F; \
@ -4104,11 +4100,7 @@ static void internal_malloc_stats(mstate m) {
} \
if (RTCHECK(ok_address(M, RP))) \
*RP = 0; \
else { \
\
CORRUPTION_ERROR_ACTION(M); \
\
} \
else { CORRUPTION_ERROR_ACTION(M); } \
\
} \
\
@ -4278,7 +4270,7 @@ static mchunkptr mmap_resize(mstate m, mchunkptr oldp, size_t nb, int flags) {
size_t offset = oldp->prev_foot;
size_t oldmmsize = oldsize + offset + MMAP_FOOT_PAD;
size_t newmmsize = mmap_align(nb + SIX_SIZE_T_SIZES + CHUNK_ALIGN_MASK);
char * cp =
char *cp =
(char *)CALL_MREMAP((char *)oldp - offset, oldmmsize, newmmsize, flags);
if (cp != CMFAIL) {
@ -4412,14 +4404,14 @@ static void *prepend_alloc(mstate m, char *newbase, char *oldbase, size_t nb) {
static void add_segment(mstate m, char *tbase, size_t tsize, flag_t mmapped) {
/* Determine locations and sizes of segment, fenceposts, old top */
char * old_top = (char *)m->top;
char *old_top = (char *)m->top;
msegmentptr oldsp = segment_holding(m, old_top);
char * old_end = oldsp->base + oldsp->size;
char *old_end = oldsp->base + oldsp->size;
size_t ssize = pad_request(sizeof(struct malloc_segment));
char * rawsp = old_end - (ssize + FOUR_SIZE_T_SIZES + CHUNK_ALIGN_MASK);
char *rawsp = old_end - (ssize + FOUR_SIZE_T_SIZES + CHUNK_ALIGN_MASK);
size_t offset = align_offset(chunk2mem(rawsp));
char * asp = rawsp + offset;
char * csp = (asp < (old_top + MIN_CHUNK_SIZE)) ? old_top : asp;
char *asp = rawsp + offset;
char *csp = (asp < (old_top + MIN_CHUNK_SIZE)) ? old_top : asp;
mchunkptr sp = (mchunkptr)csp;
msegmentptr ss = (msegmentptr)(chunk2mem(sp));
mchunkptr tnext = chunk_plus_offset(sp, ssize);
@ -4473,7 +4465,7 @@ static void add_segment(mstate m, char *tbase, size_t tsize, flag_t mmapped) {
/* Get memory from system using MORECORE or MMAP */
static void *sys_alloc(mstate m, size_t nb) {
char * tbase = CMFAIL;
char *tbase = CMFAIL;
size_t tsize = 0;
flag_t mmap_flag = 0;
size_t asize; /* allocation size */
@ -4521,7 +4513,7 @@ static void *sys_alloc(mstate m, size_t nb) {
if (MORECORE_CONTIGUOUS && !use_noncontiguous(m)) {
char * br = CMFAIL;
char *br = CMFAIL;
size_t ssize = asize; /* sbrk call size */
msegmentptr ss = (m->top == 0) ? 0 : segment_holding(m, (char *)m->top);
ACQUIRE_MALLOC_GLOBAL_LOCK();
@ -4728,7 +4720,7 @@ static size_t release_unused_segments(mstate m) {
msegmentptr sp = pred->next;
while (sp != 0) {
char * base = sp->base;
char *base = sp->base;
size_t size = sp->size;
msegmentptr next = sp->next;
++nsegs;
@ -5151,7 +5143,7 @@ void *dlmalloc(size_t bytes) {
if (!PREACTION(gm)) {
void * mem;
void *mem;
size_t nb;
if (bytes <= MAX_SMALL_REQUEST) {
@ -5430,7 +5422,7 @@ void dlfree(void *mem) {
void *dlcalloc(size_t n_elements, size_t elem_size) {
void * mem;
void *mem;
size_t req = 0;
if (n_elements != 0) {
@ -5598,9 +5590,10 @@ static void *internal_memalign(mstate m, size_t alignment, size_t bytes) {
We've allocated enough total room so that this is always
possible.
*/
char * br = (char *)mem2chunk((size_t)(
((size_t)((char *)mem + alignment - SIZE_T_ONE)) & -alignment));
char * pos = ((size_t)(br - (char *)(p)) >= MIN_CHUNK_SIZE)
char *br = (char *)mem2chunk(
(size_t)(((size_t)((char *)mem + alignment - SIZE_T_ONE)) &
-alignment));
char *pos = ((size_t)(br - (char *)(p)) >= MIN_CHUNK_SIZE)
? br
: br + alignment;
mchunkptr newp = (mchunkptr)pos;
@ -5666,10 +5659,10 @@ static void **ialloc(mstate m, size_t n_elements, size_t *sizes, int opts,
size_t element_size; /* chunksize of each element, if all same */
size_t contents_size; /* total size of elements */
size_t array_size; /* request size of pointer array */
void * mem; /* malloced aggregate space */
void *mem; /* malloced aggregate space */
mchunkptr p; /* corresponding chunk */
size_t remainder_size; /* remaining bytes while splitting */
void ** marray; /* either "chunks" or malloced ptr array */
void **marray; /* either "chunks" or malloced ptr array */
mchunkptr array_chunk; /* chunk for malloced ptr array */
flag_t was_enabled; /* to disable mmap */
size_t size;
@ -5828,7 +5821,7 @@ static size_t internal_bulk_free(mstate m, void *array[], size_t nelem) {
*a = 0;
if (RTCHECK(ok_address(m, p) && ok_inuse(p))) {
void ** b = a + 1; /* try to merge with next chunk */
void **b = a + 1; /* try to merge with next chunk */
mchunkptr next = next_chunk(p);
if (b != fence && *b == chunk2mem(next)) {
@ -5865,7 +5858,7 @@ static size_t internal_bulk_free(mstate m, void *array[], size_t nelem) {
static void internal_inspect_all(mstate m,
void (*handler)(void *start, void *end,
size_t used_bytes,
void * callback_arg),
void *callback_arg),
void *arg) {
if (is_initialized(m)) {
@ -5880,7 +5873,7 @@ static void internal_inspect_all(mstate m,
mchunkptr next = next_chunk(q);
size_t sz = chunksize(q);
size_t used;
void * start;
void *start;
if (is_inuse(q)) {
used = sz - CHUNK_OVERHEAD; /* must not be mmapped */
@ -6113,7 +6106,7 @@ size_t dlbulk_free(void *array[], size_t nelem) {
#if MALLOC_INSPECT_ALL
void dlmalloc_inspect_all(void (*handler)(void *start, void *end,
size_t used_bytes,
void * callback_arg),
void *callback_arg),
void *arg) {
ensure_initialization();
@ -6253,7 +6246,7 @@ mspace create_mspace(size_t capacity, int locked) {
size_t rs = ((capacity == 0) ? mparams.granularity
: (capacity + TOP_FOOT_SIZE + msize));
size_t tsize = granularity_align(rs);
char * tbase = (char *)(CALL_MMAP(tsize));
char *tbase = (char *)(CALL_MMAP(tsize));
if (tbase != CMFAIL) {
m = init_user_mstate(tbase, tsize);
@ -6322,7 +6315,7 @@ size_t destroy_mspace(mspace msp) {
(void)DESTROY_LOCK(&ms->mutex); /* destroy before unmapped */
while (sp != 0) {
char * base = sp->base;
char *base = sp->base;
size_t size = sp->size;
flag_t flag = sp->sflags;
(void)base; /* placate people compiling -Wunused-variable */
@ -6360,7 +6353,7 @@ void *mspace_malloc(mspace msp, size_t bytes) {
if (!PREACTION(ms)) {
void * mem;
void *mem;
size_t nb;
if (bytes <= MAX_SMALL_REQUEST) {
@ -6628,7 +6621,7 @@ void mspace_free(mspace msp, void *mem) {
void *mspace_calloc(mspace msp, size_t n_elements, size_t elem_size) {
void * mem;
void *mem;
size_t req = 0;
mstate ms = (mstate)msp;
if (!ok_magic(ms)) {

View File

@ -97,19 +97,19 @@ void __libqasan_init_malloc(void);
void __libqasan_hotpatch(void);
size_t __libqasan_malloc_usable_size(void *ptr);
void * __libqasan_malloc(size_t size);
void *__libqasan_malloc(size_t size);
void __libqasan_free(void *ptr);
void * __libqasan_calloc(size_t nmemb, size_t size);
void * __libqasan_realloc(void *ptr, size_t size);
void *__libqasan_calloc(size_t nmemb, size_t size);
void *__libqasan_realloc(void *ptr, size_t size);
int __libqasan_posix_memalign(void **ptr, size_t align, size_t len);
void * __libqasan_memalign(size_t align, size_t len);
void * __libqasan_aligned_alloc(size_t align, size_t len);
void *__libqasan_memalign(size_t align, size_t len);
void *__libqasan_aligned_alloc(size_t align, size_t len);
void * __libqasan_memcpy(void *dest, const void *src, size_t n);
void * __libqasan_memmove(void *dest, const void *src, size_t n);
void * __libqasan_memset(void *s, int c, size_t n);
void * __libqasan_memchr(const void *s, int c, size_t n);
void * __libqasan_memrchr(const void *s, int c, size_t n);
void *__libqasan_memcpy(void *dest, const void *src, size_t n);
void *__libqasan_memmove(void *dest, const void *src, size_t n);
void *__libqasan_memset(void *s, int c, size_t n);
void *__libqasan_memchr(const void *s, int c, size_t n);
void *__libqasan_memrchr(const void *s, int c, size_t n);
size_t __libqasan_strlen(const char *s);
size_t __libqasan_strnlen(const char *s, size_t len);
int __libqasan_strcmp(const char *str1, const char *str2);
@ -118,12 +118,12 @@ int __libqasan_strcasecmp(const char *str1, const char *str2);
int __libqasan_strncasecmp(const char *str1, const char *str2, size_t len);
int __libqasan_memcmp(const void *mem1, const void *mem2, size_t len);
int __libqasan_bcmp(const void *mem1, const void *mem2, size_t len);
char * __libqasan_strstr(const char *haystack, const char *needle);
char * __libqasan_strcasestr(const char *haystack, const char *needle);
void * __libqasan_memmem(const void *haystack, size_t haystack_len,
char *__libqasan_strstr(const char *haystack, const char *needle);
char *__libqasan_strcasestr(const char *haystack, const char *needle);
void *__libqasan_memmem(const void *haystack, size_t haystack_len,
const void *needle, size_t needle_len);
char * __libqasan_strchr(const char *s, int c);
char * __libqasan_strrchr(const char *s, int c);
char *__libqasan_strchr(const char *s, int c);
char *__libqasan_strrchr(const char *s, int c);
size_t __libqasan_wcslen(const wchar_t *s);
wchar_t *__libqasan_wcscpy(wchar_t *d, const wchar_t *s);
int __libqasan_wcscmp(const wchar_t *s1, const wchar_t *s2);

View File

@ -51,7 +51,7 @@ typedef struct {
struct chunk_begin {
size_t requested_size;
void * aligned_orig; // NULL if not aligned
void *aligned_orig; // NULL if not aligned
struct chunk_begin *next;
struct chunk_begin *prev;
char redzone[REDZONE_SIZE];
@ -80,7 +80,7 @@ static unsigned char __tmp_alloc_zone[TMP_ZONE_SIZE];
#else
// From dlmalloc.c
void * dlmalloc(size_t);
void *dlmalloc(size_t);
void dlfree(void *);
#define backend_malloc dlmalloc
#define backend_free dlfree

View File

@ -130,8 +130,8 @@ int libc_perms;
static void find_libc(void) {
FILE * fp;
char * line = NULL;
FILE *fp;
char *line = NULL;
size_t len = 0;
ssize_t read;
@ -147,7 +147,7 @@ static void find_libc(void) {
fields = sscanf(line,
"%" PRIx64 "-%" PRIx64 " %c%c%c%c %" PRIx64
" %x:%x %d"
" %512s",
" %511s",
&min, &max, &flag_r, &flag_w, &flag_x, &flag_p, &offset,
&dev_maj, &dev_min, &inode, path);

View File

@ -28,7 +28,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
void *__libqasan_memcpy(void *dest, const void *src, size_t n) {
unsigned char * d = dest;
unsigned char *d = dest;
const unsigned char *s = src;
if (!n) return dest;
@ -47,7 +47,7 @@ void *__libqasan_memcpy(void *dest, const void *src, size_t n) {
void *__libqasan_memmove(void *dest, const void *src, size_t n) {
unsigned char * d = dest;
unsigned char *d = dest;
const unsigned char *s = src;
if (!n) return dest;

View File

@ -626,7 +626,7 @@ static void handle_stop_sig(int sig) {
static void set_up_environment(char **argv) {
u8 * x;
u8 *x;
char *afl_preload;
char *frida_afl_preload = NULL;

View File

@ -45,7 +45,7 @@
#define LLVM_MINOR 0
#endif
static u8 * obj_path; /* Path to runtime libraries */
static u8 *obj_path; /* Path to runtime libraries */
static u8 **cc_params; /* Parameters passed to the real CC */
static u32 cc_par_cnt = 1; /* Param count, including argv0 */
static u8 clang_mode; /* Invoked as afl-clang*? */
@ -53,7 +53,7 @@ static u8 llvm_fullpath[PATH_MAX];
static u8 instrument_mode, instrument_opt_mode, ngram_size, ctx_k, lto_mode;
static u8 compiler_mode, plusplus_mode, have_instr_env = 0;
static u8 have_gcc, have_llvm, have_gcc_plugin, have_lto, have_instr_list = 0;
static u8 * lto_flag = AFL_CLANG_FLTO, *argvnull;
static u8 *lto_flag = AFL_CLANG_FLTO, *argvnull;
static u8 debug;
static u8 cwd[4096];
static u8 cmplog_mode;
@ -422,8 +422,24 @@ static void edit_params(u32 argc, char **argv, char **envp) {
if (compiler_mode == GCC_PLUGIN) {
char *fplugin_arg = alloc_printf("-fplugin=%s/afl-gcc-pass.so", obj_path);
cc_params[cc_par_cnt++] = fplugin_arg;
char *fplugin_arg;
if (cmplog_mode) {
fplugin_arg =
alloc_printf("-fplugin=%s/afl-gcc-cmplog-pass.so", obj_path);
cc_params[cc_par_cnt++] = fplugin_arg;
fplugin_arg =
alloc_printf("-fplugin=%s/afl-gcc-cmptrs-pass.so", obj_path);
cc_params[cc_par_cnt++] = fplugin_arg;
} else {
fplugin_arg = alloc_printf("-fplugin=%s/afl-gcc-pass.so", obj_path);
cc_params[cc_par_cnt++] = fplugin_arg;
}
cc_params[cc_par_cnt++] = "-fno-if-conversion";
cc_params[cc_par_cnt++] = "-fno-if-conversion2";
@ -1879,6 +1895,7 @@ int main(int argc, char **argv, char **envp) {
if (have_gcc_plugin)
SAYF(
"\nGCC Plugin-specific environment variables:\n"
" AFL_GCC_CMPLOG: log operands of comparisons (RedQueen mutator)\n"
" AFL_GCC_OUT_OF_LINE: disable inlined instrumentation\n"
" AFL_GCC_SKIP_NEVERZERO: do not skip zero on trace counters\n"
" AFL_GCC_INSTRUMENT_FILE: enable selective instrumentation by "
@ -2149,9 +2166,8 @@ int main(int argc, char **argv, char **envp) {
}
cmplog_mode = getenv("AFL_CMPLOG") || getenv("AFL_LLVM_CMPLOG");
if (!be_quiet && cmplog_mode)
printf("CmpLog mode by <andreafioraldi@gmail.com>\n");
cmplog_mode = getenv("AFL_CMPLOG") || getenv("AFL_LLVM_CMPLOG") ||
getenv("AFL_GCC_CMPLOG");
#if !defined(__ANDROID__) && !defined(ANDROID)
ptr = find_object("afl-compiler-rt.o", argv[0]);

View File

@ -558,9 +558,9 @@ void print_suggested_envs(char *mispelled_env) {
for (j = 0; afl_environment_variables[j] != NULL; ++j) {
char * afl_env = afl_environment_variables[j] + 4;
char *afl_env = afl_environment_variables[j] + 4;
size_t afl_env_len = strlen(afl_env);
char * reduced = ck_alloc(afl_env_len + 1);
char *reduced = ck_alloc(afl_env_len + 1);
size_t start = 0;
while (start < afl_env_len) {
@ -598,7 +598,7 @@ void print_suggested_envs(char *mispelled_env) {
if (found) goto cleanup;
char * reduced = ck_alloc(env_name_len + 1);
char *reduced = ck_alloc(env_name_len + 1);
size_t start = 0;
while (start < env_name_len) {
@ -1197,7 +1197,7 @@ u8 *u_stringify_time_diff(u8 *buf, u64 cur_ms, u64 event_ms) {
u32 get_map_size(void) {
uint32_t map_size = DEFAULT_SHMEM_SIZE;
char * ptr;
char *ptr;
if ((ptr = getenv("AFL_MAP_SIZE")) || (ptr = getenv("AFL_MAPSIZE"))) {

View File

@ -57,7 +57,7 @@ void load_extras_file(afl_state_t *afl, u8 *fname, u32 *min_len, u32 *max_len,
FILE *f;
u8 buf[MAX_LINE];
u8 * lptr;
u8 *lptr;
u32 cur_line = 0;
u8 val_bufs[2][STRINGIFY_VAL_SIZE_MAX];
@ -291,10 +291,10 @@ static void extras_check_and_sort(afl_state_t *afl, u32 min_len, u32 max_len,
void load_extras(afl_state_t *afl, u8 *dir) {
DIR * d;
DIR *d;
struct dirent *de;
u32 min_len = MAX_DICT_FILE, max_len = 0, dict_level = 0;
u8 * x;
u8 *x;
u8 val_bufs[2][STRINGIFY_VAL_SIZE_MAX];
@ -330,7 +330,7 @@ void load_extras(afl_state_t *afl, u8 *dir) {
while ((de = readdir(d))) {
struct stat st;
u8 * fn = alloc_printf("%s/%s", dir, de->d_name);
u8 *fn = alloc_printf("%s/%s", dir, de->d_name);
s32 fd;
if (lstat(fn, &st) || access(fn, R_OK)) {

View File

@ -146,6 +146,10 @@ void bind_to_free_cpu(afl_state_t *afl) {
}
} else {
OKF("CPU binding request using -b %d successful.", afl->cpu_to_bind);
}
return;
@ -185,7 +189,7 @@ void bind_to_free_cpu(afl_state_t *afl) {
#if defined(__linux__)
DIR * d;
DIR *d;
struct dirent *de;
d = opendir("/proc");
@ -336,8 +340,8 @@ void bind_to_free_cpu(afl_state_t *afl) {
#elif defined(__sun)
kstat_named_t *n;
kstat_ctl_t * m;
kstat_t * k;
kstat_ctl_t *m;
kstat_t *k;
cpu_stat_t cs;
u32 ncpus;
@ -653,7 +657,7 @@ void read_testcases(afl_state_t *afl, u8 *directory) {
struct dirent **nl;
s32 nl_cnt, subdirs = 1;
u32 i;
u8 * fn1, *dir = directory;
u8 *fn1, *dir = directory;
u8 val_buf[2][STRINGIFY_VAL_SIZE_MAX];
/* Auto-detect non-in-place resumption attempts. */
@ -853,7 +857,7 @@ void perform_dry_run(afl_state_t *afl) {
struct queue_entry *q;
u32 cal_failures = 0, idx;
u8 * use_mem;
u8 *use_mem;
for (idx = 0; idx < afl->queued_items; idx++) {
@ -1457,7 +1461,7 @@ void find_timeout(afl_state_t *afl) {
static u8 delete_files(u8 *path, u8 *prefix) {
DIR * d;
DIR *d;
struct dirent *d_ent;
d = opendir(path);
@ -1585,7 +1589,7 @@ dir_cleanup_failed:
static void handle_existing_out_dir(afl_state_t *afl) {
FILE *f;
u8 * fn = alloc_printf("%s/fuzzer_stats", afl->out_dir);
u8 *fn = alloc_printf("%s/fuzzer_stats", afl->out_dir);
/* See if the output directory is locked. If yes, bail out. If not,
create a lock that will persist for the lifetime of the process
@ -1878,9 +1882,9 @@ dir_cleanup_failed:
int check_main_node_exists(afl_state_t *afl) {
DIR * sd;
DIR *sd;
struct dirent *sd_ent;
u8 * fn;
u8 *fn;
sd = opendir(afl->sync_dir);
if (!sd) { return 0; }
@ -2581,7 +2585,7 @@ void check_binary(afl_state_t *afl, u8 *fname) {
if (unlikely(!fname)) { FATAL("BUG: Binary name is NULL"); }
u8 * env_path = 0;
u8 *env_path = 0;
struct stat st;
s32 fd;

View File

@ -74,7 +74,7 @@ void setup_custom_mutators(afl_state_t *afl) {
/* Try mutator library first */
struct custom_mutator *mutator;
u8 * fn = afl->afl_env.afl_custom_mutator_library;
u8 *fn = afl->afl_env.afl_custom_mutator_library;
u32 prev_mutator_count = 0;
if (fn) {
@ -176,7 +176,7 @@ void destroy_custom_mutators(afl_state_t *afl) {
struct custom_mutator *load_custom_mutator(afl_state_t *afl, const char *fn) {
void * dh;
void *dh;
struct custom_mutator *mutator = ck_alloc(sizeof(struct custom_mutator));
mutator->name = fn;

Some files were not shown because too many files have changed in this diff Show More