Veresion 2.1.41. Added ziffy, the promiscuous Z39.50 APDU sniffer
authorAdam Dickmeiss <adam@indexdata.dk>
Wed, 29 Nov 2006 22:35:17 +0000 (22:35 +0000)
committerAdam Dickmeiss <adam@indexdata.dk>
Wed, 29 Nov 2006 22:35:17 +0000 (22:35 +0000)
ny R. Carbone <rocco@ntop.org> .

22 files changed:
Makefile.am
configure.ac
include/yaz/yaz-version.h
ziffy/.cvsignore [new file with mode: 0644]
ziffy/ANNOUNCEMENT-1 [new file with mode: 0644]
ziffy/AUTHORS [new file with mode: 0644]
ziffy/COPYING [new file with mode: 0644]
ziffy/ChangeLog [new file with mode: 0644]
ziffy/FAQ [new file with mode: 0644]
ziffy/FILES [new file with mode: 0644]
ziffy/HACKING [new file with mode: 0644]
ziffy/Makefile.am [new file with mode: 0644]
ziffy/NEWS [new file with mode: 0644]
ziffy/README [new file with mode: 0644]
ziffy/TODO [new file with mode: 0644]
ziffy/apdu.c [new file with mode: 0644]
ziffy/apdu.h [new file with mode: 0644]
ziffy/fmemdmp.c [new file with mode: 0644]
ziffy/hooks.c [new file with mode: 0644]
ziffy/yaz.c [new file with mode: 0644]
ziffy/ziffy.1 [new file with mode: 0644]
ziffy/ziffy.c [new file with mode: 0644]

index c4fd190..0fac4ad 100644 (file)
@@ -1,12 +1,12 @@
 ## This file is part of the YAZ toolkit.
 ## Copyright (C) 1994-2005, Index Data, All rights reserved.
 ## This file is part of the YAZ toolkit.
 ## Copyright (C) 1994-2005, Index Data, All rights reserved.
-## $Id: Makefile.am,v 1.37 2006-10-13 11:25:47 adam Exp $
+## $Id: Makefile.am,v 1.38 2006-11-29 22:35:17 adam Exp $
 
 AUTOMAKE_OPTIONS = foreign 
 
 ACLOCAL_AMFLAGS = -I m4
 
 
 AUTOMAKE_OPTIONS = foreign 
 
 ACLOCAL_AMFLAGS = -I m4
 
-SUBDIRS = src include util test client ztest zoom doc etc
+SUBDIRS = src include util test client ztest zoom ziffy doc etc
 
 aclocaldir=$(datadir)/aclocal
 
 
 aclocaldir=$(datadir)/aclocal
 
index c8f5e61..41bddf9 100644 (file)
@@ -1,8 +1,8 @@
 dnl YAZ Toolkit, Index Data 1994-2006
 dnl See the file LICENSE for details.
 dnl YAZ Toolkit, Index Data 1994-2006
 dnl See the file LICENSE for details.
-dnl $Id: configure.ac,v 1.47 2006-11-27 14:15:53 adam Exp $
+dnl $Id: configure.ac,v 1.48 2006-11-29 22:35:17 adam Exp $
 AC_PREREQ(2.59)
 AC_PREREQ(2.59)
-AC_INIT([yaz],[2.1.40],[yaz-help@indexdata.dk])
+AC_INIT([yaz],[2.1.41],[yaz-help@indexdata.dk])
 AC_CONFIG_SRCDIR(configure.ac)
 AC_CONFIG_AUX_DIR([config])
 AM_INIT_AUTOMAKE([1.8])
 AC_CONFIG_SRCDIR(configure.ac)
 AC_CONFIG_AUX_DIR([config])
 AM_INIT_AUTOMAKE([1.8])
@@ -23,7 +23,7 @@ YAZ_DOC
 dnl 
 dnl
 dnl ------ Headers
 dnl 
 dnl
 dnl ------ Headers
-AC_CHECK_HEADERS(dirent.h fnmatch.h wchar.h locale.h langinfo.h pwd.h sys/select.h sys/socket.h sys/stat.h sys/time.h sys/types.h sys/un.h sys/wait.h unistd.h)
+AC_CHECK_HEADERS(dirent.h fnmatch.h wchar.h locale.h langinfo.h pwd.h sys/select.h sys/socket.h sys/stat.h sys/time.h sys/types.h sys/un.h sys/wait.h unistd.h netinet/if_ether.h netinet/in_systm.h)
 AC_HEADER_STDC
 if test "$ac_cv_header_stdc" = "no"; then
     AC_MSG_WARN([Your system doesn not seem to support ANSI C])
 AC_HEADER_STDC
 if test "$ac_cv_header_stdc" = "no"; then
     AC_MSG_WARN([Your system doesn not seem to support ANSI C])
@@ -163,6 +163,37 @@ if test "$with_iconv" != "no"; then
            ])
     ])
 fi
            ])
     ])
 fi
+dnl ------ libpcap
+
+AC_SUBST(PCAP_LIBS)
+AC_SUBST(PCAP_CFLAGS)
+AC_ARG_WITH(pcap-dir, [  --with-pcap-dir         libpcap root dir located in (dir)], PCAP_DIR="$withval", PCAP_DIR=no)
+
+AC_MSG_CHECKING([for libpcap (required for ziffy)])
+if test "${PCAP_DIR}" != "no" &&
+    test -r $PCAP_DIR/libpcap.a &&
+    test -r $PCAP_DIR/pcap.h; then
+    PCAP_DIR="$PCAP_DIR"
+    PCAP_LIBS="${LIBS} -L$PCAP_DIR -lpcap"
+    PCAP_CFLAGS="${INCS} -I$PCAP_DIR"
+    AC_MSG_RESULT([found in $PCAP_DIR])
+elif test -d /usr/local &&
+    test -r /usr/local/lib/libpcap.a &&
+    test -r /usr/local/include/pcap.h; then
+    PCAP_DIR="/usr/local"
+    PCAP_LIBS="${LIBS} -L$PCAP_DIR/lib -lpcap"
+    PCAP_CFLAGS="${INCS} -I$PCAP_DIR/include"
+    AC_MSG_RESULT([found in $PCAP_DIR])
+elif test -d /usr &&
+    test -r /usr/lib/libpcap.a &&
+    test -r /usr/include/pcap.h; then
+    PCAP_DIR="/usr"
+    PCAP_LIBS="${LIBS} -lpcap"
+    AC_MSG_RESULT([found in $PCAP_DIR])
+else
+    AC_MSG_RESULT([not found. ziffy disabled])
+fi
+
 dnl ------ various functions
 AC_CHECK_FUNCS(getaddrinfo vsnprintf gettimeofday poll strerror_r localtime_r usleep fopen64)
 case $host in
 dnl ------ various functions
 AC_CHECK_FUNCS(getaddrinfo vsnprintf gettimeofday poll strerror_r localtime_r usleep fopen64)
 case $host in
@@ -378,6 +409,7 @@ include/yaz/Makefile
 client/Makefile
 ztest/Makefile
 zoom/Makefile
 client/Makefile
 ztest/Makefile
 zoom/Makefile
+ziffy/Makefile
 doc/Makefile
 doc/local.ent
 doc/common/Makefile
 doc/Makefile
 doc/local.ent
 doc/common/Makefile
index 8f83335..6f8151d 100644 (file)
@@ -24,7 +24,7 @@
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
-/* $Id: yaz-version.h,v 1.104 2006-11-27 14:15:54 adam Exp $ */
+/* $Id: yaz-version.h,v 1.105 2006-11-29 22:35:18 adam Exp $ */
 /**
  * \file yaz-version.h
  * \brief Defines YAZ version.
 /**
  * \file yaz-version.h
  * \brief Defines YAZ version.
@@ -33,8 +33,8 @@
 
 #include <yaz/yconfig.h>
 
 
 #include <yaz/yconfig.h>
 
-#define YAZ_VERSION "2.1.40"
-#define YAZ_VERSIONL 0x020128
+#define YAZ_VERSION "2.1.41"
+#define YAZ_VERSIONL 0x020129
 
 #define YAZ_DATE 1
 
 
 #define YAZ_DATE 1
 
diff --git a/ziffy/.cvsignore b/ziffy/.cvsignore
new file mode 100644 (file)
index 0000000..0861ce0
--- /dev/null
@@ -0,0 +1,5 @@
+ziffy
+Makefile
+Makefile.in
+.libs
+.deps
diff --git a/ziffy/ANNOUNCEMENT-1 b/ziffy/ANNOUNCEMENT-1
new file mode 100644 (file)
index 0000000..72e7dc2
--- /dev/null
@@ -0,0 +1,24 @@
+To: z3950iw@nervm.nerdc.ufl.edu
+Cc: asf@cni.org
+Subject: ANNOUNCE: ziffy - a promiscuous, and free, Z39.50 APDU sniffer
+--text follows this line--
+
+      hi all,
+I am pleased to announce the release 0.0.1 of the 'ziffy' tool,
+a small utility program which can be of interest for the community.
+
+`ziffy' is a promiscuous, and free, Z39.50 APDU sniffer.
+It is released under the GPL License.
+
+'ziffy' is available in source tarball format by anonymous FTP from:
+
+ftp://zeta.tlcpi.finsiel.it:/pub/z3950/ziffy/ziffy-0.0.1.tar.gz
+
+
+I have tested this tool on Solaris 2.6 and Linux (Debian `slink' 2.1).
+
+Feel free to contact me for comments, suggestions, enhacements, ....
+
+Hope it helps!
+
+/rocco
diff --git a/ziffy/AUTHORS b/ziffy/AUTHORS
new file mode 100644 (file)
index 0000000..f33fbb6
--- /dev/null
@@ -0,0 +1,28 @@
+                                                                 -*-text-*-
+-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+Original authors of ziffy
+
+Rocco Carbone <rocco@ntop.org>
+-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+
+ziffy exists because of Luca Deri <deri@ntop.org>, the author
+of the popular and cool ntop program (http://www.ntop.org).
+His great work suggested me the initial idea for implementing ziffy.
+
+I am waiting for many others who want to send me patches, bug fixes,
+comments, wish-list and other stuff for ziffy.
+ziffy will be much better because of them.
+I will attempt to include folks on the Net who helped me in the following list.
+
+Contributors
+============
+o Adam Dickmeiss <adam@indexdata.dk>
+  sent me a patch to make ziffy compatible with YAZ 1.6 and 1.7
+
+
+Credits
+=======
+o luca deri       <deri@ntop.org>
+o jama musse jama <jama@tecsiel.it>
+
+
diff --git a/ziffy/COPYING b/ziffy/COPYING
new file mode 100644 (file)
index 0000000..d60c31a
--- /dev/null
@@ -0,0 +1,340 @@
+                   GNU GENERAL PUBLIC LICENSE
+                      Version 2, June 1991
+
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.
+     59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+                           Preamble
+
+  The licenses for most software are designed to take away your
+freedom to share and change it.  By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users.  This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it.  (Some other Free Software Foundation software is covered by
+the GNU Library General Public License instead.)  You can apply it to
+your programs, too.
+
+  When we speak of free software, we are referring to freedom, not
+price.  Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+  To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if you
+distribute copies of the software, or if you modify it.
+
+  For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have.  You must make sure that they, too, receive or can get the
+source code.  And you must show them these terms so they know their
+rights.
+
+  We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+  Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software.  If the software is modified by someone else and passed on, we
+want its recipients to know that what they have is not the original, so
+that any problems introduced by others will not reflect on the original
+authors' reputations.
+
+  Finally, any free program is threatened constantly by software
+patents.  We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary.  To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at all.
+
+  The precise terms and conditions for copying, distribution and
+modification follow.
+\f
+                   GNU GENERAL PUBLIC LICENSE
+   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+  0. This License applies to any program or other work which contains
+a notice placed by the copyright holder saying it may be distributed
+under the terms of this General Public License.  The "Program", below,
+refers to any such program or work, and a "work based on the Program"
+means either the Program or any derivative work under copyright law:
+that is to say, a work containing the Program or a portion of it,
+either verbatim or with modifications and/or translated into another
+language.  (Hereinafter, translation is included without limitation in
+the term "modification".)  Each licensee is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope.  The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the
+Program (independent of having been made by running the Program).
+Whether that is true depends on what the Program does.
+
+  1. You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a fee.
+
+  2. You may modify your copy or copies of the Program or any portion
+of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+    a) You must cause the modified files to carry prominent notices
+    stating that you changed the files and the date of any change.
+
+    b) You must cause any work that you distribute or publish, that in
+    whole or in part contains or is derived from the Program or any
+    part thereof, to be licensed as a whole at no charge to all third
+    parties under the terms of this License.
+
+    c) If the modified program normally reads commands interactively
+    when run, you must cause it, when started running for such
+    interactive use in the most ordinary way, to print or display an
+    announcement including an appropriate copyright notice and a
+    notice that there is no warranty (or else, saying that you provide
+    a warranty) and that users may redistribute the program under
+    these conditions, and telling the user how to view a copy of this
+    License.  (Exception: if the Program itself is interactive but
+    does not normally print such an announcement, your work based on
+    the Program is not required to print an announcement.)
+\f
+These requirements apply to the modified work as a whole.  If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works.  But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+  3. You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+    a) Accompany it with the complete corresponding machine-readable
+    source code, which must be distributed under the terms of Sections
+    1 and 2 above on a medium customarily used for software interchange; or,
+
+    b) Accompany it with a written offer, valid for at least three
+    years, to give any third party, for a charge no more than your
+    cost of physically performing source distribution, a complete
+    machine-readable copy of the corresponding source code, to be
+    distributed under the terms of Sections 1 and 2 above on a medium
+    customarily used for software interchange; or,
+
+    c) Accompany it with the information you received as to the offer
+    to distribute corresponding source code.  (This alternative is
+    allowed only for noncommercial distribution and only if you
+    received the program in object code or executable form with such
+    an offer, in accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it.  For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable.  However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+\f
+  4. You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License.  Any attempt
+otherwise to copy, modify, sublicense or distribute the Program is
+void, and will automatically terminate your rights under this License.
+However, parties who have received copies, or rights, from you under
+this License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+  5. You are not required to accept this License, since you have not
+signed it.  However, nothing else grants you permission to modify or
+distribute the Program or its derivative works.  These actions are
+prohibited by law if you do not accept this License.  Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+  6. Each time you redistribute the Program (or any work based on the
+Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions.  You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+  7. If, as a consequence of a court judgment or allegation of patent
+infringement or for any other reason (not limited to patent issues),
+conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License.  If you cannot
+distribute so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you
+may not distribute the Program at all.  For example, if a patent
+license would not permit royalty-free redistribution of the Program by
+all those who receive copies directly or indirectly through you, then
+the only way you could satisfy both it and this License would be to
+refrain entirely from distribution of the Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices.  Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+\f
+  8. If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded.  In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+  9. The Free Software Foundation may publish revised and/or new versions
+of the General Public License from time to time.  Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+Each version is given a distinguishing version number.  If the Program
+specifies a version number of this License which applies to it and "any
+later version", you have the option of following the terms and conditions
+either of that version or of any later version published by the Free
+Software Foundation.  If the Program does not specify a version number of
+this License, you may choose any version ever published by the Free Software
+Foundation.
+
+  10. If you wish to incorporate parts of the Program into other free
+programs whose distribution conditions are different, write to the author
+to ask for permission.  For software which is copyrighted by the Free
+Software Foundation, write to the Free Software Foundation; we sometimes
+make exceptions for this.  Our decision will be guided by the two goals
+of preserving the free status of all derivatives of our free software and
+of promoting the sharing and reuse of software generally.
+
+                           NO WARRANTY
+
+  11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.  EXCEPT WHEN
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
+REPAIR OR CORRECTION.
+
+  12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+                    END OF TERMS AND CONDITIONS
+\f
+           How to Apply These Terms to Your New Programs
+
+  If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+  To do so, attach the following notices to the program.  It is safest
+to attach them to the start of each source file to most effectively
+convey the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+    <one line to give the program's name and a brief idea of what it does.>
+    Copyright (C) <year>  <name of author>
+
+    This program is free software; you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation; either version 2 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program; if not, write to the Free Software
+    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program is interactive, make it output a short notice like this
+when it starts in an interactive mode:
+
+    Gnomovision version 69, Copyright (C) year  name of author
+    Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+    This is free software, and you are welcome to redistribute it
+    under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License.  Of course, the commands you use may
+be called something other than `show w' and `show c'; they could even be
+mouse-clicks or menu items--whatever suits your program.
+
+You should also get your employer (if you work as a programmer) or your
+school, if any, to sign a "copyright disclaimer" for the program, if
+necessary.  Here is a sample; alter the names:
+
+  Yoyodyne, Inc., hereby disclaims all copyright interest in the program
+  `Gnomovision' (which makes passes at compilers) written by James Hacker.
+
+  <signature of Ty Coon>, 1 April 1989
+  Ty Coon, President of Vice
+
+This General Public License does not permit incorporating your program into
+proprietary programs.  If your program is a subroutine library, you may
+consider it more useful to permit linking proprietary applications with the
+library.  If this is what you want to do, use the GNU Library General
+Public License instead of this License.
diff --git a/ziffy/ChangeLog b/ziffy/ChangeLog
new file mode 100644 (file)
index 0000000..8372751
--- /dev/null
@@ -0,0 +1,29 @@
+                                                                        -*-text-*-
+
+2001-06-27  Rocco Carbone  <rocco@ntop.org>
+
+        * version 0.0.3
+          Overview of changes in this version:
+          - adapted to compile with YAZ-1.7 by Index data
+
+1998-12-31  Rocco Carbone  <rocco@tecsiel.it>
+
+        * version 0.0.2 lives free on the Net
+
+          Overview of changes in this version:
+          - better GNU autoconf-ified distribution
+          - General documentation and a minimal web site have been prepared
+          - Command line argument fixes/upgrades
+
+
+1998-12-18  Rocco Carbone  <rocco@tecsiel.it>
+
+       * Initial public release
+          features:
+          - GNU autoconf-ified distribution
+          - Runs under Linux 2.0.x and Solaris 2.6
+          - Requires libpcap (0.4a6 tested)
+          - Uses X/ASN1 (1.0.0 tested)
+          - Uses YAZ (1.4pl2 tested)
+          - Uses SNACC (1.3 tested)
+          - Initial support for filters
diff --git a/ziffy/FAQ b/ziffy/FAQ
new file mode 100644 (file)
index 0000000..dab0fc9
--- /dev/null
+++ b/ziffy/FAQ
@@ -0,0 +1,95 @@
+
+                                                                 -*-text-*-
+
+Q. Why did you implemented ziffy?
+A. because of my own personal needs!
+
+
+Q. What can ziffy do for me?
+A. ziffy can promiscuously capture network packets from different interfaces,
+   including of course Ethernet, PPP and ISDN lines, and other interfaces
+   that your OS supports.  Each packet, as read from the network, is stripped
+   from the lower-level protocols (Ethernet/IP/TCP) header information and
+   then passed to a Z39.50 ASN.1/BER Decoder. All valid Z39.50 packets are
+   passed to a pretty print function to show all the Z39.50 information
+   that the packet carries.
+
+
+Q. Why I should use this program?
+A. So, if you are interestered in Z39.50 APDUs, please give ziffy a chance
+   to run on your system. Perhaps you are interested in network statistics
+   collection, security monitoring, network debugging, etc.
+
+   If you are a trusted user, ziffy is your friend!
+
+
+Q. Why does ziffy use the Packet Capture Library libpcap?
+A. Well, the libpcap package provides a portable framework for low-level
+   network monitoring. Its system-independent API helps in porting and
+   alleviates the need for several system-dependent packet capture modules.
+   libpcap is the choice by default for tools such as ziffy!
+
+
+Q. Why does ziffy use the YAZ Toolkit by IndexData?
+A. This is a long story.
+   To perform its task ziffy needs ASN.1 run-time BER decoding and printing
+   routines.
+
+   The initial version was based on the ZETA Core Library by Finsiel S.p.A.,
+   which in turn includes and uses the Finsiel X/ASN.1 Toolkit to perform
+   Z39.50 encoding/decoding/printing routines.
+
+   I still have and maintain this version of the X/ASN.1 software. But I do not
+   have permissions to let this software run free on the Net because of
+   copyrigth restrictions. That is the reason I decided to port ziffy
+   on freeware ASN.1 Toolkits.
+
+   The popular Yaz Toolkit:
+   o provides the required Z39.50 decoding and printing functionalities
+   o it is largely used in different contests by several people and organizations
+   o it is in the public domain
+
+    So it is the choice by default.
+    Thanks to Sebastian Hammer <quinn@indexdata.dk> and Adam Dickmeiss
+    <adam@indexdata.dk> for their superb and clean work
+
+
+Q. Had ziffy been compiled against other public domain ASN.1 Toolkits?
+A. Yes.
+   I have a version of ziffy written on top of the SNACC ASN.1 Toolkit,
+   that is not so popular in the Z39.50 community so the YAZ Toolkit does.
+
+   If you know of other public domain ASN.1 Decoders with a pretty print
+   APDUs routines, please drop me a mail.
+   I will try to include different printing routines as run-time options
+   in the following releases of ziffy.
+
+
+Q. Can I know the list of OSs and supported platforms ziffy run on?
+A. I written and tested the program on my intel based linux box.
+   And I ported it on the Solaris 2.6.
+   I think it should be ported with minimal effort on
+   o Ultrix 4.1.3
+   o Irix 6.2
+
+  AIX? who can say? it is a so different flavor of Unix
+
+  NT? oh no, again! please don't ask.
+
+
+Q. Where can I get the latest version of ziffy?
+A. You can download it from ftp anonymous site:
+        ftp://zeta.tlcpi.finsiel.it/pub/z3950/ziffy
+
+
+Q. Where can I get more information on ziffy?
+A. Visit the ziffy official home page.
+        http://zeta.tlcpi.finsiel.it/z3950/ziffy
+
+
+Q. Are there any mailinglist dedicated to ziffy?
+A. No! for the time being.
+
+
+Q. If I need support can I contact you?
+A. Yes, but I am so busy. So send me a mail and please be patient!
diff --git a/ziffy/FILES b/ziffy/FILES
new file mode 100644 (file)
index 0000000..2f8348d
--- /dev/null
@@ -0,0 +1,51 @@
+                                                                 -*-text-*-
+ANNOUNCEMENT-1  - the original announcement to the ZIG list
+AUTHORS         - the list of authors
+COPYING         - GNU GENERAL PUBLIC LICENSE
+ChangeLog       - description of differences between releases
+FAQ             - the collections of questions, with answers, from users
+FILES           - list of files distributed as a part of the package
+HACKING         - istructions to hack the program
+INSTALL         - installation procedures
+Makefile.am     - source compilation rules (input to the configure script)
+NEWS            - what happended from the lastest release
+README          - the most important file in the package :-)
+SNAPSHOT-SNACC  - Simple Output
+TODO            - what I planned for the next week-end
+VERSION         - version of this release
+
+acconfig.h      - local configuration options for the GNU autoheader tool
+acinclude.m4.in - local definitions for the GNU automake tool
+autogen.sh      - a script to start hacking the program
+                  (it tries to make all but not the coffe)
+configure.in    - source directive to the GNU autoconf tool
+
+acinclude.m4    - a machine generated file input to aclocal GNU tool
+Makefile.in     - a machine generated file from the GNU automake tool
+
+aclocal.m4      - autoconf macros
+config.guess    - a machine generated file from the GNU configure tool
+config.sub      - a machine generated file from the GNU configure tool
+configure       - configure script
+                  (run this first)
+install-sh      - GNU support file needed by the GNU configure script
+ltconfig        - GNU support file needed by the GNU configure script
+ltmain.sh       - GNU support file needed by the GNU configure script
+missing         - GNU support file needed by the GNU configure script
+mkinstalldirs   - GNU support file needed by the GNU configure script
+ziffy.h.in      - a machine generated from configure.in by GNU autoheader
+
+apdu.c          -
+apdu.h          -
+fmemdmp.c       - memory dump utility
+hooks.c         - an application/TCP/IP/Ethernet protocol filter
+recordsyntax_generic.h - a machine generated file from the SNACC Compiler
+snacc.c         - decoding and printing utility based on the SNACC Toolkit
+xasn1.c         - decoding and printing utility based on the X/ASN.1 Toolkit
+yaz.c           - decoding and printing utility based on the YAZ Toolkit
+z39_50_apdu_1995.c - a machine generated file from the SNACC Compiler
+z39_50_apdu_1995.h - a machine generated file from the SNACC Compiler
+ziffy.1         - manual entry (innacurate! please don't use)
+                  read the source code, which is always authoritative
+ziffy.c         - main program
+
diff --git a/ziffy/HACKING b/ziffy/HACKING
new file mode 100644 (file)
index 0000000..fe28d35
--- /dev/null
@@ -0,0 +1,36 @@
+                                                                   -*-text-*-
+
+The ziffy utility started from its first version to use
+GNU automake and autoconf utilities.
+
+If you want to hack on ziffy, it will make you life easier
+to have the following packages installed:
+
+  - GNU libtool 1.3.3
+  - GNU automake 1.4
+  - GNU autoconf 2.13
+
+These should be available by ftp from ftp.gnu.org or any of the
+fine GNU mirrors. Beta software can be found at ftp://alpha.gnu.org.
+                                                                
+
+This means that you will need the usual GNU tools to build these in
+maintainer mode from the development tree. You can simply type at
+your prompt:
+
+> ./autogen.sh
+
+[a simple shell script that basically does the following for you: 
+
+    aclocal
+    autoheader
+    automake --add-missing --gnu
+    autoconf
+    configure
+
+]
+
+
+have fun!
+
+/rocco
diff --git a/ziffy/Makefile.am b/ziffy/Makefile.am
new file mode 100644 (file)
index 0000000..281e955
--- /dev/null
@@ -0,0 +1,20 @@
+## -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+## auto makefile for ziffy - a promiscuous Z39.50 APDU sniffer for Ethernet
+## (this file is processed with 'automake' to produce Makefile.in)
+##
+## Copyright (c) 1998-2001 R. Carbone <rocco@ntop.org>
+
+ziffy_LDADD     = ../src/libyaz.la $(PCAP_LIBS)
+
+AM_CPPFLAGS=-I$(top_srcdir)/include $(PCAP_CFLAGS) -DHAVE_YAZ=1
+
+bin_PROGRAMS = ziffy
+
+man_MANS = ziffy.1
+EXTRA_DIST = ANNOUNCEMENT-1 AUTHORS COPYING ChangeLog \
+              FAQ FILES HACKING NEWS README TODO $(man_MANS)
+
+ziffy_SOURCES = ziffy.c yaz.c fmemdmp.c hooks.c apdu.c apdu.h
+
+
+
diff --git a/ziffy/NEWS b/ziffy/NEWS
new file mode 100644 (file)
index 0000000..775a07a
--- /dev/null
@@ -0,0 +1,5 @@
+                                                                 -*-text-*-
+
+1998-12-18  Rocco Carbone  <rocco@tecsiel.it>
+
+        * First split version of this package
diff --git a/ziffy/README b/ziffy/README
new file mode 100644 (file)
index 0000000..10d5754
--- /dev/null
@@ -0,0 +1,135 @@
+                                                                 -*-text-*-
+-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ziffy, a promiscuous Z39.50 APDU sniffer
+
+Copyright (c) 1998-2001 R. Carbone <rocco@ntop.org>
+
+This file includes:
+
+    * General information
+    * Licensing
+    * Requirements
+    * Platforms
+    * Installation
+    * References
+
+-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+
+* General information
+
+  ziffy is a promiscuous Z39.50 APDU sniffer, like the popular tcpdump.
+  ziffy can capture and show all Z39.50 traffic on your LAN segment.
+
+  To perform its task ziffy needs at least two extra packages providing the
+  following functionalities:
+
+  (a) a portable framework for low-level network capturing facility
+  (b) BER decoding, printing and freeing routines
+
+
+  I compiled and run ziffy on my `explosive' linux intel based box with:
+
+  (a) libpcap 0.4a6 API, Copyright (c) 1993, 1994, 1995, 1996, 1997
+      by The Regents of the University of California
+
+
+  (b) X/ASN.1 Toolkit 1.0.0, Copyright (c) 1989-1998 by Finsiel S.p.A.
+  (c) YAZ Toolkit 1.7 API, Copyright (c) 1995-2001 by Index Data
+  (d) SNACC Toolkit 1.3 API, Copyright (c) 1991, 1993 by Michael Sample and UCB
+                             Copyright (c) 1994 1995 by Robert Joop and GMD Fokus
+
+
+
+* Licensing
+
+  The ziffy program is released under the terms of the GNU GPL, read the file
+  COPYING for more information.
+
+
+* Requirements
+
+  ziffy depends on a couple of extra packages for working properly:
+
+       - libpcap, the Packet Capture Library. It can be found at:
+
+        ftp://ftp.ee.lbl.gov/libpcap.tar.Z
+
+
+       at least one of:
+
+       - X/ASN.1 Toolkit from Finsiel S.p.A. 
+         contact us at zeta@tlcpi.finsiel.it if you need more information
+
+
+       - YAZ Toolkit, the so popular "Yet Another Z39.50 Toolkit" from Index Data.
+
+         You can find the YAZ Toolkit in:
+
+        ftp://ftp.indexdata.dk/pub/yaz/yaz-1.7.tar.gz
+
+         for more information about YAZ please visit:
+        http://www.indexdata.dk
+
+
+       - SNACC Toolkit, the "Sample Neufeld ASN.1 to C Compiler".
+
+         You can find the most recent (1.3) version of SNACC at:
+
+        ftp://ftp.fokus.gmd.de/pub/freeware/snacc/snacc-1.3.tar.gz
+
+         [
+                old version 1.1, but commonly used, is in:
+             ftp://ftp.cs.ucb.ca/pub/local/src/snacc/snacc-1.1.tar.Z
+         ]
+
+         for more information visit SNACC home page:
+        http://www.fokus.gmd.de/ovma/freeware/snacc/entry.html
+
+
+<PLEASE>
+       If you know of other freeware ASN.1 Toolkits, please drop me a note.
+       I will try to include them in all future versions of ziffy.
+</PLEASE>
+
+
+
+* Platforms
+
+  Sun Solaris 2.5.1 and/or 2.6
+  ix?86 Linux 2.0.X  (bug on it! be patient until I have time to fix it!)
+
+
+* Installation
+
+        o To compile ziffy, you need to build and install libpcap and the
+          YAZ Toolkit or SNACC Toolkit first, or both at your choice
+
+        o Run "./configure" if you have libpcap and SNACC/YAZ Toolkit on standard 
+          places. Otherwise, to build from source distributions, run:
+
+         ./configure --with-pcap-dir=your_libpcap_location 
+              --with-yaz-dir=your_yaz_location --with-snacc-dir=your_snacc_location
+
+          "configure" will determine your system attributes and generate
+          an appropriate Makefile from Makefile.in.
+
+        o Run "make".  If everything is ok, you should have a binary
+          called "ziffy".
+
+       o Run "make install". everything will go to the right places.
+
+
+* References
+
+  Importants RFC's you should read to fully understand what we are talking 
+  about are:
+
+ [] RFC 1729: Using the Z39.50 Information Retrieval Protocol
+              in the Internet Environment
+
+
+
+<PLEASE>
+        Please send me patches for any modifications you need to compile,
+        install and run the program.
+</PLEASE>
diff --git a/ziffy/TODO b/ziffy/TODO
new file mode 100644 (file)
index 0000000..9c29741
--- /dev/null
@@ -0,0 +1,16 @@
+
+                                                                 -*-text-*-
+
+o dump the Ethernet/IP/TCP packets as options
+
+o implement timestamp presentation
+
+o find an optimal cutoff for the default snaplen
+
+o implement an APDU type filtering mechanism
+
+o implement a proxy capability
+
+o implement control of the program via the HTTP Protocol
+
+o porting code to Ultrix 4.1.3 and Irix 6.2
diff --git a/ziffy/apdu.c b/ziffy/apdu.c
new file mode 100644 (file)
index 0000000..4e83052
--- /dev/null
@@ -0,0 +1,180 @@
+/*
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ * apdu.c - 
+ *
+ * Copyright (c) 1998-2001 R. Carbone <rocco@tecsiel.it> - Finsiel S.p.A.
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ */
+
+
+/*
+ * Operating System include files
+ */
+#include <stdio.h>
+
+#include <time.h>
+#if HAVE_SYS_TIME_H
+#include <sys/time.h>
+#endif
+
+#include <sys/types.h>
+
+#include "apdu.h"
+
+/*
+ * The table of z3950 apdus
+ */
+static z3950apdu apdutable [] =
+{
+  { 20, "INIT request",      -1, NULL, NULL, 0, NULL, 0 },
+  { 21, "INIT response",     -1, NULL, NULL, 0, NULL, 0 },
+  { 22, "SEARCH request",    -1, NULL, NULL, 0, NULL, 0 },
+  { 23, "SEARCH response",   -1, NULL, NULL, 0, NULL, 0 },
+  { 24, "PRESENT request",   -1, NULL, NULL, 0, NULL, 0 },
+  { 25, "PRESENT response",  -1, NULL, NULL, 0, NULL, 0 },
+  { 26, "DELETE request",    -1, NULL, NULL, 0, NULL, 0 },
+  { 27, "DELETE response",   -1, NULL, NULL, 0, NULL, 0 },
+  { 28, "ACCESS request",    -1, NULL, NULL, 0, NULL, 0 },
+  { 29, "ACCESS response",   -1, NULL, NULL, 0, NULL, 0 },
+  { 30, "RESOURCE request",  -1, NULL, NULL, 0, NULL, 0 },
+  { 31, "RESOURCE response", -1, NULL, NULL, 0, NULL, 0 },
+  { 32, "TRIGGER request",   -1, NULL, NULL, 0, NULL, 0 },
+  { 33, "REPORT request",    -1, NULL, NULL, 0, NULL, 0 },
+  { 34, "REPORT response",   -1, NULL, NULL, 0, NULL, 0 },
+  { 35, "SCAN request",      -1, NULL, NULL, 0, NULL, 0 },
+  { 36, "SCAN response",     -1, NULL, NULL, 0, NULL, 0 },
+
+  { 43, "SORT request",      -1, NULL, NULL, 0, NULL, 0 },
+  { 44, "SORT response",     -1, NULL, NULL, 0, NULL, 0 },
+  { 45, "SEGMENT request",   -1, NULL, NULL, 0, NULL, 0 },
+  { 46, "EXTENDED request",  -1, NULL, NULL, 0, NULL, 0 },
+  { 47, "EXTENDED response", -1, NULL, NULL, 0, NULL, 0 },
+  { 48, "CLOSE request",     -1, NULL, NULL, 0, NULL, 0 },
+
+  { 0 },
+};
+
+
+z3950apdu * lookup (int tag)
+{
+  z3950apdu * found = apdutable;
+
+  for (found = apdutable; found < apdutable +
+        (sizeof (apdutable) / sizeof (apdutable [0])); found ++)
+    if (found -> tag == tag)
+       break;
+
+  return (found);
+}
+
+
+static int bertag (u_char * apdu)
+{
+  u_char * q = apdu;
+  int tag = * q & 0x1F;
+
+  if (tag > 30)
+    {
+      tag = 0;
+      q ++;
+      do
+       {
+         tag <<= 7;
+         tag |= * q & 0X7F;
+       }
+      while (* q ++ & 0X80);
+    }
+  return (tag);
+}
+
+
+/*
+ * An euristic Z39.50 event check routine that simply
+ * looks for the first tag in the APDU
+ */
+z3950apdu * parseable (u_char * apdu, int len)
+{
+  if (! len)
+    return (0);
+
+  return (lookup (bertag (apdu)));
+}
+
+
+
+struct timeval current_apdu = {0};
+struct timeval first_apdu = {0};
+struct timeval last_apdu = {0};
+
+/*
+ * The time difference in milliseconds
+ */
+time_t delta_time_in_milliseconds (const struct timeval * now,
+                                  const struct timeval * before)
+{
+  /*
+   * compute delta in second, 1/10's and 1/1000's second units
+   */
+  time_t delta_seconds = now -> tv_sec - before -> tv_sec;
+  time_t delta_milliseconds = (now -> tv_usec - before -> tv_usec) / 1000;
+
+  if (delta_milliseconds < 0)
+    { /* manually carry a one from the seconds field */
+      delta_milliseconds += 1000;              /* 1e3 */
+      -- delta_seconds;
+    }
+  return ((delta_seconds * 1000) + delta_milliseconds);
+}
+
+
+/*
+ * return a well formatted timestamp
+ */
+char * timestamp (const struct timeval * t, int fmt)
+{
+  static char buf [16];
+
+  time_t now = time ((time_t *) 0);
+  struct tm * tm = localtime (& now);
+
+  gettimeofday (& current_apdu, NULL);
+
+  switch (fmt)
+    {
+    default:
+    case DELTA_FMT:
+      /*
+       * calculate the difference in milliseconds since the previous apdus was displayed
+       */
+      sprintf (buf, "%10ld ms", delta_time_in_milliseconds (& current_apdu, & last_apdu));
+      break;
+
+    case ABS_FMT:
+      sprintf (buf, "%02d:%02d:%02d.%06d",
+              tm -> tm_hour, tm -> tm_min, tm -> tm_sec, (int) t -> tv_usec);
+      break;
+
+    case RELATIVE_FMT:
+      /*
+       * calculate the difference in milliseconds since the previous apdus was displayed
+       */
+      sprintf (buf, "%10ld ms", delta_time_in_milliseconds (& current_apdu, & first_apdu));
+      break;
+    }
+
+  return (buf);
+}
diff --git a/ziffy/apdu.h b/ziffy/apdu.h
new file mode 100644 (file)
index 0000000..f4b3cec
--- /dev/null
@@ -0,0 +1,70 @@
+/*
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ * apdu.h - 
+ *
+ * Copyright (c) 1998-2001 R. Carbone <rocco@tecsiel.it> - Finsiel S.p.A.
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ */
+
+
+extern unsigned long z3950_apduno;
+
+extern int aflag;
+
+extern int ethflag;
+extern int ipflag;
+extern int tcpflag;
+extern int z3950flag;
+
+
+extern struct timeval first_apdu;
+extern struct timeval last_apdu;
+
+
+/*
+ * The structure containing information about all the apdus
+ */
+typedef struct
+{
+  int tag;                   /* unique apdu tag identifier */
+  char * name;               /* user printable name of the apdu */
+  int minlen;                /* min length of bytes off wire (all optional fields absent) */
+  const struct timeval * t;  /* the time the apdu was captured */
+  char * calling;            /* source ip address */
+  int   srcport;             /* source port */
+  char * called;             /* destination ip address */
+  int   dstport;             /* source port */
+} z3950apdu;
+
+
+z3950apdu * parseable (unsigned char * apdu, int len);
+
+char * srchost (void);
+int    srcport (void);
+char * dsthost (void);
+int    dstport (void);
+
+
+/*
+ * time stamp presentation formats
+ */
+#define DELTA_FMT      1   /* the time since receiving the previous apdu */
+#define ABS_FMT        2   /* the current time */
+#define RELATIVE_FMT   3   /* the time relative to the first apdu received */
+
+
+char * timestamp (const struct timeval * t, int fmt);
diff --git a/ziffy/fmemdmp.c b/ziffy/fmemdmp.c
new file mode 100644 (file)
index 0000000..66d84eb
--- /dev/null
@@ -0,0 +1,106 @@
+/*
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ * fmemdmp.c - tracing utilities
+ *
+ * Copyright (c) 1998-2001 R. Carbone <rocco@ntop.org>
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ */
+
+
+
+/*
+ * Operating System include files
+ */
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <stdarg.h>
+#include <ctype.h>
+
+#include <time.h>
+#if HAVE_SYS_TIME_H
+# include <sys/time.h>
+#endif
+
+
+/*
+ * Pretty print function.
+ *
+ * This function dumps a buffer in memory in the (pretty !!) format :
+ *
+ *   off:  printable          hexadecimal notation
+ * --------------------------------------------------------------------------
+ *
+ * Dump of memory area at address 0x10000444 for 51 bytes
+ *     0:  abcdefghijklmnop   61 62 63 64 65 66 67 68 69 6a 6b 6c 6d 6e 6f 70
+ *    16:  qrstuvzxyw012345   71 72 73 74 75 76 7a 78 79 77 30 31 32 33 34 35
+ *    32:  6789~!@#$%^&*()_   36 37 38 39 7e 21 40 23 24 25 5e 26 2a 28 29 5f
+ *    48:  -+=                2d 2b 3d
+ *
+ * Dump of memory area at address 0x7fffbc03 for 16 bytes
+ *    0:  rocco@tecsiel.it    72 6f 63 63 6f 40 74 65 63 73 69 65 6c 2e 69 74
+ */
+void fmemdmp (FILE * fd, char * ptr, int size, char * text)
+{
+  int offset = 0;
+  int i = 0;
+  int bytes_in_a_line = 16;
+  unsigned int total;
+
+  if (! ptr || size <= 0)
+    return;
+
+  if (text && * text)
+    fprintf (fd, "\"%s\" at address 0x%08x for %d bytes\n",
+            text, (unsigned int) ptr, size);
+
+  for (total = 0; total < size; total += bytes_in_a_line)
+    {
+      /*
+       * Print the offset
+       */
+      fprintf (fd, "%6d:  ", offset);
+      /*
+       * Print the bytes in a line (each byte in ASCII notation)
+       */
+      for (i = 0; i < bytes_in_a_line; i ++)
+       if (total + i < size)
+         fprintf (fd, "%c",
+                  isprint (* (ptr + total + i) & 0x000000ff)
+                  ? (* (ptr + total + i))
+                  : '.');
+       else
+         fprintf (fd, " "); /* 1 blank character */
+      /*
+       * Print the separator
+       */
+      fprintf (fd, "  ");
+      /*
+       * Print the bytes in a line (each byte in Hexadecimal notation)
+       */
+      for (i = 0; i < bytes_in_a_line && i < size; i ++)
+       if (total + i < size)
+         fprintf (fd, "%02x ",
+                  * (ptr + total + i) & 0x000000ff);
+       else
+         fprintf (fd, "   "); /* 3 more blanks characters */
+
+      fprintf (fd, "\n");
+      offset += bytes_in_a_line;
+    }
+  fflush (fd);
+}
diff --git a/ziffy/hooks.c b/ziffy/hooks.c
new file mode 100644 (file)
index 0000000..7645f74
--- /dev/null
@@ -0,0 +1,316 @@
+/*
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ * hooks.c - a TCP/IP protocol filter for ziffy
+ *
+ * Copyright (c) 1998-2001 R. Carbone <rocco@ntop.org>
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ */
+
+
+#if defined(linux)
+# if !defined(_BSD_SOURCE)
+#  define _BSD_SOURCE
+# endif
+#endif
+
+/*
+ * Operating System include files
+ */
+#include <stdio.h>
+#include <string.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+
+#include <netdb.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+
+#include <net/if.h>
+
+#if HAVE_NETINET_IF_ETHER_H
+#include <netinet/if_ether.h>
+#endif
+
+#if HAVE_NETINET_IN_SYSTM_H
+#include <netinet/in_systm.h>
+#endif
+
+#include <netinet/ip.h>
+#include <netinet/tcp.h>
+
+#include "pcap.h"                   /* Packet Capture Library */
+
+#include "apdu.h"
+
+void fmemdmp (FILE * fd, char * ptr, int size, char * text);
+
+
+/* external */
+extern int dlt;
+
+
+/*
+ * to allow a pretty-print of lower-layers address I save
+ * relevant pointers to all the protocol data units in global variables,
+ * rather than pass them across function calls.
+ * So, for example, if someone is interested in the paired source and
+ * destination IP addressed, they can be easily accessed by global 'ip' pointer.
+ */
+
+
+/*
+ * hooks to the known protocols in the ethernet packets
+ */
+static struct ether_header * e = NULL;
+static struct ip * ip          = NULL;
+static struct tcphdr * tcp     = NULL;
+extern u_char * z3950;
+
+/*
+ * sizes of the known protocols in the ethernet packets
+ */
+static int eth_size   = 0;
+static int eth_hlen   = 0;
+static int ip_size    = 0;
+static int ip_hlen    = 0;
+static int tcp_size   = 0;
+static int tcp_hlen   = 0;
+extern int z3950_size;
+
+
+char * srchost (void)
+{
+  static char buf [256];  /* should be enough for humans !!! */
+
+  struct hostent * host = NULL;
+
+  if (aflag)
+    host = gethostbyaddr ((char *) & ip -> ip_src, sizeof (ip -> ip_src), AF_INET);
+
+  sprintf (buf, "%s", host ? host -> h_name : inet_ntoa (ip -> ip_src));
+  return (buf);
+}
+
+
+int srcport (void)
+{
+  return ((int) ntohs (tcp -> th_sport));
+}
+
+
+char * dsthost (void)
+{
+  static char buf [256];  /* should be enough for humans !!! */
+
+  struct hostent * host = NULL;
+
+  if (aflag)
+    host = gethostbyaddr ((char *) & ip -> ip_dst, sizeof (ip -> ip_dst), AF_INET);
+
+  sprintf (buf, "%s", host ? host -> h_name : inet_ntoa (ip -> ip_dst));
+  return (buf);
+}
+
+
+int dstport (void)
+{
+  return ((int) ntohs (tcp -> th_dport));
+}
+
+
+/*
+ * stolen from the addrtoname.c in tcpdump
+ */
+static char hex [] = "0123456789abcdef";
+
+static char * etheraddr_string (u_char * e)
+{
+  static char buf [sizeof ("00:00:00:00:00:00")];
+
+  int i;
+  int j;
+  char * p;
+
+  strcpy (buf, "00:00:00:00:00:00");
+
+  /*
+   * hacked to manage DLT_NULL
+   */
+  if (! e)
+    return (buf);
+
+  p = buf;
+  if ((j = * e >> 4) != 0)
+    * p ++ = hex [j];
+  * p ++ = hex [* e ++ & 0xf];
+  for (i = 5; -- i >= 0; )
+    {
+      * p ++ = ':';
+      if ((j = * e >> 4) != 0)
+       * p ++ = hex [j];
+    * p ++ = hex [* e ++ & 0xf];
+    }
+  * p = '\0';
+  return (buf);
+}
+
+
+/*
+ * Parse the incoming Ethernet Packet and set hooks to all pertinent data.
+ *
+ * 'h' is the pointer to the packet header (independent from interfaces)
+ * 'p' is the pointer to the packet data
+ *
+ * Warning: I really want libpcap to give me aligned packets
+ */
+z3950apdu * pduhook (const struct pcap_pkthdr * h, const u_char * p)
+{
+  static unsigned long ethno = 0;  /* # of ethernet packets received by the decoder */
+  static unsigned long ipno = 0;   /* # of IP packets received by the decoder */
+  static unsigned long tcpno = 0;  /* # of TCP packets received by the decoder */
+
+  u_char * q;
+
+  z3950apdu * apdu = NULL;
+
+  /*
+   * Ethernet Protocol
+   */
+  e = (struct ether_header *) p;
+
+  /*
+   * Ethernet sizes
+   *
+   * The header is only 4 bytes long in case of no link-layer encapsulation (DLT_NULL).
+   * It contains a network order 32 bit integer that specifies the family, e.g. AF_INET
+   */
+  eth_size = h -> len;
+  eth_hlen = dlt == DLT_NULL ? 4 : sizeof (struct ether_header);
+
+  ++ ethno;
+
+  if (ethflag)
+    printf ("ETHER:  ----- Ether Header -----\n"),
+      printf ("ETHER:\n"),
+      printf ("ETHER:  Packet %ld arrived at %s\n", ethno, timestamp (& h -> ts, ABS_FMT)),
+      printf ("ETHER:  Total size  = %d : header = %d : data = %d\n",
+             eth_size, eth_hlen, eth_size - eth_hlen),
+      printf ("ETHER:  Source      = %s\n",
+             etheraddr_string (dlt == DLT_NULL ? NULL : (char *) & e -> ether_shost)),
+      printf ("ETHER:  Destination = %s\n",
+             etheraddr_string (dlt == DLT_NULL ? NULL : (char *) & e -> ether_dhost)),
+      fflush (stdout),
+      fmemdmp (stdout, (char *) e, eth_size, "Ethernet Packet");
+
+  /*
+   * Process only IP packets (or loopback packets when testing at home sweet home)
+   */
+  if (dlt == DLT_NULL || ntohs (e -> ether_type) == ETHERTYPE_IP)
+    {
+      /*
+       * IP Protocol
+       */
+      ip = (struct ip *) (p + eth_hlen);
+
+      /*
+       * IP sizes
+       *
+       * ip->ip_hl*4        = size of the IP (Header Only)
+       * ntohs (ip->ip_len) = size of the IP (Full Packet)
+       *            ip_size = eth_size - eth_hlen (better IMO)
+       */
+      ip_size = eth_size - eth_hlen;
+      ip_hlen = ip -> ip_hl * 4;
+
+      ++ ipno;
+
+      if (ipflag)
+       printf ("IP:     ----- IP Header -----\n"),
+         printf ("IP:\n"),
+         printf ("IP:     Packet %ld arrived at %s\n", ipno, timestamp (& h -> ts, ABS_FMT)),
+         printf ("IP:     Total size  = %d : header = %d : data = %d\n",
+                 ip_size, ip_hlen, ip_size - ip_hlen),
+         printf ("IP:     Source      = %s\n", inet_ntoa (ip -> ip_src)),
+         printf ("IP:     Destination = %s\n", inet_ntoa (ip -> ip_dst)),
+         fflush (stdout);
+
+#if (0)
+      fmemdmp (stdout, (char *) ip, ip_size, "IP Packet");
+#endif
+
+      /*
+       * i am looking for Z39.50 APDUs over TCP/IP. so...
+       */
+      if (ip -> ip_p == IPPROTO_TCP)
+       {
+         /*
+          * TCP Protocol
+          */
+         q = (u_char *) ip + ip_hlen;
+         tcp = (struct tcphdr *) q;
+
+         /*
+          * TCP sizes
+          *
+          * tcp->th_off*4 = size of the TCP (Header Only)
+          */
+         tcp_size = ip_size - ip_hlen;
+         tcp_hlen = tcp -> th_off * 4;
+
+         ++ tcpno;
+
+         if (tcpflag)
+           printf ("TCP:    ----- TCP Header -----\n"),
+             printf ("TCP:\n"),
+             printf ("TCP:    Packet %ld arrived at %s\n", tcpno, timestamp (& h -> ts, ABS_FMT)),
+             printf ("TCP:    Total size  = %d : header = %d : data = %d\n",
+                     tcp_size, tcp_hlen, tcp_size - tcp_hlen),
+             printf ("TCP:    Source      = %d\n", ntohs (tcp -> th_sport)),
+             printf ("TCP:    Destination = %d\n", ntohs (tcp -> th_dport)),
+             fflush (stdout),
+             fmemdmp (stdout, (char *) tcp, tcp_size, "TCP Packet");
+
+         /*
+          * Application Protocol
+          * (time to play with Z39.50 APDUs here)
+          */
+         z3950 = (u_char *) e + eth_hlen + ip_hlen + tcp_hlen;
+
+         /*
+          * Higher Protocol Packet Size
+          */
+         z3950_size = tcp_size - tcp_hlen;
+
+         apdu = parseable (z3950, z3950_size);
+
+         if (tcpflag && apdu)
+           printf ("TCP:    ----- TCP Header -----\n"),
+             printf ("TCP:\n"),
+             printf ("TCP:    Packet %ld arrived at %s\n", tcpno, timestamp (& h -> ts, ABS_FMT)),
+             printf ("TCP:    Total size  = %d : header = %d : data = %d\n",
+                     tcp_size, tcp_hlen, tcp_size - tcp_hlen),
+             printf ("TCP:    Source      = %d\n", ntohs (tcp -> th_sport)),
+             printf ("TCP:    Destination = %d\n", ntohs (tcp -> th_dport)),
+             fflush (stdout),
+             fmemdmp (stdout, (char *) tcp, tcp_size, "TCP Packet");
+
+
+         return (apdu);
+       }
+    }
+  return (NULL);
+}
diff --git a/ziffy/yaz.c b/ziffy/yaz.c
new file mode 100644 (file)
index 0000000..b73a3e2
--- /dev/null
@@ -0,0 +1,145 @@
+/*
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ * yaz.c - decoding and printing utility based on the YAZ Toolkit
+ *
+ * Copyright (c) 1998-2001 R. Carbone <rocco@ntop.org>
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ */
+
+
+/*
+ * Operating System include files
+ */
+#include <stdio.h>
+#include <sys/time.h>
+
+/*
+ * YAZ include files
+ */
+#include "yaz/odr.h"
+#include "yaz/proto.h"
+
+#include "apdu.h"
+
+
+void please_yaz_help_me (z3950apdu * hook)
+{
+  extern unsigned char * z3950;
+  extern int z3950_size;
+
+  /*
+   * Variable to keep the Z39.50 APDUs. The definitions are in the
+   * the structures defined by the YAZ Toolkit.
+   */
+  Z_APDU * apdu = NULL;
+
+  /*
+   * Decoding/Printing streams
+   */
+  ODR printing;
+  ODR decode;
+
+  /*
+   * The stream used for decoding
+   */
+#define MAXBERSIZE (2048 * 2048)
+  unsigned char berbuffer [MAXBERSIZE];
+
+  /*
+   * Allocate a stream for input data
+   */
+  decode = odr_createmem (ODR_DECODE);
+  if (! decode)
+    {
+      printf ("Not enough memory to create an input stream\n");
+      return;
+    }
+
+  /*
+   * Allocate a stream for printing data
+   */
+  printing = odr_createmem (ODR_PRINT);
+  if (! printing)
+    {
+      printf ("Not enough memory to create a printing stream\n");
+      odr_destroy (decode);
+      return;
+    }
+
+  /*
+   * Initialize the decoding routines
+   */
+  memcpy (berbuffer, z3950, z3950_size);
+
+  odr_setbuf (decode, berbuffer, z3950_size, 0);
+
+  /*
+   * Perform BER decoding
+   */
+  if (z_APDU (decode, & apdu, 0, 0))
+    {
+      ++ z3950_apduno;
+
+      if (z3950flag)
+       printf ("Z3950:  ----- Z39.50 APDU -----\n"),
+         printf ("Z3950:  APDU %ld arrived at %s\n", z3950_apduno,
+                 timestamp (hook -> t, ABS_FMT)),
+         printf ("Z3950:  Total size  = %d\n", z3950_size),
+         fflush (stdout);
+
+      /*
+       * save the time the last apdu was displayed
+       */
+      if (z3950_apduno == 1)
+       gettimeofday (& first_apdu, NULL);
+
+      /*
+       * print standard summary information accordingly to the format
+       *
+       * id   time     source:port ->   destination:port    type
+       */
+      printf ("Z3950: %5ld %s %s:%d -> %s:%d %s\n",
+             z3950_apduno, timestamp (hook -> t, DELTA_FMT),
+             hook -> calling, hook -> srcport, hook -> called, hook -> dstport,
+             hook -> name),
+       fflush (stdout);
+
+      gettimeofday (& last_apdu, NULL);
+
+#if (0)
+      fmemdmp (stdout, z3950, z3950_size, "Z39.50 APDU");
+#endif
+
+      /*
+       * Yup! We have the APDU now. Try to print it
+       */
+      odr_setbuf (printing, berbuffer, z3950_size, 0);
+      fflush (stdout);
+
+      z_APDU (printing, & apdu, 0, 0);
+      fflush (stderr);
+
+      odr_reset (printing);
+      printing -> buf = NULL;
+    }
+
+  /*
+   * release memory previously allocated
+   */
+  odr_destroy (decode);
+  odr_destroy (printing);
+}
diff --git a/ziffy/ziffy.1 b/ziffy/ziffy.1
new file mode 100644 (file)
index 0000000..98826e0
--- /dev/null
@@ -0,0 +1,186 @@
+.\"
+.\" -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+.\" ziffy.1 - a promiscuous Z39.50 APDU sniffer for Ethernet
+.\"
+.\" Copyright (c) 1998 R. Carbone - Finsiel S.p.A.
+.\" -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+.\"
+.\" This program is free software; you can redistribute it and/or modify
+.\" it under the terms of the GNU General Public License as published by
+.\" the Free Software Foundation; either version 2 of the License, or
+.\" (at your option) any later version.
+.\"
+.\" This program is distributed in the hope that it will be useful,
+.\" but WITHOUT ANY WARRANTY; without even the implied warranty of
+.\" MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+.\" GNU General Public License for more details.
+.\"
+.\" You should have received a copy of the GNU General Public License
+.\" along with this program; if not, write to the Free Software
+.\" Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+.\" 
+.TH ZIFFY 1 "0.0.2" "28 December 1998" "The Z39.50 Network Sniffer"
+.SH NAME
+ziffy \- capture and display Z39.50 APDUs on a live network
+.SH SYNOPSYS
+.na
+.B ziffy
+[
+.B \-alloptionshere
+]
+.br
+.ti +6
+[
+.B \-i
+.I interface
+] [
+.B \-r
+.I file
+]
+[
+.B \-s
+.I snaplen
+]
+.br
+.ti +8
+[
+.B \-T
+.I type
+]
+[
+.B \-w
+.I file
+]
+[
+.I expression
+]
+.br
+.ad
+.SH DESCRIPTION
+\fBziffy\fR is a Z39.50 protocol analyzer based on the \fBLIBPCAP\fR,
+the current standard Unix library for packet capturing. It can be started both in interactive
+mode to capture, decode and show all information in the Z39.50 APDUs from a live network,
+and in batch mode to analyze the APDUs off-line from a previously created file.
+\fBziffy\fR uses the standard BPF network packet filter for more reliable capture mechanism.
+An additional expression can be given on the command line to capture only packets
+for which \fIexpression\fP is `true'.
+By default \fBziffy\fR displays Z39.50 APDUs in a single-line summary form. In this format
+only the name of the captured APDU is displayed in the summary line while the underlaying TCP,
+IP, and Ethernet frames information are discarded.
+Multi-lines are also supported if either of verbose modes are enabled.
+This allows an high degree of monitoring, from simple checks of functional processes down
+to full APDUs hexacimal dump for interoperability and debugging testing phases.
+.SH OPTIONS
+.TP
+.B \-a
+Attempt to convert network addresses to names. By default, \fBziffy\fR will ___not___
+resolve IP addresses to FQDN's.
+.TP
+.B \-c
+Capture a maximum of \fIcount\fP number of APDUs and then exit.
+.TP
+.B \-e
+Enable the display of the link-level header.
+.TP
+.B \-f
+Do not traslate `foreign' internet addresses.
+.TP
+.B \-h
+Display a help screen and quit.
+.TP
+.B \-i
+Define the name of the interface to use for live packet capture. It should match
+one of the names listed in \*(L"\fBnetstat \-i\fR\*(R" or \*(L"\fBifconfig \-a\fR\*(R".
+By default \fBziffy\fR will automatically choose the first non-loopback interface it finds.
+.TP
+.B \-l
+Make stdout line buffered. Useful if you want to see the data while capturing it.
+.TP
+.B \-n
+Disable domain name qualification of host names.
+.TP
+.B \-p
+Set the interface in non-promiscuous mode. Only packets addressed to the local host machine
+will be captured.
+.TP
+.B \-r
+Read packet data from \fIfile\fR.  Currently, \fBziffy\fR only understands
+\fBpcap\fR / \fBtcpdump\fR formatted files.
+.TP
+.B \-s
+Truncate each packet after \fIsnaplen\fP bytes when capturing live data.
+No more than \fIsnaplen\fR bytes of each network packet will be read into memory,
+or saved to disk.
+.br
+While 68 bytes is adequate for lower-level protocol such as IP, ICMP, TCP and UDP,
+it is inadeguate for Z39.50 and the exact cut-off is not easy to determine.
+The default value is set to 10K which should be enough for most networks.
+You should limit \fIsnaplen\fP to the smallest number that will allow you to
+capture all the Z39.50 protocol information.
+.br
+Note that taking larger snapshots both increases the amount of time it takes to
+process packets and, effectively, decreases the amount of packet buffering.
+This may cause packets to be lost.
+.TP
+.B \-t
+Sets the format of the packet timestamp displayed.
+
+INSERIRE QUI LA SBRODOLATA PER I VARI FORMATI DI PRESENTAZIONE
+
+.TP
+.B \-v
+Print the program version and exit.
+.TP
+.B \-w
+Write the raw Z39.50 APDUs to \fIfile\fR rather than printing them out.
+They can later be printed with the \-r option.
+Standard output is used if \fIfile\fR is ``-''.
+.TP
+.B \-1
+Set verbose output at level 1.
+.TP
+.B \-2
+Set verbose output at level 2.
+.TP
+.B \-T
+With this option you can filter out certain APDU types from beeing 
+shown. For example, if you only wanted to see all APDU's except 
+"init" and "sort" you could use:
+.B % \fBziffy\fR -T init -T sort
+Currently known APDU types are:
+\fBinit\fR
+\fBseach\fR
+\fBpresent\fR
+\fBscan\fR
+\fBsort\fR
+
+
+.Sp
+A display filter can be entered into the strip at the bottom.  It must
+have the same format as \fBtcpdump\fR filter strings, since both programs use
+the same underlying library.
+.SH EXAMPLES
+.LP
+To print all APDUs arriving at or departing from \fIzeta.tlcpi.finsiel.it\fP:
+.RS
+.nf
+\fBziffy host zeta.tlcpi.finsiel.it\fP
+.fi
+.RE
+.SH OUTPUT FORMAT
+The output of \fIziffy\fP is Z39.50 APDU dependent. The following
+gives a brief description and examples of most of the formats.
+.SH WARNING
+To run
+.I ziffy
+you must be root or it must be installed setuid to root.
+.SH "SEE ALSO"
+tcpdump(1), pcap(3), xasn1(3), yaz(3), snacc(3)
+.SH NOTES
+The latest version of \fBziffy\fR can be found at
+\fBhttp://zeta.tlcpi.finsiel.it/ziffy\fR
+.SH AUTHOR
+Rocco Carbone <rocco@ntop.org>
+.SH BUGS
+Please send bug reports to the author <rocco@ntop.org>
+
diff --git a/ziffy/ziffy.c b/ziffy/ziffy.c
new file mode 100644 (file)
index 0000000..31bdee1
--- /dev/null
@@ -0,0 +1,501 @@
+/*
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ * ziffy.c - a promiscuous Z39.50 APDU sniffer for Ethernet
+ *
+ * Copyright (c) 1998-2001 R. Carbone <rocco@ntop.org>
+ * -=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ */
+
+
+/*
+ * Operating System include files
+ */
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <string.h>
+#include <signal.h>
+
+#include <time.h>
+#if HAVE_SYS_TIME_H
+#include <sys/time.h>
+#endif
+#include <sys/utsname.h>
+
+#if 1
+#include "getopt.h"
+#endif
+
+#include "pcap.h"               /* Packet Capture Library */
+
+#include "apdu.h"
+
+
+/*
+ * external
+ */
+z3950apdu * pduhook (const struct pcap_pkthdr * h, const u_char * p);
+
+
+#if defined(HAVE_XASN1)
+void please_finsiel_help_me (z3950apdu * hook);
+#endif /* HAVE_XASN1 */
+
+#if defined(HAVE_YAZ)
+void please_yaz_help_me (z3950apdu * hook);
+#endif /* HAVE_YAZ */
+
+#if defined(HAVE_SNACC)
+void please_snacc_help_me (z3950apdu * hook);
+#endif /* HAVE_SNACC */
+
+
+/*
+ * global variables
+ */
+time_t now;                           /* current time */
+time_t start_time;                    /* time the program was started */
+time_t firstapdu_time;                /* time the first APDU was received */
+time_t laststapdu_time;               /* time the last APDU was received */
+
+unsigned long int z3950_apduno = 0;   /* # of z3950 apdus so far received */
+u_char * z3950   = NULL;              /* pointer to the last apdu received */
+int z3950_size   = 0;                 /* and its size */
+
+/*
+ * I currently tested the program at home in a null networked environment
+ * and on ethernet 10M lan. the following variable keeps the data-link
+ * encapsulation type. more info in net/bpf.h
+ */
+int dlt = -1;
+
+int aflag     = 0; /* attempt to convert numeric network addresses to FQDN */
+
+int ethflag   = 0;
+int ipflag    = 0;
+int tcpflag   = 0;
+int z3950flag = 0;
+
+
+/*
+ * Length of saved portion of packet
+ */
+#define DEFAULT_SNAPLEN 65536  /* This should be enough... */
+static int snaplen = DEFAULT_SNAPLEN;
+
+#define DEFAULT_MAXAPDUS -1    /* that means indefinite */
+static int maxapdus = DEFAULT_MAXAPDUS;
+
+/*
+ * A handler for pcap, it needs to be global because there is no other way to
+ * pass it to the signal handler, the same can be said about the file descriptor
+ * for SOCK_PACKET.
+ */
+pcap_t * ph = NULL;
+
+
+/*
+ * package info
+ */
+static char __copyright__   [] = "Copyright (c) 1998-2001";
+static char __author__      [] = "R. Carbone <rocco@ntop.org>";
+static char __version__     [] = "Version 0.0.3";
+static char __released__    [] = "June 2001";
+
+
+#if (0)
+struct option options [] =
+{
+  /* Default args */
+  { "help",            no_argument,            NULL,   'h' },
+  { "version",         no_argument,            NULL,   'v' },
+
+  /* Session Management stuff */
+  { "restart-session", required_argument,      NULL,   'S' },
+  { "discard-session", required_argument,      NULL,   'D' },
+
+  { NULL, 0, NULL, 0 }
+};
+#endif
+
+char ebuf [PCAP_ERRBUF_SIZE] = {0};
+struct pcap_stat pcapstats = {0};
+
+/*
+ * signal handler
+ */
+void on_signal (int signo)
+{
+  /*
+   * time for statistics
+   */
+  if (pcap_stats (ph, & pcapstats) != 0)
+    {
+      printf ("Cannot get the statistics due to %s\n", ebuf),
+      exit (-1);
+    }
+  else
+    {
+      printf ("\n\n");
+
+      printf ("%u packets received by decoder\n", pcapstats . ps_recv);
+      printf ("%u packets dropped by kernel\n", pcapstats . ps_drop);
+    }
+
+  fflush (stdout);
+
+  /*
+   * bye bye !
+   */
+  pcap_close (ph);
+
+  exit (0);
+}
+
+
+
+/*
+ * You are welcome!
+ */
+void welcome (char * progname)
+{
+  time_t now = ((time_t) time ((time_t *) 0));
+  char * nowstring = ctime (& now);
+  struct utsname machine;
+
+  nowstring [24] = '\0';
+  uname (& machine);
+
+  printf ("This is %s %s of %s\n", progname, __version__, __released__);
+  printf ("%s %s\n", __copyright__, __author__);
+  printf ("Started at %s on %s\n\n", nowstring, machine . nodename);
+  printf ("\n");
+  fflush (stdout);
+  fflush (stderr);
+}
+
+
+/*
+ * Wrong. Please try again accordingly to ....
+ */
+void usage (char * progname)
+{
+  welcome (progname);
+
+  printf ("Usage: %s [--help] [--version]\n\n", progname);
+  printf ("Options:\n");
+  printf ("        h, --help             display this help and exit\n");
+  printf ("        v, --version          output version information and exit\n");
+
+  printf ("         , --                 print filter code\n");
+  printf ("         , --                 print ethernet header\n");
+  printf ("         , --                 try to resolve ip addresses\n");
+  printf ("         , --                 remove domains from printed host names\n");
+  printf ("         , --                 don't translate _foreign_ IP address\n");
+  printf ("         , --                 print packet arrival time\n");
+
+  printf ("        s, --snaplen          \n");
+  printf ("        N, --non-promiscuous  capture APDUs addressed to the host machine\n");
+  printf ("        C, --maxcount         capture maxcount APDUs and then terminate\n");
+
+  printf ("        D, --dropped-packets  display number of packets dropped during capture\n");
+  fflush (stdout);
+}
+
+
+/*
+ * This is really the `main' function of the sniffer.
+ *
+ * Parse the incoming APDU, and when possible show all pertinent data.
+ *
+ * 'h' is the pointer to the packet header (independent from interfaces)
+ * 'p' is the pointer to the packet data
+ * 'caplen' is the number of bytes actually captured
+ * 'length' is the length of the packet off the wire
+ */
+void parse_pdu (u_char * user_data,
+               const struct pcap_pkthdr * h,
+               const u_char * p)
+{
+  z3950apdu * hook;
+  int done = 0;
+
+  if (! (hook = pduhook (h, p)))
+    return;
+
+  /*
+   * update the descriptor of the apdu
+   */
+  hook -> t = & h -> ts;
+  hook -> calling = srchost ();
+  hook -> srcport = srcport ();
+  hook -> called  = dsthost ();
+  hook -> dstport = dstport ();
+
+#if defined(HAVE_XASN1)
+  if (! done)
+    please_finsiel_help_me (hook);
+  done = 1;
+#endif /* HAVE_XASN1 */
+
+#if defined(HAVE_YAZ)
+  if (! done)
+    please_yaz_help_me (hook);
+  done = 1;
+#endif /* HAVE_YAZ */
+
+#if defined(HAVE_SNACC)
+  if (! done)
+    please_snacc_help_me (hook);
+  done = 1;
+#endif /* HAVE_SNACC */
+}
+
+
+/*
+ * Oh no! yet another main here
+ */
+int main (int argc, char * argv [])
+{
+  int option;
+  char * optstr = "hvac:ef:i:lnprs:twxz";
+
+  char * progname;
+
+  char * interface = NULL;
+  char * filename = NULL;
+
+  char * filter = NULL;
+  struct bpf_program program = {0};
+  bpf_u_int32 network = {0};
+  bpf_u_int32 netmask = {0};
+
+
+  /*
+   * notice the program name
+   */
+  progname = strrchr (argv [0], '/');
+  if (! progname || ! * progname)
+    progname = * argv;
+  else
+    progname ++;
+
+#if (0)
+  /*
+   * initialize getopt
+   */
+  optarg = NULL;
+  optind = 0;
+  optopt = 0;
+  opterr = 0;  /* this prevents getopt() to send error messages to stderr */
+#endif
+
+  /*
+   * Parse command-line options
+   */
+  while ((option = getopt (argc, argv, optstr)) != EOF)
+    {
+      switch (option)
+       {
+       default:
+         usage (progname);
+         return (-1);
+
+       case '?':
+         printf ("%s: unrecognized option %c\n", progname, optopt);
+         usage (progname);
+         return (-1);
+
+       case ':':
+         printf ("%s: missing parameter %c\n", progname, optopt);
+         usage (progname);
+         return (-1);
+
+       case 'h':
+         usage (progname);
+         return (0);
+
+       case 'a':
+         aflag = 1;
+         break;
+
+       case 'c':
+         maxapdus = atoi (optarg);
+         if (maxapdus <= 0)
+           printf ("malformed max apdus counter %s", optarg), maxapdus = DEFAULT_MAXAPDUS;
+         break;
+
+       case 'e':
+         ethflag = 1;
+         break;
+
+       case 'f':
+         filename = strdup (optarg);
+         break;
+
+       case 'i':
+         interface = strdup (optarg);
+         break;
+
+       case 'l':
+         break;
+
+       case 'n':
+         break;
+
+       case 'p':
+         break;
+
+       case 'r':
+         break;
+
+       case 's':
+         snaplen = atoi (optarg);
+         if (snaplen <= 0)
+           printf ("malformed snaplen %s", optarg), snaplen = DEFAULT_SNAPLEN;
+         break;
+
+       case 't':
+         tcpflag = 1;
+         break;
+
+       case 'w':
+         break;
+
+       case 'x':
+         ipflag = 1;
+         break;
+
+       case 'z':
+         z3950flag = 1;
+         break;
+       }
+    }
+
+  /*
+   * You are welcome
+   */
+  welcome (progname);
+
+
+  /*
+   * build a string from all remaining arguments
+   */
+  filter = NULL;
+  {
+    int roomsize = 0;
+    while (optind < argc)
+      {
+        roomsize += (strlen (argv [optind]) + 1 + 1);
+        if (filter)
+          {
+            strcat (filter, " ");
+            filter = realloc (filter, roomsize);
+            strcat (filter, argv [optind ++]);
+          }
+        else
+          {
+            filter = malloc (roomsize);
+            strcpy (filter, argv [optind ++]);
+          }
+      }
+  }
+
+
+  /*
+   * find a suitable interface, if i don't have one
+   */
+  if (! filename && ! interface && ! (interface = pcap_lookupdev (ebuf)))
+    {
+      printf ("No suitable interfaces found, please specify one with -i\n");
+      exit (-1);
+    }
+
+
+  if ((getuid () && geteuid ()) || setuid (0))
+    {
+      printf ("Sorry, you must be root in order to run this program.\n");
+      exit (-1);
+    }
+
+  /*
+   * time to initialize the libpcap
+   */
+  ph = filename ? pcap_open_offline (filename, ebuf) :
+    pcap_open_live (interface, snaplen, 1, 1000, ebuf);
+
+  if (! ph)
+    printf ("Cannot initialize the libpcap package due to %s\n", ebuf),
+      exit (-1);
+
+  /*
+   * get the interface network number and its mask
+   * (unless we are reading data from a file)
+   */
+  if (! filename && pcap_lookupnet (interface, & network, & netmask, ebuf) < 0)
+    printf ("Cannot lookup for the network due to %s\n", ebuf),
+      exit (-1);
+
+  /*
+   * determine the type of the underlying network and the data-link encapsulation method
+   * (unless we are reading data from a file)
+   */
+  dlt = pcap_datalink (ph);
+
+  if (! filename && dlt != DLT_NULL && dlt != DLT_IEEE802 && dlt != DLT_EN10MB)
+    printf ("Unsupported data-link encapsulation %d\n", dlt),
+      exit (-1);
+
+  /*
+   * compile an optional filter into a BPF program
+   */
+  if (filter && pcap_compile (ph, & program, filter, 1, netmask) == -1)
+    printf ("Cannot compile the filter %s\n", filter),
+      exit (-1);
+
+  /*
+   * apply the filter to the handler
+   */
+  if (filter && pcap_setfilter (ph, & program) == -1)
+    printf ("Cannot set the filter %s\n", filter),
+      exit (-1);
+
+  /*
+   * announce to the world
+   */
+  printf ("%s %s: listening on %s\n", progname, __version__, interface);
+  fflush (stdout);
+
+  /*
+   * Setup signal handlers
+   */
+  signal (SIGTERM, on_signal);
+  signal (SIGINT, on_signal);
+
+
+  /*
+   * Go for fun! and handle any packet received
+   */
+  if (pcap_loop (ph, -1, parse_pdu, NULL) == -1)
+    printf ("%s: error while capturing packets due to %s\n", progname, pcap_geterr (ph)),
+      exit (-1);
+
+  pcap_close (ph);
+
+
+  return (0);
+}