summaryrefslogtreecommitdiff
path: root/_posts
diff options
context:
space:
mode:
authorJoseph Bisch <joseph.bisch@gmail.com>2018-01-25 06:25:49 -0500
committerGitHub <noreply@github.com>2018-01-25 06:25:49 -0500
commitee833153851ea5e41516e1c6366e6c8c9cd8d87d (patch)
tree512b80ff7f2d99b9c0d934bc62dbe1affcff0523 /_posts
parentd9b5c952dd9241de80d1fe132f8093859fa53d8c (diff)
parent5c8c22dac5988cf4868ab4cc36e7405699d2a026 (diff)
downloadirssi.github.io-ee833153851ea5e41516e1c6366e6c8c9cd8d87d.zip
Merge pull request #53 from josephbisch/add-pyircfuzz-blog-post
new blog entry: pyircfuzz
Diffstat (limited to '_posts')
-rw-r--r--_posts/2018-01-24-pyircfuzz.markdown132
1 files changed, 132 insertions, 0 deletions
diff --git a/_posts/2018-01-24-pyircfuzz.markdown b/_posts/2018-01-24-pyircfuzz.markdown
new file mode 100644
index 0000000..58db507
--- /dev/null
+++ b/_posts/2018-01-24-pyircfuzz.markdown
@@ -0,0 +1,132 @@
+---
+layout: post
+title: "PyIRCFuzz"
+author: "Joseph Bisch"
+email: "jbisch@irssi.org"
+---
+
+This blog post is a follow up to [my first post on this blog about fuzzing
+Irssi](https://irssi.org/2017/05/12/fuzzing-irssi/). This time we will look at
+using pyircfuzz instead of afl-fuzz.
+
+First we are going to get pyircfuzz itself and run it. Pyircfuzz acts as an IRC
+server, but it sends a variety of messages (not always well formed) to the IRC
+client(s) that are connected in an attempt to crash the client(s).
+
+```
+git clone https://github.com/josephbisch/pyircfuzz
+cd pyircfuzz
+python3 ircfuzz.py
+```
+
+Next we need to get Irssi and checkout 1.0.2, because we know it actually has
+bugs for us to find. Then, after we have built Irssi, we are going to run it
+and connect to the pyircfuzz instance on localhost and log the error output to
+a file.
+
+```
+git clone https://github.com/irssi/irssi
+cd irssi
+git checkout 1.0.2
+ASAN_OPTIONS=detect_leaks=0 ./autogen.sh CC=clang CFLAGS="-g -Og -fsanitize=address"
+make
+./src/fe-text/irssi -c localhost 2> asan.log
+```
+
+Here is a picture of what Irssi looks like at this point. It crashed so quickly
+(remember we are using an outdated version of Irssi) that I didn't have time to
+get a screenshot of the fuzzing in action.
+
+<img style="max-width:100%" src="/images/irssi_pyircfuzz_crash.png" />
+
+Here is the AddressSanitizer output (from asan.log):
+
+
+```
+ASAN:DEADLYSIGNAL
+=================================================================
+==31221==ERROR: AddressSanitizer: SEGV on unknown address 0x0000000000d8 (pc 0x55c7bc8f46da bp 0x611000019540 sp 0x7ffd110925a0 T0)
+==31221==The signal is caused by a READ memory access.
+==31221==Hint: address points to the zero page.
+ #0 0x55c7bc8f46d9 in dcc_request /home/joseph/irssi-blog-temp/irssi/src/fe-common/irc/dcc/fe-dcc-get.c:43:2
+ #1 0x55c7bc9b760c in signal_emit_real /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:242:3
+ #2 0x55c7bc9b717c in signal_emit /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:286:3
+ #3 0x55c7bc978f39 in ctcp_msg_dcc_send /home/joseph/irssi-blog-temp/irssi/src/irc/dcc/dcc-get.c:525:2
+ #4 0x55c7bc9b760c in signal_emit_real /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:242:3
+ #5 0x55c7bc9b717c in signal_emit /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:286:3
+ #6 0x55c7bc971658 in ctcp_msg_dcc /home/joseph/irssi-blog-temp/irssi/src/irc/dcc/dcc.c:371:7
+ #7 0x55c7bc9b760c in signal_emit_real /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:242:3
+ #8 0x55c7bc9b717c in signal_emit /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:286:3
+ #9 0x55c7bc9714c8 in ctcp_msg /home/joseph/irssi-blog-temp/irssi/src/irc/dcc/dcc.c:339:2
+ #10 0x55c7bc9b760c in signal_emit_real /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:242:3
+ #11 0x55c7bc9b717c in signal_emit /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:286:3
+ #12 0x55c7bc9693f4 in event_privmsg /home/joseph/irssi-blog-temp/irssi/src/irc/core/ctcp.c:287:3
+ #13 0x55c7bc9b760c in signal_emit_real /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:242:3
+ #14 0x55c7bc9b717c in signal_emit /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:286:3
+ #15 0x55c7bc940cb6 in irc_server_event /home/joseph/irssi-blog-temp/irssi/src/irc/core/irc.c:308:7
+ #16 0x55c7bc9b760c in signal_emit_real /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:242:3
+ #17 0x55c7bc9b7b76 in signal_emit_id /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:304:3
+ #18 0x55c7bc940f4e in irc_parse_incoming_line /home/joseph/irssi-blog-temp/irssi/src/irc/core/irc.c:362:3
+ #19 0x55c7bc9b760c in signal_emit_real /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:242:3
+ #20 0x55c7bc9b7b76 in signal_emit_id /home/joseph/irssi-blog-temp/irssi/src/core/signals.c:304:3
+ #21 0x55c7bc94121a in irc_parse_incoming /home/joseph/irssi-blog-temp/irssi/src/irc/core/irc.c:383:3
+ #22 0x55c7bc997b33 in irssi_io_invoke /home/joseph/irssi-blog-temp/irssi/src/core/misc.c:55:3
+ #23 0x7f82e17d80bd in g_main_context_dispatch (/usr/lib/libglib-2.0.so.0+0x6b0bd)
+ #24 0x7f82e17d9f68 (/usr/lib/libglib-2.0.so.0+0x6cf68)
+ #25 0x7f82e17d9fad in g_main_context_iteration (/usr/lib/libglib-2.0.so.0+0x6cfad)
+ #26 0x55c7bc8d8c30 in main /home/joseph/irssi-blog-temp/irssi/src/fe-text/irssi.c:321:3
+ #27 0x7f82e06a3f69 in __libc_start_main (/usr/lib/libc.so.6+0x20f69)
+ #28 0x55c7bc7af509 in _start (/home/joseph/irssi-blog-temp/irssi/src/fe-text/irssi+0x103509)
+
+AddressSanitizer can not provide additional info.
+SUMMARY: AddressSanitizer: SEGV /home/joseph/irssi-blog-temp/irssi/src/fe-common/irc/dcc/fe-dcc-get.c:43:2 in dcc_request
+==31221==ABORTING
+```
+
+In the pyircfuzz directory, there is an ircfuzz.log file. This is a list of all
+the IRC messages that the fuzzer sent to the IRC client leading up to the
+crash. So it should act as a reproducer. Make sure you rename it if you want to
+save it, because running pyircfuzz again will overwrite that file. I already
+know from the stacktrace that the crash happened in the DCC code. So I can do
+the following to filter out irrelevant lines from the reproducer:
+
+```
+grep -a "DCC" ircfuzz.log > ircfuzz-dcc.log
+```
+
+Pyircfuzz doesn't currently have a minimizer included, so you either have to
+figure out yourself what line(s) cause the crash or use a minimizer from
+another fuzzer like afl-tmin. But just greping for the lines with DCC in them
+already limits the number of lines to look through (at least in my case).
+
+You can reproduce the crash by doing the following:
+
+```
+cat ircfuzz.log | nc -l -p 6667
+```
+
+Then in another terminal:
+
+```
+./src/fe-text/irssi -c localhost
+```
+
+You should see the AddressSanitizer output in the terminal you ran Irssi in if
+the bug is indeed reproducible.
+
+### Conclusion
+
+I have found pyircfuzz to be an effective tool for fuzzing IRC clients. It has
+found bugs in Irssi that haven't been found other ways (such as with afl-fuzz
+or libfuzzer). Part of the reason is the ease of fuzzing the whole client
+without modification. That's not to say that afl-fuzz and libfuzzer aren't
+capable of finding these bugs if the proper fuzz targets are written, but it is
+just so easy to connect to the fuzzer as you would any other IRC server.
+
+I hope you find pyircfuzz useful. As usual, we would like to hear about any
+bugs you find, whether by fuzzing or other methods. You can report non-security
+bugs via the [Irssi GitHub repo](https://github.com/irssi/irssi). Security bugs
+can be reported to Irssi staff. Staff can be reached at staff@irssi.org.
+
+Also, patches to improve pyircfuzz are welcome via the [GitHub
+repo](https://github.com/josephbisch/pyircfuzz).