pax_global_header00006660000000000000000000000064130126073710014512gustar00rootroot0000000000000052 comment=d2338d20ff2ff8bd4f32da86d92b7f4b7b2383e9 sniffit-sniffit-0.4.0/000077500000000000000000000000001301260737100146155ustar00rootroot00000000000000sniffit-sniffit-0.4.0/AUTHORS000066400000000000000000000003451301260737100156670ustar00rootroot00000000000000Initial author, the Sniffit creator, active up to 0.3.7 beta version (between 1996 and 1998): - Brecht Claerhout Current authors: - Joao Eriberto Mota Filho sniffit-sniffit-0.4.0/CHANGELOG000066400000000000000000000102071301260737100160270ustar00rootroot00000000000000Version 0.4.0, 2016-11-15 [ Joao Eriberto Mota Filho ] * Added all patches from Debian. * Full conversion to autotools: - Previous configure.ac rewritten. - Created Makefile.am. - Created autogen.sh to use autoreconf (yes, it works fine now). * Removed embedded libpcap. * Removed the statement about libpcap from LICENSE file. * Reorganized the source code. * Several adjustments and fixes (including CVE-2014-5439). * Long life to sniffit! ############################################################################ ### ### ### THE FOLLOWING LINES ARE THE OLD CHANGELOG (UP TO 0.3.7 BETA VERSION) ### ### ### ############################################################################ #*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*# * Sniffit History * #*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*# BUGFIXES ---------- (PRIOR TO 0.2.0 - some are LINUX only) - Kernel 1.2.(some) incompatibility should be fixed. (like 1.2.5) (all credit for that to Godmar Back) - logging connections with lots of data is okay too now. 'the integer that needed to be a long'-bug. It was an overflow prob. - off course there are always minor ameliorations not worth mentioning (SINCE 0.2.0) - MAXCOUNT bug - interactive part lock-up bugs - output format (SINCE 0.3.0) - a wildcard bug - a Makefile bug (nothing important) (SINCE 0.3.1) - a typo caused the screwing up of the wildcard option (0.3.1) - 'select from host' didn't work... (SINCE 0.3.2) - a functions that had a parameter missing. - all interactive mode problems. (SINCE 0.3.3) - Interactive mode, with non-color-modes. - External program firing... (SINCE 0.3.4) - Interactive mode NON-IP packet detection. - errorhandeling starting of external programs from interface - various improvements for the porting (thx, beta-testers) (SINCE 0.3.5) - Seg fault on small Fragmented IP packets handled. - core dump bug fixed with unknown network devices NEW STUFF ----------- V.0.1.0 - First test of the ncurses interface (never use this version, it's megaslow) V.0.1.1 - Added '-x' for extra information on TCP packets - Added '-A ' for you 'password-horny-dudes' ;) - beginning of ICMP support ('-P ') - First 'real' test for the interface V.0.1.2 - IP debugging info - UDP support - extended ICMP info (almost complete....) - logging on another terminal V.0.2.0 - SUN port (I now hate SPARC's ;) V.0.2.1 - SGI port V.0.2.2 - Netload statistics (interactive part) - Massive debugging of interactive part V.0.3.0 - Wildcards in non-interactive mode - time-out in non interactive mode, so you won't stuff memory by connections that weren't closed like they're supposed to be. - Forcing the use of a snif device - MTU changeble in config.h - ppp use V.0.3.1 (1996) - Flexible network trafic selection with config file. V.0.3.2 (1996) - IP checksum check - First introduction of a logfile for monitoring - Adding of loglevel: 1, 10, 12 V.0.3.3 (Oct 1996) - rewrite of some parts (big clean-up of interactive part) - Auto adjusting to screen of interface - Starting of external programs from interface V.0.3.4 (Beta) - Use of Autoconf - Upgrade of Libpcap to 0.3 - Added Packet generation - Added UDP selectivity - Added "plugins" V.0.3.5 (April 1997) - cleaned out 0.3.4 beta V.0.3.6 (alpha, special HIP preview) - '-I' mode (locally refered to as 'Iliet' mode (pronounce in Dutch), officialy 'Extended Interactive') - alpha version session recording - alpha version 'sniffit_pb' added (concept canceled in 0.3.7) - an init function for plugins V.0.3.7 (July 1998) - Thrown away the old style recording, and changed the concept - Gracefull shutdown with restoring original interface mode ------------------------ Thx for using Sniffit(tm) --------------------------- sniffit-sniffit-0.4.0/CONTRIBUTING.md000066400000000000000000000014041301260737100170450ustar00rootroot00000000000000## HOW TO CONTRIBUTE TO SNIFFIT DEVELOPMENT Sniffit is available at https://github.com/eribertomota/sniffit If you are interested in contribute to sniffit development, please, follow these steps: 1. Send me a patch that fix an issue or that implement a new feature. Alternatively, you can do a 'pull request'[1] in GitHub. [1] https://help.github.com/articles/using-pull-requests 2. Ask for join to the Sniffit project in GitHub, if you want to work officially. Note that this second step is not compulsory. However, to accept you in project, I need a minimum collaboration before. You can do easy works, as fix compilatiion warnings. If you want to join, please contact me: eriberto at eriberto.pro.br -- Eriberto, Tue, 15 Nov 2016 09:40:21 -0200 sniffit-sniffit-0.4.0/CREDITS000066400000000000000000000033601301260737100156370ustar00rootroot000000000000000.4.0 version: - Cyril Brulebois Sent a patch to solve Debian bug #535506. It fixed a fail to build on GNU/kFreeBSD. - Hector Marco < hmarco@hmarco.org> and Ismael Ripoll written a fix for CVE-2014-5439 (Root shell on Sniffit). It was published at http://hmarco.org/bugs/CVE-2014-5439-sniffit_0.3.7-stack-buffer-overflow.html - James Westby Sent a patch to solve Debian bug #532581. It fixed crashes caused by missing #includes leads to wrong prototypes. - Joao Eriberto Mota Filho See the CHANGELOG. - Joshua Kwan Sent a patch to solve Debian bug #195548. It solved a fail with gcc-3.3. - LaMont Jones Sent a patch to solve Debian bug #103633. It fixed some issues in on-line program help. - Nicolas Sévelin-Radiguet Sent a patch to solve Debian bug #741125. I fixed a fail when building sniffit with clang. - Sebastian Harl Sent a patch to solve Debian bug #644978. It fixed a segfault on amd64. - "VDR dai \(deb\)" Sent a patch to solve Debian bug #649817. It enabled hardening options. - Debian maintainers over time, up to November 2016: 1997 Patrick J. Edwards 1998 Damjan Marion 1999 Hamish Moffatt 1999-2008 Edward Betts 2000-2002 Torsten Landschoff 2008-2012 William Vera 2011 HIGUCHI Daisuke (VDR dai) 2012 Aron Xu 2015-2016 Joao Eriberto Mota Filho (I am Eriberto, the current maintainer in Debian) sniffit-sniffit-0.4.0/LICENSE000066400000000000000000000026751301260737100156340ustar00rootroot00000000000000Sniffit 0.4.0 Copyright 1996-1998 Brecht Claerhout Copyright 2016 Joao Eriberto Mota Filho All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The name of the author may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. sniffit-sniffit-0.4.0/Makefile.am000066400000000000000000000010071301260737100166470ustar00rootroot00000000000000# Makefile.am for sniffit # Copyright 2016 Joao Eriberto Mota Filho # Under BSD-3-CLause license. SUBDIRS = src man_MANS = man/sniffit.5 man/sniffit.8 clean: rm -f src/*.o rm -f src/sniffit clean-local: rm -f aclocal.m4 rm -f compile rm -f configure rm -f config.cache rm -f config.log rm -f config.status rm -f depcomp rm -f install-sh rm -f Makefile rm -f Makefile.in rm -f missing rm -f stamp-h1 rm -rf autom4te.cache rm -rf config.h* rm -rf src/.deps rm -f src/Makefile rm -f src/Makefile.in sniffit-sniffit-0.4.0/README.md000066400000000000000000000037041301260737100161000ustar00rootroot00000000000000# SNIFFIT **Historical packet sniffer and monitoring tool**

**1. HELP THIS PROJECT**
**2. I AND SNIFFIT**
**2. WHAT IS AXEL?**
**3. BUILDING FROM SOURCE**
**4. LICENSE**
-------------------- 1. HELP THIS PROJECT -------------------- Sniffit needs your help. **If you are a programmer** and if you wants to help a nice project, this is your opportunity. My name is Eriberto and **I am not a C developer**. I imported Sniffit from Internet to GitHub (the original homepage and developer are inactive). After this, I applied all patches found in Debian project and other places for this program. All my initial work was registered in CHANGELOG file (version 0.4.0 and later releases). I also maintain Sniffit packaged in Debian[1]. If you are interested to help Axel, read the [CONTRIBUTING.md](CONTRIBUTING.md) file. [1] https://packages.qa.debian.org/s/sniffit.html
---------------- 2. I AND SNIFFIT ---------------- Well, sniffit is a very old packet sniffer, originally developed by Brecht Claerhout, between 1996 and 1998. This was the first program that I compiled in GNU/Linux (in 1997). So, I have a special fondness for this program. So, since 2015 I have maintained it as a package in Debian. Since November 2016 I am trying to maintain it in GitHub but I need help! Please, help this project (see above how to do it). ------------------- 3. WHAT IS SNIFFIT? ------------------- sniffit is a packet sniffer for TCP/UDP/ICMP packets over IPv4. It is able to give you a very detailed technical info on these packets, as SEQ, ACK, TTL, Window, etc. The packet contents also can be viewed, in different formats (hex or plain text, etc.). ----------------------- 4. BUILDING FROM SOURCE ----------------------- Run `./autogen.sh` to create the configure script, then run ./configure, make and make install. This program depends of the libpcap and libncurses. ---------- 5. LICENSE ---------- Sniffit is under BSD-3-Clause license. sniffit-sniffit-0.4.0/autogen.sh000077500000000000000000000044741301260737100166270ustar00rootroot00000000000000#!/bin/sh # autogen.sh with clean option, v0.2 # Copyright 2016 Joao Eriberto Mota Filho # # This file is under BSD-3-Clause license. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in the # documentation and/or other materials provided with the distribution. # 3. Neither the name of the authors nor the names of its contributors # may be used to endorse or promote products derived from this software # without specific prior written permission. # # THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND # ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE # ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE # FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL # DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS # OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) # HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY # OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF # SUCH DAMAGE. # Use clean option if [ "$1" = "clean" -a ! -e Makefile ] then echo "Vanishing the code" rm -rf aclocal.m4 autom4te.cache compile config.h.* configure depcomp \ .deps install-sh Makefile.in missing stamp-h1 src/Makefile.in echo "Done" exit 0 fi # Do not use clean option if [ "$1" = "clean" -a -e Makefile ] then echo "I can not clean. Use '$ make distclean'." exit 0 fi # Do autoreconf autoreconf -fi \ && { echo " "; \ echo "Done. You can use the 'clean' option to vanish the source code."; \ echo "Example of use: $ ./autogen.sh clean"; \ echo " "; \ echo "Now run ./configure, make, and make install."; \ } \ || { echo "We have a problem..."; exit 1; } sniffit-sniffit-0.4.0/configure.ac000066400000000000000000000034751301260737100171140ustar00rootroot00000000000000# configure.ac for sniffit # Copyright 1997-1998 Brecht Claerhout # Copyright 2016 Joao Eriberto Mota Filho # Under BSD-3-CLause license. AC_PREREQ([2.69]) AC_INIT([sniffit], [0.4.0], [https://github.com/eribertomota/sniffit/issues]) AC_CONFIG_SRCDIR([src/sn_generation.h]) AC_CONFIG_HEADERS([config.h]) # Checks for programs. AC_PROG_CC # Checks for libraries. AC_CHECK_LIB(ncurses, main, , [AC_MSG_ERROR([Couldn't find libncurses])]) AC_CHECK_LIB(pcap, pcap_open_live, , [AC_MSG_ERROR([Couldn't find libpcap])]) # Checks for header files. AC_CHECK_HEADERS([arpa/inet.h fcntl.h netdb.h netinet/in.h stdlib.h string.h sys/socket.h sys/time.h termios.h unistd.h]) AC_CHECK_HEADERS([ncurses.h], AC_DEFINE([HAVE_NCURSES_H], 1, [none]), AC_MSG_ERROR([ncurses.h not found])) AC_CHECK_HEADERS([pcap.h], , AC_MSG_ERROR([pcap.h not found])) # Checks for typedefs, structures, and compiler characteristics. AC_TYPE_SIZE_T # Checks for library functions. AC_FUNC_FORK AC_FUNC_MALLOC AC_FUNC_REALLOC AC_CHECK_FUNCS([alarm bzero gethostbyname socket strchr strdup strstr]) dnl Check Shared Memory support AC_CHECK_FUNCS(shmget) dnl exit function check AC_CHECK_FUNCS(atexit) # Other checks dnl Check the datalength AC_CHECK_SIZEOF(unsigned short int) if test $ac_cv_sizeof_unsigned_short_int -ne 2; then echo "unsigned short is NOT 2 bytes... quiting" exit fi AC_CHECK_SIZEOF(unsigned long int) if test $ac_cv_sizeof_unsigned_long_int -eq 4; then AC_DEFINE(USE_32_LONG_INT, 1, [none]) else echo "unsigned long is NOT 4 bytes... hmmm..." AC_CHECK_SIZEOF(unsigned int) if test $ac_cv_sizeof_unsigned_int -ne 4; then echo "unsigned int is NOT 4 bytes either... quiting" exit else AC_DEFINE(USE_32_INT, 1, [none]) fi fi AC_CONFIG_FILES([Makefile src/Makefile]) AM_INIT_AUTOMAKE([foreign]) AC_OUTPUT sniffit-sniffit-0.4.0/docs/000077500000000000000000000000001301260737100155455ustar00rootroot00000000000000sniffit-sniffit-0.4.0/docs/PLUGIN-HOWTO000066400000000000000000000141561301260737100173730ustar00rootroot000000000000001. What are Sniffit plugins (READ) 2. How to install a plugin (READ) 3. How to make a plugin (Only for programmers) 4. Contense of structs (Only for programmers) 5. Standard Plugins (READ) 1. What are Sniffit plugins --------------------------- Sniffit Plugins are a very fancy name for a very primitive system. The plugins allow you to add your own code to Sniffit without many problems. This has the advantage you can create your own sniffer within Sniffit, without having to worry about the packet filtering. 2. How to install a plugin -------------------------- Well, as I plan to release some plugins myself, and maybe ppl are going to share their own plugins, a little word on the installation. It's pretty simple, you get the plugin, put it in the sniffit directory and you edit the sn_plugin.h file like this: #define PLUGIN0_NAME "Dummy Plugin" #define PLUGIN0(x) main_plugin_function(x) #define PLUGIN0_INIT() init_plugin() /* (optional) */ #include "my_plugin.plug" Some notes: a) You can have plugins from 0 to 9 so PLUGIN0_NAME to PLUGIN1_NAME. Numbers don't have to be consecutive. (so also a PLUGIN0(x) to PLUGIN9(x) corresponding with the PLUGIN?_NAMES) b) The PLUGIN?_NAME contains the name that will be displayed when just typing sniffit. c) main_plugin_function should be a name provided by the author of the plugin. It is the name of the function that should be called by Sniffit. Details on this for making your own plugins are explained below. d) init_plugin() is also a function that can be provided by the author. Some plugins will not have an init function. e) #include "my_plugin.plug" Where my_plugin.plug is the name of the plugin source code file. 3. How to make a plugin ----------------------- I know it's primitive, but it pretty much works and is very easy. A plugins should consists of a function (here PL_dummy) void PL_dummy (struct Plugin_data *PLD) { .... } It's no problem to use several functions. It's no problem to use global data, as long as it doesn't interfer with sniffits global data (or other plugins global data). So it is wise to make all global variables and functions like: PL_nameofplugin_nameofvariable/function * NEW: If you define a PL_init_function * e.g: #define PLUGIN0_INIT() init_plugin() * * This function will be runned when Sniffit starts, and the plugin * is selected by the user, it is usefull for initialising some data. 4. Contense of structs ---------------------- NOTE: I don't use the standard structures for packets. This has it's 'historical' reasons, and has rather become a drag than a positive point. But it would be even a greater drag (time loss) to overturn everything completely and recode the appropriate parts of Sniffit, maybe I will do it someday, maybe I won't. I hope you can live with it... Notice you get a pointer to a structure ('struct Plugin_data *PLD') when your plugin is called. This structure is totally yours and you may modify it without any problems. It is defined as: struct Plugin_data { struct unwrap PL_info; struct IP_header PL_iphead; struct TCP_header PL_tcphead; struct UDP_header PL_udphead; unsigned char PL_data[MTU]; unsigned char PL_packet[MTU]; }; PL_info : contains some general usefull info PL_iphead : contains the IP_header (no options) PL_tcphead: contains the TCP_header if it is a TCP packet (no options) PL_udphead: contains the TCP_header if it is a UDP packet (no options) PL_data : contains the packet data (no headers) PL_packet : contains the entire packet Details on the Packet structures below (You know, the unconventional ones) (It is best that you grab your book on packets and have a look at the fields. The structures are composed the same way, and are an exact copy of those headers. So watch it! You might need to use ntohs() and ntohl() now and then!) (Have a look at the Dummy Plugin and the DNS Plugin for examples) struct IP_header /* The IPheader (without options) */ { unsigned char verlen, type; unsigned short length, ID, flag_offset; unsigned char TTL, protocol; unsigned short checksum; unsigned long int source, destination; }; struct TCP_header /* The TCP header (without options) */ { unsigned short source, destination; unsigned long int seq_nr, ACK_nr; unsigned short offset_flag, window, checksum, urgent; }; struct UDP_header /* The UDP header */ { unsigned short source, destination; unsigned short length, checksum; }; 5. Standard Plugins ------------------- There are 2 Plugins that are currently included in the distribution of Sniffit: A dummy Plugin, and a DNS Plugin. The Dummy Plugin: As it says, it does nothing ;) example: sniffit -M 0 -bN -t foo.bar Will output some useless information on the intercepted packet (that has passed the filtering you defined). Example of output: Dummy Plugin Report: IP header: 20 bytes TCP header: 20 bytes / 1 Databytes The DNS Plugin: The DNS plugin will examine any UDP packet that is passes the filter you have setup for sniffit from/to port 53. These packets are DNS packets, and that plugin will decode them and output some information to the standard output. e.g.: sniffit -M1 -N -P UDP -t @ Will examine all DNS traffic. An example of output is: DNS Sniffit Plugin Report: Packet: 111.33.111.11 53 -> 111.111.66.33 53 ID: 5782 STATUS: Answer (opcode: 0) , , , , rec. NOT Av. , ret: 0 Q: 1 Answ: 0 Auth: 2 Add: 2 Query: 21.158.245.200.in-addr.arpa. Type: 12 Class: IP Answer 1/4: 245.200.IN-ADDR.ARPA. Type: 2 Class: IP Answer 2/4: 245.200.IN-ADDR.ARPA. Type: 2 Class: IP Answer 3/4: DIXIT.ANSP.BR. Type: 1 Class: IP Data: 143.108.1.17. Answer 4/4: FPSP.FAPESP.BR. Type: 1 Class: IP Data: 143.108.1.1. sniffit-sniffit-0.4.0/docs/README.FIRST000066400000000000000000000671651301260737100173320ustar00rootroot00000000000000#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*# * Sniffit V.0.3.7 Beta * # By Brecht Claerhout # * * # This program is intended to demonstrate the unsafeness of TCP (currently) # * No illegal activities are encouraged! * # Please read the LICENSE file # * * # Sniffit grew a little upon its original intentions and is now # * extended for network debugging (UDP, ICMP, netload, etc.) * #*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*# * Libpcap library * # This product includes software developed by the Computer Systems # * Engineering Group at Lawrence Berkeley Laboratory. * #*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*#*# 0. Introduction, and some stuff you should know. 0.1 Credits and contact 0.2 Compiling 0.3 License 1. Programmers notes excuses for my incompetence 2. Use of the program flags and examples 3. Extra info on use 3.1 Running interactive mode 3.2 Forcing network devices (*READ*) 3.3 Format of the config file 3.4 Loglevels 4. The output 4.1 Normal 4.2 Logfile 5. IMPORTANT NOTES, READ! this also! ------------------------------------------------------------------------------ 0. Introduction, and some stuff you should know. ------------------------------------------------ 0.3.7 (Beta). It has been a while I know. But this year has been a hell, last year of uni, projects, thesis, .... it didn't stop. Well that is behind us now, the most important thing, is that I'm back working on the program again, and intend to keep on doing it. I hope you enjoy this beta version. Like always, I removed some bugs. There is a new 'logging' feature. It is now possible to record traffic with Sniffit and process it later! (it is completely different from the logging done in the 0.3.6 version, that is known to some hardcore Sniffit users) Please take a minute to skim through the text and read the passages marked with a '*', these are the new features. (Please read BETA-TESTING) I use the libpcap library developed at Berkeley Laboratory, for easy porting (Read the licence). 0.1 Credits and contact ----------------------- Credits go to (in order of appearance on the Sniffit scene): Wim Vandeputte , best friend and UNIX guru, for support, testing and providing me with a WWW site. Godmar Back, for fixing that kernel 1.2.X bug (Sniffit 0.1.X). Peter Kooiman, of Paradigm Systems Technology for providing the facilities to port Sniffit, and for the endless testing (although he laughs this away with "no big deal, I don't need no credits"). Without him, there would have been no ports at all. Brooke Paul, for providing me with an SGI account. Qing Long, for the bash/zsh libpcap/configure script. Guy Gustavson, for giving me a FreeBSD account. Woju , for the ncurses SunOS/FreeBSD fixing, and for his other efforts. Amlan Saha , for adding Packet Generation to Sniffit, and adding other features (not implemented yet). I'm sure that in the near future you will see more of his work in Sniffit. Shudoh Kazuyuki, for changing getaddrbyname() and improving the config-file interpreting. Fyodor , for pointing out the hideous small fragments problem. David O'Brien , for netbsd information. everybody, who ever mailed me with suggestions help, etc... Also a big thanks to my Beta testers (alphabetically, I hope)... Charles G Stuart IRIX / RedHat LINUX Patrick Schoppenhorst IRIX Shahid Mahmood Slackware LINUX / SunOS Stephen Hillier RedHat LINUX And many others who wish to be anonymous.... Suggestions and comments can be sent to: coder@reptile.rug.ac.be Brecht Claerhout Meulebeeksestw. 51 8700 Tielt Belgium The original distribution program can be obtained from (my site): http://sniffit.rug.ac.be/sniffit/sniffit.html MIND YOU: this program is run as root, and thus could easily contain dangerous trojans. If you get it from the above site you can safely compile and use it. (no trojan versions are discovered yet.. it's just a warning) 0.2 Compiling ------------- Just type 'configure' and then 'make' (if configure made it without errors). Mind you, you can still modify some things in the 'sn_config.h' file, but by default all sections that can be added on your system are added. IMPORTANT NOTES: 1. This source code has only been tested with GNU versions of make/C compiler. (i.e. don't come complaining to me if your 'native' system compiler screws up, use GNU!) 2. curses IS NOT equal to ncurses. (ncurses is available at your local sunsite mirror.) 3. READ THE FAQ when experiencing problems. Other stuff.... make clean : cleans all directories for a compiling from scratch 0.3 License (this is a copy of the LICENSE file) ----------- Sniffit 0.3.7 Copyright (c) 1996-1998 Brecht Claerhout All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The name of the author may not be used to endorse or promote products derived from this software without specific prior written permission. 4. Redistribution of source code must be conform with the 'libpcap' copyright conditions, if that library is included. THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 1. Programmers notes -------------------- I wasn't educated to be a programmer, so I write lousy code. Please forgive me. Still I note the use of shared memory, with Linux you should take extra care when recompiling your kernel! Answer YES to 'System V IPC (CONFIG_SYSVIPC) [y]'. 2. Use of the program --------------------- (The man pages have detailed info on what parameters you can mix) (* indicates New Features) Options: ONE of these is required! -v Show version and exit (just added because it's such a wide spread option) -t tells the sniffer to check out packets GOING TO -s tells the sniffer to check out packets COMING FROM You can use the '@' wildcard (only IP NUMBERS of course). e.g. -t 199.145.@ -t 199.14@ mind you -t @ is also a valid option. -i Interactive mode, overrides all other options * -I Extended Interactive mode, overrides all other options * Much more fun then -i, watch and enjoy... * (best viewed in a xterm that is stretched wide...) -c Use as a config file for Sniffit See 3.3 for format of the config file. NOTE: -t or -s only apply to TCP and UDP packages, ICMP, IP packages are ALL interpreted. Also, any selection on ports, -p only applies to TCP, UDP packages. Parameters for all modes: -F force sniffit to use a network device (READ 3.2 ON THIS SUBJECT, IMPORTANT) -n Turn off IP checksum checking. This can show you bogus packets. (mind you ARP, RARP, other non-IP packets will show up bogus too) (compatible with ALL options) -N Disables all functions that Sniffit has build in, useful for wanting to run ONLY a plugin Parameters for not running in -i: -b does both -t and -s, doesn't matter what function you used (-t or -s) -d Dump mode, shows the packets on the screen in bytes (not like tcpdump). For test purposes. (numbers are hex) -a same of '-d' but outputs ASCII. -x Prints extended info on TCP packets (SEQ numbers, ACK, Flags) Like SEQ, ACK, the flags, etc... (works wit '-a', '-d', '-s', '-t', '-b' or on its own.) (Mind you it is always shown on stdout, so not logged when using '-t', '-s', '-b' without another parameter) * -R Record all traffic in * This file can then be fed to Sniffit with the '-r' option. * -r This option feeds the recorded to Sniffit. This * option requires the '-F' option with the correct device. * Suppose you log a file on a machine with 'eth0'. When * feeding the logged file to sniffit, you will need to add '-F eth0' * or '-F eth' to the command line. * It doesn't need much explanation that using '-i' or '-I' * in combination with '-r' makes no sense (at this moment). -A When in logging mode, all non-printable chars will be replaced by . (see note below 4.The output) -P protocol specify the protocols examined (default TCP) possible options currently are: IP, TCP, ICMP, UDP They can be combined. -p Logs connections on port , 0 means all ports, default is 0 (all), look out with that on loaded nets! -l Amount of information to log (default 300 bytes). Length 0 logs everything. (look out with diskspace when logging everything!) -M Activate Plugin nr. , for a list on all plugins compiled in your version, just type 'sniffit'. Read all about Plugins in the PLUGIN-HOWTO (READ IT!) Parameters with -i,-I: -D All logging output will be send to that device. It's cool to get the same IRC screen as the guy y'r sniffing upon ;-) Parameters with -c: * -L enable logging with as 'loglevel' * 'loglevels' were not flexible enough I think, so I changed * the system to 'logparameters'. * can be a concatenation of any of these words: * * raw : Raw level * norm : Normal level * telnet: Log passwords (login port 23) * ftp : Log passwords (ftp port 21) * mail : Log mailinfo (mail port 25) * e.g 'ftpmailnorm' would be a valid * (see '2. The Output' for more info) Some examples: Imagine the following setup: 2 hosts on a subnet, one is running the sniffer (sniffit.com), the other one is 66.66.66.7 (target.com). 1. You want to test if the sniffer is working: sniffit:~/# sniffit -d -p 7 -t 66.66.66.7 and in another window: sniffit:~/$ telnet target.com 7 you should see the sniffer giving you packets as you telnet to the 'echo' service. 2. I want to log some passwords from people on 66.66.66.7: sniffit:~/# sniffit -p 23 -t 66.66.66.7 3. Root of target.com tells me he gets strange ftp connections and wants to find out the commands typed: sniffit:~/# sniffit -p 21 -l 0 -t 66.66.66.7 4. You want to read all incoming and outgoing mail on target.com: sniffit:~/# sniffit -p 25 -l 0 -b -t 66.66.66.7 & or sniffit:~/# sniffit -p 25 -l 0 -b -s 66.66.66.7 & 5. You want to use the menu based interface. sniffit:~/# sniffit -i 6. Something is really wrong and you want to see the Control Messages with error codes. sniffit:~/# sniffit -P icmp -b -s 66.66.66.7 7. Go wild on scrolling the screen. sniffit:~/# sniffit -P ip -P icmp -P tcp -p 0 -b -a -d -x -s 66.66.66.7 witch is the same as sniffit:~/# sniffit -P ipicmptcp -p 0 -b -a -d -x -s 66.66.66.7 8. Log passwords in that way you can read them with 'more 66*' sniffit:~/# sniffit -p 23 -A . -t 66.66.66.7 or sniffit:~/# sniffit -p 23 -A ^ -t dummy.net 9. This could go on for ever.............. 3. Extra info on use -------------------- 3.1 Running interactive mode ---------------------------- When running in interactive mode: UP or 'k' : self explanatory DOWN or j': self explanatory F1 or '1' : Enter a host (enter 'all' for no mask) for packet filtering (host that sends the packets) F2 or '2' : Enter a host (enter 'all' for no mask) for packet filtering. (host that receives the packets) F3 or '3' : Enter a port (enter '0' for no mask) for packet filtering. (host that sends the packets) F4 or '4' : Enter a port (enter '0' for no mask) for packet filtering. (host that receives the packets) F5 or '5' : Start a program 'sniffit_key5' with arguments If the program doesn't exist, nothing is done. Sniffit should be in the same path as sniffit was STARTED FROM (not necessarily the path sniffit is stored in) This is useful for interactive connection killing or extra monitoring. A little shell script can always transform the arguments given and pass them on to other programs. F6 or '6' : Same as F5 or '5', but with program 'sniffit_key6' F7 or '7' : Same as F5 or '5', but with program 'sniffit_key7' F8 or '8' : Same as F5 or '5', but with program 'sniffit_key8' ENTER : a window will pop up and log the connection, or the connection output will be send at a chosen device if you used the '-D' option. 'q' : When in logging mode, stop logging. Otherwise, quit. 'n' : Toggle netstatistics. These are sampled at 3 secs, look in the config.h file to change this (could be needed if y'r computer is slow). 'g' : Generate Packets! Sniffit is now able to generate some traffic load. Currently this is a 'underdeveloped' feature with very few options, but it will be expanded a lot... Currently only UDP packets are generated. When pressing 'G' you will be asked the source/dest IP/port and how many packets are to be transmitted. Packets contain the line: "This Packet was fired with Sniffit!" 'r' : Reset.. clears all current connections from memory and restarts. 3.2 Forcing network devices (*READ*) -------------------------------------- NOTE: the correct name (for sniffit) of a device can be found by running 'ifconfig', 'route', ... When forcing network devices, sniffit tries to find out what device it is. If sniffit recognises the name, everything is okay. If it does not recognise the name it will set the ethernet headlength according to the compiled-in value FORCED_HEAD_LENGTH. The ethernet headlength is the length in bytes of an ethernet packet header. So if you have to force a non-ethernet device that is not recognised by sniffit, make sure you change that headlength correctly in the 'sn_config.h' file. The -F option was added, because I noticed device names can differ from system to system, and because some ppl have multiple devices present. When having problems with this option, please think twice before you mail me. e.g: sniffit -F eth1 -t foobar.com -dx Notice you don't have to add /dev/ (some ppl mentioned me this was not completely clear). 3.3 Format of the config file ----------------------------- The configfile should have lines with the following format: [] (separators are spaces (any number of), NO TABS!!!) Lines that don't match this pattern are discarded, so standard unix comments '#' can be used in this file... (this also means that if you have a typo there, Sniffit won't report it but just discard the line) * Be sure to end the file with a blank line. If you don't do so, the last * line of the command file will be ignored. (read this list, even if you don't get it at first, it will become clear in the examples) can be: select : Sniffit will look for packets that match the following description (other fields) deselect : Sniffit will ignore packets that match the description logfile : change the logfile name to instead of the default 'sniffit.log' can be: from : Packets FROM the host matching the following desc. are considered to : similar, Packets TO the.... both : similar, Packets FROM or TO the.... a filename : as an argument of 'logfile' in can be: host : The (de)selection criteria involves a hostname. port : similar, ... a portnumber mhosts : The (de)selection criteria involves multiple-hosts, like with the wildcards in 0.3.0, but without the 'x' can be: * either a hostname, a portnumber, a service name or a number-dot partial * notation indicating multiple hosts depending on * (service names like 'ftp' are resolved as the services available * present on the host that runs Sniffit, and translated into a port nr) can be: a portnumber or service name, if was 'host' or 'mhosts' Maybe it would have been wise to mention explicitly, that the config-file currently only works with TCP packets. examples: 1. Look at this configuration file: select from host 100.100.12.2 select from host 100.100.12.3 1400 select to host coder.sniffit.com select both port 23 This file would cause Sniffit to give you the packets: a) Send by host 100.100.12.2 b) Send by host 100.100.12.3 from port 1400 c) Send to coder.sniffit.com d) All packets on our subnet going to or coming from a telnet port. 2. another example: select both mhosts 100.100.12. deselect both port 80 select both host enemy.sniffit.com This file would cause Sniffit to give you the packets: a) Send by hosts '100.100.12.*' b) EXCEPT the WWW packets c) BUT showing the WWW packets concerning enemy.sniffit.com The config file is interpreted SEQUENTIALLY, so mixing up those lines could have unwanted results e.g.: select both mhosts 100.100.12. select both host enemy.sniffit.org deselect both port 80 This will give you the packets: a) Send by hosts '100.100.12.*' b) Send from/to enemy.sniffit.org c) deselecting all WWW packets on the subnet So if someone on enemy.sniffit.org is netscaping (assuming his 'target' has his httpd installed on port 80), you would see the packets with the first config file, BUT NOT with the second file, and that could spoil y'r fun when he's surfing to some kinky page. 3. example: select both mhosts 1 select both mhosts 2 deselect both mhosts 1 80 deselect both mhosts 2 80 This would show you all subnet traffic excluding WWW traffic (concerning port 80.) 4. example: * select both host target.com 21 * and * select both host target.com ftp * are equal configurations. NOTE: Everything is DESELECTED by default, so an empty config file will get you nothing. 3.4 Loglevels ------------- * The system of loglevels was not flexible enough, so I changed it. I expect * you will like it more this way. * * Loglevels are now activated by '-L '. * The following 's are valid (concatenation is allowed): * * 'raw': * Log all SYN, FIN, RST packets. This will give you an overview of * all network (TCP) traffic in a 'RAW' way (a connection starting could * give you at least 2 SYN packets, etc...). * This is a great way to waste diskspace... * Messages are: * Connection initiated. (SYN) * Connection ending. (FIN) * Connection reset. (RST) * * 'norm' (levels 10-29) * Same as 'raw', but a bit more intelligent. Unless packets are * transmitted multiple times because of packet loss, you will * only get 1 notice of a connection starting or ending. (the packet id * will state the host that initiated the connection first) * Messages are: * Connection initiated. * Connection closed. * * 'telnet': * Sniffit will try to catch user and passwords for the telnet login * on port 23. * * NOTE: * We only try to catch the first attempt, so if someone fails the * first login, you will miss his password. * A '~' in the login and passwords fields can be a nonprintable * character (if in the beginning of a field, probably due to an early * start of registration) or a '~'. * This all makes it sound a little messy, but I 'test-drove' a lot and * was pleased with the results after adding some funky shit (if y'r * interested have a look at in function 'packethandler' in * sniffit.*.c) * * 'ftp': * Sniffit will try to catch user and passwords for ftp sessions * on port 21. * * NOTE: * Easy catching. Even multiple tries are registered. * * 'mail': * Interested in who writes mail to who? Well you get all senders and * recipients nicely logged with this feature (port 25 mail). 4. The output ------------- 4.1 Normal ---------- - IP header info (not logged, displayed): Examples: from 100.100.60.80 to 100.100.69.63 IP Packet precedence: Routine (-T-) FLAGS: -- -- Time to live (secs): 59 Protocol (6): TCP from 100.100.69.31 to 100.100.69.63 IP Packet precedence: Routine (---) FLAGS: -- -- Time to live (secs): 60 Protocol (17): UDP from 100.100.69.51 to 100.100.69.63 IP Packet precedence: Routine (---) FLAGS: -- -- Time to live (secs): 255 Protocol (1): ICMP explanation: Precedence can be: Routine, Priority, Immediate, Flash, Flash override, Critical, Internetwork Control, Network control The Flags between brackets: (DTR) Delay-Throughput-reliability FLAGS: DF MF DF=Don't Fragment MF=More Fragments - TCP Packets (logged or displayed): The sniffer logs the data in ascii format. So when logging telnet connections, you will need to use 'joe' or something else that can support control chars (look for '-A ' below). Telnet 'negotiates' (binary) in the beginning of every connection, and 'catting' an output file, will most of the time show nothing (due to control chars). Of course when logging mail, there are no problems. The new '-A ' takes care of the control characters, that way you will be able to read the logfiles with 'more', 'vi', etc... -a and -d give you raw packets i.e. not unwrapped, on the screen (nothing is logged), -x gives you more info on the TCP package (everything is still logged unless using -a or -d mode), The flags are: U: Urgent pointer significant A: Acknowledgement is signif (will be shown) P: Push function R: Reset the connection S: Synchronizes sequence numbers F: No more data from sender (end connection) Filenames Created: Imagine a subnet with the hosts 66.66.66.66 and 66.66.66.7, and we run a sniffer on the first. The sniffer creates the following files: When logging packets TO host 66.66.66.7 (-t 66.66.66.7) files like 77.77.7.7.15000-66.66.66.7.23 are created, when the data CAME FROM host 77.77.7.7-15000 (with 15000 port used on 77.77.7.7 for that connection, and received on port 23 of 66.66.66.7) When logging packets FROM host 66.66.66.7 (-s 66.66.66.7) files like 66.66.66.7.15000-77.77.7.7-23 are created, when the data GOES TO host 77.77.7.7 (with 15000 port used on 66.66.66.7 for that connection) - ICMP Packets (not logged, displayed): On host 100.100.69.63 someone tried 'telnet 100.100.23.23' Suppose this host is unreachable, this could be a possible output: ICMP message id: 100.100.69.254 > 100.100.69.63 ICMP type: Destination unreachable Error: Host unreachable ICMP message concerned following IP packet: from 100.100.69.63 to 100.100.23.23 IP Packet precedence: Routine (---) FLAGS: -- -- Time to live (secs): 63 Protocol (6): TCP - UDP Packets (not logged, displayed) You get the package id. When using -d, -a you get the contents of the package. (pretty basic) 4.2 Logfile ----------- If you use a configfile (-c) and enable the Logging option, a logfile is created. Unless you set 'logfile' in the config file, that file will be named 'sniffit.log'. It will contain lines with the following FIXED format: 1) Date - Connection id.: message e.g. [Mon Aug 19 22:38:56 1996] - 100.100.10.10.1046-110.110.11.11.23: Connection initiated. (conn. init. on the same line as the rest) 2) Except the starting line and the ending line of each session, they are: [Mon Aug 19 22:38:51 1996] - Sniffit session started. [Mon Aug 19 22:39:44 1996] - Sniffit session ended. 3) Lines containing other data (future versions), will NOT begin with '[' and will have also easily interpretable formats. Other data is e.g. packet contents I do this because I can imagine (when this is more expanded) that people will use their own parsers for these logfiles. Well, if you respect those 3 rules, your parser will work on all future versions of Sniffit. 5. IMPORTANT NOTES, READ! ------------------------- First of all, some stuff people who use this program should already know, if you don't, well here ya got it: Some other notes: - Sniffers can only be run by ROOT - Sniffers can only log packets that 'travel' on THEIR ethernet cable. So there has to be some host on your subnet involved (either as sender or receiver). - Working with '-d' or '-a' gives you raw packets, they are still packed in IP, when logging to files, only sent data is logged, the packets are 'unwrapped'. - Sniffers can NORMALLY not be detected by outsiders (or outsiders SHOULD not be able to...). Unfortunately some systems contain bugs that will allow outsiders to probe your network device for PROMISC mode (which is a good indication for 'sniffer running') - (LINUX) Your KERNEL should support System V IPC. If you will use '-i' or '-I'. - (BSD systems) Your KERNEL should have BPF included. ------------------------ Thx for using Sniffit(tm) --------------------------- sniffit-sniffit-0.4.0/docs/UPDATE-CHECK000066400000000000000000000003031301260737100172610ustar00rootroot00000000000000When updating, change these files (if needed): - AUTHORS - ChangeLog - CREDITS - configure.ac (VERSION) - manpage version and date - src/sn_defines.h (VERSION) (check copyright years in header) sniffit-sniffit-0.4.0/docs/old-docs/000077500000000000000000000000001301260737100172515ustar00rootroot00000000000000sniffit-sniffit-0.4.0/docs/old-docs/BETA-TESTING000066400000000000000000000046661301260737100210360ustar00rootroot00000000000000This is a beta version, that means that some things need testing or fine-tuning. This file includes the things I would like to be informed about. So if you are able to test one of these things, please do so and mail me back the results. (coder@reptile.rug.ac.be) 1. LINUX 2. SunOS/Solaris 3. Irix 4. FreeBSD 5. BSDi 6. DEC/OSF 7. NetBSD ----------------------------------------------------------------------------- 1. LINUX - Does sniffing a SLIP connection work? 2. SunOS/Solaris 3. Irix - Does sniffing a PPP connection work? If sniffit just sits there, doing nothing, try changing (sn_data.h) #ifdef IRIX #define NETDEV_NR 2 char *NETDEV[]={"ppp","et"}; int HEADSIZE[]={0 ,14}; /* ppp: 4 or 0 or nothing */ #endif to: #ifdef IRIX #define NETDEV_NR 2 char *NETDEV[]={"ppp","et"}; int HEADSIZE[]={4 ,14}; /* ppp: 4 or 0 or nothing */ #endif 4. FreeBSD - Does sniffing a PPP connection work? To try this, remove the lines that are marked below with X in the sn_data.h file: #ifdef FREEBSD /* ppp: 4 or 0 ? */ /* X #define NETDEV_NR 2 char *NETDEV[]={"ppp","ed"}; int HEADSIZE[]={4 ,14}; */ X #define NETDEV_NR 1 X char *NETDEV[]={"ed"}; X int HEADSIZE[]={14}; X #endif If it doesn't work, and sniffit just sits there, try changing: int HEADSIZE[]={4 ,14}; to: int HEADSIZE[]={0 ,14}; 5. BSDi - Does sniffing a PPP connection work? To try this, remove the lines that are marked below with X in the sn_data.h file: #ifdef BSDI /* ppp: 4 or 0 ? */ /* X #define NETDEV_NR 2 char *NETDEV[]={"ppp","ef"}; int HEADSIZE[]={4 ,14}; */ X #define NETDEV_NR 1 X char *NETDEV[]={"ef"}; X int HEADSIZE[]={14}; X #endif If it doesn't work, and sniffit just sits there, try changing: int HEADSIZE[]={4 ,14}; to: int HEADSIZE[]={0 ,14}; 6. DEC/OSF 7. NetBSD - Does sniffing a PPP connection work? If sniffit just sits there, doing nothing, try changing the sn_data.h file. Search the line: #ifdef NETBSD from there on change in every "int HEADSIZE[]={}" the 4 to a 0. e.g.: int HEADSIZE[]={4 ,14 ,14}; becomes: int HEADSIZE[]={0 ,14 ,14}; sniffit-sniffit-0.4.0/docs/sniffit-FAQ000066400000000000000000000062301301260737100175400ustar00rootroot00000000000000------[ The Sniffit-FAQ V.0.2]------------------------------------------------ As the same questions keep popping up in my mailbox, I decided to write a Sniffit-FAQ. ------[ The Questions ]------------------------------------------------------- 1. 'sniffit -i' doesn't work. It says unknown option. 1.b. I'm sure I have NCURSES, but I still have that problem! 2. I can only see packets to/from my own computer, what is wrong? (BTW: I'm on PPP). 3. I have e.g. to ethernetcards, but 'sniffit -F /dev/eth1' doesn't work, why? 4. How can I find the device names? 5. Why can't my LINUX capture packets? 6. Why can't my BSD style system capture packets? ------[ The Answers ]--------------------------------------------------------- 1. 'sniffit -i' doesn't work. It says unknown option. Prior to 0.3.5 you had to configure Sniffit manual, that was a drag, so I made it configure itself. Problem now is that it is too automatic. When running the 'configure' script, it looks for 'ncurses' (which is needed for the interactive mode), when it does not find 'ncurses', it just excludes interactive mode, so '-i' becomes an unknown option. Solution: if you haven't got 'ncurses', install it (to be found at any sunsite mirror). If you are sure you have it, well it probably isn't in the right directories, maybe use some symbolic links. These are the dirs 'configue' looks in: /usr/include:/usr/include/ncurses:/usr/include/curses /usr/local/include:/usr/local/include/ncurses: /usr/local/include/curses and as of 0.3.6 Sniffit also looks in: ./:./ncurses (BTW: it looks for a file 'ncurses.h') 1.b. I'm sure I have NCURSES, but I still have that problem! Sometimes you have NCURSES, but no 'ncurses.h' file. Simple, just link (soft) 'ncurses.h' to 'curses.h'. 2. I can only see packets to/from my own computer, what is wrong? (BTW: I'm on PPP) PPP: Point to Point connection. Per defenition, this protocol will only carry packets that contain information for the connected computer. As a consequence on your side, you see only things that got to/come from your computer, so Sniffit works fine. To see traffic of whole subnets, you need protocols like ethernet (the coax cable). 3. I have e.g. to ethernetcards, but 'sniffit -F /dev/eth1' doesn't work, why? Don't put any path in front of the devices. These names aren't even listed in /dev/. The correct line would be: 'sniffit -F eth1' 4. How can I find the device names? Well in case Sniffit doesn't find the correct name itself, you will have to find it, and use the '-F' parameter. The devices can be found by using the 'ifconfig' or 'route' commands. 5. Why can't my LINUX capture packets? You should upgrade the kernel. Normally Sniffit should work on all kernels older then 2.0.0. But I advise using a kernel older then 2.0.25. (You could also downgrade the libpcap version to that used wityh Sniffit 0.3.3 if all else fails) 6. Why can't my BSD style system capture packets? You should recompile your kernel with BPF support. ------[ The End ]------------------------------------------------------------- sniffit-sniffit-0.4.0/examples/000077500000000000000000000000001301260737100164335ustar00rootroot00000000000000sniffit-sniffit-0.4.0/examples/sample_config_file000066400000000000000000000004331301260737100221630ustar00rootroot00000000000000# Sniffit V.0.3.3-0.3.7 Sample Config file -- Brecht Claerhout # First select all packets! select both mhosts 1 select both mhosts 2 # Now deselect all packets from/to those damn 'surfers' deselect both port 80 deselect both port 8001 # Be sure to end this file with a blank line!sniffit-sniffit-0.4.0/man/000077500000000000000000000000001301260737100153705ustar00rootroot00000000000000sniffit-sniffit-0.4.0/man/sniffit.5000066400000000000000000000063051301260737100171240ustar00rootroot00000000000000.\" sniffit config file man page - Brecht Claerhout .\" Some fixes by Joao Eriberto Mota Filho .\" .TH SNIFFIT 5 .SH NAME sniffit \- configuration file for sniffit (name arbitrary) .SH DESCRIPTION This page describes the format for the config file for .B sniffit (see .BR sniffit (8) ). This file allows you to specify in great detail witch packets should be processed by .B sniffit. This file also controls (or will control) some functions for the continuous logging ('\-L' option). .LP A .B sniffit config file might look like (Be sure to end it with a BLANK line): .IP .nf # Sniffit Sample Config file -- Brecht Claerhout logfile /var/log/sniffit.today.log # First select all packets! select both mhosts 1 select both mhosts 2 # Now deselect all packets from/to those damn 'surfers' deselect both port 80 deselect both port 8001 .fi .LP This file will tell .B sniffit to process all packets on the subnet except those FROM/TO ports 80 and 8001 (thus we don't want logs of those mass WWW connections witch turn our logs unreadable). .SH "GLOBAL FORMAT" The file consists of lines, lines are formed by fields, fields are separated with SPACES (NO TABS). Unix comment lines (starting with '#' are allowed). So this gives us: .IP .SH "FIELD FORMAT" .IP "" .B select - .B Sniffit will look for packets that match the following description (other fields) .IP .B deselect - .B Sniffit will ignore packets that match the description .IP .B logfile - change the logfile name to instead of the default 'sniffit.log' .IP "" .B from - Packets FROM the host matching the following desc. are considered. .IP .B to - similar, Packets TO the.... .IP .B both - similar, Packets FROM or TO the.... .IP .B "a filename" - as an argument of 'logfile' in .IP "" .B host - The (de)selection criteria involves a hostname. .IP .B port - similar, ... a portnumber .IP .B mhosts - The (de)selection criteria involves multiple-hosts, like with the wildcards in 0.3.0, but without the 'x' .IP "" Either a hostname, a portnumber, a service name or a number-dot partial notation indicating multiple hosts depending on (service names like 'ftp' are resolved as the services available present on the host that runs Sniffit, and translated into a port nr) .IP "" A portnumber, if was 'host' or 'mhosts' (optional, if not filled in, all ports are going to be (de)selected) .SH "FILE INTERPRETING" The config file is interpreted SEQUENTIAL, so watch it, don't mix lines in a file. Example: .IP .nf select both mhosts 100.100.12. deselect both port 80 select both host 100.100.12.2 This file will get you the packets: a) Send by hosts '100.100.12.*' b) EXCEPT the WWW packets c) BUT showing the WWW packets concerning 100.100.12.2 .fi .IP .nf select both mhosts 100.100.12. select both host 100.100.12.2 deselect both port 80 Will give you the packets (probably unwanted result): a) Send by hosts '100.100.12.*' b) Send from/to 100.100.12.2 (useless line) c) deselecting all WWW packets on the subnet .SH AUTHOR Brecht Claerhout .SH "SEE ALSO" .BR sniffit (8) sniffit-sniffit-0.4.0/man/sniffit.8000066400000000000000000000232021301260737100171220ustar00rootroot00000000000000.\" Sniffit man page file - Brecht Claerhout .\" Some fixes by Joao Eriberto Mota Filho .\" Process this file with .\" groff -man -Tascii foo.1 .\" .TH SNIFFIT 8 .SH NAME sniffit \- packet sniffer and monitoring tool .SH SYNOPSIS .B sniffit [-xdabvnN] [-P .I proto .B ] [-A .I char .B ] [-p .I port .B ] [(-r|-R) .I recordfile .B ] [-l .I sniflen .B ] [-L .I logparam .B ] [-F .I snifdevice .B ] [-D .I tty .B ] [-M .I plugin .B ] [(-t .I Target-IP .B | -s .I Source-IP .B ) | (-i|-I) | -c .I config-file .B ] .SH DESCRIPTION .B sniffit is a packet sniffer for TCP/UDP/ICMP packets. .B sniffit is able to give you very detailed technical info on these packets (SEQ, ACK, TTL, Window, ...) but also packet contents in different formats (hex or plain text, ...). .LP .B sniffit can by default handle ethernet and PPP devices, but can easily be forced into using other devices (read the .B README.FIRST and .B sn_config.h files on this subject!) .LP The sniffer can easily be configured in order to 'filter' the incoming packets (to make the sniffing results easier to study). The config file (see .BR sniffit (5) ) allows you to be very specific on the packets to be processed. .LP .B sniffit also has an interactive mode for active monitoring, and can also be used for continuous monitoring on different levels. .SH NOTE This man page is supposed to be a reference manual. So please read .B README.FIRST first, and use this only for better understanding or for a quick check on the use of .B sniffit .SH OPTIONS .IP -v Shows the version of .B sniffit you are running and exits .I "(overrides all)" .IP "-t Target-IP" Only process packets TO Target-IP. If Target-IP is in dot-nr notation, \'x' is allowed as wildcard. (e.g. '\-t 157.193.x', '\-t x', ...) .I "(NOT compatible with: '-s' '-i' '-I' '-c' '-v' '-L')" .IP "-s Source-IP" Similar to '\-t', only process packets FROM Source-IP. .I "(NOT compatible with: '-t' '-i' '-I' '-c' '-v' '-L')" .IP -b \'both' mode, together with '\-s' or '\-t', only process FROM/TO the IP specified by '\-s' or '\-t' .I "(NOT compatible with: '-t' '-i' '-I' '-c' '-v' '-L')" .IP "-c config-file" Use .I config-file for the packet filtering. This allows you to be very specific on the packets to be processed (see .BR sniffit (5) for details on the format). .I "(NOT compatible with: '-t' '-s' '-i' '-I' '-v' '-L')" .IP -i Launch the ncurses interface for active monitoring ('interactive mode'). (NOT available if you compiled without INTERACTIVE support see .B sn_config.h and .B README.FIRST ) (one of the options '\-t' '\-s' '\-i' '\-I' '\-c' is required) .I "(NOT compatible with: '-t' '-s' '-c' '-v' '-L')" .IP -I Same as '\-i', but gives you more information. (one of the options '\-t' '\-s' '\-i' '\-I' '\-c' is required) .I "(NOT compatible with: '-t' '-s' '-c' '-v' '-L')" .IP "-R " Record all traffic in .I This file can then be fed to Sniffit with the '\-r' option. .I "(Needs a selection parameter like '-c' '-t' '-s')" .I "(NOT compatible with '-i' '-I' '-v' '-L' '-r')" .IP "-r " This option feeds the recorded .I to .B sniffit. It requires the '\-F' option with the correct device. Suppose you log a file on a machine with 'eth0'. When feeding the logged file to .B sniffit , you will need to add '\-F eth0' or '\-F eth' to the command line. It doesn't need much explanation that using '\-i' or '\-I' in combination with '\-r' makes no sense (at this moment). .I "(requires '-F', NOT compatible with '-R' '-i' '-I')" .IP -n Turn of IP checksum checking. This can show you bogus packets. (mind you ARP, RARP, other non-IP packets will show up bogus too) .I "(compatible with ALL options)" .IP -N Don't perform any of the build in Sniffit functions. Useful for only running a Plugin. .I "(compatible with ALL options)" .IP -x Prints extended info on TCP packets to stdout (SEQ, ACK, Flags, etc...) Interesting when tracing spoofs, packet loss and other real net debugging/checking tasks. (if you want to log this, pipe stdout to a file) .I "(NOT compatible with: '-i' 'I' '-v')" .IP -d \'dump mode', shows the packets on the screen (stdout) instead of logging into files (default). Data is printed in bytes (hex). .I "(NOT compatible with: '-i' 'I' '-v' '-L')" .IP -a \'dump mode', same of '\-d' but outputs ASCII. Non printable chars are replaced by '.'. ('\-d' and '\-a' mix without any problem) .I "(NOT compatible with: '-i' '-I' '-v' '-L')" .IP "-P proto" Specify the protocols that should be processed (default TCP). Possible options currently are: IP, TCP, ICMP, UDP. They can be combined. IP, ICMP, UDP info is dumped to stdout. IP gives ADDITIONAL info on the IPwrapping around other packets, it is not needed to specify IP for TCP packet logging. IP, ICMP packets are not filtered (UDP packets are as of 0.3.4). .I "(NOT compatible with: '-i' '-I' '-v' '-L')" .IP "-A char" When in 'normal mode' (not '\-d','\-a','\-i','\-I','\-L'), all non-printable chars will be replaced by .I char .I "(NOT compatible with: '-a' '-d' '-i' '-I' '-v' '-L')" .IP "-p port" Only checks packets going TO (!!) port .I port , 0 means all ports, default is 0 (all). .I "(NOT compatible with: '-c' '-i' '-I' '-v' '-L')" .IP "-l sniflen" Amount of data to log (default 300 bytes) in 'normal mode'. The first .B sniflen bytes of every connection are logged. Length 0 logs means everything. (look out with diskspace!) .I "(NOT compatible with: '-i' '-I' '-v' '-L')" .IP "-F snifdevice" Force sniffit to use a certain network device. .I snifdevice can be found with .I ifconfig (see .BR ifconfig (8)). .B sniffit supports ethernet and PPP by default. Read .B README.FIRST for info on forcing the use of other devices. .I "(compatible with ALL options)" .IP "-D tty" All logging output will be send to that device. .I "(ONLY works with '-i' and '-I')" .IP "-M plugin" Activate Plugin nr. .B Plugin , for a list on all plugins compiled in your version, just type ' .B sniffit \'. Read all about Plugins in the PLUGIN-HOWTO (READ IT!) .I "(NOT compatible with: '-i' '-I' '-v')" .IP "-L logparam" Use .B sniffit as a monitoring tool and enable different logging modes ( .I logparam ) The File for logging can be specified in the config file (see .BR sniffit (5) ) but is .B sniffit.log by default. Different .I logparam can be combined. .I "(ONLY works with '-c')" .SH "NORMAL MODE" A bunch of .I sniflen initial bytes (default 300) of each connection is logged into a file .B x.x.x.x.p-y.y.y.y.o where 'x.x.x.x' is the sending host (port 'p') and 'y.y.y.y' the receiving host (port 'o'). .SH "DUMP MODE ('-d' and/or '-a')" Output is dumped to stdout, the packet contents is shown in it's unwrapped form (the complete IP packet). .SH "INTERACTIVE MODE ('-i' or '-I')" Keys available in interactive mode: .IP "'UP or 'k'" self explanatory .IP "DOWN or j'" self explanatory .IP "F1 or '1'" Enter a host (enter 'all' for no mask) for packet filtering (host that sends the packets) .IP "F2 or '2'" Enter a host (enter 'all' for no mask) for packet filtering. (host that receives the packets) .IP "F3 or '3'" Enter a port (enter '0' for no mask) for packet filtering. (host that sends the packets) .IP "F4 or '4'" Enter a port (enter '0' for no mask) for packet filtering. (host that receives the packets) .IP "F5 or '5'" Start a program 'sniffit_key5' with arguments .I " " If the program doesn't exist, nothing is done. Sniffit should be in the same path as sniffit was STARTED FROM (not necessarily the path sniffit is stored in) This function is useful for interactive connection killing or extra monitoring. A little shell script can always transform the arguments given and pass them on to other programs. .IP "F6 or '6'" Same as F5 or '5', but with program 'sniffit_key6' .IP "F7 or '7'" Same as F5 or '5', but with program 'sniffit_key7' .IP "F8 or '8'" Same as F5 or '5', but with program 'sniffit_key8' .IP "ENTER" a window will pop up and log the connection, or the connection output will be send at a chosen device if you used the '\-D' option. .IP "'q'" When in logging mode, stop logging. Otherwise, quit. .IP "'n'" Toggle netstatistics. These are sampled at 3 secs, look in the sn_config.h file to change this. .IP "'g'" .B Sniffit is now able to generate some traffic load. Currently this is a 'underdevelloped' feature with very few options, but it will be expanded a lot. Currently only UDP packets are generated. When pressing 'g' you will be asked the source/dest IP/port and how much packets are needed to be transmitted. Packets contain the line: "This Packet was fired with Sniffit! .IP "'r'" Reset.. clears all current connections from memory and restarts. .SH "LOGGING MODE ('-L')" Output is saved to .B sniffit.log , unless you have specified some other name in the config file (see .BR sniffit (5) ). .LP .IP "raw" Log all SYN, FIN, RST packets. This will give you an overview of all network (TCP) trafic in a 'RAW' way (a connection starting could gives you at least 2 SYN packets, etc...). .IP "norm" Same as raw, but a bit more intelligent. Unless packets are transmitted multiple times because of packet loss, you will only get 1 notice of a connection starting or ending. (the packet id will give you the host that initiated the connection first) .IP "telnet" Sniffit will try to catch login and passwords for this application. (see .BR telnet (1) ) .IP "ftp" Sniffit will try to catch login and passwords for this application. (see .BR ftp (1) ) .IP "mail" Sniffit will try to identify all mail that was logged. .SH "IP ICMP UDP LOGGING" Information on these packets is dumped to stdout. Packet Filtering options only refer to TCP and UDP packets. The contents of UDP packets is only shown when enabling '\-a' or '\-d'. .SH AUTHOR Brecht Claerhout .SH "SEE ALSO" .BR sniffit (5) sniffit-sniffit-0.4.0/src/000077500000000000000000000000001301260737100154045ustar00rootroot00000000000000sniffit-sniffit-0.4.0/src/Makefile.am000066400000000000000000000014641301260737100174450ustar00rootroot00000000000000# Makefile.am for sniffit # Copyright 2016 Joao Eriberto Mota Filho # Under BSD-3-CLause license. sbin_PROGRAMS = sniffit sniffit_SOURCES = sn_packets.c sn_generation.c sn_interface.c sn_cfgfile.c sn_logfile.c sn_resolv.c sniffit.c AM_CPPFLAGS = -DPACKAGE_NAME=\"\" -DPACKAGE_TARNAME=\"\" -DPACKAGE_VERSION=\"\" -DPACKAGE_STRING=\"\" -DPACKAGE_BUGREPORT=\"\" \ -DPACKAGE_URL=\"\" -DHAVE_LIBNCURSES=1 -DHAVE_SHMGET=1 -DHAVE_ATEXIT=1 -DSTDC_HEADERS=1 -DHAVE_SYS_TYPES_H=1 \ -DHAVE_SYS_STAT_H=1 -DHAVE_STDLIB_H=1 -DHAVE_STRING_H=1 -DHAVE_MEMORY_H=1 -DHAVE_STRINGS_H=1 -DHAVE_INTTYPES_H=1 \ -DHAVE_STDINT_H=1 -DHAVE_UNISTD_H=1 -DSIZEOF_UNSIGNED_SHORT_INT=2 -DSIZEOF_UNSIGNED_LONG_INT=8 -DSIZEOF_UNSIGNED_INT=4 \ -DUSE_32_INT=1 -DLINUX=1 AM_CFLAGS = -lncurses -lpcap sniffit-sniffit-0.4.0/src/dns_plugin.plug000066400000000000000000000113601301260737100204400ustar00rootroot00000000000000/* Sniffit Plugin example */ /* - by: Brecht Claerhout */ /* */ /* This Plugin scans for DNS packets and decodes them. */ /* It is used to demonstrate how you can easily add your own features */ /* without having to worry about the packet intercepting and filtering. */ /* Plus the fact that all other features of Sniffit remain functional, */ /* and that multiple plugins are combinable. */ struct PL_DNS_header { unsigned short id, flags; unsigned short nr_quest, nr_answ_RR, nr_auth_RR, nr_add_RR; }; int PL_pos_max; #define PL_DNS_QR 0x8000 #define PL_DNS_OPCODE 0x7800 #define PL_DNS_AA 0x0400 #define PL_DNS_TC 0x0200 #define PL_DNS_RD 0x0100 #define PL_DNS_RA 0x0080 #define PL_DNS_RCODE 0x000F void PL_DNS_error(void) { printf("\n\nSorry... could not decode the DNS packet!\n\n"); } int PL_DNS_decode(char *buf, int start_pos,char *string, int start_string) { int count, pos, i, j; unsigned short offset; j=start_string; pos=start_pos; if(pos > PL_pos_max) return -1; if( (count=(buf[pos]&63))!=buf[pos] ) { offset= ((short)(buf[pos]&63)*256) + ((short)(buf[pos+1])&0xFF); if(offset > PL_pos_max+12) return -1; if(PL_DNS_decode(buf,offset-12,string,j)<0) return -1; pos++; goto end_field; } while(count!=0) { for(i=0;i PL_pos_max) return -1; if(string==NULL) {printf("%c",buf[pos]);} else {string[j]=buf[pos];string[j+1]=0;j++;} } printf("."); pos++; if( (count=(buf[pos]&63))!=buf[pos] ) { offset= ((short)(buf[pos]&63)*256) + ((short)(buf[pos+1])&0xFF); if(PL_DNS_decode(buf,offset-12,string,j)<0) return -1; pos++; goto end_field; } } end_field: pos++; return pos; } void PL_DNS_plugin (struct Plugin_data *PLD) { struct IP_header *dns_iphead; struct UDP_header *dns_udphead; struct PL_DNS_header *dns_dnshead; int i, j, dec_pos, answers, count, udp_start, len; long pos; unsigned char *so,*dest, *dns_p, *dns_buffer; unsigned short fl, *r_dlen; unsigned short *type, *class; dns_buffer=PLD->PL_packet; udp_start = PLD->PL_info.IP_len; len=PLD->PL_info.IP_len + PLD->PL_info.UDP_len + PLD->PL_info.DATA_len; dns_iphead= (struct IP_header *) dns_buffer; dns_udphead= (struct UDP_header *) (dns_buffer+udp_start); dns_dnshead= (struct DNS_header *) (dns_buffer+udp_start+sizeof(struct UDP_header)); PL_pos_max = PLD->PL_info.DATA_len - 12; so=(unsigned char *)&(dns_iphead->source); dest=(unsigned char *)&(dns_iphead->destination); if((ntohs(dns_udphead->source)!=53)&&(ntohs(dns_udphead->destination)!=53)) return; printf("DNS Sniffit Plugin Report:\n"); printf("Packet: %u.%u.%u.%u %u -> %u.%u.%u.%u %u\n", so[0],so[1],so[2],so[3],ntohs(dns_udphead->source), dest[0],dest[1],dest[2],dest[3],ntohs(dns_udphead->destination)); printf("ID: %d \n",ntohs(dns_dnshead->id)); fl=ntohs(dns_dnshead->flags); printf(" STATUS: %s ",(fl & PL_DNS_QR)? "Answer": "Query"); printf("(opcode: %X) , ",(fl & PL_DNS_OPCODE)>>11); printf("%s , ",(fl & PL_DNS_AA)? "Auth. A.": ""); printf("%s , ",(fl & PL_DNS_TC)? "TRUNC": ""); printf("%s , ",(fl & PL_DNS_RD)? "Rec. Desired": ""); printf("%s , ",(fl & PL_DNS_RA)? "rec. Avail.": "rec. NOT Av."); printf("ret: %d\n",(fl & PL_DNS_RCODE)); printf(" Q: %d Answ: %d Auth: %d Add: %d", ntohs(dns_dnshead->nr_quest), ntohs(dns_dnshead->nr_answ_RR), ntohs(dns_dnshead->nr_auth_RR), ntohs(dns_dnshead->nr_add_RR)); dns_p=(dns_buffer+udp_start+sizeof(struct UDP_header)+12); dec_pos=0; for(i=0;inr_quest);i++) { printf("\n Query: "); dec_pos=PL_DNS_decode(dns_p,dec_pos,NULL,0); if(dec_pos<0) {PL_DNS_error(); return;} type=(unsigned short *) &(dns_p[dec_pos]); class=(unsigned short *) &(dns_p[dec_pos+2]); printf("\n Type: %d Class: %s",ntohs(*type),(ntohs(*class))?"IP":"Unknown"); dec_pos+=4; } if(fl & PL_DNS_TC) { printf("Truncated packet, not displayed...\n"); return; } /* dec_pos at beginning first answer field */ answers=ntohs(dns_dnshead->nr_answ_RR)+ntohs(dns_dnshead->nr_auth_RR)+ ntohs(dns_dnshead->nr_add_RR); for(i=0;iPL_info.IP_len); if(PLD->PL_info.TCP_len!=0) { printf(" TCP header: %d bytes / %d Databytes\n",PLD->PL_info.TCP_len, PLD->PL_info.DATA_len); } if(PLD->PL_info.UDP_len!=0) { printf(" UDP header: %d bytes / %d Databytes\n",PLD->PL_info.UDP_len, PLD->PL_info.DATA_len); } } sniffit-sniffit-0.4.0/src/sn_analyse.c000066400000000000000000000145731301260737100177160ustar00rootroot00000000000000/* Analyse traffic for logging mode */ /* - by: Brecht Claerhout */ const unsigned char *data; memcpy(&tcphead,header,sizeof(struct TCP_header)); dummy_pointer=search_dynam(filename, TCP); if(dummy_pointer!=NULL) status=1; if(status==0) /* make a new entry unless it's reset */ { if(finish!=TCP_FINISH) if((dummy_pointer=add_dynam(filename, TCP, 0,ntohl(tcphead.seq_nr),info.DATA_len))==NULL) return 1; }; if(finish==TCP_FINISH) /* let's reset the connection */ {delete_dynam(filename, TCP, 0);} /*** return before using any search or pointer!!!!!!!! ***/ /* Connections with FIN have deleted entries! */ dummy=ntohs(tcphead.offset_flag); if(LOGPARAM & LOGPARAM_RAW) /* Raw logging */ { if(dummy&SYN) print_conn(filename,"Connection initiated. (SYN)"); if(dummy&FIN) print_conn(filename,"Connection ending. (FIN)"); if(dummy&RST) print_conn(filename,"Connection reset. (RST)"); return 1; }; data = sp+PROTO_HEAD+info.IP_len+info.TCP_len; if(LOGPARAM & LOGPARAM_NORM) /* NORM logging */ { if(search_dynam(filename2, TCP)==NULL) { if(dummy&SYN) print_conn(filename,"Connection initiated."); if(dummy&FIN) print_conn(filename2,"Connection closed."); if(dummy&RST) print_conn(filename2,"Connection closed."); }; }; if((dummy&FIN)||(dummy&RST)) return 1; /* needed, cauz entry don't exist */ /*** TELNET *****************************************************************/ if(LOGPARAM & LOGPARAM_TELNET) { dummy_pointer=search_dynam(filename, TCP); /* don't forget to check dummy_pointer!!! */ if( (ntohs(tcphead.source) == 23)&&(dummy_pointer!=NULL))/* from telnet */ { sbuf_update(dummy_pointer,ntohl(tcphead.seq_nr),data,info.DATA_len); /* detect login */ strlower(dummy_pointer->scroll_buf); if((dummy_pointer->log!=LOG_NO_DETECT)&& (strstr(dummy_pointer->scroll_buf,"login")!=NULL)) { dummy_pointer->log=LOG_NO_DETECT; dummy_pointer=search_dynam(filename2, TCP); if(dummy_pointer!=NULL) { dummy_pointer->log=LOG_LOGIN; dummy_pointer->bytes=0; dummy_pointer->buffer=malloc(LOG_PASS_BUF); if(dummy_pointer->buffer==NULL) exit(1); dummy_pointer->buffer[0]=0; } else {print_conn(filename2,"Password missed due to overload.");};\ #ifdef DEBUG_ONSCREEN printf("Login detected, data initialised.\n"); #endif } } if( (ntohs(tcphead.destination) == 23)&&(dummy_pointer!=NULL))/* TO telnet */ { if(dummy_pointer->log==LOG_LOGIN) /* log login */ { record_buf(dummy_pointer,ntohl(tcphead.seq_nr),data,info.DATA_len,0); if(dummy_pointer->log==LOG_LOGIN_RECORDED) /* login recorded */ { print_login(filename,dummy_pointer->buffer); dummy_pointer->log=LOG_PWD; dummy_pointer->bytes=0; dummy_pointer->buffer[0]=0; } } else { if(dummy_pointer->log==LOG_PWD) /* log pwd */ { record_buf(dummy_pointer,ntohl(tcphead.seq_nr),data,info.DATA_len,0); if(dummy_pointer->log==LOG_PWD_RECORDED) /* passwd recorded */ { print_pwd(filename,dummy_pointer->buffer); dummy_pointer->log=LOG_NO_LOG; dummy_pointer->bytes=0; dummy_pointer->buffer[0]=0; } } } } } /*** END TELNET - LOGIN ***************************************************/ /*** FTP *******************************************************************/ if(LOGPARAM & LOGPARAM_FTP) /* loglevel 12 */ { dummy_pointer=search_dynam(filename, TCP); /* don't forget to check dummy_pointer!!! */ if( (ntohs(tcphead.destination) == 21) && (dummy_pointer!=NULL))/* to FTP */ { sbuf_update(dummy_pointer,ntohl(tcphead.seq_nr),data,info.DATA_len); /* detect USER en PASS */ if((help=strstr(dummy_pointer->scroll_buf,"USER"))!=NULL) { help+=strlen("USER "); for(i=0;iscroll_buf[i]==FTP_ENTER) dummy_pointer->scroll_buf[i]=0; print_ftp_user(filename,help); for(i=0;iscroll_buf[i]=' '; } if((help=strstr(dummy_pointer->scroll_buf,"PASS"))!=NULL) { help+=strlen("PASS "); for(i=0;iscroll_buf[i]==FTP_ENTER) dummy_pointer->scroll_buf[i]=0; print_ftp_pass(filename,help); for(i=0;iscroll_buf[i]=' '; } } } /*** END FTP ***************************************************************/ /*** MAIL ******************************************************************/ if(LOGPARAM & LOGPARAM_MAIL) /* loglevel 12 */ { /* dummy_pointer=search_dynam(filename, TCP); */ /* don't forget to check dummy_pointer!!! */ if( (ntohs(tcphead.destination) == 25) ) /* to MAIL */ { if(info.DATA_len!=0) { char workbuf1[MTU]; char *wb_dummy; char *p; size_t len = info.DATA_len <= MTU-1 ? info.DATA_len : MTU-1; strncpy(workbuf1,data,len); workbuf1[len]=0; strlower(workbuf1); if((p=strstr(workbuf1,"mail from"))!=NULL) { char workbuf2[MTU]; strcpy(workbuf2, p); if(strchr(workbuf2,13)!=NULL) /* remove trailing enter */ {wb_dummy=strchr(workbuf2,13); *wb_dummy=0;} if(strchr(workbuf2,10)!=NULL) {wb_dummy=strchr(workbuf2,10); *wb_dummy=0;} print_mail(filename,workbuf2); } if((p=strstr(workbuf1,"rcpt to"))!=NULL) { char workbuf2[MTU]; strcpy(workbuf2, p); if(strchr(workbuf2,13)!=NULL) /* remove trailing enter */ {wb_dummy=strchr(workbuf2,13); *wb_dummy=0;} if(strchr(workbuf2,10)!=NULL) {wb_dummy=strchr(workbuf2,10); *wb_dummy=0;} print_mail(filename,workbuf2); } } } } /*** END MAIL **************************************************************/ if( (dummy_pointer=search_dynam(filename, TCP)) !=NULL) { if(ntohl(tcphead.seq_nr)==dummy_pointer->exp_seq) dummy_pointer->exp_seq+=info.DATA_len; /* if we miss a packet... no probs seq nr's get updated */ /* cauz' we can't rely on ACK's from other side */ /* it's pretty good this way */ if(ntohl(tcphead.seq_nr)>dummy_pointer->exp_seq) dummy_pointer->exp_seq=ntohl(tcphead.seq_nr)+info.DATA_len; } return 1; return 1; /* DON'T FORGET THEM!!!! */ sniffit-sniffit-0.4.0/src/sn_cfgfile.c000066400000000000000000000315471301260737100176610ustar00rootroot00000000000000/* Sniffit Cfgfile source file */ /* - by : Brecht Claerhout */ /* - improvements: Shudoh Kazuyuki */ #include #include #include #include /* for getservbyname() */ #include "sn_config.h" #include "sn_defines.h" #include "sn_structs.h" #include "sn_cfgfile.h" #include "sn_resolv.h" #include "sniffit.h" /* #include "sn_generation.h" */ extern struct cfg_file_contense *select_from_list; /* pointers for cfg lists */ extern struct cfg_file_contense *select_to_list; extern struct cfg_file_contense *deselect_from_list; extern struct cfg_file_contense *deselect_to_list; extern int select_from_length; /* length of cfg lists */ extern int select_to_length; extern int deselect_from_length; extern int deselect_to_length; extern int Priority; /* The higher the priority, the more important */ extern char dot_notation[20]; /* for easy working, Q&D */ extern char Logfile[250]; void clear_list_buffer (struct cfg_file_contense *help) { help->host[0]=0; help->priority=0; help->port=0; help->wildcard=0; } struct cfg_file_contense *adjust_select_from_list (void) { Priority++; select_from_length++; if(select_from_list==NULL) { select_from_list=(struct cfg_file_contense *)malloc(sizeof(struct cfg_file_contense)); } else { select_from_list=(struct cfg_file_contense *)realloc(select_from_list, select_from_length*sizeof(struct cfg_file_contense)); } if(select_from_list==NULL) {printf("Sniffit heartattack... out of memory!\n"); exit(1);} clear_list_buffer(&(select_from_list[select_from_length-1])); return &(select_from_list[select_from_length-1]); } struct cfg_file_contense *adjust_select_to_list (void) { Priority++; select_to_length++; if(select_to_list==NULL) { select_to_list=(struct cfg_file_contense *)malloc(sizeof(struct cfg_file_contense)); } else { select_to_list=(struct cfg_file_contense *)realloc(select_to_list, select_to_length*sizeof(struct cfg_file_contense)); }; if(select_to_list==NULL) {printf("Sniffit heartattack... out of memory!\n"); exit(1);} clear_list_buffer(&(select_to_list[select_to_length-1])); return &(select_to_list[select_to_length-1]); } struct cfg_file_contense *adjust_deselect_from_list (void) { Priority++; deselect_from_length++; if(deselect_from_list==NULL) { deselect_from_list=(struct cfg_file_contense *)malloc(sizeof(struct cfg_file_contense)); } else { deselect_from_list=(struct cfg_file_contense *)realloc(deselect_from_list, deselect_from_length*sizeof(struct cfg_file_contense)); } if(deselect_from_list==NULL) {printf("Sniffit heartattack... out of memory!\n"); exit(1);} clear_list_buffer(&(deselect_from_list[deselect_from_length-1])); return (&(deselect_from_list[deselect_from_length-1])); } struct cfg_file_contense *adjust_deselect_to_list (void) { Priority++; deselect_to_length++; if(deselect_to_list==NULL) { deselect_to_list=(struct cfg_file_contense *)malloc(sizeof(struct cfg_file_contense)); } else { deselect_to_list=(struct cfg_file_contense *)realloc(deselect_to_list, deselect_to_length*sizeof(struct cfg_file_contense)); } if(deselect_to_list==NULL) {printf("Sniffit heartattack... out of memory!\n"); exit(1);} clear_list_buffer(&(deselect_to_list[deselect_to_length-1])); return &(deselect_to_list[deselect_to_length-1]); } char *clean_string (char *string) { char help[20]; int i, j; if(strlen(string) >= 20){ fprintf(stderr, "Error: String too long [%s]\n", string); exit(-1); } j=0; for(i=0;i= 20){ fprintf(stderr, "Error: String too long [%s]\n", string); exit(-1); } j=0; for(i=0;is_port);} else {ret = atoi(buf);} free(buf); if (ret <= 0) { printf("Invalid port no or service name in config file: %s\n", servname); exit(1); } return ret; } void interprete_line (char *line) { struct cfg_file_contense *help, *helpp; char *field; size_t i; field=strtok(line," "); if(field!=NULL) { /* comment line */ if(*field == '#') return; if(*field == ';') return; strlower(field); if(strcmp(strlower(field),"logfile")==0) { field=clean_filename(strtok(NULL," ")); if(field != NULL) strcpy(Logfile,field); } else if(strcmp(strlower(field),"select")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"from")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"host")==0) /* select from host */ { help=adjust_select_from_list(); make_nr_dot(strtok(NULL," ")); strcpy(help->host,dot_notation); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; return; } if(strcmp(strlower(field),"port")==0) /* select from port */ { help=adjust_select_from_list(); help->port=make_portno( strtok(NULL," ") ); help->priority=Priority; return; } if(strcmp(strlower(field),"mhosts")==0) /* select from mhosts */ { help=adjust_select_from_list(); strcpy(help->host, clean_string(strtok(NULL," "))); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; help->wildcard=1; return; } } if(strcmp(strlower(field),"to")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"host")==0) /* select to host */ { help=adjust_select_to_list(); make_nr_dot(strtok(NULL," ")); strcpy(help->host,dot_notation); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; return; } if(strcmp(strlower(field),"port")==0) /* select to port */ { help=adjust_select_to_list(); help->port=make_portno( strtok(NULL," ") ); help->priority=Priority; return; } if(strcmp(strlower(field),"mhosts")==0) /* select to mhosts */ { help=adjust_select_to_list(); strcpy(help->host, clean_string(strtok(NULL," "))); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; help->wildcard=1; return; } } if(strcmp(strlower(field),"both")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"host")==0) /* select both host */ { help=adjust_select_from_list(); helpp=adjust_select_to_list(); make_nr_dot(strtok(NULL," ")); strcpy(help->host,dot_notation); strcpy(helpp->host,dot_notation); if( (field=strtok(NULL," "))!=NULL) {help->port=make_portno(field); helpp->port=make_portno(field);} help->priority=Priority; helpp->priority=Priority; return; } if(strcmp(strlower(field),"port")==0) /* select both port */ { help=adjust_select_from_list(); helpp=adjust_select_to_list(); field=strtok(NULL," "); help->port=make_portno(field); helpp->port=make_portno(field); help->priority=Priority; helpp->priority=Priority; return; } if(strcmp(strlower(field),"mhosts")==0) /* select both mhosts */ { help=adjust_select_from_list(); helpp=adjust_select_to_list(); field=clean_string(strtok(NULL," ")); strcpy(help->host, field); strcpy(helpp->host, field); if( (field=strtok(NULL," "))!=NULL) {help->port=make_portno(field); helpp->port=make_portno(field);} help->priority=Priority; helpp->priority=Priority; help->wildcard=1; helpp->wildcard=1; return; } } } if(strcmp(strlower(field),"deselect")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"from")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"host")==0) /* select from host */ { help=adjust_deselect_from_list(); make_nr_dot(strtok(NULL," ")); strcpy(help->host,dot_notation); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; return; } if(strcmp(strlower(field),"port")==0) /* select from port */ { help=adjust_deselect_from_list(); help->port=make_portno(strtok(NULL," ")); help->priority=Priority; return; } if(strcmp(strlower(field),"mhosts")==0) /* select from mhosts */ { help=adjust_deselect_from_list(); strcpy(help->host, clean_string(strtok(NULL," "))); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; help->wildcard=1; return; } } if(strcmp(strlower(field),"to")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"host")==0) /* deselect to host */ { help=adjust_deselect_to_list(); make_nr_dot(strtok(NULL," ")); strcpy(help->host,dot_notation); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; return; } if(strcmp(strlower(field),"port")==0) /* deselect to port */ { help=adjust_deselect_to_list(); help->port=make_portno(strtok(NULL," ")); help->priority=Priority; return; } if(strcmp(strlower(field),"mhosts")==0) /* deselect to mhosts */ { help=adjust_deselect_to_list(); strcpy(help->host, clean_string(strtok(NULL," "))); if( (field=strtok(NULL," "))!=NULL) help->port=make_portno(field); help->priority=Priority; help->wildcard=1; return; } } if(strcmp(strlower(field),"both")==0) { field=strtok(NULL," "); if(strcmp(strlower(field),"host")==0) /* deselect both host */ { help=adjust_deselect_from_list(); helpp=adjust_deselect_to_list(); make_nr_dot(strtok(NULL," ")); strcpy(help->host,dot_notation); strcpy(helpp->host,dot_notation); if( (field=strtok(NULL," "))!=NULL) {helpp->port = help->port = make_portno(field);} help->priority=Priority; helpp->priority=Priority; return; } if(strcmp(strlower(field),"port")==0) /* deselect both port */ { help=adjust_deselect_from_list(); helpp=adjust_deselect_to_list(); field=strtok(NULL," "); helpp->port = help->port = make_portno(field); help->priority=Priority; helpp->priority=Priority; return; } if(strcmp(strlower(field),"mhosts")==0) /* deselect both mhosts */ { help=adjust_deselect_from_list(); helpp=adjust_deselect_to_list(); field=clean_string(strtok(NULL," ")); strcpy(help->host, field); strcpy(helpp->host, field); if( (field=strtok(NULL," "))!=NULL) {help->port=make_portno(field); helpp->port=make_portno(field);} help->priority=Priority; helpp->priority=Priority; help->wildcard=1; helpp->wildcard=1; return; } } } } } void read_cfg_file (char *file) { FILE *cfgfile; size_t line_length; char lineptr[260]; select_from_list=NULL; select_to_list=NULL; deselect_from_list=NULL; deselect_to_list=NULL; Priority=0; if((cfgfile = fopen(file,"r"))==NULL) {fprintf(stderr,"Couldn't find config file... giving up.\n"); exit(1);} while(feof(cfgfile)==0) { fgets(lineptr,259,cfgfile); if(feof(cfgfile)==0) { interprete_line(lineptr);} } fclose(cfgfile); }; sniffit-sniffit-0.4.0/src/sn_cfgfile.h000066400000000000000000000010141301260737100176500ustar00rootroot00000000000000/* Sniffit Config File include */ void clear_list_buffer (struct cfg_file_contense *); struct cfg_file_contense *adjust_select_from_list (void); struct cfg_file_contense *adjust_select_to_list (void); struct cfg_file_contense *adjust_deselect_from_list (void); struct cfg_file_contense *adjust_deselect_to_list (void); char *clean_string (char *); char *clean_filename (char *); void make_nr_dot (char *); void interprete_line (char *); void read_cfg_file (char *); sniffit-sniffit-0.4.0/src/sn_config.h000066400000000000000000000061761301260737100175340ustar00rootroot00000000000000/* Sniffit Config File */ /* - By: Brecht Claerhout */ /* Because of the use of GNU autoconfig, this file manages pretty much */ /* itself, you could however still add your personal touch in some parts */ #define INCLUDE_INTERFACE /* By default */ #ifndef HAVE_SHMGET /* No Shared memory */ #undef INCLUDE_INTERFACE #endif #ifndef HAVE_LIBNCURSES /* ncurses not found */ #undef INCLUDE_INTERFACE #endif //#ifndef HAVE_NCURSES_H /* ncurses not found */ //#undef INCLUDE_INTERFACE //#endif #ifdef IRIX /* No interface on IRIX */ #undef INCLUDE_INTERFACE #endif /* Not supported yet */ #ifdef BSDI #undef INCLUDE_INTERFACE #endif #ifdef HAVE_ATEXIT #define exit_func(x) atexit(x) #else #define exit_func(x) on_exit (x,0) #endif /***************************************************************************/ /* If you want to allow the program to be used 'set user id' */ /* #define ALLOW_SUID */ #undef ALLOW_SUID /***************************************************************************/ /* Following parameters describe the connections that can be handled at */ /* once, MAXCOUNT stands for connections handled in normal mode. As */ /* memory in normal mode is now handled dynamically, you can pump this */ /* number up without having to much trouble (Watch it, the machine */ /* could be slowed down a lot, and packets could get missed) */ /* CONNECTION_CAPACITY is the same, except in interactive mode, this is */ /* more dangerous to change, if you machine goes to slow (when sniffing */ /* in interactive mode), lower this number. */ #define MAXCOUNT 500 #ifdef INCLUDE_INTERFACE #define CONNECTION_CAPACITY 100 #endif /* This is the interval time for the netstatistics */ #define INFO_TIMER 3 /* In seconds */ /***************************************************************************/ /* Enable/Disable Packet generation function */ #undef GENERATION #ifdef INCLUDE_INTERFACE #define GENERATION /* #undef GENERATION */ #endif /***************************************************************************/ /* Read about forcing the sniff device in the README.FIRST file */ #define FORCED_HEAD_LENGTH 14 /* default */ /* MTU: this could need a change on interfaces different from ethernet or on non-standard */ /* configured systems. Get the info out of 'ifconfig'. */ /* But 1500 is a standard. */ #define MTU 5000 /*************** Don't change anything below this line *********************/ #undef DEBUG /* Debugging (to tty) - sigh */ /* #define DEBUG */ #define DEBUG_DEVICE "/dev/ttyp6" #undef DEBUG_ONSCREEN /* Debugging (to screen) - sigh */ /* #define DEBUG_ONSCREEN */ #ifdef DEBUG void close_debug_device (void); void debug_msg(char *); #endif sniffit-sniffit-0.4.0/src/sn_conn_desc.c000066400000000000000000000062641301260737100202130ustar00rootroot00000000000000/* Connection description detection file */ /* - by: Brecht Claerhout */ /* Simple PORT BASED detection */ /*** FTP sessions ********************************************************/ if( (ntohs(tcphead.source)==FTP_DATA_1)||(ntohs(tcphead.destination)==FTP_DATA_1) ) {strcpy(desc_string, "FTP DATA");} if( (ntohs(tcphead.source)==FTP_1)||(ntohs(tcphead.destination)==FTP_1) ) { if(info->DATA_len==0) strcpy(desc_string, "FTP"); if(info->DATA_len>5) { const unsigned char *data= sp+PROTO_HEAD+info->IP_len+info->TCP_len; strcpy(desc_string,"FTP: "); j=5; /* 5 = "FTP: " */ for(i=0;iDATA_len;i++) { if( (isalnum(data[i]) || ispunct(data[i]) || data[i]==' ')&&(j<(*DESC_LEN)-1) ) {desc_string[j]=data[i]; desc_string[j+1]=0; j++; } else {if( (isspace(data[i]) && data[i]!=' ')&&(j<(*DESC_LEN)-1) ) {desc_string[j]=' '; desc_string[j+1]=0; j++; } } } } } /*** TELNET sessions *****************************************************/ if( (ntohs(tcphead.source)==TELNET_1)||(ntohs(tcphead.destination)==TELNET_1) ) {strcpy(desc_string, "TELNET");} /*** SSH sessions ********************************************************/ if( (ntohs(tcphead.source)==SSH_1)||(ntohs(tcphead.destination)==SSH_1) ) {strcpy(desc_string, "Secure Shell");} /*** MAIL sessions *****************************************************/ if( (ntohs(tcphead.source)==MAIL_1)||(ntohs(tcphead.destination)==MAIL_1) ) {strcpy(desc_string, "MAIL");} /*** IDENT **************************************************************/ if( (ntohs(tcphead.source)==IDENT_1)||(ntohs(tcphead.destination)==IDENT_1) ) {strcpy(desc_string, "IDENT");} /*** IRC ***************************************************************/ if( (ntohs(tcphead.source)==IRC_1)||(ntohs(tcphead.destination)==IRC_1) ) {strcpy(desc_string, "IRC");} /*** X11 sessions *******************************************************/ if( (ntohs(tcphead.source)==X11_1)||(ntohs(tcphead.destination)==X11_1) ) {strcpy(desc_string, "X-Windows");} /*** HTTP ***************************************************************/ if( (ntohs(tcphead.source)==HTTP_1)||(ntohs(tcphead.source)==HTTP_2)|| (ntohs(tcphead.source)==HTTP_3)||(ntohs(tcphead.source)==HTTP_4) ) { strcpy(desc_string, "HTTP"); } if( (ntohs(tcphead.destination)==HTTP_1)||(ntohs(tcphead.destination)==HTTP_2) || (ntohs(tcphead.destination)==HTTP_3)||(ntohs(tcphead.destination)==HTTP_4) ) { if(info->DATA_len==0) strcpy(desc_string, "HTTP"); if(info->DATA_len>5) { const unsigned char *data= sp+PROTO_HEAD+info->IP_len+info->TCP_len; strcpy(desc_string,"HTTP: "); j=6; /* 5 = "HTTP: " */ for(i=0;iDATA_len;i++) if( (isalnum(data[i]) || ispunct(data[i]) || data[i]==' ')&&(j<(*DESC_LEN)-1) ) {desc_string[j]=data[i]; desc_string[j+1]=0; j++; } else {if( (isspace(data[i]) && data[i]!=' ')&&(j<(*DESC_LEN)-1) ) {desc_string[j]=' '; desc_string[j+1]=0; j++; } } } } sniffit-sniffit-0.4.0/src/sn_curses.h000066400000000000000000000000251301260737100175560ustar00rootroot00000000000000#include sniffit-sniffit-0.4.0/src/sn_data.h000066400000000000000000000142441301260737100171730ustar00rootroot00000000000000/* Sniffit Data File */ /**** Network Devices *******************************************************/ /* Older configuration system of Sniffit */ /* ether: 14 */ /* ppp : 4 */ /* slip : 16 */ /* lo : 4 */ #ifdef LINUX /* #define NETDEV_NR 3 char *NETDEV[]={"lo","ppp","eth"}; int HEADSIZE []={4 ,0 ,14}; */ #define NETDEV_NR 3 char *NETDEV[]={"ppp","slip","eth"}; /* echo on loopback */ int HEADSIZE []={0 ,0 ,14}; /* slip needs testing */ #endif #ifdef SUNOS #define NETDEV_NR 3 char *NETDEV[]={"le","hme"}; int HEADSIZE[]={14 ,14}; /* ppp: 4 or 0 or nothing? */ #endif #ifdef IRIX #define NETDEV_NR 2 char *NETDEV[]={"ppp","et"}; int HEADSIZE[]={0 ,14}; /* ppp: 4 or 0 or nothing */ #endif #ifdef FREEBSD /* ppp: 4 or 0 ? */ /* #define NETDEV_NR 2 char *NETDEV[]={"ppp","ed"}; int HEADSIZE[]={4 ,14}; */ #define NETDEV_NR 1 char *NETDEV[]={"ed"}; int HEADSIZE[]={14}; #endif #ifdef BSDI /* ppp: 4 or 0 ? */ /* #define NETDEV_NR 2 char *NETDEV[]={"ppp","ef"}; int HEADSIZE[]={4 ,14}; */ #define NETDEV_NR 1 char *NETDEV[]={"ef"}; int HEADSIZE[]={14}; #endif #ifdef DEC_OSF #define NETDEV_NR 1 char *NETDEV[]={"ln"}; int HEADSIZE[]={14}; #endif #ifdef NETBSD #ifdef i386 #define NETDEV_NR 21 char *NETDEV[]={"ppp","ai","de","ec","ef","eg","el","en","ep","fe","fea","fpa","fxp","ix","iy","lc","le","ne","sm","tl","we"}; int HEADSIZE[]={4 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 ,14 }; #elif defined(sparc) #define NETDEV_NR 3 char *NETDEV[]={"ppp","le","ie"}; int HEADSIZE[]={4 ,14 ,14}; #elif defined(amiga) #define ETH_DEV_NR 6 char *NETDEV[]={"ppp","bah","ed","es","le","qn"}; int HEADSIZE[]={4 ,14 ,14 ,14 ,14 ,14}; #else #error Unknown network devices for this NetBSD architecture. #endif #endif #ifdef AIX /* only for the AIX powerpack ;) */ #define NETDEV_NR 4 /* not usefull without it */ char *NETDEV[]={"en","et","tr","fi"}; int HEADSIZE[]={14 ,22 ,22 ,24}; #endif #ifdef HPUX /* only for the HPUX powerpack ;) */ #define NETDEV_NR 2 /* not usefull without it */ char *NETDEV[]={"le","sam"}; int HEADSIZE[]={14 ,14 }; #endif /**** Global data **********************************************************/ pcap_t *dev_desc; pcap_dumper_t *dev_dump; void *start_dynam; int dynam_len; char Logfile[250]; /* name of logfile */ FILE *LogFILE; /* logfile stream */ /* char *IP; *//* was with older '-p' */ char IP[256]; unsigned long SNIFLEN; /* bytes we need to snif */ short DEST_PORT, SRC_PORT; /* destination port */ char non_printable, *logging_device; /**** Global data (packets) *************************************************/ int PROTO_HEAD; /* Base Protocol head length (ethernet, PPP ,....) */ char *IP_TYPE_precedence[8]= {"Routine", "Priority", "Immediate", "Flash", "Flash override", "Critical", "Internetwork control", "Network control"}; char *IP_PROTOCOL_number[34]= {"Reserved","ICMP","IGMP","GGP","Unassigned","ST","TCP","UCL","EGP","IGP", "BBN-MON","NVP-II","PUP","ARGUS","EMCOM","XNET","CHAOS","UDP","MUX", "DCN-MEAS","HMP","PRM","XNS-IDP","TRUNK-1","TRUNK-2","LEAF-1","LEAF-2", "RDP","IRTP","ISO-TP4","NETBLT","MFE-NSP","MERIT-INP","SEP"}; char *ICMP_type_3_code[6]= {"Net unreachable", "Host unreachable", "Protocol unreachable", "Port unreachable", "Fragmentation needed and DF set", "Source route failed"}; char *ICMP_type_5_code[4]= {"Redirect datagrams for the network", "Redirect datagrams for the host", "Redirect datagrams for the \'type of service\' and the network", "Redirect datagrams for the \'type of service\' and the host"}; char *ICMP_type_11_code[2]= {"Time-to-live exceeded in transmit", "Fragment reassembly time exceeded"}; /**** Global data (config) **************************************************/ struct cfg_file_contense *select_from_list; /* pointers for cfg lists */ struct cfg_file_contense *select_to_list; struct cfg_file_contense *deselect_from_list; struct cfg_file_contense *deselect_to_list; int select_from_length=0; /* length of cfg lists */ int select_to_length=0; int deselect_from_length=0; int deselect_to_length=0; int Priority=0; /* The higher the priority, the more important */ char dot_notation[20]; /* for easy working, Q&D */ /**** Global data (plugins) *************************************************/ char Plugin_Active[10]; /**** Global data (interactive) *********************************************/ #ifdef INCLUDE_INTERFACE /**** shared memory pointers ************************************************/ char *SHARED, *connection_data, *timing, *running_connections, *logged_connections; int *LISTlength, *DATAlength, memory_id; unsigned int *TCP_nr_of_packets, *ICMP_nr_of_packets, *UDP_nr_of_packets; unsigned int *IP_nr_of_packets; unsigned long *TCP_bytes_in_packets, *UDP_bytes_in_packets; int *DESC_LEN; /**** data structures *******************************************************/ struct snif_mask *mask; struct shared_logged_conn *log_conn; FILE *log_dev_stream; struct stat log_dev_stat; volatile int LOGGING=0, screen_busy=0; char PACKET_INFO; int POINTpos=0, LISTpos=0; unsigned char COLOR_AVAIL=0; /**** screen **************************************************************/ int MASK_WINDOW_ROWS, MASK_WINDOW_COLS; int MAIN_WINDOW_ROWS, MAIN_WINDOW_COLS; int INFO_WINDOW_ROWS, INFO_WINDOW_COLS; int DATA_WINDOW_ROWS, DATA_WINDOW_COLS; int INFO_WINDOW_X, INFO_WINDOW_Y; int MASK_WINDOW_X, MASK_WINDOW_Y; int DATA_WINDOW_X, DATA_WINDOW_Y; WINDOW *menu_window; struct box_window data_box, main_box, mask_box, packets_box; int Pid=0; #endif /* DEBUG section */ #ifdef DEBUG FILE *debug_dev; unsigned int debug_cnt=0; #endif sniffit-sniffit-0.4.0/src/sn_defines.h000066400000000000000000000102431301260737100176720ustar00rootroot00000000000000/* Sniffit Defines File */ #include "sn_config.h" /*** typedefs ******************/ #ifdef USE_32_LONG_INT typedef unsigned long int _32_bit; #endif #ifdef USE_32_INT typedef unsigned int _32_bit; #endif typedef unsigned short _16_bit; /*** Normal Sniffit operations */ #define VERSION "0.4.0" /* Program Version */ #define SNAPLEN MTU /* Ethernet Packet Length */ #define MSDELAY 1000 /* pcap timeout */ #define PACKETS 1 /* pcap dispatch */ #define CNT -1 /* pcap loop count */ #define LENGTH_OF_INTERPROC_DATA 5*SNAPLEN /* buffer capacity */ #define SCBUF 30 /* scroll buffer length */ #define LOG_PASS_BUF 20+1 /* login/pwd buffer length */ #define TELNET_ENTER 0x0d /* Enter in telnet login session */ #define FTP_ENTER 0x0d /* first char of Enter in FTP login session */ #define DEST 0 #define SOURCE 1 #define BOTH 2 #define INTERACTIVE 99 /* Packet examining defines (finish) */ /* 0-9 : TCP */ /* 10-19: ICMP */ /* 20-29: UDP */ #define DROP_PACKET -2 /* Skip Packet completely */ #define DONT_EXAMINE -1 /* Skip Packet */ #define TCP_EXAMINE 0 /* TCP - 'for us' */ #define TCP_FINISH 1 /* TCP - end connection */ #define TCP_EX_FRAG_HEAD 2 /* defined lower */ #define TCP_EX_FRAG_NF 3 #define ICMP_EXAMINE 10 /* ICMP - examine */ #define UDP_EXAMINE 20 /* UDP - examine */ #define F_TCP 1 /* Flags for PROTOCOLS */ #define F_ICMP 2 #define F_UDP 4 #define F_IP 8 /*** Logparam defines */ #define LOGPARAM_LOG_ON 1 #define LOGPARAM_RAW 2 #define LOGPARAM_NORM 4 #define LOGPARAM_TELNET 8 #define LOGPARAM_FTP 16 #define LOGPARAM_MAIL 32 /*** Interface defines */ #ifdef INCLUDE_INTERFACE #define ENTER 13 #define WIN_COLOR_NORMAL 1 /* Color pairs for various functions */ #define WIN_COLOR_POINT 2 #define WIN_COLOR_DATA 3 #define WIN_COLOR_INPUT 4 #define WIN_COLOR_MENU 5 #define WIN_COLOR_PACKET_INFO 6 #define WIN_COLOR_PKTCNT 7 #define CONN_NAMELEN 56 /* length of string */ #define DESC_BYTES 60 /* length of description */ #define MENU " Masks: F1-Source IP F2-Dest. IP F3-Source Port F4-Dest. Port" #endif /* First undefine all Plugins, just to be sure */ #undef PLUGIN0_NAME #undef PLUGIN1_NAME #undef PLUGIN2_NAME #undef PLUGIN3_NAME #undef PLUGIN4_NAME #undef PLUGIN5_NAME #undef PLUGIN6_NAME #undef PLUGIN7_NAME #undef PLUGIN8_NAME #undef PLUGIN9_NAME #define IP_VERSION 4 #define URG 32 /*TCP-flags */ #define ACK 16 #define PSH 8 #define RST 4 #define SYN 2 #define FIN 1 /* unwrap packet */ #define NOT_SUPPORTED -1 #define NO_IP 0 #define NO_IP_4 1000 #define CORRUPT_IP 1001 #define TCP_FRAG_HEAD 1002 #define UDP_FRAG_HEAD 1003 #define ICMP_FRAG_HEAD 1004 #define ICMP 1 /* Protocol Numbers */ #define TCP 6 #define UDP 17 #define ICMP_HEADLENGTH 4 /* fixed ICMP header length */ #define UDP_HEADLENGTH 8 /* fixed UDP header length */ #define IP_DELAY 32 #define IP_THROUGHPUT 16 #define IP_RELIABILITY 8 #define IP_DF 2 #define IP_MF 1 /*** ICMP types ********************************************************/ #define ICMP_TYPE_0 "Echo reply" #define ICMP_TYPE_3 "Destination unreachable" #define ICMP_TYPE_4 "Source quench" #define ICMP_TYPE_5 "Redirect" #define ICMP_TYPE_8 "Echo" #define ICMP_TYPE_11 "Time exceeded" #define ICMP_TYPE_12 "Parameter problem" #define ICMP_TYPE_13 "Timestamp" #define ICMP_TYPE_14 "Timestamp reply" #define ICMP_TYPE_15 "Information request" #define ICMP_TYPE_16 "Information reply" #define ICMP_TYPE_17 "Address mask request" #define ICMP_TYPE_18 "Address mask reply" /*** Services (standardised) *******************************************/ #define FTP_DATA_1 20 #define FTP_1 21 #define SSH_1 22 #define TELNET_1 23 #define MAIL_1 25 #define IDENT_1 113 #define HTTP_1 80 #define HTTP_2 80 #define HTTP_3 80 #define HTTP_4 80 #define IRC_1 6667 #define X11_1 6000 sniffit-sniffit-0.4.0/src/sn_generation.c000066400000000000000000000306211301260737100204050ustar00rootroot00000000000000/* Sniffit Packet Generation File */ /* - Idea/development/code:Amlan Saha */ /* - Packet code/debugging: Brecht Claerhout */ #include "sn_config.h" #ifdef INCLUDE_INTERFACE #ifdef GENERATION #include #include #include #include #include #include "sn_curses.h" #include "sn_defines.h" #include "sn_structs.h" #include "sn_generation.h" extern volatile int screen_busy; void exec_generate(struct generate_mask *generate) { WINDOW *Msg_dsp; int count=0, count_ptr, fd; char msg[80]; char dummy_data[]="This Packet was fired with Sniffit!"; #ifdef DEBUG debug_msg("Gener: Start of execution"); #endif count_ptr=(generate->pkt_no); Msg_dsp=newwin(1,COLS,LINES-1,0); wattrset(Msg_dsp,A_BOLD); wattrset(Msg_dsp,COLOR_PAIR(WIN_COLOR_PKTCNT)); fd=open_sending(); while(countsource_ip, generate->source_port, generate->dest_ip, generate->dest_port); #ifdef DEBUG debug_msg("Gener: End"); #endif if(count==count_ptr-1) { sprintf(msg,"DISPATCH COMPLETE-Press ENTER"); } else { sprintf(msg,"Packet No: %d dispatched.",count+1); } mvwaddstr(Msg_dsp,0,27,msg); while(screen_busy!=0) {}; wnoutrefresh(Msg_dsp); doupdate(); count++; } delwin(Msg_dsp); close(fd); input_field(msg,NULL,0); forced_refresh(); } /**************************************************************************/ /* Actual packet generation functions below */ /* code stolen from Spoofit (my own ;) */ /* */ /* int open_sending (void) */ /* Returns a filedescriptor to the sending socket. */ /* close it with close (int filedesc) */ /* */ /* void transmit_TCP (int sp_fd, char *sp_data, */ /* int sp_ipoptlen, int sp_tcpoptlen, int sp_datalen, */ /* char *sp_source, unsigned short sp_source_port, */ /* char *sp_dest,unsigned short sp_dest_port, */ /* _32_bit sp_seq, _32_bit sp_ack, */ /* unsigned short sp_flags) */ /* fire data away in a TCP packet */ /* sp_fd : raw socket filedesc. */ /* sp_data : IP options (you should do the padding) */ /* TCP options (you should do the padding) */ /* data to be transmitted */ /* (NULL is nothing) */ /* note that all is optional, and IP en TCP options are*/ /* not often used. */ /* All data is put after eachother in one buffer. */ /* sp_ipoptlen : length of IP options (in bytes) */ /* sp_tcpoptlen : length of TCP options (in bytes) */ /* sp_datalen : amount of data to be transmitted (bytes) */ /* sp_source : spoofed host that"sends packet" */ /* sp_source_port: spoofed port that "sends packet" */ /* sp_dest : host that should receive packet */ /* sp_dest_port : port that should receive packet */ /* sp_seq : sequence number of packet */ /* sp_ack : ACK of packet */ /* sp_flags : flags of packet (URG,ACK,PSH,RST,SYN,FIN) */ /* */ /* void transmit_UDP (int sp_fd, char *sp_data, */ /* int sp_ipoptlen, int sp_datalen, */ /* char *sp_source, unsigned short sp_source_port, */ /* char *sp_dest, unsigned short sp_dest_port) */ /* fire data away in an UDP packet */ /* sp_fd : raw socket filedesc. */ /* sp_data : IP options */ /* data to be transmitted */ /* (NULL if none) */ /* sp_ipoptlen : length of IP options (in bytes) */ /* sp_datalen : amount of data to be transmitted */ /* sp_source : spoofed host that"sends packet" */ /* sp_source_port: spoofed port that "sends packet" */ /* sp_dest : host that should receive packet */ /* sp_dest_port : port that should receive packet */ /* */ /**************************************************************************/ #define SP_IP_HEAD_BASE 20 /* using fixed lengths to send */ #define SP_TCP_HEAD_BASE 20 /* no options etc... */ #define SP_UDP_HEAD_BASE 8 /* Always fixed */ int open_sending (void) { struct protoent *sp_proto; int sp_fd; int dummy=1; /* they don't come rawer */ if ((sp_fd = socket(AF_INET, SOCK_RAW, IPPROTO_RAW))==-1) perror("Couldn't open Socket."), exit(1); #ifdef DEBUG printf("Raw socket ready\n"); #endif return sp_fd; } void sp_send_packet (struct sp_data_exchange *sp, unsigned char proto) { int sp_status; struct sockaddr_in sp_server; struct hostent *sp_help; int HEAD_BASE; /* Construction of destination */ bzero((char *)&sp_server, sizeof(struct sockaddr)); sp_server.sin_family = AF_INET; sp_server.sin_addr.s_addr = sp->dest; /* if (sp_server.sin_addr.s_addr == (unsigned int)-1) { if (!(sp_help=gethostbyname(sp->dest))) fprintf(stderr,"unknown host %s\n", sp->dest), exit(1); bcopy(sp_help->h_addr, (caddr_t)&sp_server.sin_addr, sp_help->h_length); }; */ switch(proto) { case 6: HEAD_BASE = SP_TCP_HEAD_BASE; break; /* TCP */ case 17: HEAD_BASE = SP_UDP_HEAD_BASE; break; /* UDP */ default: exit(1); break; }; sp_status = sendto(sp->fd, (char *)(sp->buffer), sp->datalen+HEAD_BASE+SP_IP_HEAD_BASE+sp->IP_optlen, 0, (struct sockaddr *)&sp_server,sizeof(struct sockaddr)); if (sp_status < 0 || sp_status != sp->datalen+HEAD_BASE+SP_IP_HEAD_BASE+sp->IP_optlen) { if (sp_status < 0) perror("Sendto"), exit(1); printf("hmm... Only transmitted %d of %d bytes.\n", sp_status, sp->datalen+HEAD_BASE); }; #ifdef DEBUG printf("Packet transmitted...\n"); #endif } void sp_fix_IP_packet (struct sp_data_exchange *sp, unsigned char proto) { struct IP_header *sp_help_ip; int HEAD_BASE; switch(proto) { case 6: HEAD_BASE = SP_TCP_HEAD_BASE; break; /* TCP */ case 17: HEAD_BASE = SP_UDP_HEAD_BASE; break; /* UDP */ default: exit(1); break; }; sp_help_ip = (struct IP_header *) (sp->buffer); sp_help_ip->verlen = (IP_VERSION << 4) | ((SP_IP_HEAD_BASE+sp->IP_optlen)/4); sp_help_ip->type = 0; sp_help_ip->length = htons(SP_IP_HEAD_BASE+HEAD_BASE+sp->datalen+sp->IP_optlen+sp->TCP_optlen); sp_help_ip->ID = htons(12545); /* TEST */ sp_help_ip->flag_offset = 0; sp_help_ip->TTL = 69; sp_help_ip->protocol = proto; sp_help_ip->source = sp->source; sp_help_ip->destination = sp->dest; sp_help_ip->checksum=in_cksum((unsigned short *) (sp->buffer), SP_IP_HEAD_BASE+sp->IP_optlen); #ifdef DEBUG printf("IP header fixed...\n"); #endif } void sp_fix_TCP_packet (struct sp_data_exchange *sp) { char sp_pseudo_ip_construct[MTU]; struct TCP_header *sp_help_tcp; struct pseudo_IP_header *sp_help_pseudo; int i; for(i=0;ibuffer+SP_IP_HEAD_BASE+sp->IP_optlen); sp_help_pseudo = (struct pseudo_IP_header *) sp_pseudo_ip_construct; sp_help_tcp->offset_flag = htons( (((SP_TCP_HEAD_BASE+sp->TCP_optlen)/4)<<12) | sp->flags); sp_help_tcp->seq_nr = htonl(sp->seq); sp_help_tcp->ACK_nr = htonl(sp->ack); sp_help_tcp->source = htons(sp->source_port); sp_help_tcp->destination = htons(sp->dest_port); sp_help_tcp->window = htons(0x7c00); /* dummy for now 'wujx' */ sp_help_pseudo->source = sp->source; sp_help_pseudo->destination = sp->dest; sp_help_pseudo->zero_byte = 0; sp_help_pseudo->protocol = 6; sp_help_pseudo->TCP_UDP_len = htons(sp->datalen+SP_TCP_HEAD_BASE+sp->TCP_optlen); memcpy(sp_pseudo_ip_construct+12, sp_help_tcp, sp->TCP_optlen+sp->datalen+SP_TCP_HEAD_BASE); sp_help_tcp->checksum=in_cksum((unsigned short *) sp_pseudo_ip_construct, sp->datalen+12+SP_TCP_HEAD_BASE+sp->TCP_optlen); #ifdef DEBUG printf("TCP header fixed...\n"); #endif } void transmit_TCP (int sp_fd, char *sp_data, int sp_ipoptlen, int sp_tcpoptlen, int sp_datalen, _32_bit sp_source, unsigned short sp_source_port, _32_bit sp_dest, unsigned short sp_dest_port, _32_bit sp_seq, _32_bit sp_ack, unsigned short sp_flags) { char sp_buffer[1500]; struct sp_data_exchange sp_struct; bzero(sp_buffer,1500); if (sp_ipoptlen!=0) memcpy(sp_buffer+SP_IP_HEAD_BASE,sp_data,sp_ipoptlen); if (sp_tcpoptlen!=0) memcpy(sp_buffer+SP_IP_HEAD_BASE+SP_TCP_HEAD_BASE+sp_ipoptlen, sp_data+sp_ipoptlen,sp_tcpoptlen); if (sp_datalen!=0) memcpy(sp_buffer+SP_IP_HEAD_BASE+SP_TCP_HEAD_BASE+sp_ipoptlen+sp_tcpoptlen, sp_data+sp_ipoptlen+sp_tcpoptlen,sp_datalen); sp_struct.fd = sp_fd; sp_struct.data = sp_data; sp_struct.datalen = sp_datalen; sp_struct.source = sp_source; sp_struct.source_port = sp_source_port; sp_struct.dest = sp_dest; sp_struct.dest_port = sp_dest_port; sp_struct.seq = sp_seq; sp_struct.ack = sp_ack; sp_struct.flags = sp_flags; sp_struct.buffer = sp_buffer; sp_struct.IP_optlen = sp_ipoptlen; sp_struct.TCP_optlen = sp_tcpoptlen; sp_fix_TCP_packet(&sp_struct); sp_fix_IP_packet(&sp_struct, 6); sp_send_packet(&sp_struct, 6); } void sp_fix_UDP_packet (struct sp_data_exchange *sp) { char sp_pseudo_ip_construct[MTU]; struct UDP_header *sp_help_udp; struct pseudo_IP_header *sp_help_pseudo; int i; for(i=0;ibuffer+SP_IP_HEAD_BASE+sp->IP_optlen); sp_help_pseudo = (struct pseudo_IP_header *) sp_pseudo_ip_construct; sp_help_udp->source = htons(sp->source_port); sp_help_udp->destination = htons(sp->dest_port); sp_help_udp->length = htons(sp->datalen+SP_UDP_HEAD_BASE); sp_help_pseudo->source = sp->source; sp_help_pseudo->destination = sp->dest; sp_help_pseudo->zero_byte = 0; sp_help_pseudo->protocol = 17; sp_help_pseudo->TCP_UDP_len = htons(sp->datalen+SP_UDP_HEAD_BASE); memcpy(sp_pseudo_ip_construct+12, sp_help_udp, sp->datalen+SP_UDP_HEAD_BASE); sp_help_udp->checksum=in_cksum((unsigned short *) sp_pseudo_ip_construct, sp->datalen+12+SP_UDP_HEAD_BASE); #ifdef DEBUG printf("UDP header fixed...\n"); #endif } void transmit_UDP (int sp_fd, char *sp_data, int sp_ipoptlen, int sp_datalen, _32_bit sp_source, unsigned short sp_source_port, _32_bit sp_dest, unsigned short sp_dest_port) { char sp_buffer[1500]; struct sp_data_exchange sp_struct; bzero(sp_buffer,1500); if (sp_ipoptlen!=0) memcpy(sp_buffer+SP_IP_HEAD_BASE,sp_data,sp_ipoptlen); if (sp_data!=NULL) memcpy(sp_buffer+SP_IP_HEAD_BASE+SP_UDP_HEAD_BASE+sp_ipoptlen, sp_data+sp_ipoptlen,sp_datalen); sp_struct.fd = sp_fd; sp_struct.data = sp_data; sp_struct.datalen = sp_datalen; sp_struct.source = sp_source; sp_struct.source_port = sp_source_port; sp_struct.dest = sp_dest; sp_struct.dest_port = sp_dest_port; sp_struct.buffer = sp_buffer; sp_struct.IP_optlen = sp_ipoptlen; sp_struct.TCP_optlen = 0; sp_fix_UDP_packet(&sp_struct); sp_fix_IP_packet(&sp_struct, 17); sp_send_packet(&sp_struct, 17); } #endif #endif sniffit-sniffit-0.4.0/src/sn_generation.h000066400000000000000000000013211301260737100204050ustar00rootroot00000000000000/* Sniffit Packet Generation File */ void exec_generate(struct generate_mask *); void transmit_TCP (int, char *, int, int , int , _32_bit, unsigned short, _32_bit, unsigned short, _32_bit, _32_bit, unsigned short); void transmit_UDP (int, char *, int, int, _32_bit, unsigned short, _32_bit, unsigned short); int open_sending (void); void sp_send_packet (struct sp_data_exchange *, unsigned char); void sp_fix_TCP_packet (struct sp_data_exchange *); void sp_fix_UDP_packet (struct sp_data_exchange *); void sp_fix_IP_packet (struct sp_data_exchange *, unsigned char); sniffit-sniffit-0.4.0/src/sn_global.h000066400000000000000000000005561301260737100175230ustar00rootroot00000000000000/* Sniffit Global File */ /* some things that are better defined before all the rest */ /* currently some option data */ char SNIFMODE, DUMPMODE, PROTOCOLS, ASC, WILDCARD, CFG_FILE, NO_CHKSUM; char INTERACTIVE_EXTEND; int LOGPARAM; /* All option shit */ sniffit-sniffit-0.4.0/src/sn_interface.c000066400000000000000000000601661301260737100202210ustar00rootroot00000000000000/* Sniffit Interface source File */ /* - by: Brecht Claerhout */ #include "sn_config.h" #ifdef INCLUDE_INTERFACE #include #include #include #include #include #include #include #include "sn_curses.h" #include "sn_defines.h" #include "sn_structs.h" #include "sn_interface.h" #include "sn_generation.h" #include "sn_resolv.h" /*** extern stuff ********/ extern char *SHARED, *connection_data, *timing, *running_connections, *logged_connections; extern int *LISTlength, *DATAlength, memory_id; extern unsigned int *TCP_nr_of_packets, *ICMP_nr_of_packets, *UDP_nr_of_packets; unsigned int *IP_nr_of_packets; extern unsigned long *TCP_bytes_in_packets, *UDP_bytes_in_packets; extern int *DESC_LEN; /* For the connection desciption */ extern char INTERACTIVE_EXTEND; extern struct snif_mask *mask; extern struct shared_logged_conn *log_conn; extern FILE *log_dev_stream; extern struct stat log_dev_stat; extern volatile int LOGGING, screen_busy; extern char PACKET_INFO; extern int POINTpos, LISTpos; extern unsigned char COLOR_AVAIL; extern WINDOW *menu_window; extern struct box_window data_box, main_box, mask_box, packets_box; extern int Pid; extern char *logging_device; /*** Screen Parameters ***/ extern int MASK_WINDOW_ROWS, MASK_WINDOW_COLS, MAIN_WINDOW_ROWS, MAIN_WINDOW_COLS; extern int INFO_WINDOW_ROWS, INFO_WINDOW_COLS, DATA_WINDOW_ROWS, DATA_WINDOW_COLS; extern int INFO_WINDOW_X, INFO_WINDOW_Y, MASK_WINDOW_X, MASK_WINDOW_Y; extern int DATA_WINDOW_X, DATA_WINDOW_Y; /*** Sreen operations ***/ void init_screen (void) { initscr(); cbreak(); noecho(); nonl(); clear(); if(has_colors()==TRUE) { COLOR_AVAIL=1; start_color(); init_pair(WIN_COLOR_NORMAL,COLOR_WHITE,COLOR_BLUE); init_pair(WIN_COLOR_POINT,COLOR_BLUE,COLOR_CYAN); init_pair(WIN_COLOR_DATA,COLOR_BLUE,COLOR_CYAN); init_pair(WIN_COLOR_INPUT,COLOR_BLUE,COLOR_CYAN); init_pair(WIN_COLOR_MENU,COLOR_BLUE,COLOR_CYAN); init_pair(WIN_COLOR_PACKET_INFO,COLOR_BLUE,COLOR_CYAN); } else { COLOR_AVAIL=0; } MAIN_WINDOW_ROWS = LINES-5; MAIN_WINDOW_COLS = COLS; MASK_WINDOW_ROWS = 4; MASK_WINDOW_COLS = COLS; MASK_WINDOW_X = 0; MASK_WINDOW_Y = LINES-5; INFO_WINDOW_ROWS = 8; INFO_WINDOW_COLS = 35; INFO_WINDOW_X = 3; INFO_WINDOW_Y = MAIN_WINDOW_ROWS-INFO_WINDOW_ROWS-2; DATA_WINDOW_ROWS = (MAIN_WINDOW_ROWS/3)*2; DATA_WINDOW_COLS = (MAIN_WINDOW_COLS/3)*2; DATA_WINDOW_X = COLS-DATA_WINDOW_COLS-2; DATA_WINDOW_Y = 3; exit_func(screen_exit); if( (COLS<80)||(LINES<18) ) exit(0); }; void f_box_window (struct box_window *Win, int num_lines, int num_cols, int begy,int begx, int col_mode) /* col_mode : color selection */ { int i; Win->main_window=newwin(num_lines,num_cols,begy,begx); Win->work_window=subwin(Win->main_window,num_lines-2,num_cols-2,begy+1,begx+1); if(COLOR_AVAIL) { switch(col_mode) { case 0: wattrset(Win->main_window,COLOR_PAIR(WIN_COLOR_NORMAL)); wattrset(Win->work_window,COLOR_PAIR(WIN_COLOR_NORMAL)); break; case 1: wattrset(Win->main_window,COLOR_PAIR(WIN_COLOR_PACKET_INFO)); wattrset(Win->work_window,COLOR_PAIR(WIN_COLOR_PACKET_INFO)); break; default:break; } for(i=0;i<=(num_lines-2);i++) { wmove(Win->work_window,i,0); whline(Win->work_window,' ',num_cols-2); } } keypad(Win->work_window,1); box(Win->main_window,ACS_VLINE,ACS_HLINE); mvwprintw(Win->main_window,0,3,"Sniffit %s",VERSION); wmove(Win->work_window,0,0); wnoutrefresh(Win->main_window);wnoutrefresh(Win->work_window); doupdate(); } void data_window (struct box_window *Win, struct box_window *P_Win, int num_lines, int num_cols, int begy,int begx, char *buffer, int listitem) { int i=0, j=0; struct shared_conn_data *conn; conn = (struct shared_conn_data *) buffer; while((j=CONNECTION_CAPACITY+1) return; j=0; Win->main_window=newwin(num_lines,num_cols,begy,begx); Win->work_window=subwin(Win->main_window,num_lines-5,num_cols-2,begy+1,begx+1); scrollok(Win->work_window,1); if(COLOR_AVAIL) wattrset(Win->main_window,COLOR_PAIR(WIN_COLOR_DATA)); box(Win->main_window,ACS_VLINE,ACS_HLINE); wmove(Win->main_window,num_lines-3,1); whline(Win->main_window,ACS_HLINE,num_cols-2); wmove(Win->main_window,num_lines-2,1); whline(Win->main_window,' ',num_cols-2); wmove(Win->main_window,num_lines-2,2); waddstr(Win->main_window, conn[i].connection); strcpy(log_conn->log_enter,conn[i].connection); wmove(Win->work_window,0,0); wnoutrefresh(Win->main_window);wnoutrefresh(Win->work_window); doupdate(); } void data_device (char *buffer, int listitem) { int i=0, j=0; struct shared_conn_data *conn; conn = (struct shared_conn_data *) buffer; while((j=CONNECTION_CAPACITY+1) return; strcpy(log_conn->log_enter, conn[i].connection); } void mask_status (struct box_window *Work_win) { unsigned char *ad; int i; wmove(Work_win->work_window,0,1); for(i=0;i<2;i++) {wmove(Work_win->work_window,i,0); whline(Work_win->work_window,' ',COLS-2);} wmove(Work_win->work_window,0,1); wprintw(Work_win->work_window,"Source IP : "); ad=&(mask->source_ip); if(mask->source_ip==0) wprintw(Work_win->work_window,"All"); else wprintw(Work_win->work_window,"%u.%u.%u.%u",ad[0],ad[1],ad[2],ad[3]); wmove(Work_win->work_window,1,1); wprintw(Work_win->work_window,"Destination IP: "); ad=&(mask->destination_ip); if(mask->destination_ip==0) wprintw(Work_win->work_window,"All"); else wprintw(Work_win->work_window,"%u.%u.%u.%u",ad[0],ad[1],ad[2],ad[3]); wmove(Work_win->work_window,0,35); wprintw(Work_win->work_window,"Source PORT : "); if(mask->source_port==0) wprintw(Work_win->work_window,"All"); else wprintw(Work_win->work_window,"%u",mask->source_port); wmove(Work_win->work_window,1,35); wprintw(Work_win->work_window,"Destination PORT: "); if(mask->destination_port==0) wprintw(Work_win->work_window,"All"); else wprintw(Work_win->work_window,"%u",mask->destination_port); wnoutrefresh(Work_win->main_window); wnoutrefresh(Work_win->work_window); doupdate(); } void fill_box_window (struct box_window *Work_win, char *buffer, int begin_item, int boxlen, int rowlen) /* 0 is the first item */ { int i=0, j=0, line=0; struct shared_conn_data *conn; conn = (struct shared_conn_data *) buffer; while((j=CONNECTION_CAPACITY+1) return; j=0; while((linework_window,line,0); whline(Work_win->work_window,' ',rowlen); if(strcmp(log_conn->log_enter,conn[i+j].connection) != 0) { if(INTERACTIVE_EXTEND==1) wprintw(Work_win->work_window," %s : %s",conn[i+j].connection,conn[i+j].desc); else wprintw(Work_win->work_window," %s",conn[i+j].connection); } else { if(INTERACTIVE_EXTEND==1) wprintw(Work_win->work_window," %s : [LOGGED]", conn[i+j].connection); else wprintw(Work_win->work_window," %s [LOGGED]", conn[i+j].connection); } line++; } j++; } for(i=line;iwork_window,i,0); whline(Work_win->work_window,' ',rowlen); }; wnoutrefresh(Work_win->work_window); } void point_item (struct box_window *Work_win, char *buffer, int item, int begin_item, int boxlen, int rowlen) { int i=0, j=0; struct shared_conn_data *conn; if(item<0) return; /* POINTpos 0 = first item -1 = no items */ /* LISTlength 0 = 1 -1 = no items */ /* DANGER - there should always be >= */ /* connections than 'item' */ conn = (struct shared_conn_data *) buffer; while((j=CONNECTION_CAPACITY+1) return; j=0; #ifdef DEBUG debug_msg(conn[i].connection); #endif if(COLOR_AVAIL!=0) wattrset(Work_win->work_window,COLOR_PAIR(WIN_COLOR_POINT)); else wattron(Work_win->work_window,A_REVERSE); wmove(Work_win->work_window,item-begin_item,0); whline(Work_win->work_window,' ',rowlen); if(strcmp(log_conn->log_enter,conn[i].connection)!=0) { if(INTERACTIVE_EXTEND==1) mvwprintw(Work_win->work_window,item-begin_item,0, " %s : %s", conn[i].connection, conn[i].desc); else mvwprintw(Work_win->work_window,item-begin_item,0," %s", conn[i].connection); } else { if(INTERACTIVE_EXTEND==1) mvwprintw(Work_win->work_window,item-begin_item,0, " %s : [LOGGED]",conn[i].connection); else mvwprintw(Work_win->work_window,item-begin_item,0, " %s [LOGGED]",conn[i].connection); } wnoutrefresh(Work_win->work_window); if(COLOR_AVAIL!=0) wattrset(Work_win->work_window,COLOR_PAIR(WIN_COLOR_NORMAL)); else wattroff(Work_win->work_window,A_REVERSE); } void forced_refresh (void) { #ifdef DEBUG char debug_line[200]; #endif if((POINTpos<0)&&(*LISTlength>=0)) POINTpos=0; if((POINTpos>*LISTlength)&&(*LISTlength>=0)) POINTpos=*LISTlength; if((POINTpos>*LISTlength)&&(*LISTlength<0)) POINTpos=-1; while(screen_busy!=0) {}; /* wait till screen operations stop */ #ifdef DEBUG sprintf(debug_line,"FIX: POINTpos: %d LISTlength: %d LISTpos: %d\n",POINTpos,*LISTlength,LISTpos); debug_msg(debug_line); #endif fill_box_window(&main_box, running_connections,LISTpos, MAIN_WINDOW_ROWS-2,MAIN_WINDOW_COLS-2); point_item(&main_box, running_connections, POINTpos,LISTpos, MAIN_WINDOW_ROWS-2,MAIN_WINDOW_COLS-2); if((LOGGING==1)&&(logging_device==NULL)) { touchwin(data_box.main_window);touchwin(data_box.work_window); wnoutrefresh(data_box.main_window);wnoutrefresh(data_box.work_window); } if(PACKET_INFO==1) { touchwin(packets_box.main_window);touchwin(packets_box.work_window); wnoutrefresh(packets_box.main_window); wnoutrefresh(packets_box.work_window); } doupdate(); } void menu_line (void) { int i; if(menu_window==NULL) menu_window=newwin (1,COLS,LINES-1,0); if(COLOR_AVAIL!=0) wattrset(menu_window,COLOR_PAIR(WIN_COLOR_MENU)); else wattron(menu_window,A_REVERSE); wmove(menu_window,0,0); whline(menu_window,' ',COLS); mvwaddstr(menu_window,0,0,MENU); wnoutrefresh(menu_window); } char *input_field(char *string, char *input, int flag) { int i; char dummy[500]; WINDOW *Work_txt, *Work_inp; #ifdef DEBUG debug_msg("IntAct: Input Field activated"); #endif Work_txt=newwin(1,COLS,LINES-1,0); Work_inp=newwin(1,50,LINES-1,strlen(string)); if(COLOR_AVAIL!=0) { wattrset(Work_inp,COLOR_PAIR(WIN_COLOR_INPUT)); wattrset(Work_txt,COLOR_PAIR(WIN_COLOR_NORMAL)); } whline(Work_txt,' ',COLS); whline(Work_inp,' ',50); mvwaddstr(Work_txt,0,0,string); while(screen_busy!=0) {}; wnoutrefresh(Work_txt);wnoutrefresh(Work_inp); doupdate(); echo();mvwgetstr(Work_inp,0,0,dummy);noecho(); if(input!=NULL) {strcpy(input,dummy);} delwin(Work_inp);delwin(Work_txt); menu_line(); forced_refresh(); #ifdef DEBUG debug_msg("IntAct: Input Field Ended"); #endif return input; } void exec_mask (void) { LISTpos=0; POINTpos=-1; /* otherwise we get never ending loop */ clear_shared_mem(1); mask_status(&mask_box); if(LOGGING==1) stop_logging(); forced_refresh(); } /* signaling */ void sig_blocking(char on_off, int sig) { sigset_t set; sigemptyset(&set);sigaddset(&set,sig); if(on_off==1) {sigprocmask(SIG_BLOCK,&set,NULL);} else {sigprocmask(SIG_UNBLOCK,&set,NULL);} } void set_signal (int signum, sig_hand new_action) { struct sigaction new_sigusr; sigset_t sig_mask; sigemptyset(&sig_mask); sigaddset(&sig_mask,SIGUSR1); sigaddset(&sig_mask,SIGALRM); new_sigusr.sa_handler=new_action; new_sigusr.sa_mask=sig_mask; new_sigusr.sa_flags=0; sigaction(signum,&new_sigusr,NULL); } void interaction (int sig) /* invoked when data arrives */ { int i; struct shared_conn_data *conn; /* timeout increase */ conn = (struct shared_conn_data *) running_connections; for(i=0;ilog_enter[0]==0)) stop_logging(); screen_busy=1; if((LOGGING==1)&&(*DATAlength!=0)) { if(logging_device==NULL) { for(i=0;i<*DATAlength;i++) waddch(data_box.work_window, isprint(*(connection_data+i))? *(connection_data+i):'.'); } else { for(i=0;i<*DATAlength;i++) fputc(*(connection_data+i),log_dev_stream); fflush(log_dev_stream); } *DATAlength=0; } screen_busy=0; forced_refresh(); set_signal(SIGUSR1,interaction); } void packet_info_handler (int signum) { #ifdef DEBUG debug_msg("ALARM RANG"); #endif screen_busy=1; mvwprintw(packets_box.work_window,0,1,"IP packets/sec. : % 12u",(*IP_nr_of_packets)/INFO_TIMER); mvwprintw(packets_box.work_window,1,1,"TCP packets/sec. : % 12u",(*TCP_nr_of_packets)/INFO_TIMER); mvwprintw(packets_box.work_window,2,1,"ICMP packets/sec.: % 12u",(*ICMP_nr_of_packets)/INFO_TIMER); mvwprintw(packets_box.work_window,3,1,"UDP packets/sec. : % 12u",(*UDP_nr_of_packets)/INFO_TIMER); mvwprintw(packets_box.work_window,4,1,"bytes/sec. (TCP) : % 12ld",(*TCP_bytes_in_packets)/INFO_TIMER); mvwprintw(packets_box.work_window,5,1,"bytes/sec. (UDP) : % 12ld",(*UDP_bytes_in_packets)/INFO_TIMER); screen_busy=0; forced_refresh(); /* reinstall handler, reset alarm */ *IP_nr_of_packets=0; *TCP_nr_of_packets=*TCP_bytes_in_packets=0; *ICMP_nr_of_packets=0; *UDP_nr_of_packets=*UDP_bytes_in_packets=0; set_signal(SIGALRM, packet_info_handler); alarm(INFO_TIMER); } /* at/on_exit's */ void child_exit (void) { kill(Pid,SIGKILL); }; void screen_exit (void) { endwin(); /* next line added by Edward Betts , should not be needed * because endwin should be calling it, without this the console has no echo * after exiting in an xterm */ reset_shell_mode(); }; void mem_exit (void) { if(shmctl(memory_id,IPC_RMID,0)<0) {perror("Sniffer Hartattack (you are fucked!) ");exit(0);}; } /* Some other stuff */ void stop_logging (void) { LOGGING=0; log_conn->log_enter[0]=0; if(logging_device==NULL) {delwin(data_box.work_window); delwin(data_box.main_window);} forced_refresh(); } void stop_packet_info (void) { PACKET_INFO=0; alarm(0); delwin(packets_box.work_window), delwin(packets_box.main_window); forced_refresh(); } int add_itemlist(char *buffer, char *string, char *desc) { int i, to_help, to_item; struct shared_conn_data *conn; /*invoked every time a packet comes in */ conn = (struct shared_conn_data *) buffer; for(i=0;ito_help) if(strcmp(conn[i].connection,log_conn->log_enter)!=0) { to_help=conn[i].timeout; to_item=i; } strcpy(conn[to_item].connection, string); strcpy(conn[to_item].desc, desc); /* For description of connect */ conn[to_item].timeout=0; return to_item; } int del_itemlist(char *buffer, char *string) { int i; struct shared_conn_data *conn; conn = (struct shared_conn_data *) buffer; for(i=0;ilog_enter, string)==0) {log_conn->log_enter[0]=0;} return i; } return -1; } void clear_shared_mem(char mode) /* mode = 0 all */ /* mode = 1 keep mask */ /* keep packet count */ { int i; struct shared_conn_data *conn; *timing=1; *DATAlength=0; *LISTlength=-1; if(mode==0) { mask->source_ip=mask->destination_ip=mask->source_port=mask->destination_port=0; *IP_nr_of_packets=0; *TCP_nr_of_packets=*TCP_bytes_in_packets=0; *ICMP_nr_of_packets=0; *UDP_nr_of_packets=*UDP_bytes_in_packets=0; } log_conn->log_enter[0]=0; conn = (struct shared_conn_data *) running_connections; for(i=0;i=CONNECTION_CAPACITY+1) return; j=0; strcpy(e_dummy,conn[i].connection); /* OLD STUFF -- Previous line format */ /* strtok(e_dummy," "); strcpy(esource,strtok(NULL," ")); strcpy(es_port,strtok(NULL," ")); strtok(NULL," "); strcpy(edest,strtok(NULL," ")); strcpy(ed_port,strtok(NULL," ")); */ strcpy(esource,strtok(e_dummy," ")); strcpy(es_port,strtok(NULL," ")); strtok(NULL," "); strcpy(edest,strtok(NULL," ")); strcpy(ed_port,strtok(NULL," ")); #ifdef DEBUG debug_msg(esource); debug_msg(es_port); debug_msg(edest); debug_msg(ed_port); #endif } /*** Main interface program */ void run_interface(void) { int i,key_hit; char dummy[100]; char exec_s[20],exec_sp[20],exec_d[20],exec_dp[20]; struct generate_mask generate; POINTpos=-1; *LISTlength=-1; LISTpos=0; LOGGING=0; PACKET_INFO=0; screen_busy=0; set_signal (SIGCHLD, SIG_IGN); set_signal(SIGUSR1,interaction); init_screen(); /* The whole screen setup */ if( MAIN_WINDOW_COLS-2-CONN_NAMELEN-1 < DESC_BYTES) *DESC_LEN=MAIN_WINDOW_COLS-2-CONN_NAMELEN-1; else *DESC_LEN=DESC_BYTES; f_box_window(&mask_box,MASK_WINDOW_ROWS,MASK_WINDOW_COLS,MASK_WINDOW_Y,MASK_WINDOW_X,0); mask_status(&mask_box); f_box_window(&main_box,MAIN_WINDOW_ROWS,MAIN_WINDOW_COLS,0,0,0); fill_box_window(&main_box, running_connections,LISTpos, MAIN_WINDOW_ROWS-2,MAIN_WINDOW_COLS-2); point_item(&main_box, running_connections,POINTpos,LISTpos, MAIN_WINDOW_ROWS-2,MAIN_WINDOW_COLS-2); menu_window=NULL; menu_line(); doupdate(); /* And..... draw it! */ while(1) { key_hit=wgetch(main_box.work_window); #ifdef DEBUG debug_msg("IntAct: Key Hit Received"); #endif sig_blocking(1, SIGALRM); sig_blocking(1, SIGUSR1); switch(key_hit) { case KEY_DOWN: case 'J': case 'j': if(POINTpos>=*LISTlength) break; if( POINTpos<(LISTpos+(MAIN_WINDOW_ROWS-3)) ) POINTpos++; else {if(LISTpos>=*LISTlength) break; LISTpos++; POINTpos++;}; forced_refresh(); break; case KEY_UP: case 'K': case 'k': if(POINTpos==0) break; if(POINTpos>LISTpos) POINTpos--; else {if(LISTpos==0) break; LISTpos--; POINTpos--;}; forced_refresh(); break; case ENTER: if(*LISTlength<0) break; if(LOGGING==0) { if(logging_device==NULL) data_window(&data_box,&main_box,DATA_WINDOW_ROWS, DATA_WINDOW_COLS,DATA_WINDOW_Y, DATA_WINDOW_X, running_connections,POINTpos); else data_device(running_connections,POINTpos); LOGGING=1; } else { stop_logging(); if(logging_device==NULL) data_window(&data_box,&main_box,DATA_WINDOW_ROWS, DATA_WINDOW_COLS,DATA_WINDOW_Y, DATA_WINDOW_X, running_connections,POINTpos); else data_device(running_connections,POINTpos); LOGGING=1; }; break; case 'N': case 'n': if(PACKET_INFO==0) { f_box_window(&packets_box,INFO_WINDOW_ROWS,INFO_WINDOW_COLS, INFO_WINDOW_Y, INFO_WINDOW_X ,1); PACKET_INFO=1; *IP_nr_of_packets=0; *TCP_nr_of_packets=*TCP_bytes_in_packets=0; *ICMP_nr_of_packets=0; *UDP_nr_of_packets=*UDP_bytes_in_packets=0; packet_info_handler(SIGALRM); } else {stop_packet_info();} break; #ifdef GENERATION case 'g': case 'G': input_field("Source IP for PKT Generation: ",dummy,1); generate.source_ip=getaddrbyname(dummy); input_field("Source Port: ",dummy,1); generate.source_port=atoi(dummy); input_field("Dest IP for PKT Generation: ",dummy,1); generate.dest_ip=getaddrbyname(dummy); input_field("Dest Port: ",dummy,1); generate.dest_port=atoi(dummy); input_field("Number of PKTs: ",dummy,1); generate.pkt_no=atoi(dummy); exec_generate(&generate); break; #endif case 'q': case 'Q': case KEY_F(10): if(LOGGING==1) {stop_logging();} else {kill(Pid,SIGKILL);exit(0);} break; case '1': case KEY_F(1): input_field("Source Ip: ",dummy,0); mask->source_ip=getaddrbyname(dummy); exec_mask(); break; case '2': case KEY_F(2): input_field("Destination Ip: ",dummy,0); mask->destination_ip=getaddrbyname(dummy); exec_mask(); break; case '3': case KEY_F(3): input_field("Source Port: ",dummy,0); mask->source_port=atoi(dummy); exec_mask(); break; case '4': case KEY_F(4): input_field("Destination Port: ",dummy,0); mask->destination_port=atoi(dummy); exec_mask(); break; case '5': case KEY_F(5): if(*LISTlength<0) break; if(access("./sniffit_key5", X_OK)<0) break; create_arguments(exec_s,exec_sp,exec_d, exec_dp,running_connections,POINTpos); if(fork()==0) /* CHILD */ { close(0); close(1); close(2); sig_blocking(0, SIGALRM); sig_blocking(0, SIGUSR1); set_signal(SIGALRM,SIG_DFL); set_signal(SIGUSR1,SIG_DFL); execl("./sniffit_key5","sniffit_key5",exec_s,exec_sp,exec_d,exec_dp,NULL); exit(0); }; break; case '6': case KEY_F(6): if(*LISTlength<0) break; if(access("./sniffit_key6", X_OK)<0) break; create_arguments(exec_s,exec_sp,exec_d, exec_dp,running_connections,POINTpos); if(fork()==0) /* CHILD */ { close(0); close(1); close(2); sig_blocking(0, SIGALRM); sig_blocking(0, SIGUSR1); set_signal(SIGALRM,SIG_DFL); set_signal(SIGUSR1,SIG_DFL); execl("./sniffit_key6","sniffit_key6",exec_s,exec_sp,exec_d,exec_dp,NULL); exit(0); }; break; case '7': case KEY_F(7): if(*LISTlength<0) break; if(access("./sniffit_key7", X_OK)<0) break; create_arguments(exec_s,exec_sp,exec_d, exec_dp,running_connections,POINTpos); if(fork()==0) /* CHILD */ { sig_blocking(0, SIGALRM); sig_blocking(0, SIGUSR1); set_signal(SIGALRM,SIG_DFL); set_signal(SIGUSR1,SIG_DFL); close(0); close(1); close(2); execl("./sniffit_key7","sniffit_key7",exec_s,exec_sp,exec_d,exec_dp,NULL); exit(0); }; break; case '8': case KEY_F(8): if(*LISTlength<0) break; if(access("./sniffit_key8", X_OK)<0) break; create_arguments(exec_s,exec_sp,exec_d, exec_dp,running_connections,POINTpos); if(fork()==0) /* CHILD */ { sig_blocking(0, SIGALRM); sig_blocking(0, SIGUSR1); set_signal(SIGALRM,SIG_DFL); set_signal(SIGUSR1,SIG_DFL); close(0); close(1); close(2); execl("./sniffit_key8","sniffit_key8",exec_s,exec_sp,exec_d,exec_dp,NULL); exit(0); }; break; case 'r': case 'R': /* mask does an auto reset */ exec_mask(); break; default: break; } sig_blocking(0, SIGALRM); sig_blocking(0, SIGUSR1); } }; #endif sniffit-sniffit-0.4.0/src/sn_interface.h000066400000000000000000000026141301260737100202200ustar00rootroot00000000000000/* Sniffit Data File */ #include "pcap.h" typedef void (*sig_hand)(int ); /* sighandler_t gave errors, weird */ int add_itemlist(char *, char *, char *); void child_exit (void); void clear_shared_mem(char); void data_device (char *, int); void data_window (struct box_window *, struct box_window *, int, int, int, int, char *, int); int del_itemlist(char *, char *); void exec_mask (void); void f_box_window (struct box_window *, int, int, int, int, int); void fill_box_window (struct box_window *, char *, int, int, int); void forced_refresh (void); void init_screen (void); char *input_field(char *, char *, int); void interaction (int); void mask_status (struct box_window *); void mem_exit (void); void menu_line (void); void point_item (struct box_window *, char *, int, int, int, int); void run_interface (void); void screen_exit (void); void set_signal (int, sig_hand); void sig_blocking(char, int); void stop_logging (void); int check_mask (const struct packetheader *,const unsigned char *, char *, char *, char *, struct unwrap *); pcap_handler interactive_packethandler( char *, const struct packetheader *, const unsigned char *); void stop_packet_info (void); void packet_info_handler (int); void create_arguments(char *, char *, char *, char *, char *, int); sniffit-sniffit-0.4.0/src/sn_logfile.c000066400000000000000000000043031301260737100176710ustar00rootroot00000000000000/* Sniffit Logfile include file */ /* - by: Brecht Claerhout */ #include "sn_config.h" #include #include #include #include #include #include #include "sn_defines.h" #include "sn_structs.h" #include "sn_logfile.h" extern char Logfile[250]; /* name of logfile */ extern FILE *LogFILE; /* logfile stream */ extern char LOGPARAM; extern char DUMPMODE; /* recorded or not */ void logfile_exit (void) /* at/on_exit closing of logfile */ { printf("Sniffit Logging session ended.\n"); print_logline("Sniffit session ended."); fflush(LogFILE); fclose(LogFILE); } char *gettime (void) { time_t t; char *tm; static char recorded[] = "Recorded"; time(&t); tm=ctime(&t); tm[24]=0; return (DUMPMODE&16)?recorded:tm; } void print_logline (char *logline) { fprintf(LogFILE,"[%s] - %s\n",gettime(),logline); fflush(LogFILE); } void print_ftp_user (char *conn, char *user) { char line[250]; snprintf(line,sizeof(line),"%s: USER [%s]",conn,user); print_logline (line); } void print_ftp_pass(char *conn, char *pass) { char line[250]; snprintf(line,sizeof(line),"%s: PASS [%s]",conn,pass); print_logline (line); } void print_login (char *conn, char *login) { char line[250]; snprintf(line,sizeof(line),"%s: login [%s]",conn,login); print_logline (line); } void print_mail (char *conn, char *msg) { char line[250]; snprintf(line,sizeof(line),"%s: mail [%s]",conn,msg); print_logline (line); } void print_pwd (char *conn, char *pwd) { char line[250]; snprintf(line,sizeof(line),"%s: password [%s]",conn,pwd); print_logline (line); } void print_conn (char *conn, char *msg) { char line[250]; snprintf(line,sizeof(line),"%s: %s",conn,msg); print_logline (line); } void open_logfile (void) { if(Logfile[0]==0) strcpy(Logfile,"sniffit.log"); LogFILE=fopen(Logfile,"a"); if(LogFILE==NULL) printf("Sniffit heartattack.. couldn't create/open logfile...\n"), exit(1); exit_func(logfile_exit); fchmod(LogFILE, S_IWUSR|S_IRUSR); print_logline("Sniffit session started."); printf("Sniffit Logging started.\n"); } sniffit-sniffit-0.4.0/src/sn_logfile.h000066400000000000000000000010341301260737100176740ustar00rootroot00000000000000/* Sniffit Data File */ #define LOG_NO_DETECT 99 #define LOG_NO_LOG 0 #define LOG_LOGIN 1 #define LOG_LOGIN_RECORDED 2 #define LOG_PWD 3 #define LOG_PWD_RECORDED 4 void logfile_exit (void); char *gettime (void); void print_logline (char *); void print_ftp_user (char *, char *); void print_ftp_pass(char *, char *); void print_login (char *, char *); void print_pwd (char *, char *); void print_conn (char *, char *); void print_mail (char *, char *); void open_logfile (void); sniffit-sniffit-0.4.0/src/sn_packets.c000066400000000000000000000162441301260737100177110ustar00rootroot00000000000000/* Sniffit Packet Discription File */ /* - by: Brecht Claerhout */ #include "sn_config.h" #include "sn_defines.h" #include "sn_structs.h" #include #include extern int PROTO_HEAD; extern char NO_CHKSUM; /* This routine stolen from ping.c */ unsigned short in_cksum(unsigned short *addr,int len) { register int nleft = len; /* leave this alone.. my opinion is that the */ register unsigned short *w = addr; /* register is needed to make it work for both */ register int sum = 0; /* BIG and LITTLE endian machines */ unsigned short answer = 0; /* but then again, who am I to make such statement */ while (nleft > 1) { sum += *w++; nleft -= 2; } if (nleft == 1) { *(unsigned char *)(&answer) = *(unsigned char *)w ; sum += answer; } sum = (sum >> 16) + (sum & 0xffff); sum += (sum >> 16); answer = ~sum; return(answer); } int unwrap_packet (unsigned char *sp, struct unwrap *unwrapped) { struct IP_header IPhead; struct TCP_header TCPhead; struct ICMP_header ICMPhead; struct UDP_header UDPhead; int i; short int dummy; /* 2 bytes, important */ /* printf("\n"); for(i=0;i<20;i++) printf("%X ",sp[i]); printf("\n"); */ memcpy(&IPhead,(sp+PROTO_HEAD),sizeof(struct IP_header)); /* IP header Conversion */ unwrapped->IP_len = (IPhead.verlen & 0xF) << 2; unwrapped->TCP_len = 0; /* Reset structure NEEDED!!! */ unwrapped->UDP_len = 0; unwrapped->DATA_len= 0; unwrapped->FRAG_f = 0; unwrapped->FRAG_nf = 0; if(NO_CHKSUM == 0) { sp[PROTO_HEAD+10]=0; /* reset checksum to zero, Q&D way*/ sp[PROTO_HEAD+11]=0; if(in_cksum((sp+PROTO_HEAD),unwrapped->IP_len) != IPhead.checksum) { #ifdef DEBUG_ONSCREEN printf("Packet dropped... (invalid IP chksum)\n"); printf("%X %X (len %d)\n",in_cksum((sp+PROTO_HEAD),unwrapped->IP_len),IPhead.checksum,unwrapped->IP_len); #endif return NO_IP; } if(0) { #ifdef DEBUG_ONSCREEN printf("Packet dropped... (invalid IP version)\n"); #endif return NO_IP_4; } memcpy((sp+PROTO_HEAD),&IPhead,sizeof(struct IP_header)); /* restore orig buffer */ /* general programming rule */ } #ifdef DEBUG_ONSCREEN printf("IPheadlen: %d total length: %d\n", unwrapped->IP_len, ntohs(IPhead.length)); #endif dummy=ntohs(IPhead.flag_offset); dummy<<=3; if( dummy!=0 ) /* we have offset */ { unwrapped->FRAG_nf = 1; } dummy=ntohs(IPhead.flag_offset); dummy>>=13; if( (dummy&IP_MF)&&(unwrapped->FRAG_nf==0) ) /* first frag */ { unwrapped->FRAG_f = 1; } if(IPhead.protocol == TCP ) /* TCP */ { if(unwrapped->FRAG_nf == 0) /* packet contains TCP header */ { if( (ntohs(IPhead.length)-(unwrapped->IP_len))<20 ) { if(unwrapped->FRAG_f==1) {unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len); if(unwrapped->DATA_len<0) {unwrapped->DATA_len=0; return CORRUPT_IP;} return TCP_FRAG_HEAD; } else {return CORRUPT_IP;} } memcpy(&TCPhead,(sp+PROTO_HEAD+(unwrapped->IP_len)), sizeof(struct TCP_header)); unwrapped->TCP_len = ntohs(TCPhead.offset_flag) & 0xF000; unwrapped->TCP_len >>= 10; unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len) - (unwrapped->TCP_len); /* IP options can not cause SEGFAULT */ if(unwrapped->DATA_len<0) /* Fragmented TCP options */ { if(unwrapped->FRAG_f==1) {unwrapped->TCP_len=0; unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len); if(unwrapped->DATA_len<0) {unwrapped->DATA_len=0; return CORRUPT_IP;} return TCP_FRAG_HEAD; } else {return CORRUPT_IP;} } } else { unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len); if(unwrapped->DATA_len<0) {unwrapped->DATA_len=0; return CORRUPT_IP;} } return TCP; } if(IPhead.protocol == ICMP ) /* ICMP */ { if(unwrapped->FRAG_nf == 0) /* Should contain header */ { if( (ntohs(IPhead.length)-(unwrapped->IP_len))<4 ) {return NOT_SUPPORTED;}; /* no handling of frag headers*/ memcpy(&ICMPhead,(sp+PROTO_HEAD+(unwrapped->IP_len)), sizeof(struct ICMP_header)); unwrapped->ICMP_len = ICMP_HEADLENGTH; unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len) - (unwrapped->ICMP_len); if(unwrapped->DATA_len<0) { if(unwrapped->FRAG_f==1) {unwrapped->TCP_len=0; unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len); if(unwrapped->DATA_len<0) {unwrapped->DATA_len=0; return CORRUPT_IP;} return NOT_SUPPORTED; /* don't handle fragmented ICMP */ } else {return CORRUPT_IP;} } return ICMP; } else { return NOT_SUPPORTED; /* don't handle fragmented ICMP */ } } if(IPhead.protocol == UDP ) /* UDP */ { if(unwrapped->FRAG_nf == 0) { if( ((IPhead.length)-(unwrapped->IP_len))<8 ) {return NOT_SUPPORTED;}; /* don't handle frag. header */ memcpy(&UDPhead,(sp+PROTO_HEAD+(unwrapped->IP_len)), sizeof(struct UDP_header)); unwrapped->UDP_len = UDP_HEADLENGTH; unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len) - (unwrapped->UDP_len); if(unwrapped->DATA_len<0) { if(unwrapped->FRAG_f==1) {unwrapped->UDP_len=0; unwrapped->DATA_len = ntohs(IPhead.length) - (unwrapped->IP_len); if(unwrapped->DATA_len<0) {unwrapped->DATA_len=0; return CORRUPT_IP;} return NOT_SUPPORTED; } /* don't handle fragmented UDP */ else {return CORRUPT_IP;} } return UDP; } else { return NOT_SUPPORTED; /* don't handle fragmented UDP */ } } return NOT_SUPPORTED; } sniffit-sniffit-0.4.0/src/sn_packets.h000066400000000000000000000003731301260737100177120ustar00rootroot00000000000000/* Sniffit Packets include file */ #ifndef _SN_PACKETS_H_ #define _SN_PACKETS_H_ unsigned short in_cksum(unsigned short *,int); int unwrap_packet (const unsigned char *, struct unwrap *); #endif sniffit-sniffit-0.4.0/src/sn_packetstructs.h000066400000000000000000000030741301260737100211600ustar00rootroot00000000000000/* Sniffit Packet Discription File */ #ifndef _SN_PACKETSTRUCTS_H_ #define _SN_PACKETSTRUCTS_H_ #include struct packetheader { struct timeval ts; /* time stamp */ unsigned long caplen; /* length of portion present */ unsigned long len; /* length this packet (off wire) */ }; struct IP_header /* The IPheader (without options) */ { unsigned char verlen, type; unsigned short length, ID, flag_offset; unsigned char TTL, protocol; unsigned short checksum; _32_bit source, destination; }; struct pseudo_IP_header { _32_bit source, destination; char zero_byte, protocol; unsigned short TCP_UDP_len; }; struct TCP_header /* The TCP header (without options) */ { unsigned short source, destination; _32_bit seq_nr, ACK_nr; unsigned short offset_flag, window, checksum, urgent; }; struct ICMP_header /* The ICMP header */ { unsigned char type, code; unsigned short checksum; }; struct UDP_header /* The UDP header */ { unsigned short source, destination; unsigned short length, checksum; }; struct unwrap /* some extra info */ { int IP_len, TCP_len, ICMP_len, UDP_len; /* header lengths */ int DATA_len; /* keep signed! */ char FRAG_f; /* first fragment */ char FRAG_nf; /* not the first fragment */ }; #endifsniffit-sniffit-0.4.0/src/sn_plugins.h000066400000000000000000000022141301260737100177350ustar00rootroot00000000000000/* Sniffit Pluginfile include file - Brecht Claerhout */ /* You should install the plugins, by adding three lines. */ /* You should define a Plugin name, an alias for the plugin function, */ /* and include the source code of it. */ /* Example: */ /* #define PLUGIN0_NAME "Dummy Plugin" */ /* #define PLUGIN0(x) PL_real_function_name(x) */ /* #define PLUGIN0_INIT() PL_init_real_function_name() (optional) */ /* #include "plugin_include_filename.plug" */ /* PLUGIN0_NAME and PLUGIN0 are fixed names, numbers can go from 0 to 9 */ /* These to plugins come standard with the Sniffit package as examples. */ /* the "Dummy Plugin" is quite useless, but the "DNS Plugin" is going */ /* to be appreciated by some of you. Read the PLUGIN-HOWTO file. */ #define PLUGIN0_NAME "Dummy Plugin" #define PLUGIN0(x) PL_dummy_plugin(x) #include "dummy_plugin.plug" #define PLUGIN1_NAME "DNS Plugin" #define PLUGIN1(x) PL_DNS_plugin(x) #include "dns_plugin.plug" sniffit-sniffit-0.4.0/src/sn_resolv.c000066400000000000000000000011441301260737100175620ustar00rootroot00000000000000/* Sniffit hostname resolving part */ /* - getaddrbyname: Godmar Back / Shudoh Kazuyuki */ #include "sn_defines.h" #include #include _32_bit getaddrbyname (const char *name) { _32_bit ret; struct hostent *he; if ((ret = inet_addr (name)) != INADDR_NONE) { /* dotted-decimal */ return ret; } else { if (!(he = gethostbyname (name))) { #ifdef DEBUG debug_msg ("GetAddr: Couldn't get host."); #endif /* perror(name); */ } return he ? *(_32_bit *) *he->h_addr_list : 0; } } sniffit-sniffit-0.4.0/src/sn_resolv.h000066400000000000000000000002601301260737100175650ustar00rootroot00000000000000/* Sniffit hostname resolving part include */ #ifndef _SN_RESOLV_H_ #define _SN_RESOLV_H_ extern _32_bit getaddrbyname (const char *); #endifsniffit-sniffit-0.4.0/src/sn_structs.h000066400000000000000000000055141301260737100177710ustar00rootroot00000000000000/* Sniffit Structs File */ #ifndef _SN_STRUCTS_H_ #define _SN_STRUCTS_H_ #include #include "sn_packetstructs.h" /**** Global data **********************************************************/ struct file_info { char proto, filename[50]; FILE *f; unsigned long bytes; _32_bit exp_seq; /* expected seq to avoid double logging */ int time_out; char log; /* log=0 : do nothing */ /* log=1 : log 'login' */ /* log=2 : 'login' logged */ /* log=3 : log password */ /* log=4 : password logged */ /* log=99 : no more detection */ char scroll_buf[SCBUF+1]; /* scroll buffer */ char *buffer; /* pointer to a buffer */ struct file_info *next; }; /**** Global data (config) **************************************************/ struct cfg_file_contense { unsigned char host[16]; unsigned int priority; unsigned char wildcard; unsigned short port; }; /**** Global data (plugins) *************************************************/ struct Plugin_data { struct unwrap PL_info; struct IP_header PL_iphead; struct TCP_header PL_tcphead; struct UDP_header PL_udphead; unsigned char PL_data[MTU]; unsigned char PL_packet[MTU]; }; /**** Global data (interactive) *********************************************/ #ifdef INCLUDE_INTERFACE #include "sn_curses.h" struct box_window { WINDOW *main_window, *work_window; }; struct shared_conn_data /* shared memory connection datastructure */ { char connection [CONN_NAMELEN]; /* full ID string of conn */ char desc [DESC_BYTES]; /* connection description */ int timeout; }; struct shared_logged_conn /* shared memory logging datastructure */ { char log_enter [CONN_NAMELEN]; /* normal logging */ }; struct snif_mask /* struct for mask */ { _32_bit source_ip, destination_ip; _16_bit source_port, destination_port; }; /* (packet generation) */ struct generate_mask { _32_bit dest_ip, source_ip; _16_bit dest_port, source_port; _32_bit pkt_no; }; struct sp_data_exchange { int fd; /* Sh!t from transmit_TCP */ char *data; int datalen; _32_bit source; unsigned short source_port; _32_bit dest; unsigned short dest_port; _32_bit seq, ack; unsigned short flags; char *buffer; /* work buffer */ int IP_optlen; /* IP options length in bytes */ int TCP_optlen; /* TCP options length in bytes */ }; #endif #endif sniffit-sniffit-0.4.0/src/sniffit.c000066400000000000000000001473521301260737100172260ustar00rootroot00000000000000/* Sniffit main program file */ /* - by : Brecht Claerhout */ #include "sn_config.h" /* Config header file */ #include #include #include #include #include #include /* #include */ #include #include #include #include #include #include /* #include */ /* for inet_addr() */ #ifdef INCLUDE_INTERFACE #include #include #endif #include "pcap.h" /************************ Own includes *************************************/ #include "sn_defines.h" /* Various defines */ #include "sn_structs.h" /* All structures */ #include "sn_global.h" /* some global defs */ #include "sn_data.h" /* data defs */ #include "sn_packets.h" /* My own packet structs */ #include "sn_logfile.h" #include "sn_cfgfile.h" /* Config file handling */ #include "sn_resolv.h" /* Host resolution */ #include "sn_plugins.h" /* Sniffit Plugins file */ #ifdef INCLUDE_INTERFACE #include "sn_interface.h" /* all ncurses stuff */ #endif #ifdef GENERATION #include "sn_generation.h" /* Sniffit Packet generation */ #endif #include "sniffit.h" /* definition of functions */ static char Copyright[] = "Sniffit - Brecht Claerhout - Copyright 1996-98"; void quit (char *prog_name) /* Learn to use the program */ { printf ( "usage: %s [-xdabvnN] [-P proto] [-A char] [-p port] [(-r|-R) recordfile]\n" " [-l sniflen] [-L logparam] [-F snifdevice] [-M plugin]\n", prog_name); #ifdef INCLUDE_INTERFACE printf ( " [-D tty]" " (-t | -s)" " | (-i|-I) | -c]\n"); #else printf ( " (-t | -s) | -c]\n"); #endif printf ("Plugins Available:\n"); #ifdef PLUGIN0_NAME printf (" 0 -- %s\n", PLUGIN0_NAME); #endif #ifdef PLUGIN1_NAME printf (" 1 -- %s\n", PLUGIN1_NAME); #endif #ifdef PLUGIN2_NAME printf (" 2 -- %s\n", PLUGIN2_NAME); #endif #ifdef PLUGIN3_NAME printf (" 3 -- %s\n", PLUGIN3_NAME); #endif #ifdef PLUGIN4_NAME printf (" 4 -- %s\n", PLUGIN4_NAME); #endif #ifdef PLUGIN5_NAME printf (" 5 -- %s\n", PLUGIN5_NAME); #endif #ifdef PLUGIN6_NAME printf (" 6 -- %s\n", PLUGIN6_NAME); #endif #ifdef PLUGIN7_NAME printf (" 7 -- %s\n", PLUGIN7_NAME); #endif #ifdef PLUGIN8_NAME printf (" 8 -- %s\n", PLUGIN8_NAME); #endif #ifdef PLUGIN9_NAME printf (" 9 -- %s\n", PLUGIN9_NAME); #endif exit (0); } void close_dumpfile(void) {pcap_dump_close(dev_dump);}; void close_pcapdev(void) {pcap_close(dev_desc);}; void my_exit (void) { fflush(NULL); printf("Graceful shutdown...\n"); exit (0); }; /* DEBUGGING INFO */ #ifdef DEBUG void close_debug_device (void) { fclose (debug_dev); } void debug_msg (char *debug_text) { fprintf (debug_dev, "%s (%d)\n", debug_text, debug_cnt); debug_cnt++; } #endif char *strlower (char *string) { int i; for (i = 0; i < strlen (string); i++) *(string + i) = (isupper (*(string + i)) ? tolower (*(string + i)) : *(string + i)); return string; } void start_plugin (int PL_nr, struct Plugin_data *PL_d) { switch (PL_nr) { #ifdef PLUGIN0_NAME case 0: PLUGIN0 (PL_d); break; #endif #ifdef PLUGIN1_NAME case 1: PLUGIN1 (PL_d); break; #endif #ifdef PLUGIN2_NAME case 2: PLUGIN2 (PL_d); break; #endif #ifdef PLUGIN3_NAME case 3: PLUGIN3 (PL_d); break; #endif #ifdef PLUGIN4_NAME case 4: PLUGIN4 (PL_d); break; #endif #ifdef PLUGIN5_NAME case 5: PLUGIN5 (PL_d); break; #endif #ifdef PLUGIN5_NAME case 5: PLUGIN5 (PL_d); break; #endif #ifdef PLUGIN6_NAME case 6: PLUGIN6 (PL_d); break; #endif #ifdef PLUGIN7_NAME case 7: PLUGIN7 (PL_d); break; #endif #ifdef PLUGIN8_NAME case 8: PLUGIN8 (PL_d); break; #endif #ifdef PLUGIN9_NAME case 9: PLUGIN9 (PL_d); break; #endif default: fprintf (stderr, "Plugin does not exist...\n"); exit (1); break; } } void reset_all (void) { start_dynam = NULL; dynam_len = 0; } /* if do_file == 0, then don't handle the files */ /* this is for the global logfile option */ struct file_info * add_dynam (char *file, char ptype, char do_file, _32_bit cur_seq, int len) { int i; FILE *f; int last_time_out = 0; struct file_info *dummy_pointer; struct file_info *search_pointer; if (dynam_len >= MAXCOUNT) { /* * remove less effective connection from list */ search_pointer = start_dynam; dummy_pointer = start_dynam; do { if (search_pointer->time_out > last_time_out) { last_time_out = search_pointer->time_out; dummy_pointer = search_pointer; } search_pointer = search_pointer->next; } while (search_pointer != NULL); #ifdef DEBUG debug_msg ("Auto timeout engaged (filename follows)"); debug_msg (dummy_pointer->filename); #endif if (dummy_pointer->f == NULL) delete_dynam (dummy_pointer->filename, dummy_pointer->proto, 0); else delete_dynam (dummy_pointer->filename, dummy_pointer->proto, 1); printf ("Too many connections... auto timeout\n"); } if ((dummy_pointer = (struct file_info *) malloc (sizeof (struct file_info))) == NULL) { printf ("Couldn't allocate memory.\n"); exit (0); }; dummy_pointer->bytes = 0; dummy_pointer->proto = ptype; strcpy (dummy_pointer->filename, file); if (do_file != 0) { f = fopen (file, "a"); if (f == NULL) perror ("Couldn't open logfile:"), exit (0); dummy_pointer->f = f; } else { dummy_pointer->f = NULL; } dummy_pointer->next = NULL; dummy_pointer->buffer = NULL; dummy_pointer->log = 0; dummy_pointer->exp_seq = cur_seq + len; for (i = 0; i < SCBUF; i++) dummy_pointer->scroll_buf[i] = ' '; dummy_pointer->scroll_buf[SCBUF] = 0; if (start_dynam == NULL) start_dynam = dummy_pointer; else { search_pointer = start_dynam; while (search_pointer->next != NULL) search_pointer = search_pointer->next; search_pointer->next = dummy_pointer; } dynam_len++; return dummy_pointer; } void delete_dynam (char *file, char ptype, char do_file) { struct file_info *search_pointer; struct file_info *dummy_pointer; if (start_dynam == NULL) return; search_pointer = start_dynam; if ((strcmp (search_pointer->filename, file) == 0) && (search_pointer->proto == ptype)) { if (do_file != 0) fclose (search_pointer->f); start_dynam = search_pointer->next; dynam_len--; return; } search_pointer = start_dynam; if (search_pointer->next == NULL) return; while (search_pointer->next != NULL) { if ((strcmp (search_pointer->next->filename, file) == 0) && (search_pointer->next->proto == ptype)) { if (do_file != 0) fclose (search_pointer->next->f); dummy_pointer = search_pointer->next; search_pointer->next = search_pointer->next->next; if (dummy_pointer->buffer != NULL) free (dummy_pointer->buffer); free (dummy_pointer); dynam_len--; return; } search_pointer = search_pointer->next; } } /* returns NULL on failure */ struct file_info * search_dynam (char *file, char ptype) { struct file_info *search_pointer; if (start_dynam == NULL) return NULL; search_pointer = start_dynam; /* time_out add */ do { search_pointer->time_out += 1; search_pointer = search_pointer->next; } while (search_pointer != NULL); search_pointer = start_dynam; /* actual search */ do { if ((strcmp (search_pointer->filename, file) == 0) && (search_pointer->proto == ptype)) { search_pointer->time_out = 0; /* timeout reset */ return search_pointer; } search_pointer = search_pointer->next; } while (search_pointer != NULL); return NULL; } /* Type 0: TELNET */ void record_buf (struct file_info *dummy_pointer, _32_bit cur_seq_nr, char *data, int len, int type) { int i, j, noloop = 0; if (dummy_pointer->exp_seq != cur_seq_nr) { return; } noloop = 0; for (i = 0; i < len; i++) { j = dummy_pointer->bytes; switch (type) { case 0: if (data[i] == TELNET_ENTER) /* return found */ { dummy_pointer->log++; noloop = 1; }; break; default: break; } if (noloop == 1) break; if (j >= LOG_PASS_BUF) break; if (isprint (data[i])) { dummy_pointer->buffer[j] = data[i]; } else { dummy_pointer->buffer[j] = '~'; }; dummy_pointer->buffer[j + 1] = 0; dummy_pointer->bytes += 1; } #ifdef DEBUG_ONSCREEN printf ("Record buffer: >%s< (%d)\n", dummy_pointer->buffer, dummy_pointer->bytes); #endif } void sb_shift (struct file_info *dummy_pointer) { int i, j; for (i = 1; i < SCBUF; i++) dummy_pointer->scroll_buf[i - 1] = dummy_pointer->scroll_buf[i]; } void sbuf_update (struct file_info *dummy_pointer, _32_bit cur_seq_nr, char *data, int len) { int i; if (dummy_pointer->exp_seq != cur_seq_nr) { return; } for (i = 0; i < len; i++) { sb_shift (dummy_pointer); if (data[i] != 0) /* * used to be 'isprint', not possible for ftp logging */ { dummy_pointer->scroll_buf[SCBUF - 1] = data[i]; } else { dummy_pointer->scroll_buf[SCBUF - 1] = '.'; }; } #ifdef DEBUG_ONSCREEN printf ("scr_buf: %s\n", dummy_pointer->scroll_buf); #endif } void print_iphead (struct IP_header *iphead, char icmp_or_plain) { int dummy; unsigned char *so, *dest; if (icmp_or_plain != 0) printf ("ICMP message concerned following IP packet:\n"); so = (unsigned char *) &(iphead->source); dest = (unsigned char *) &(iphead->destination); printf ("from %u.%u.%u.%u to %u.%u.%u.%u\n", so[0], so[1], so[2], so[3], dest[0], dest[1], dest[2], dest[3]); dummy = iphead->type; dummy >>= 5; printf ("IP Packet precedence: %s (%c%c%c)\n", IP_TYPE_precedence[dummy], (iphead->type & IP_DELAY) ? 'D' : '-', (iphead->type & IP_THROUGHPUT) ? 'T' : '-', (iphead->type & IP_RELIABILITY) ? 'R' : '-'); dummy = ntohs (iphead->flag_offset); dummy >>= 13; printf ("ID: 0x%X FLAGS: %s %s Time to live (secs): %d\n", ntohs(iphead->ID), (dummy & IP_DF) ? "DF" : "--", (dummy & IP_MF) ? "MF" : "--", iphead->TTL); if (iphead->protocol < 34) printf ("Protocol (%d): %s\n", iphead->protocol, IP_PROTOCOL_number[iphead->protocol]); else printf ("Protocol (%d) not recognised\n", iphead->protocol); printf ("\n"); } int check_packet (_32_bit ipaddr, const struct packetheader *p_header, const unsigned char *sp, char *file, char *file2, struct unwrap *info, char *detail, int MODE) /* MODE 0: -t MODE 1: -s */ /* MODE 2: -b */ { unsigned char *so, *dest; char wc_so[20], wc_dest[20]; struct IP_header iphead; struct TCP_header tcphead; struct ICMP_header icmphead; struct UDP_header udphead; int proto; unsigned int prior; char selected; int i; /* Wildcard stuff */ unsigned char *str_IP; unsigned int n_s; /* strlen short notation for wc bugfix */ proto = unwrap_packet (sp, info); if(proto == NOT_SUPPORTED) { #ifdef DEBUG_ONSCREEN printf("unwrap: NOT_SUPPORTED\n"); #endif return DROP_PACKET;} /* no use in trying */ if(proto == NO_IP) { #ifdef DEBUG_ONSCREEN printf("unwrap: NO_IP\n"); #endif return DROP_PACKET;} /* no use in trying */ if(proto == NO_IP_4) { #ifdef DEBUG_ONSCREEN printf("unwrap: NO_IP_4\n"); #endif return DROP_PACKET;} /* no use in trying */ if(proto == CORRUPT_IP) { #ifdef DEBUG_ONSCREEN printf("unwrap: CORRUPT_IP\n"); #endif printf("Suspicious Packet detected... \n"); return DROP_PACKET;} memcpy (&iphead, (sp + PROTO_HEAD), sizeof (struct IP_header)); so = (unsigned char *) &(iphead.source); dest = (unsigned char *) &(iphead.destination); if ( ((proto == TCP)||(proto==TCP_FRAG_HEAD)) && (PROTOCOLS & F_TCP)) { #ifdef DEBUG_ONSCREEN printf ("TCP Packet\n"); #endif if((info->FRAG_nf==0)&&(proto!=TCP_FRAG_HEAD)) { memcpy (&tcphead, (sp + PROTO_HEAD + info->IP_len), sizeof (struct TCP_header)); memcpy (detail, &tcphead, sizeof (struct TCP_header)); } if ((WILDCARD == 0) && (CFG_FILE == 0)) /* Selection criteria */ { if (MODE == DEST && ipaddr != iphead.destination /* -t */ || MODE == SOURCE && ipaddr != iphead.source /* -s */ || MODE == BOTH && ipaddr != iphead.destination /* -b */ && ipaddr != iphead.source ) return DONT_EXAMINE; /* Check destination/source IP */ } else { if (WILDCARD != 0) /* Wildcards */ { #ifdef DEBUG_ONSCREEN printf ("WILDCARD\n"); #endif sprintf (wc_so, "%u.%u.%u.%u", so[0], so[1], so[2], so[3]); sprintf (wc_dest, "%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3]); n_s = strlen (IP); if (MODE == DEST && (strncmp (wc_dest, IP, n_s) != 0) /* -t */ || MODE == SOURCE && (strncmp (wc_so, IP, n_s) != 0) /* -s */ || MODE == BOTH && (strncmp (wc_dest, IP, n_s) != 0) /* -b */ && (strncmp (wc_so, IP, n_s) != 0) ) return DONT_EXAMINE; /* Check destination/source IP */ } else { /* We are using the config file (4*Check) */ prior = 0; selected = 0; sprintf (wc_so, "%u.%u.%u.%u", so[0], so[1], so[2], so[3]); sprintf (wc_dest, "%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3]); #ifdef DEBUG_ONSCREEN if((info->FRAG_nf!=0)||(proto==TCP_FRAG_HEAD)) printf ("CONCERNING: %s %d - %s %d\n", wc_so, ntohs (tcphead.source), wc_dest, ntohs (tcphead.destination)); #endif /* Highest prior last (backward+break for speed) */ for (i = (select_from_length - 1); i >= 0; i--) { if (prior > select_from_list[i].priority) break; str_IP = select_from_list[i].host; #ifdef DEBUG_ONSCREEN printf ("SF: %s %d Prior:%d\n", str_IP, select_from_list[i].port, select_from_list[i].priority); #endif /* tcphead is reserved anyway (even when fragmented) */ if ((select_from_list[i].port == 0) || (select_from_list[i].port == ntohs (tcphead.source)) || (info->FRAG_nf!=0)||(proto==TCP_FRAG_HEAD) ) { if (select_from_list[i].wildcard == 0) { /* NO wildcard */ if (strcmp (wc_so, str_IP) == 0) { selected = 1; prior = select_from_list[i].priority; break; } } else { /* wildcard */ if (strncmp (wc_so, str_IP, strlen (str_IP)) == 0) { selected = 1; prior = select_from_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 1; break; }; } } for (i = (select_to_length - 1); i >= 0; i--) { if (prior > select_to_list[i].priority) break; str_IP = select_to_list[i].host; #ifdef DEBUG_ONSCREEN printf ("ST: %s %d Prior:%d\n", str_IP, select_to_list[i].port, select_to_list[i].priority); #endif if ((select_to_list[i].port == 0) || (select_to_list[i].port == ntohs (tcphead.destination))|| (info->FRAG_nf!=0)||(proto==TCP_FRAG_HEAD) ) { if (select_to_list[i].wildcard == 0) { /* NO wildcard */ if (strcmp (wc_dest, str_IP) == 0) { selected = 1; prior = select_to_list[i].priority; break; } } else { /* wildcard */ if (strncmp (wc_dest, str_IP, strlen (str_IP)) == 0) { selected = 1; prior = select_to_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 1; break; }; } } for (i = (deselect_from_length - 1); i >= 0; i--) { if (prior > deselect_from_list[i].priority) break; str_IP = deselect_from_list[i].host; #ifdef DEBUG_ONSCREEN printf ("DF: %s %d Prior:%d\n", str_IP, deselect_from_list[i].port, deselect_from_list[i].priority); #endif if ((deselect_from_list[i].port == 0) || (deselect_from_list[i].port == ntohs (tcphead.source))|| (info->FRAG_nf!=0)||(proto==TCP_FRAG_HEAD) ) { if (deselect_from_list[i].wildcard == 0) { /* NO wildcard */ if (strcmp (wc_so, str_IP) == 0) { selected = 0; prior = deselect_from_list[i].priority; break; } } else { /* wildcard */ if (strcmp (wc_so, str_IP) == 0) { selected = 0; prior = deselect_from_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 0; break; }; } } for (i = (deselect_to_length - 1); i >= 0; i--) { if (prior > deselect_to_list[i].priority) break; str_IP = deselect_to_list[i].host; #ifdef DEBUG_ONSCREEN printf ("DT: %s %d Prior:%d\n", str_IP, deselect_to_list[i].port, deselect_to_list[i].priority); #endif if ((deselect_to_list[i].port == 0) || (deselect_to_list[i].port == ntohs (tcphead.destination))|| (info->FRAG_nf!=0)||(proto==TCP_FRAG_HEAD) ) { if (deselect_to_list[i].wildcard == 0) { /* NO wildcard */ if (strncmp (wc_dest, str_IP, strlen (str_IP)) == 0) { selected = 0; prior = deselect_to_list[i].priority; break; } } else { /* wildcard */ if (strncmp (wc_dest, str_IP, strlen (str_IP)) == 0) { selected = 0; prior = deselect_to_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 0; break; }; } } #ifdef DEBUG_ONSCREEN printf ("Selected: %d\n", selected); #endif if (selected == 0) return DONT_EXAMINE; } } if( (info->FRAG_nf==0)&&(proto!=TCP_FRAG_HEAD) ) if( (MODE!=BOTH && DEST_PORT && ntohs (tcphead.destination)!=DEST_PORT) || (MODE!=BOTH && SRC_PORT && ntohs (tcphead.source)!=SRC_PORT) || (MODE==BOTH && SRC_PORT && ntohs (tcphead.source)!=SRC_PORT && ntohs (tcphead.destination)!=SRC_PORT) ) /* with BOTH SRC_PORT&DEST_PORT should be the same!! */ /* DEST/SRC do not depend on the SOURCE or DEST modes! */ return DONT_EXAMINE; /* Check dest. PORT */ #ifdef DEBUG_ONSCREEN printf ("Packet accepted\n"); #endif if( (info->FRAG_nf==0)&&(proto!=TCP_FRAG_HEAD) ) { /* inet_ntoa gave wrong output sometimes */ sprintf (file, "%u.%u.%u.%u.%u-%u.%u.%u.%u.%u", so[0], so[1], so[2], so[3], (unsigned short) ntohs (tcphead.source), dest[0], dest[1], dest[2], dest[3], (unsigned short) ntohs (tcphead.destination)); sprintf (file2, "%u.%u.%u.%u.%u-%u.%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3], (unsigned short) ntohs (tcphead.destination), so[0], so[1], so[2], so[3], (unsigned short) ntohs (tcphead.source)); } else { /* inet_ntoa gave wrong output sometimes */ sprintf (file, "%u.%u.%u.%u-%u.%u.%u.%u", so[0], so[1], so[2], so[3], dest[0], dest[1], dest[2], dest[3]); sprintf (file2, "%u.%u.%u.%u-%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3], so[0], so[1], so[2], so[3]); } if(info->FRAG_nf!=0) return TCP_EX_FRAG_NF; if(proto==TCP_FRAG_HEAD) return TCP_EX_FRAG_HEAD; if ((ntohs(tcphead.offset_flag) & FIN) != 0) /* check for reset conn. */ return TCP_FINISH; /* packet is a FIN */ if ((ntohs(tcphead.offset_flag) & RST) != 0) /* check for reset conn. */ return TCP_FINISH; /* * Used to be for speed, '-x' needs all info, so this too! * if (info->DATA_len == 0) * return DONT_EXAMINE; */ return TCP_EXAMINE; /* interprete packet */ }; /***** WARNING: Remove if later fragment handling is done *************/ if(info->FRAG_nf!=0) {printf("Fragment Skipped...\n"); return DONT_EXAMINE; }; if ((proto == ICMP) && (PROTOCOLS & F_ICMP)) /* ICMP packet checking */ { memcpy (&icmphead, (sp + PROTO_HEAD + info->IP_len), sizeof (struct ICMP_header)); memcpy (detail, &icmphead, sizeof (struct ICMP_header)); sprintf (file, "%u.%u.%u.%u > %u.%u.%u.%u", so[0], so[1], so[2], so[3], dest[0], dest[1], dest[2], dest[3]); return ICMP_EXAMINE; }; if ((proto == UDP) && (PROTOCOLS & F_UDP)) /* UDP packet checking */ { #ifdef DEBUG_ONSCREEN printf ("UDP Packet\n"); #endif memcpy (&udphead, (sp + PROTO_HEAD + info->IP_len), sizeof (struct UDP_header)); memcpy (detail, &udphead, sizeof (struct UDP_header)); if ((WILDCARD == 0) && (CFG_FILE == 0)) /* Selection criteria */ { if (MODE == DEST && ipaddr != iphead.destination /* -t */ || MODE == SOURCE && ipaddr != iphead.source /* -s */ || MODE == BOTH && ipaddr != iphead.destination /* -b */ && ipaddr != iphead.source ) return DONT_EXAMINE; /* Check destination/source IP */ } else { if (WILDCARD != 0) /* Wildcards */ { sprintf (wc_so, "%u.%u.%u.%u", so[0], so[1], so[2], so[3]); sprintf (wc_dest, "%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3]); n_s = strlen (IP); if (MODE == DEST && (strncmp (wc_dest, IP, n_s) != 0) /* -t */ || MODE == SOURCE && (strncmp (wc_so, IP, n_s) != 0) /* -s */ || MODE == BOTH && (strncmp (wc_dest, IP, n_s) != 0) /* -b */ && (strncmp (wc_so, IP, n_s) != 0) ) return DONT_EXAMINE; /* Check destination/source IP */ } else { /* We are using the config file (4*Check) */ prior = 0; selected = 0; sprintf (wc_so, "%u.%u.%u.%u", so[0], so[1], so[2], so[3]); sprintf (wc_dest, "%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3]); #ifdef DEBUG_ONSCREEN printf ("CONCERNING: %s %d - %s %d\n", wc_so, ntohs (udphead.source), wc_dest, ntohs (udphead.destination)); #endif /* Highest prior last (backward+break for speed) */ for (i = (select_from_length - 1); i >= 0; i--) { if (prior > select_from_list[i].priority) break; str_IP = select_from_list[i].host; #ifdef DEBUG_ONSCREEN printf ("SF: %s %d Prior:%d\n", str_IP, select_from_list[i].port, select_from_list[i].priority); #endif if ((select_from_list[i].port == 0) || (select_from_list[i].port == ntohs (udphead.source))) { if (select_from_list[i].wildcard == 0) { /* * NO wildcard */ if (strcmp (wc_so, str_IP) == 0) { selected = 1; prior = select_from_list[i].priority; break; } } else { /* * wildcard */ if (strncmp (wc_so, str_IP, strlen (str_IP)) == 0) { selected = 1; prior = select_from_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 1; break; }; } } for (i = (select_to_length - 1); i >= 0; i--) { if (prior > select_to_list[i].priority) break; str_IP = select_to_list[i].host; #ifdef DEBUG_ONSCREEN printf ("ST: %s %d Prior:%d\n", str_IP, select_to_list[i].port, select_to_list[i].priority); #endif if ((select_to_list[i].port == 0) || (select_to_list[i].port == ntohs (udphead.destination))) { if (select_to_list[i].wildcard == 0) { /* * NO wildcard */ if (strcmp (wc_dest, str_IP) == 0) { selected = 1; prior = select_to_list[i].priority; break; } } else { /* * wildcard */ if (strncmp (wc_dest, str_IP, strlen (str_IP)) == 0) { selected = 1; prior = select_to_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 1; break; }; } } for (i = (deselect_from_length - 1); i >= 0; i--) { if (prior > deselect_from_list[i].priority) break; str_IP = deselect_from_list[i].host; #ifdef DEBUG_ONSCREEN printf ("DF: %s %d Prior:%d\n", str_IP, deselect_from_list[i].port, deselect_from_list[i].priority); #endif if ((deselect_from_list[i].port == 0) || (deselect_from_list[i].port == ntohs (udphead.source))) { if (deselect_from_list[i].wildcard == 0) { /* NO wildcard */ if (strcmp (wc_so, str_IP) == 0) { selected = 0; prior = deselect_from_list[i].priority; break; } } else { /* wildcard */ if (strcmp (wc_so, str_IP) == 0) { selected = 0; prior = deselect_from_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 0; break; }; } } for (i = (deselect_to_length - 1); i >= 0; i--) { if (prior > deselect_to_list[i].priority) break; str_IP = deselect_to_list[i].host; #ifdef DEBUG_ONSCREEN printf ("DT: %s %d Prior:%d\n", str_IP, deselect_to_list[i].port, deselect_to_list[i].priority); #endif if ((deselect_to_list[i].port == 0) || (deselect_to_list[i].port == ntohs (udphead.destination))) { if (deselect_to_list[i].wildcard == 0) { /* NO wildcard */ if (strncmp (wc_dest, str_IP, strlen (str_IP)) == 0) { selected = 0; prior = deselect_to_list[i].priority; break; } } else { /* wildcard */ if (strncmp (wc_dest, str_IP, strlen (str_IP)) == 0) { selected = 0; prior = deselect_to_list[i].priority; break; } } if (str_IP[0] == 0) { selected = 0; break; }; } } #ifdef DEBUG_ONSCREEN printf ("Selected: %d\n", selected); #endif if (selected == 0) return DONT_EXAMINE; } } if( (MODE!=BOTH && DEST_PORT && ntohs (udphead.destination)!=DEST_PORT) || (MODE!=BOTH && SRC_PORT && ntohs (udphead.source)!=SRC_PORT) || (MODE==BOTH && SRC_PORT && ntohs (udphead.source)!=SRC_PORT && ntohs (udphead.destination)!=SRC_PORT) ) /* with BOTH SRC_PORT&DEST_PORT should be the same!! */ /* DEST/SRC do not depend on the SOURCE or DEST modes! */ return DONT_EXAMINE; /* Check dest. PORT */ /* inet_ntoa gave wrong output sometimes */ sprintf (file, "%u.%u.%u.%u.%u-%u.%u.%u.%u.%u", so[0], so[1], so[2], so[3], (unsigned short) ntohs (udphead.source), dest[0], dest[1], dest[2], dest[3], (unsigned short) ntohs (udphead.destination)); sprintf (file2, "%u.%u.%u.%u.%u-%u.%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3], (unsigned short) ntohs (udphead.destination), so[0], so[1], so[2], so[3], (unsigned short) ntohs (udphead.source)); return UDP_EXAMINE; /* interprete packet */ } return DONT_EXAMINE; } /* Default Processing of packets */ pcap_handler packethandler (unsigned char *ipaddrpoint, const struct packetheader * p_header, const unsigned char *sp) { char filename[50], filename2[50], header[SNAPLEN]; FILE *f; struct file_info *dummy_pointer; unsigned char status = 0; char *help; int dummy, finish; /* look out it's signed */ unsigned long datalen, position, total_length, i, n; _32_bit ipaddr; struct unwrap info; struct IP_header iphead; struct TCP_header tcphead; struct ICMP_header icmphead; struct IP_header iphead_icmp; struct UDP_header udphead; struct Plugin_data PL_d, PL_dex; memcpy (&ipaddr, ipaddrpoint, sizeof (_32_bit)); finish = check_packet (ipaddr, p_header, sp, filename, filename2, &info, header, SNIFMODE); if (finish == DROP_PACKET) return 0; /* Packet is broken */ if( (PROTOCOLS&F_IP)&&((PROTOCOLS&F_TCP)==0)) memcpy (&iphead, (sp + PROTO_HEAD), sizeof (struct IP_header)), print_iphead (&iphead, 0); if (finish == DONT_EXAMINE) return 0; /* Packet is not for us */ if(DUMPMODE==8) /* Recording */ { pcap_dump((unsigned char *) dev_dump, p_header, sp); return 1; } if((PROTOCOLS & F_IP)&&(PROTOCOLS & F_TCP)&&(finish<10)) memcpy (&iphead, (sp + PROTO_HEAD), sizeof (struct IP_header)), print_iphead (&iphead, 0); #ifdef DEBUG_ONSCREEN printf ("Processing Packet (finish: %d)\n", finish); #endif if ((finish < 10) || (finish >= 20 && finish < 30)) /* Start plugin */ { if( (finish!=TCP_EX_FRAG_HEAD)&&(finish!=TCP_EX_FRAG_NF) ) { /* no fragments to PLUGINS yet */ /* fixing data structure */ memcpy (&(PL_d.PL_info), &info, sizeof (struct unwrap)); memcpy (&(PL_d.PL_iphead), (sp + PROTO_HEAD), sizeof (struct IP_header)); memcpy (&(PL_d.PL_tcphead), (sp + PROTO_HEAD + info.IP_len), sizeof (struct TCP_header)); memcpy (&(PL_d.PL_udphead), (sp + PROTO_HEAD + info.IP_len), sizeof (struct UDP_header)); if (PL_d.PL_iphead.protocol == TCP) memcpy (PL_d.PL_data, (sp + PROTO_HEAD + info.IP_len + info.TCP_len), info.DATA_len); if (PL_d.PL_iphead.protocol == UDP) memcpy (PL_d.PL_data, (sp + PROTO_HEAD + info.IP_len + info.UDP_len), info.DATA_len); memcpy (PL_d.PL_packet, (sp + PROTO_HEAD), info.IP_len + info.TCP_len + info.UDP_len + info.DATA_len); /* starting all plugins */ for (i = 0; i < 10; i++) if (Plugin_Active[i] == 1) { memcpy (&PL_dex, &PL_d, sizeof (struct Plugin_data)); start_plugin (i, &PL_dex); } } } if ((DUMPMODE & 32) && (finish < 10)) /* extended info TCP only */ { if( (finish!=TCP_EX_FRAG_HEAD)&&(finish!=TCP_EX_FRAG_NF) ) { memcpy (&tcphead, header, sizeof (struct TCP_header)); dummy = ntohs (tcphead.offset_flag); printf ("\n"); printf ("TCP Packet ID (from_IP.port-to_IP.port): %s\n", filename); printf (" SEQ (hex): %lX ", ntohl (tcphead.seq_nr)); if (dummy & ACK) printf ("ACK (hex): %lX\n", ntohl (tcphead.ACK_nr)); printf (" FLAGS: %c%c%c%c%c%c", (dummy & URG) ? 'U' : '-', (dummy & ACK) ? 'A' : '-', (dummy & PSH) ? 'P' : '-', (dummy & RST) ? 'R' : '-', (dummy & SYN) ? 'S' : '-', (dummy & FIN) ? 'F' : '-'); if (dummy & ACK) printf (" Window: %X\n", ntohs (tcphead.window)); else printf ("\n"); } }; if ((finish < 10) && (LOGPARAM == 0)) /* TCP packet */ /* I didn't use flags for later extention, and they */ /* don't come in pairs anyhow */ /* use return instead of else {if}, for later extention */ { if( (finish!=TCP_EX_FRAG_HEAD)&&(finish!=TCP_EX_FRAG_NF) ) memcpy (&tcphead, header, sizeof (struct TCP_header)); switch (DUMPMODE & 199) /* without bit 3,4,5 (8,16,32) */ { case 0: /* LOG mode */ if( (finish==TCP_EX_FRAG_HEAD)||(finish==TCP_EX_FRAG_NF) ) break; /* no FRAG handling in log mode yet */ status = 0; dummy_pointer = search_dynam (filename, TCP); if (dummy_pointer != NULL) status = 1; /* make a new entry unless it's reset */ if (status == 0) { if (finish == TCP_FINISH) return 1; /* there was never data transmitted */ /* seq_nr & datalen not important here yet */ if ((dummy_pointer = add_dynam (filename, TCP, 1, 0, 0)) == NULL) return 1; } f = dummy_pointer->f; if (dummy_pointer->bytes <= SNIFLEN) { const unsigned char *data= sp + PROTO_HEAD + info.IP_len + info.TCP_len; if (SNIFLEN != 0) dummy_pointer->bytes += info.DATA_len; /* last packet is written */ /* don't care about length */ if (ASC == 0) { for (i = 0; i < info.DATA_len; i++) fprintf (f, "%c", data[i]); } else { for (i = 0; i < info.DATA_len; i++) fprintf (f, "%c", isprint (data[i]) ? data[i] : non_printable); }; fflush (f); /* write all */ } if (finish == TCP_FINISH) /* let's reset the connection */ delete_dynam (filename, TCP, 1); break; case 1: /* DUMP mode */ case 2: case 3: memcpy (&iphead, (sp + PROTO_HEAD), sizeof (struct IP_header)); printf ("Packet ID (from_IP.port-to_IP.port): %s\n", filename); total_length = info.IP_len + info.TCP_len + info.DATA_len; if(info.FRAG_f!=0) printf("The following packet is an IP Fragment (first/ID: %0X)...\n", ntohs(iphead.ID)); if( (finish==TCP_EX_FRAG_HEAD)||(finish==TCP_EX_FRAG_NF) ) { total_length = info.IP_len + info.DATA_len; if(finish==TCP_EX_FRAG_HEAD) printf("WARNING: Fragmented TCP header... suspicious... (ID: %0X) \n", ntohs(iphead.ID)); if(finish==TCP_EX_FRAG_NF) printf("The following packet is a continued IP Fragment (ID: %0X)...\n", ntohs(iphead.ID)); }; n = 0; for (i = 0; i < total_length; i++) { unsigned char c = sp[PROTO_HEAD + i]; if (n > 75) n = 0, printf ("\n"); if (DUMPMODE & 1) n += printf (" %02X", c); if (DUMPMODE & 2) n += printf (" %c", isprint (c) ? c : '.'); } printf ("\n\n"); break; case 128: break; /* NO LOGGING MODE */ default: printf ("\nYou mixed incompatible options!\n"); exit (1); } return 1; } if ((finish < 10) && (LOGPARAM != 0)) /* TCP packet - logfile */ /* This mode will grow, so I just copied the other if() */ /* instead of adding a dumpmode, I think this will keep */ /* things more simpel. Also I use the smart dynam */ /* managment of connections */ { if( (finish!=TCP_EX_FRAG_HEAD)&&(finish!=TCP_EX_FRAG_NF) ) { /* no FRAG handling in logfile mode yet */ #include "sn_analyse.c" /* dirty, but it got too confusing */ } } if (finish < 20) /* ICMP packet */ { memcpy (&icmphead, header, sizeof (struct ICMP_header)); memcpy (&iphead_icmp, (sp + PROTO_HEAD + info.IP_len + ICMP_HEADLENGTH + 4), sizeof (struct IP_header)); printf ("ICMP message id: %s\n", filename); printf (" ICMP type: "); switch (icmphead.type) { case 0: printf ("%s\n", ICMP_TYPE_0); break; case 3: printf ("%s\n", ICMP_TYPE_3); printf (" Error: %s\n", ICMP_type_3_code[icmphead.code]); print_iphead (&iphead_icmp, 1); break; case 4: printf ("%s\n", ICMP_TYPE_4); print_iphead (&iphead_icmp, 1); break; case 5: printf ("%s\n", ICMP_TYPE_5); printf (" Error: %s\n", ICMP_type_5_code[icmphead.code]); print_iphead (&iphead_icmp, 1); break; case 8: printf ("%s\n", ICMP_TYPE_8); break; case 11: printf ("%s\n", ICMP_TYPE_11); printf (" Error: %s\n", ICMP_type_11_code[icmphead.code]); print_iphead (&iphead_icmp, 1); break; case 12: printf ("%s\n", ICMP_TYPE_12); print_iphead (&iphead_icmp, 1); break; case 13: printf ("%s\n", ICMP_TYPE_13); break; case 14: printf ("%s\n", ICMP_TYPE_14); break; case 15: printf ("%s\n", ICMP_TYPE_15); break; case 16: printf ("%s\n", ICMP_TYPE_16); break; case 17: printf ("%s\n", ICMP_TYPE_17); break; case 18: printf ("%s\n", ICMP_TYPE_18); break; default: printf ("Unknown ICMP type!\n"); break; } printf ("\n"); return 1; } if (finish < 30) /* nothing yet */ { memcpy (&udphead, header, sizeof (struct UDP_header)); switch (DUMPMODE & 223) { case 0: break; case 1: /* DUMP mode */ case 2: case 3: printf ("UDP Packet ID (from_IP.port-to_IP.port): %s\n", filename); total_length = info.IP_len + info.UDP_len + info.DATA_len; n = 0; for (i = 0; i < total_length; i++) { unsigned char c = sp[PROTO_HEAD + i]; if (n > 75) n = 0, printf ("\n"); if (DUMPMODE & 1) n += printf (" %02X", c); if (DUMPMODE & 2) n += printf (" %c", isprint (c) ? c : '.'); } printf ("\n\n"); break; case 128: break; /* NO LOGGING MODE */ default: printf ("\nImpossible error! Sniffer Heartattack!\n"); exit (0); } return 1; } } #ifdef INCLUDE_INTERFACE /* Interactive packethandling */ int check_mask (const struct packetheader *p_header, const unsigned char *sp, char *conn_name, char *conn_name2, char *desc_string, struct unwrap *info) /* return -1 : packet not for us */ /* else finish value */ { char helpstr1[20], helpstr2[20]; unsigned char *so, *dest; struct IP_header iphead; struct TCP_header tcphead; int proto, i,j; proto = unwrap_packet (sp, info); /* Interface, no output allowed to stdout */ if(proto == NOT_SUPPORTED) return DROP_PACKET; /* no use in trying */ if (proto == NO_IP) return DROP_PACKET; /* no use in trying */ if (proto == NO_IP_4) return DROP_PACKET; /* no use in trying */ if(proto == CORRUPT_IP) return DROP_PACKET; /* no use in trying */ if((info->FRAG_nf!=0)||(info->FRAG_f!=0)) {return DONT_EXAMINE; }; /* No fragments studied at all */ (*IP_nr_of_packets)++; if (proto == ICMP) { (*ICMP_nr_of_packets)++; return DONT_EXAMINE; } if (proto == UDP) { (*UDP_nr_of_packets)++; (*UDP_bytes_in_packets) += (info->UDP_len + info->DATA_len + info->IP_len); return DONT_EXAMINE; } if (proto != TCP) return DONT_EXAMINE; /* Packet info */ (*TCP_nr_of_packets)++; (*TCP_bytes_in_packets) += (info->TCP_len + info->DATA_len + info->IP_len); /* Not a TCP packet */ memcpy (&iphead, (sp + PROTO_HEAD), sizeof (struct IP_header)); memcpy (&tcphead, (sp + PROTO_HEAD + info->IP_len), sizeof (struct TCP_header)); if (mask->source_ip != 0 && iphead.source != mask->source_ip) return DONT_EXAMINE; if (mask->destination_ip != 0 && iphead.destination != mask->destination_ip) return DONT_EXAMINE; if (mask->destination_port && ntohs (tcphead.destination) != mask->destination_port) return DONT_EXAMINE; if (mask->source_port && ntohs (tcphead.source) != mask->source_port) return DONT_EXAMINE; /* inet_ntoa gave wrong output sometimes */ so = (unsigned char *) &(iphead.source); dest = (unsigned char *) &(iphead.destination); sprintf (helpstr1, "%u.%u.%u.%u", so[0], so[1], so[2], so[3]); sprintf (helpstr2, "%u.%u.%u.%u", dest[0], dest[1], dest[2], dest[3]); sprintf (conn_name, "%16s %5u -> %16s %5u", helpstr1, ntohs (tcphead.source), helpstr2, ntohs (tcphead.destination)); sprintf (conn_name2, "%16s %5u -> %16s %5u", helpstr2, ntohs (tcphead.destination), helpstr1, ntohs (tcphead.source)); if(INTERACTIVE_EXTEND==1) { #include "sn_conn_desc.c" /* Some detection */ } if ((ntohs (tcphead.offset_flag) & FIN) != 0) /* check for reset conn. */ return TCP_FINISH; /* packet is a FIN */ if ((ntohs (tcphead.offset_flag) & RST) != 0) /* check for reset conn. */ return TCP_FINISH; /* packet is a RST */ if (info->DATA_len == 0) return DONT_EXAMINE; /*packet not for us */ return TCP_EXAMINE; /* interprete packet */ } pcap_handler interactive_packethandler (char *dummy, const struct packetheader * p_header, const unsigned char *sp) { char conn_name[CONN_NAMELEN], conn_name2[CONN_NAMELEN]; char desc_string[DESC_BYTES]; int finish; /* look out it's signed */ struct unwrap info; if(INTERACTIVE_EXTEND==1) strcpy (desc_string, "Unknown"); finish = check_mask (p_header, sp, conn_name, conn_name2, desc_string, &info); if (finish == DROP_PACKET) return 0; /* Packet is broken */ if (finish == DONT_EXAMINE) return 0; /* Packet is not for us */ if (finish != TCP_FINISH) /* finish: already logged, or to short to add */ add_itemlist (running_connections, conn_name, desc_string); if (strcmp (log_conn->log_enter, conn_name) == 0) { const unsigned char *data = sp + PROTO_HEAD + info.IP_len + info.TCP_len; if (*DATAlength + info.DATA_len < LENGTH_OF_INTERPROC_DATA) { memcpy ((connection_data + *DATAlength), data, info.DATA_len); *DATAlength += info.DATA_len; } } if (finish == TCP_FINISH) { del_itemlist (running_connections, conn_name); del_itemlist (running_connections, conn_name2); } kill (getppid (), SIGUSR1); } #endif int main (int argc, char *argv[]) { char *dev, forced_dev[20], buffer[SNAPLEN]; char ebuf[PCAP_ERRBUF_SIZE]; unsigned char *DUMPfile; /* file used for packed logging */ int c, i; unsigned long memsize; _32_bit ipaddr; int flag = 0, doboth = 0, FORCE_DEV = 0, SUPPORTED = 0; extern char *optarg; signal (SIGINT, my_exit); /* graceful termination in different ways */ signal (SIGHUP, my_exit); signal (SIGTERM, my_exit); SNIFLEN = 300; /* Set defaults */ DEST_PORT = SRC_PORT = 0; /* dest & source Port */ INTERACTIVE_EXTEND=SNIFMODE = DUMPMODE = PROTOCOLS = ASC = WILDCARD = CFG_FILE = NO_CHKSUM = 0; LOGPARAM = 0; Logfile[0] = 0; logging_device = NULL; IP[0]=0; for (i = 0; i < 10; i++) Plugin_Active[i] = 0; /* Active plugins */ #ifdef DEBUG if ((debug_dev = fopen (DEBUG_DEVICE, "a")) < 0) { printf ("Couldn't open DEBUG device!\n"); exit (0); } else { fprintf (debug_dev, "\n\nDEVICE OPENED FOR SNIFFIT DEBUGGING\n\n"); exit_func (close_debug_device); } #endif #ifdef INCLUDE_INTERFACE while ((c = getopt (argc, argv, "D:A:P:iIdp:l:xabt:s:F:c:nvL:M:Nr:R:")) != -1) { #else while ((c = getopt (argc, argv, "A:P:dp:l:xabt:s:F:c:nvL:M:Nr:R:")) != -1) { #endif /* Argument treating */ switch (c) { case 'v': printf ("Sniffit Version %s - Copyright 1996-98 Brecht Claerhout\n", VERSION); #ifdef __DATE__ printf ("Binary build %s %s\n", __DATE__, __TIME__); #endif quit (argv[0]); break; case 'd': if(DUMPMODE&8) quit(argv[0]); DUMPMODE |= 1; break; case 'a': if(DUMPMODE&8) quit(argv[0]); DUMPMODE |= 2; break; case 'R': /* recording (not mixable) */ if(DUMPMODE) quit(argv[0]); DUMPMODE=8; DUMPfile=(unsigned char *)optarg; break; case 'r': if(DUMPMODE&8) quit(argv[0]); DUMPMODE|=16; /* reading (mixable) */ DUMPfile=(unsigned char *)optarg; break; case 'x': if(DUMPMODE&8) quit(argv[0]); DUMPMODE |= 32; break; case 'N': if(DUMPMODE&8) quit(argv[0]); DUMPMODE |= 128; break; case 'p': if(DEST_PORT!=0) printf("Conflicting ports... (using %d as destination port)\n", atoi(optarg)); DEST_PORT = atoi(optarg); break; case 'l': SNIFLEN = atol (optarg); break; case 'L': LOGPARAM |= LOGPARAM_LOG_ON; strlower (optarg); if (strstr (optarg, "raw")) LOGPARAM |= LOGPARAM_RAW; if (strstr (optarg, "norm")) LOGPARAM |= LOGPARAM_NORM; if (strstr (optarg, "telnet")) LOGPARAM |= LOGPARAM_TELNET; if (strstr (optarg, "ftp")) LOGPARAM |= LOGPARAM_FTP; if (strstr (optarg, "mail")) LOGPARAM |= LOGPARAM_MAIL; break; case 'b': doboth = 1; break; case 'A': ASC = 1; non_printable = *optarg; break; case 'D': logging_device = optarg; break; case 'P': strlower (optarg); if (strstr (optarg, "tcp")) PROTOCOLS |= F_TCP; if (strstr (optarg, "icmp")) PROTOCOLS |= F_ICMP; if (strstr (optarg, "udp")) PROTOCOLS |= F_UDP; if (strstr (optarg, "ip")) PROTOCOLS |= F_IP; break; case 's': { char hlp[300], *hlp2; flag++; SNIFMODE = SOURCE; hlp[299]=0; strncpy(hlp,optarg,299); hlp2=(char *)strtok(hlp,":"); IP[255]=0; strncpy(IP,hlp2,255); if((hlp2=(char *)strtok(NULL,":"))!=NULL) SRC_PORT = atoi(hlp2); break; } case 't': { char hlp[300], *hlp2; flag++; SNIFMODE = DEST; hlp[299]=0; strncpy(hlp,optarg,299); hlp2=(char *)strtok(hlp,":"); IP[255]=0; strncpy(IP,hlp2,255); if((hlp2=(char *)strtok(NULL,":"))!=NULL) { if(DEST_PORT!=0) printf("Conflicting ports... (using %d as destination port)\n", atoi(hlp2)); DEST_PORT = atoi(hlp2); } break; } case 'i': flag++; SNIFMODE = INTERACTIVE; INTERACTIVE_EXTEND=0; break; case 'I': flag++; SNIFMODE = INTERACTIVE; INTERACTIVE_EXTEND=1; break; case 'n': NO_CHKSUM = 1; break; case 'M': if ((atoi (optarg) >= 0) && (atoi (optarg) <= 9)) Plugin_Active[atoi (optarg)] = 1; break; case 'F': strcpy (forced_dev, optarg); FORCE_DEV = 1; break; case 'c': flag++; read_cfg_file (optarg); #ifdef DEBUG_ONSCREEN printf ("FINISHED INTERPRETING\n"); printf ("sf:%d st:%d df:%d dt:%d\n", select_from_length, select_to_length, deselect_from_length, deselect_to_length); #endif CFG_FILE = 1; break; case '?': quit(argv[0]); break; default: break; } } #ifdef ALLOW_SUID if ((getuid () != 0) && (geteuid () != 0)) printf ("You should be root to run this program!\n"), exit (1); #else if (getuid () != 0) printf ("You should be root to run this program!\n"), exit (1); #endif if (flag != 1) quit (argv[0]); if ((LOGPARAM != 0) && (CFG_FILE == 0)) quit (argv[0]); if (LOGPARAM != 0) open_logfile (); if (PROTOCOLS == 0) PROTOCOLS |= F_TCP; if (doboth) { SNIFMODE = BOTH; if( DEST_PORT&&SRC_PORT&&(DEST_PORT!=SRC_PORT) ) printf("Conflicting ports... (result might not be what you want!)\n"); if(DEST_PORT==0) DEST_PORT=SRC_PORT; /* ports should be the same for BOTH */ else SRC_PORT=DEST_PORT; } if ((SNIFMODE != INTERACTIVE) && (CFG_FILE == 0)) { /* if(index(IP,'@')) For SunOS */ if (strchr (IP, '@')) { printf ("Wildcard detected, IP nr. not checked...\n"); WILDCARD = 1; /* strcpy(index(IP,'@'),"\0"); */ strcpy (strchr (IP, '@'), "\0"); } else { ipaddr = getaddrbyname (IP); if (ipaddr == 0) printf ("Non existing host!\n"), exit (1); } } reset_all (); /* just to be sure */ if(DUMPMODE&16) /* read from a file */ { if(FORCE_DEV==0) quit(argv[0]); if((dev_desc=pcap_open_offline(DUMPfile,ebuf))==NULL) fprintf (stderr,"%s\n",ebuf), exit (0); } /* real device */ if (FORCE_DEV != 0) /* 0.3.6 core dump fix */ { if((dev=malloc(strlen(forced_dev)+1))==NULL) fprintf(stderr,"Couldn't allocate memory...\n"); strcpy (dev, forced_dev); printf ("Forcing device to %s (user requested)...\n", dev); printf ("Make sure you have read the docs carefully.\n"); PROTO_HEAD = FORCED_HEAD_LENGTH; } else { if((dev = pcap_lookupdev (ebuf)) == NULL) fprintf (stderr,"%s\n",ebuf), exit (1); } for (i = 0; i < NETDEV_NR; i++) if (strstr (dev, NETDEV[i])) /* For expansion */ { PROTO_HEAD = HEADSIZE[i]; printf ("Supported Network device found. (%s)\n", dev); SUPPORTED = 1; break; } if ((SUPPORTED == 0) && (FORCE_DEV == 0)) /* not supported & not forced */ { printf ("Network device found... BUT not known by Sniffit, use '-F ' option!\n"); printf ("Read the README.FIRST on how to force network devices.\n"); exit (1); } if(!(DUMPMODE&16)) if ((dev_desc = pcap_open_live (dev, SNAPLEN, 1, MSDELAY, ebuf)) == NULL) fprintf (stderr,"%s\n",ebuf), exit (0); else exit_func(close_pcapdev); if(FORCE_DEV!=0) {free(dev);} /* no longer needed */ #ifdef PLUGIN0_INIT() if (Plugin_Active[0] == 1) PLUGIN0_INIT (); #endif #ifdef PLUGIN1_INIT() if (Plugin_Active[1] == 1) PLUGIN1_INIT (); #endif #ifdef PLUGIN2_INIT() if (Plugin_Active[2] == 1) PLUGIN2_INIT (); #endif #ifdef PLUGIN3_INIT() if (Plugin_Active[3] == 1) PLUGIN3_INIT (); #endif #ifdef PLUGIN4_INIT() if (Plugin_Active[4] == 1) PLUGIN4_INIT (); #endif #ifdef PLUGIN5_INIT() if (Plugin_Active[5] == 1) PLUGIN5_INIT (); #endif #ifdef PLUGIN6_INIT() if (Plugin_Active[6] == 1) PLUGIN6_INIT (); #endif #ifdef PLUGIN7_INIT() if (Plugin_Active[7] == 1) PLUGIN7_INIT (); #endif #ifdef PLUGIN8_INIT() if (Plugin_Active[8] == 1) PLUGIN8_INIT (); #endif #ifdef PLUGIN9_INIT() if (Plugin_Active[9] == 1) PLUGIN9_INIT (); #endif #ifdef INCLUDE_INTERFACE if (SNIFMODE == INTERACTIVE) { memsize = sizeof (int) + sizeof (int) + LENGTH_OF_INTERPROC_DATA + sizeof (int) + sizeof (struct snif_mask) + sizeof (struct shared_logged_conn) + (CONNECTION_CAPACITY * sizeof (struct shared_conn_data)) + sizeof (int) + sizeof (unsigned long) + sizeof (int) + sizeof (int) + sizeof (unsigned long) + sizeof (int) + sizeof (int); memory_id = shmget (0, memsize, 0700); if (memory_id < 0) { perror ("Interactive Sniffer Heartattack (No Shared mem avail!)"); exit (0); } exit_func (mem_exit); if ((SHARED = shmat (memory_id, 0, SHM_RND)) == NULL) { perror ("Interactive Sniffer Heartattack (Wow something is wrong here)"); exit (0); }; printf ("Entering Shared memory at %p\n", SHARED); printf ("Shared %d\n", memsize); timing = SHARED; /* set all pointers */ DATAlength = timing + sizeof (int); connection_data = DATAlength + sizeof (int); LISTlength = connection_data + LENGTH_OF_INTERPROC_DATA; mask = LISTlength + sizeof (int); logged_connections = mask + sizeof (struct snif_mask); log_conn = (struct shared_logged_conn *) logged_connections; running_connections = logged_connections + sizeof (struct shared_logged_conn); TCP_nr_of_packets = running_connections + (sizeof (struct shared_conn_data) * CONNECTION_CAPACITY); TCP_bytes_in_packets = TCP_nr_of_packets + sizeof (int); ICMP_nr_of_packets = TCP_bytes_in_packets + sizeof (unsigned long); UDP_nr_of_packets = ICMP_nr_of_packets + sizeof (int); UDP_bytes_in_packets = UDP_nr_of_packets + sizeof (int); IP_nr_of_packets = UDP_bytes_in_packets + sizeof (unsigned long); DESC_LEN = IP_nr_of_packets + sizeof (int); clear_shared_mem (0); *DESC_LEN = 10; /* not necessary, but for security (eliminate very unlikely races) */ if ((Pid = fork ()) < 0) { perror ("Interactive Sniffer Heartattack (Couldn't fork)"); exit (0); }; if (Pid == 0) { sleep (4); if (pcap_loop (dev_desc, CNT, interactive_packethandler, NULL) < 0) printf ("Capturing Packets Failed\n"), exit (0); } else { exit_func (child_exit); signal (SIGCHLD, SIG_IGN); if (logging_device != NULL) { if (stat (logging_device, &log_dev_stat) < 0) perror ("\'-D\' option error"), exit (0); if ((log_dev_stream = fopen (logging_device, "a")) == NULL) printf ("Couldn't open device for logging output\n"), exit (0); } run_interface (); } } else { #endif if (CFG_FILE == 0) printf ("Sniffit.%s is up and running.... (%s)\n\n", VERSION, IP); else printf ("Sniffit.%s is up and running.... (Config File Used)\n\n", VERSION); if(DUMPMODE&8) { if((dev_dump=pcap_dump_open(dev_desc, DUMPfile))==NULL) fprintf (stderr, "Capturing Packets Failed\n"), exit (0); exit_func(close_dumpfile); } switch (pcap_loop (dev_desc, CNT, packethandler, (unsigned char *) &ipaddr)) { case -1: fprintf (stderr, "Capturing Packets Failed\n"), exit (0); break; case 0: exit(0); default: break; } #ifdef INCLUDE_INTERFACE } #endif } sniffit-sniffit-0.4.0/src/sniffit.h000066400000000000000000000025231301260737100172210ustar00rootroot00000000000000/* Sniffit Data File */ #ifndef _SNIFFIT_H_ #define _SNIFFIT_H_ #include "pcap.h" /**** Sniffit functions *****************************************************/ int check_packet(_32_bit, const struct packetheader *, const unsigned char *,char *, char *, struct unwrap *,char *,int); pcap_handler packethandler(unsigned char *,const struct packetheader *, const unsigned char *); int check_mask (const struct packetheader *,const unsigned char *, char *, char *, char *, struct unwrap *); pcap_handler interactive_packethandler( char *, const struct packetheader *, const unsigned char *); void print_iphead (struct IP_header *, char); void quit (char *); void reset_all (void); char *strlower (char *); struct file_info *add_dynam (char *, char, char, _32_bit, int); void delete_dynam (char *, char, char); void record_buf(struct file_info *, _32_bit, char *, int, int); void sb_shift(struct file_info *); void sbuf_update(struct file_info *, _32_bit, char *, int); struct file_info *search_dynam(char *, char); void my_exit (void); /**** Sniffit functions (plugins) *******************************************/ void start_plugin (int, struct Plugin_data *); #endif