ia64/xen-unstable

changeset 5132:9f22db685802

bitkeeper revision 1.1536 (429399e9qNO_CnmTploLs7q5t-754Q)

Merge firebug.cl.cam.ac.uk:/auto/groups/xeno-xenod/BK/xen-unstable.bk
into firebug.cl.cam.ac.uk:/local/scratch/cl349/xen-unstable.bk
author cl349@firebug.cl.cam.ac.uk
date Tue May 24 21:17:29 2005 +0000 (2005-05-24)
parents d74dea34e69b 3615dfd94bdb
children 3ba11d3c9826
files .rootkeys tools/Makefile tools/Rules.mk tools/blktap/Makefile tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/Makefile.in tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/configure tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/configure.in tools/ioemu/target-i386-dm/Makefile tools/libxc/Makefile tools/libxc/xc_private.h tools/libxutil/Makefile tools/libxutil/allocate.c tools/libxutil/allocate.h tools/libxutil/debug.h tools/libxutil/enum.c tools/libxutil/enum.h tools/libxutil/fd_stream.c tools/libxutil/fd_stream.h tools/libxutil/file_stream.c tools/libxutil/file_stream.h tools/libxutil/gzip_stream.c tools/libxutil/gzip_stream.h tools/libxutil/hash_table.c tools/libxutil/hash_table.h tools/libxutil/iostream.c tools/libxutil/iostream.h tools/libxutil/kernel_stream.c tools/libxutil/kernel_stream.h tools/libxutil/lexis.c tools/libxutil/lexis.h tools/libxutil/socket_stream.c tools/libxutil/socket_stream.h tools/libxutil/string_stream.c tools/libxutil/string_stream.h tools/libxutil/sxpr.c tools/libxutil/sxpr.h tools/libxutil/sxpr_parser.c tools/libxutil/sxpr_parser.h tools/libxutil/sys_net.c tools/libxutil/sys_net.h tools/libxutil/sys_string.c tools/libxutil/sys_string.h tools/libxutil/util.c tools/libxutil/util.h tools/misc/Makefile tools/misc/cpuperf/Makefile tools/python/setup.py tools/python/xen/lowlevel/xc/xc.c tools/vnet/Makefile tools/vnet/libxutil/Makefile tools/vnet/libxutil/allocate.c tools/vnet/libxutil/allocate.h tools/vnet/libxutil/debug.h tools/vnet/libxutil/enum.c tools/vnet/libxutil/enum.h tools/vnet/libxutil/fd_stream.c tools/vnet/libxutil/fd_stream.h tools/vnet/libxutil/file_stream.c tools/vnet/libxutil/file_stream.h tools/vnet/libxutil/gzip_stream.c tools/vnet/libxutil/gzip_stream.h tools/vnet/libxutil/hash_table.c tools/vnet/libxutil/hash_table.h tools/vnet/libxutil/iostream.c tools/vnet/libxutil/iostream.h tools/vnet/libxutil/kernel_stream.c tools/vnet/libxutil/kernel_stream.h tools/vnet/libxutil/lexis.c tools/vnet/libxutil/lexis.h tools/vnet/libxutil/socket_stream.c tools/vnet/libxutil/socket_stream.h tools/vnet/libxutil/string_stream.c tools/vnet/libxutil/string_stream.h tools/vnet/libxutil/sxpr.c tools/vnet/libxutil/sxpr.h tools/vnet/libxutil/sxpr_parser.c tools/vnet/libxutil/sxpr_parser.h tools/vnet/libxutil/sys_net.c tools/vnet/libxutil/sys_net.h tools/vnet/libxutil/sys_string.c tools/vnet/libxutil/sys_string.h tools/vnet/libxutil/util.c tools/vnet/libxutil/util.h tools/vnet/vnet-module/Makefile.vnet tools/vnet/vnetd/Makefile tools/xcs/Makefile tools/xcutils/Makefile tools/xentrace/Makefile
line diff
     1.1 --- a/.rootkeys	Tue May 24 21:10:23 2005 +0000
     1.2 +++ b/.rootkeys	Tue May 24 21:17:29 2005 +0000
     1.3 @@ -698,40 +698,6 @@ 42337174PxyzzPk62raDiYCIsfStDg tools/lib
     1.4  4273458duzL--nsTfT6e_q6Kfij48g tools/libxc/xc_ptrace_core.c
     1.5  41ebbfe9U0b0kI-HgjK7VEY4EvW7_w tools/libxc/xc_sedf.c
     1.6  41dde8b0pLfAKMs_L9Uri2hnzHiCRQ tools/libxc/xc_vmx_build.c
     1.7 -40e1b09dMYB4ItGCqcMIzirdMd9I-w tools/libxutil/Makefile
     1.8 -40e033325Sjqs-_4TuzeUEprP_gYFg tools/libxutil/allocate.c
     1.9 -40e03332KYz7o1bn2MG_KPbBlyoIMA tools/libxutil/allocate.h
    1.10 -41a216cav5JJbtDQnusfuMa_1x_Xpw tools/libxutil/debug.h
    1.11 -40e9808eyjiahG5uF6AMelNVujBzCg tools/libxutil/enum.c
    1.12 -40e9808eZpbdn9q2KSSMGCNvY_ZgpQ tools/libxutil/enum.h
    1.13 -4284c2ecWyadIhHF1u_QSgWqIXkaLA tools/libxutil/fd_stream.c
    1.14 -4284c2ecEOOcF6fZUf_NsZzYAoNo-w tools/libxutil/fd_stream.h
    1.15 -40e03332p5Dc_owJQRuN72ymJZddFQ tools/libxutil/file_stream.c
    1.16 -40e03332jWfB2viAhLSkq1WK0r_iDQ tools/libxutil/file_stream.h
    1.17 -40e03332rUjNMGg11n2rN6V4DCrvOg tools/libxutil/gzip_stream.c
    1.18 -40e033321O5Qg22haLoq5lpmk4tooQ tools/libxutil/gzip_stream.h
    1.19 -40e9808easXCzzAZQodEfKAhgUXSPA tools/libxutil/hash_table.c
    1.20 -40e9808e94BNXIVVKBFHC3rnkvwtJg tools/libxutil/hash_table.h
    1.21 -40e03332ihnBGzHykVwZnFmkAppb4g tools/libxutil/iostream.c
    1.22 -40e03332UGwbLR4wsw4ft14p0Yw5pg tools/libxutil/iostream.h
    1.23 -40e0333245DLDzJemeSVBLuutHtzEQ tools/libxutil/kernel_stream.c
    1.24 -40e03332aK0GkgpDdc-PVTkWKTeOBg tools/libxutil/kernel_stream.h
    1.25 -40e9808epW9iHcLXuO3QfUfLzB7onw tools/libxutil/lexis.c
    1.26 -40e9808egccMhCizayQRGtpBA3L5MQ tools/libxutil/lexis.h
    1.27 -41a216caM4z39Fzjb91rv9Ed_4By1A tools/libxutil/socket_stream.c
    1.28 -41a216caqinvF1I5FQMHA4HTRz8MSA tools/libxutil/socket_stream.h
    1.29 -40e03332KT_tnnoAMbPVAZBB7kSOAQ tools/libxutil/string_stream.c
    1.30 -40e03332-VtK6_OZa1vMHXFil8uq6w tools/libxutil/string_stream.h
    1.31 -40e9808e5_PLdodqVOSx0b4T_f5aeg tools/libxutil/sxpr.c
    1.32 -40e9808e0O4sHZtkDv5hlSqjYcdQAQ tools/libxutil/sxpr.h
    1.33 -40ec1cc6SIiGbynOi-1NtPesOlzF-Q tools/libxutil/sxpr_parser.c
    1.34 -40ec1cc6wpvvGxZiq4EFvNOcw0tUFg tools/libxutil/sxpr_parser.h
    1.35 -40e03332Rkvq6nn_UNjzAAK_Tk9v1g tools/libxutil/sys_net.c
    1.36 -40e03332lQHvQHw4Rh7VsT1_sui29A tools/libxutil/sys_net.h
    1.37 -40e033321smklZd7bDSdWvQCeIshtg tools/libxutil/sys_string.c
    1.38 -40e03332h5V611rRWURRLqb1Ekatxg tools/libxutil/sys_string.h
    1.39 -41a216cayFe2FQroFuzvNPw1AvNiqQ tools/libxutil/util.c
    1.40 -41a216ca7mgVSnCBHPCLkGOIqPS1CQ tools/libxutil/util.h
    1.41  3f776bd2Xd-dUcPKlPN2vG89VGtfvQ tools/misc/Makefile
    1.42  4225f56d7sa9aEARfjNeCVTMYDAmZA tools/misc/cpuperf/Makefile
    1.43  4225f56dS5TGdKojmuBnrV3PzbE6Rg tools/misc/cpuperf/README.txt
    1.44 @@ -967,6 +933,40 @@ 41a21888FGQhPR5LJ1GRtOSIIN3QEw tools/vne
    1.45  41a21888QPgKrulCfR9SY_pxZKU0KA tools/vnet/examples/vnet97.sxp
    1.46  41a21888Gm0UBs1i7HqveT7Yz0u8DQ tools/vnet/examples/vnet98.sxp
    1.47  41a21888r4oGPuGv2Lxl-thgV3H54w tools/vnet/examples/vnet99.sxp
    1.48 +40e1b09dMYB4ItGCqcMIzirdMd9I-w tools/vnet/libxutil/Makefile
    1.49 +40e033325Sjqs-_4TuzeUEprP_gYFg tools/vnet/libxutil/allocate.c
    1.50 +40e03332KYz7o1bn2MG_KPbBlyoIMA tools/vnet/libxutil/allocate.h
    1.51 +41a216cav5JJbtDQnusfuMa_1x_Xpw tools/vnet/libxutil/debug.h
    1.52 +40e9808eyjiahG5uF6AMelNVujBzCg tools/vnet/libxutil/enum.c
    1.53 +40e9808eZpbdn9q2KSSMGCNvY_ZgpQ tools/vnet/libxutil/enum.h
    1.54 +4284c2ecWyadIhHF1u_QSgWqIXkaLA tools/vnet/libxutil/fd_stream.c
    1.55 +4284c2ecEOOcF6fZUf_NsZzYAoNo-w tools/vnet/libxutil/fd_stream.h
    1.56 +40e03332p5Dc_owJQRuN72ymJZddFQ tools/vnet/libxutil/file_stream.c
    1.57 +40e03332jWfB2viAhLSkq1WK0r_iDQ tools/vnet/libxutil/file_stream.h
    1.58 +40e03332rUjNMGg11n2rN6V4DCrvOg tools/vnet/libxutil/gzip_stream.c
    1.59 +40e033321O5Qg22haLoq5lpmk4tooQ tools/vnet/libxutil/gzip_stream.h
    1.60 +40e9808easXCzzAZQodEfKAhgUXSPA tools/vnet/libxutil/hash_table.c
    1.61 +40e9808e94BNXIVVKBFHC3rnkvwtJg tools/vnet/libxutil/hash_table.h
    1.62 +40e03332ihnBGzHykVwZnFmkAppb4g tools/vnet/libxutil/iostream.c
    1.63 +40e03332UGwbLR4wsw4ft14p0Yw5pg tools/vnet/libxutil/iostream.h
    1.64 +40e0333245DLDzJemeSVBLuutHtzEQ tools/vnet/libxutil/kernel_stream.c
    1.65 +40e03332aK0GkgpDdc-PVTkWKTeOBg tools/vnet/libxutil/kernel_stream.h
    1.66 +40e9808epW9iHcLXuO3QfUfLzB7onw tools/vnet/libxutil/lexis.c
    1.67 +40e9808egccMhCizayQRGtpBA3L5MQ tools/vnet/libxutil/lexis.h
    1.68 +41a216caM4z39Fzjb91rv9Ed_4By1A tools/vnet/libxutil/socket_stream.c
    1.69 +41a216caqinvF1I5FQMHA4HTRz8MSA tools/vnet/libxutil/socket_stream.h
    1.70 +40e03332KT_tnnoAMbPVAZBB7kSOAQ tools/vnet/libxutil/string_stream.c
    1.71 +40e03332-VtK6_OZa1vMHXFil8uq6w tools/vnet/libxutil/string_stream.h
    1.72 +40e9808e5_PLdodqVOSx0b4T_f5aeg tools/vnet/libxutil/sxpr.c
    1.73 +40e9808e0O4sHZtkDv5hlSqjYcdQAQ tools/vnet/libxutil/sxpr.h
    1.74 +40ec1cc6SIiGbynOi-1NtPesOlzF-Q tools/vnet/libxutil/sxpr_parser.c
    1.75 +40ec1cc6wpvvGxZiq4EFvNOcw0tUFg tools/vnet/libxutil/sxpr_parser.h
    1.76 +40e03332Rkvq6nn_UNjzAAK_Tk9v1g tools/vnet/libxutil/sys_net.c
    1.77 +40e03332lQHvQHw4Rh7VsT1_sui29A tools/vnet/libxutil/sys_net.h
    1.78 +40e033321smklZd7bDSdWvQCeIshtg tools/vnet/libxutil/sys_string.c
    1.79 +40e03332h5V611rRWURRLqb1Ekatxg tools/vnet/libxutil/sys_string.h
    1.80 +41a216cayFe2FQroFuzvNPw1AvNiqQ tools/vnet/libxutil/util.c
    1.81 +41a216ca7mgVSnCBHPCLkGOIqPS1CQ tools/vnet/libxutil/util.h
    1.82  41a21888c9TCRlUwJS9WBjB3e9aWgg tools/vnet/vnet-module/00README
    1.83  41a21888K2ItolEkksc1MUqyTDI_Kg tools/vnet/vnet-module/Makefile
    1.84  41a21888mJsFJD7bVMm-nrnWnalGBw tools/vnet/vnet-module/Makefile-2.4
     2.1 --- a/tools/Makefile	Tue May 24 21:10:23 2005 +0000
     2.2 +++ b/tools/Makefile	Tue May 24 21:17:29 2005 +0000
     2.3 @@ -2,7 +2,6 @@ XEN_ROOT = ../
     2.4  include $(XEN_ROOT)/tools/Rules.mk
     2.5  
     2.6  SUBDIRS :=
     2.7 -SUBDIRS += libxutil
     2.8  SUBDIRS += libxc
     2.9  SUBDIRS += misc
    2.10  SUBDIRS += examples
     3.1 --- a/tools/Rules.mk	Tue May 24 21:10:23 2005 +0000
     3.2 +++ b/tools/Rules.mk	Tue May 24 21:17:29 2005 +0000
     3.3 @@ -4,7 +4,6 @@ include $(XEN_ROOT)/Config.mk
     3.4  
     3.5  XEN_XC             = $(XEN_ROOT)/tools/python/xen/lowlevel/xc
     3.6  XEN_LIBXC          = $(XEN_ROOT)/tools/libxc
     3.7 -XEN_LIBXUTIL       = $(XEN_ROOT)/tools/libxutil
     3.8  
     3.9  ifeq ($(XEN_TARGET_ARCH),x86_32)
    3.10  CFLAGS  += -m32 -march=i686
     4.1 --- a/tools/blktap/Makefile	Tue May 24 21:10:23 2005 +0000
     4.2 +++ b/tools/blktap/Makefile	Tue May 24 21:17:29 2005 +0000
     4.3 @@ -47,7 +47,6 @@ CFLAGS   += -Wno-unused
     4.4  CFLAGS   += -g3
     4.5  CFLAGS   += -fno-strict-aliasing
     4.6  CFLAGS   += -I $(XEN_LIBXC)
     4.7 -CFLAGS   += -I $(XEN_LIBXUTIL)
     4.8  CFLAGS   += $(INCLUDES) -I.
     4.9  CFLAGS   += -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -D_LARGEFILE64_SOURCE
    4.10  # Get gcc to generate the dependencies for us.
    4.11 @@ -97,16 +96,16 @@ libblktap.so:
    4.12  libblktap.so.$(MAJOR):
    4.13  	ln -sf libblktap.so.$(MAJOR).$(MINOR) $@
    4.14  libblktap.so.$(MAJOR).$(MINOR): $(OBJS)
    4.15 -	$(CC) -Wl,-soname -Wl,$(SONAME) -shared -o $@ $^ -lpthread -L../libxutil -lxutil -lz
    4.16 +	$(CC) -Wl,-soname -Wl,$(SONAME) -shared -o $@ $^ -lpthread -lz
    4.17  
    4.18  blkdump: $(LIB)
    4.19 -	$(CC) $(CFLAGS) -o blkdump -L$(XEN_LIBXC) -L$(XEN_LIBXUTIL) -L. -l blktap blkdump.c
    4.20 +	$(CC) $(CFLAGS) -o blkdump -L$(XEN_LIBXC) -L. -l blktap blkdump.c
    4.21  
    4.22  parallax: $(LIB) $(PLX_SRCS)
    4.23 -	$(CC) $(CFLAGS) -o parallax -L$(XEN_LIBXC) -L$(XEN_LIBXUTIL) -L. -lblktap -lpthread $(PLX_SRCS) 
    4.24 +	$(CC) $(CFLAGS) -o parallax -L$(XEN_LIBXC) -L. -lblktap -lpthread $(PLX_SRCS) 
    4.25  
    4.26  parallax-threaded: $(LIB) $(PLXT_SRCS)
    4.27 -	$(CC) $(CFLAGS) -o parallax-threaded -L$(XEN_LIBXC) -L$(XEN_LIBXUTIL) -L. -lpthread -lblktap $(PLXT_SRCS)
    4.28 +	$(CC) $(CFLAGS) -o parallax-threaded -L$(XEN_LIBXC) -L. -lpthread -lblktap $(PLXT_SRCS)
    4.29  
    4.30  vdi_list: $(LIB) vdi_list.c $(VDI_SRCS)
    4.31  	$(CC) $(CFLAGS) -g3 -o vdi_list vdi_list.c -lpthread $(VDI_SRCS)
     5.1 --- a/tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/Makefile.in	Tue May 24 21:10:23 2005 +0000
     5.2 +++ b/tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/Makefile.in	Tue May 24 21:17:29 2005 +0000
     5.3 @@ -83,7 +83,7 @@ READLINE_DEP = $$(READLINE_DIR)
     5.4  # -I. for config files.
     5.5  # -I${srcdir} for our headers.
     5.6  # -I$(srcdir)/../regformats for regdef.h.
     5.7 -INCLUDE_CFLAGS = -I. -I${srcdir} -I$(srcdir)/../regformats -I$(INCLUDE_DIR)  -I../../../../libxc/ -I../../../../libxutil/
     5.8 +INCLUDE_CFLAGS = -I. -I${srcdir} -I$(srcdir)/../regformats -I$(INCLUDE_DIR)  -I../../../../libxc/
     5.9  
    5.10  # M{H,T}_CFLAGS, if defined, has host- and target-dependent CFLAGS
    5.11  # from the config/ directory.
     6.1 --- a/tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/configure	Tue May 24 21:10:23 2005 +0000
     6.2 +++ b/tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/configure	Tue May 24 21:17:29 2005 +0000
     6.3 @@ -3475,7 +3475,7 @@ USE_THREAD_DB=
     6.4  
     6.5  
     6.6  GDBSERVER_DEPFILES="$srv_regobj $srv_tgtobj $srv_thread_depfiles"
     6.7 -GDBSERVER_LIBS="$srv_libs -L../../../../libxc/ -L../../../../libxutil/ -lxc -lxutil"
     6.8 +GDBSERVER_LIBS="$srv_libs -L../../../../libxc/ -lxc"
     6.9  
    6.10  
    6.11  
     7.1 --- a/tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/configure.in	Tue May 24 21:10:23 2005 +0000
     7.2 +++ b/tools/gdb/gdb-6.2.1-xen-sparse/gdb/gdbserver/configure.in	Tue May 24 21:17:29 2005 +0000
     7.3 @@ -107,7 +107,7 @@ USE_THREAD_DB=
     7.4  
     7.5  
     7.6  GDBSERVER_DEPFILES="$srv_regobj $srv_tgtobj $srv_thread_depfiles"
     7.7 -GDBSERVER_LIBS="$srv_libs -L../../../../libxc/ -L../../../../libxutil/ -lxc -lxutil"
     7.8 +GDBSERVER_LIBS="$srv_libs -L../../../../libxc/ -lxc"
     7.9  
    7.10  AC_SUBST(GDBSERVER_DEPFILES)
    7.11  AC_SUBST(GDBSERVER_LIBS)
     8.1 --- a/tools/ioemu/target-i386-dm/Makefile	Tue May 24 21:10:23 2005 +0000
     8.2 +++ b/tools/ioemu/target-i386-dm/Makefile	Tue May 24 21:17:29 2005 +0000
     8.3 @@ -189,7 +189,7 @@ endif
     8.4  #########################################################
     8.5  
     8.6  DEFINES+=-D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE
     8.7 -LIBS+=-lm -L../../libxc -L../../libxutil -lxc -lxutil
     8.8 +LIBS+=-lm -L../../libxc -lxc
     8.9  ifndef CONFIG_USER_ONLY
    8.10  LIBS+=-lz
    8.11  endif
     9.1 --- a/tools/libxc/Makefile	Tue May 24 21:10:23 2005 +0000
     9.2 +++ b/tools/libxc/Makefile	Tue May 24 21:17:29 2005 +0000
     9.3 @@ -12,9 +12,6 @@ CC       = gcc
     9.4  XEN_ROOT = ../..
     9.5  include $(XEN_ROOT)/tools/Rules.mk
     9.6  
     9.7 -vpath %c       $(XEN_LIBXUTIL)
     9.8 -INCLUDES += -I $(XEN_LIBXUTIL)
     9.9 -
    9.10  SRCS     :=
    9.11  SRCS     += xc_sedf.c
    9.12  SRCS     += xc_bvtsched.c
    9.13 @@ -105,6 +102,6 @@ libxc.so.$(MAJOR): libxc.so.$(MAJOR).$(M
    9.14  	ln -sf $< $@
    9.15  
    9.16  libxc.so.$(MAJOR).$(MINOR): $(PIC_OBJS)
    9.17 -	$(CC) $(CFLAGS) $(LDFLAGS) -Wl,-soname -Wl,libxc.so.$(MAJOR) -shared -o $@ $^ -L../libxutil -lxutil -lz
    9.18 +	$(CC) $(CFLAGS) $(LDFLAGS) -Wl,-soname -Wl,libxc.so.$(MAJOR) -shared -o $@ $^ -lz
    9.19  
    9.20  -include $(DEPS)
    11.1 --- a/tools/libxutil/Makefile	Tue May 24 21:10:23 2005 +0000
    11.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    11.3 @@ -1,77 +0,0 @@
    11.4 -
    11.5 -XEN_ROOT = ../..
    11.6 -INSTALL		= install
    11.7 -INSTALL_DATA	= $(INSTALL) -m0644
    11.8 -INSTALL_PROG	= $(INSTALL) -m0755
    11.9 -INSTALL_DIR	= $(INSTALL) -d -m0755
   11.10 -
   11.11 -include $(XEN_ROOT)/tools/Rules.mk
   11.12 -
   11.13 -LIB_SRCS :=
   11.14 -LIB_SRCS += allocate.c
   11.15 -LIB_SRCS += enum.c
   11.16 -LIB_SRCS += file_stream.c
   11.17 -LIB_SRCS += gzip_stream.c
   11.18 -LIB_SRCS += hash_table.c
   11.19 -LIB_SRCS += iostream.c
   11.20 -LIB_SRCS += lexis.c
   11.21 -LIB_SRCS += string_stream.c
   11.22 -LIB_SRCS += sxpr.c
   11.23 -LIB_SRCS += sxpr_parser.c
   11.24 -LIB_SRCS += sys_net.c
   11.25 -LIB_SRCS += sys_string.c
   11.26 -LIB_SRCS += util.c
   11.27 -
   11.28 -LIB_OBJS := $(LIB_SRCS:.c=.o)
   11.29 -PIC_OBJS := $(LIB_SRCS:.c=.opic)
   11.30 -
   11.31 -CFLAGS   += -Wall -Werror -O3 -fno-strict-aliasing
   11.32 -
   11.33 -# Get gcc to generate the dependencies for us.
   11.34 -CFLAGS   += -Wp,-MD,.$(@F).d
   11.35 -DEPS     = .*.d
   11.36 -
   11.37 -MAJOR    := 3.0
   11.38 -MINOR    := 0
   11.39 -LIB      := libxutil.so 
   11.40 -LIB      += libxutil.so.$(MAJOR)
   11.41 -LIB      += libxutil.so.$(MAJOR).$(MINOR)
   11.42 -LIB      += libxutil.a
   11.43 -
   11.44 -all: build
   11.45 -build: check-for-zlib
   11.46 -	$(MAKE) $(LIB)
   11.47 -
   11.48 -libxutil.so: libxutil.so.$(MAJOR)
   11.49 -	ln -sf $^ $@
   11.50 -
   11.51 -libxutil.so.$(MAJOR): libxutil.so.$(MAJOR).$(MINOR)
   11.52 -	ln -sf $^ $@
   11.53 -
   11.54 -libxutil.so.$(MAJOR).$(MINOR): $(PIC_OBJS)
   11.55 -	$(CC) $(CFLAGS) -Wl,-soname -Wl,libxutil.so.$(MAJOR) -shared -o $@ $^
   11.56 -
   11.57 -libxutil.a: $(LIB_OBJS)
   11.58 -	$(AR) rc $@ $^
   11.59 -
   11.60 -check-for-zlib:
   11.61 -	@if [ ! -e /usr/include/zlib.h ]; then \
   11.62 -	echo "***********************************************************"; \
   11.63 -	echo "ERROR: install zlib header files (http://www.gzip.org/zlib)"; \
   11.64 -	echo "***********************************************************"; \
   11.65 -	false; \
   11.66 -	fi
   11.67 -
   11.68 -install: build
   11.69 -	[ -d $(DESTDIR)/usr/$(LIBDIR) ] || $(INSTALL_DIR) -p $(DESTDIR)/usr/$(LIBDIR)
   11.70 -	$(INSTALL_PROG) libxutil.so.$(MAJOR).$(MINOR) $(DESTDIR)/usr/$(LIBDIR)
   11.71 -	$(INSTALL_DATA) libxutil.a $(DESTDIR)/usr/$(LIBDIR)
   11.72 -	ln -sf libxutil.so.$(MAJOR).$(MINOR) $(DESTDIR)/usr/$(LIBDIR)/libxutil.so.$(MAJOR)
   11.73 -	ln -sf libxutil.so.$(MAJOR) $(DESTDIR)/usr/$(LIBDIR)/libxutil.so
   11.74 -
   11.75 -clean:
   11.76 -	$(RM) *.a *.so* *.o *.opic *.rpm 
   11.77 -	$(RM) *~
   11.78 -	$(RM) $(DEPS)
   11.79 -
   11.80 --include $(DEPS)
    12.1 --- a/tools/libxutil/allocate.c	Tue May 24 21:10:23 2005 +0000
    12.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    12.3 @@ -1,116 +0,0 @@
    12.4 -/*
    12.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    12.6 - *
    12.7 - * This library is free software; you can redistribute it and/or modify
    12.8 - * it under the terms of the GNU Lesser General Public License as published by
    12.9 - * the Free Software Foundation; either version 2.1 of the License, or
   12.10 - * (at your option) any later version.
   12.11 - *
   12.12 - * This library is distributed in the hope that it will be useful,
   12.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   12.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   12.15 - * GNU Lesser General Public License for more details.
   12.16 - *
   12.17 - * You should have received a copy of the GNU Lesser General Public License
   12.18 - * along with this library; if not, write to the Free Software
   12.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   12.20 - */
   12.21 -
   12.22 -#include "allocate.h"
   12.23 -
   12.24 -/** @file
   12.25 - * Support for allocating memory.
   12.26 - * Usable from user code or kernel code (with __KERNEL__ defined).
   12.27 - * In user code will use GC if USE_GC is defined.
   12.28 - */
   12.29 -
   12.30 -#ifdef __KERNEL__
   12.31 -/*----------------------------------------------------------------------------*/
   12.32 -#  include <linux/config.h>
   12.33 -#  include <linux/slab.h>
   12.34 -#  include <linux/string.h>
   12.35 -#  include <linux/types.h>
   12.36 -
   12.37 -#  define DEFAULT_TYPE    0
   12.38 -#  define MALLOC(n, type) kmalloc(n, type)
   12.39 -#  define FREE(ptr)       kfree(ptr)
   12.40 -
   12.41 -/*----------------------------------------------------------------------------*/
   12.42 -#else /* ! __KERNEL__ */
   12.43 -
   12.44 -#  include <stdlib.h>
   12.45 -#  include <string.h>
   12.46 -
   12.47 -#  define DEFAULT_TYPE    0
   12.48 -
   12.49 -#ifdef USE_GC
   12.50 -#  include "gc.h"
   12.51 -#  define MALLOC(n, typ)  GC_malloc(n)
   12.52 -#  define FREE(ptr)       (ptr=NULL)
   12.53 -//typedef void *GC_PTR;
   12.54 -//GC_PTR (*GC_oom_fn)(size_t n);
   12.55 -#else
   12.56 -#  define MALLOC(n, type) malloc(n)
   12.57 -#  define FREE(ptr)       free(ptr)
   12.58 -#endif
   12.59 -
   12.60 -/*----------------------------------------------------------------------------*/
   12.61 -#endif
   12.62 -
   12.63 -/** Function to call when memory cannot be allocated. */
   12.64 -AllocateFailedFn *allocate_failed_fn = NULL;
   12.65 -
   12.66 -/** Allocate memory and zero it.
   12.67 - * The type is only relevant when calling from kernel code,
   12.68 - * from user code it is ignored.
   12.69 - * In kernel code the values accepted by kmalloc can be used:
   12.70 - * GFP_USER, GFP_ATOMIC, GFP_KERNEL.
   12.71 - *
   12.72 - * @param size number of bytes to allocate
   12.73 - * @param type memory type to allocate (kernel only)
   12.74 - * @return pointer to the allocated memory or zero
   12.75 - * if malloc failed
   12.76 - */
   12.77 -void *allocate_type(int size, int type){
   12.78 -    void *p = MALLOC(size, type);
   12.79 -    if(p){
   12.80 -        memzero(p, size);
   12.81 -    } else if(allocate_failed_fn){
   12.82 -        allocate_failed_fn(size, type);
   12.83 -    }
   12.84 -    return p;
   12.85 -}
   12.86 -
   12.87 -/** Allocate memory and zero it.
   12.88 - *
   12.89 - * @param size number of bytes to allocate
   12.90 - * @return pointer to the allocated memory or zero
   12.91 - * if malloc failed
   12.92 - */
   12.93 -void *allocate(int size){
   12.94 -    return allocate_type(size, DEFAULT_TYPE);
   12.95 -}
   12.96 -
   12.97 -/** Free memory allocated by allocate().
   12.98 - * No-op if 'p' is null.
   12.99 - *
  12.100 - * @param p memory to free
  12.101 - */
  12.102 -void deallocate(void *p){
  12.103 -    if(p){
  12.104 -        FREE(p);
  12.105 -    }
  12.106 -}
  12.107 -
  12.108 -/** Set bytes to zero.
  12.109 - * No-op if 'p' is null.
  12.110 - *
  12.111 - * @param p memory to zero
  12.112 - * @param size number of bytes to zero
  12.113 - */
  12.114 -void memzero(void *p, int size){
  12.115 -    if(p){
  12.116 -        memset(p, 0, (size_t)size);
  12.117 -    }
  12.118 -}
  12.119 -
    13.1 --- a/tools/libxutil/allocate.h	Tue May 24 21:10:23 2005 +0000
    13.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    13.3 @@ -1,45 +0,0 @@
    13.4 -/*
    13.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    13.6 - *
    13.7 - * This library is free software; you can redistribute it and/or modify
    13.8 - * it under the terms of the GNU Lesser General Public License as published by
    13.9 - * the Free Software Foundation; either version 2.1 of the License, or
   13.10 - * (at your option) any later version.
   13.11 - *
   13.12 - * This library is distributed in the hope that it will be useful,
   13.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   13.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   13.15 - * GNU Lesser General Public License for more details.
   13.16 - *
   13.17 - * You should have received a copy of the GNU Lesser General Public License
   13.18 - * along with this library; if not, write to the Free Software
   13.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   13.20 - */
   13.21 -
   13.22 -#ifndef _XUTIL_ALLOCATE_H_
   13.23 -#define _XUTIL_ALLOCATE_H_
   13.24 -
   13.25 -/** Allocate memory for a given type, and cast. */
   13.26 -#define ALLOCATE(ctype) (ctype *)allocate(sizeof(ctype))
   13.27 -
   13.28 -/** Allocate memory for a given type, and cast. */
   13.29 -#define ALLOCATE_TYPE(ctype, type) (ctype *)allocate(sizeof(ctype))
   13.30 -
   13.31 -extern void *allocate_type(int size, int type);
   13.32 -extern void *allocate(int size);
   13.33 -extern void deallocate(void *);
   13.34 -extern void memzero(void *p, int size);
   13.35 -
   13.36 -typedef void AllocateFailedFn(int size, int type);
   13.37 -extern AllocateFailedFn *allocate_failed_fn;
   13.38 -
   13.39 -#endif /* _XUTIL_ALLOCATE_H_ */
   13.40 -
   13.41 -
   13.42 -
   13.43 -
   13.44 -
   13.45 -
   13.46 -
   13.47 -
   13.48 -
    14.1 --- a/tools/libxutil/debug.h	Tue May 24 21:10:23 2005 +0000
    14.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    14.3 @@ -1,72 +0,0 @@
    14.4 -/*
    14.5 - * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    14.6 - *
    14.7 - * This library is free software; you can redistribute it and/or modify
    14.8 - * it under the terms of the GNU Lesser General Public License as published by
    14.9 - * the Free Software Foundation; either version 2.1 of the License, or
   14.10 - * (at your option) any later version.
   14.11 - *
   14.12 - * This library is distributed in the hope that it will be useful,
   14.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   14.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   14.15 - * GNU Lesser General Public License for more details.
   14.16 - *
   14.17 - * You should have received a copy of the GNU Lesser General Public License
   14.18 - * along with this library; if not, write to the Free Software
   14.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   14.20 - */
   14.21 -#ifndef _XUTIL_DEBUG_H_
   14.22 -#define _XUTIL_DEBUG_H_
   14.23 -
   14.24 -#ifndef MODULE_NAME
   14.25 -#define MODULE_NAME ""
   14.26 -#endif
   14.27 -
   14.28 -#ifdef __KERNEL__
   14.29 -#include <linux/config.h>
   14.30 -#include <linux/kernel.h>
   14.31 -
   14.32 -#ifdef DEBUG
   14.33 -
   14.34 -#define dprintf(fmt, args...) printk(KERN_DEBUG   "[DBG] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   14.35 -#define wprintf(fmt, args...) printk(KERN_WARNING "[WRN] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   14.36 -#define iprintf(fmt, args...) printk(KERN_INFO    "[INF] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   14.37 -#define eprintf(fmt, args...) printk(KERN_ERR     "[ERR] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   14.38 -
   14.39 -#else
   14.40 -
   14.41 -#define dprintf(fmt, args...) do {} while(0)
   14.42 -#define wprintf(fmt, args...) printk(KERN_WARNING "[WRN] " MODULE_NAME fmt, ##args)
   14.43 -#define iprintf(fmt, args...) printk(KERN_INFO    "[INF] " MODULE_NAME fmt, ##args)
   14.44 -#define eprintf(fmt, args...) printk(KERN_ERR     "[ERR] " MODULE_NAME fmt, ##args)
   14.45 -
   14.46 -#endif
   14.47 -
   14.48 -#else
   14.49 -
   14.50 -#include <stdio.h>
   14.51 -
   14.52 -#ifdef DEBUG
   14.53 -
   14.54 -#define dprintf(fmt, args...) fprintf(stdout, "%d [DBG] " MODULE_NAME ">%s" fmt, getpid(), __FUNCTION__, ##args)
   14.55 -#define wprintf(fmt, args...) fprintf(stderr, "%d [WRN] " MODULE_NAME ">%s" fmt, getpid(),__FUNCTION__, ##args)
   14.56 -#define iprintf(fmt, args...) fprintf(stderr, "%d [INF] " MODULE_NAME ">%s" fmt, getpid(),__FUNCTION__, ##args)
   14.57 -#define eprintf(fmt, args...) fprintf(stderr, "%d [ERR] " MODULE_NAME ">%s" fmt, getpid(),__FUNCTION__, ##args)
   14.58 -
   14.59 -#else
   14.60 -
   14.61 -#define dprintf(fmt, args...) do {} while(0)
   14.62 -#define wprintf(fmt, args...) fprintf(stderr, "%d [WRN] " MODULE_NAME fmt, getpid(), ##args)
   14.63 -#define iprintf(fmt, args...) fprintf(stderr, "%d [INF] " MODULE_NAME fmt, getpid(), ##args)
   14.64 -#define eprintf(fmt, args...) fprintf(stderr, "%d [ERR] " MODULE_NAME fmt, getpid(), ##args)
   14.65 -
   14.66 -#endif
   14.67 -
   14.68 -#endif
   14.69 -
   14.70 -/** Print format for an IP address.
   14.71 - * See NIPQUAD(), HIPQUAD()
   14.72 - */
   14.73 -#define IPFMT "%u.%u.%u.%u"
   14.74 -
   14.75 -#endif /* ! _XUTIL_DEBUG_H_ */
    15.1 --- a/tools/libxutil/enum.c	Tue May 24 21:10:23 2005 +0000
    15.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    15.3 @@ -1,61 +0,0 @@
    15.4 -/*
    15.5 - * Copyright (C) 2002, 2004 Mike Wray <mike.wray@hp.com>
    15.6 - *
    15.7 - * This library is free software; you can redistribute it and/or modify
    15.8 - * it under the terms of the GNU Lesser General Public License as
    15.9 - * published by the Free Software Foundation; either version 2.1 of the
   15.10 - * License, or  (at your option) any later version. This library is 
   15.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   15.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   15.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   15.14 - * See the GNU Lesser General Public License for more details.
   15.15 - *
   15.16 - * You should have received a copy of the GNU Lesser General Public License
   15.17 - * along with this library; if not, write to the Free Software Foundation,
   15.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   15.19 - */
   15.20 -
   15.21 -#ifdef __KERNEL__
   15.22 -#include <linux/errno.h>
   15.23 -#else
   15.24 -#include <errno.h>
   15.25 -#endif
   15.26 -
   15.27 -#include "sys_string.h"
   15.28 -#include "enum.h"
   15.29 -
   15.30 -/** Map an enum name to its value using a table.
   15.31 - *
   15.32 - * @param name enum name
   15.33 - * @param defs enum definitions
   15.34 - * @return enum value or -1 if not known
   15.35 - */
   15.36 -int enum_name_to_val(char *name, EnumDef *defs){
   15.37 -    int val = -1;
   15.38 -    for(; defs->name; defs++){
   15.39 -	if(!strcmp(defs->name, name)){
   15.40 -	    val = defs->val;
   15.41 -	    break;
   15.42 -	}
   15.43 -    }
   15.44 -    return val;
   15.45 -}
   15.46 -
   15.47 -/** Map an enum value to its name using a table.
   15.48 - *
   15.49 - * @param val enum value
   15.50 - * @param defs enum definitions
   15.51 - * @param defs_n number of definitions
   15.52 - * @return enum name or NULL if not known
   15.53 - */
   15.54 -char *enum_val_to_name(int val, EnumDef *defs){
   15.55 -    char *name = NULL;
   15.56 -    for(; defs->name; defs++){
   15.57 -	if(val == defs->val){
   15.58 -	    name = defs->name;
   15.59 -	    break;
   15.60 -	}
   15.61 -    }
   15.62 -    return name;
   15.63 -}
   15.64 -
    16.1 --- a/tools/libxutil/enum.h	Tue May 24 21:10:23 2005 +0000
    16.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    16.3 @@ -1,30 +0,0 @@
    16.4 -/*
    16.5 - * Copyright (C) 2002, 2004 Mike Wray <mike.wray@hp.com>
    16.6 - *
    16.7 - * This library is free software; you can redistribute it and/or modify
    16.8 - * it under the terms of the GNU Lesser General Public License as
    16.9 - * published by the Free Software Foundation; either version 2.1 of the
   16.10 - * License, or  (at your option) any later version. This library is 
   16.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   16.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   16.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   16.14 - * See the GNU Lesser General Public License for more details.
   16.15 - *
   16.16 - * You should have received a copy of the GNU Lesser General Public License
   16.17 - * along with this library; if not, write to the Free Software Foundation,
   16.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   16.19 - */
   16.20 -
   16.21 -#ifndef _XUTIL_ENUM_H_
   16.22 -#define _XUTIL_ENUM_H_
   16.23 -
   16.24 -/** Mapping of an enum value to a name. */
   16.25 -typedef struct EnumDef {
   16.26 -    int val;
   16.27 -    char *name;
   16.28 -} EnumDef;
   16.29 -
   16.30 -extern int enum_name_to_val(char *name, EnumDef *defs);
   16.31 -extern char *enum_val_to_name(int val, EnumDef *defs);
   16.32 -
   16.33 -#endif /* _XUTIL_ENUM_H_ */
    17.1 --- a/tools/libxutil/fd_stream.c	Tue May 24 21:10:23 2005 +0000
    17.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    17.3 @@ -1,184 +0,0 @@
    17.4 -/*
    17.5 - * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    17.6 - *
    17.7 - * This library is free software; you can redistribute it and/or modify
    17.8 - * it under the terms of the GNU Lesser General Public License as published by
    17.9 - * the Free Software Foundation; either version 2.1 of the License, or
   17.10 - * (at your option) any later version.
   17.11 - *
   17.12 - * This library is distributed in the hope that it will be useful,
   17.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   17.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   17.15 - * GNU Lesser General Public License for more details.
   17.16 - *
   17.17 - * You should have received a copy of the GNU Lesser General Public License
   17.18 - * along with this library; if not, write to the Free Software
   17.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   17.20 - */
   17.21 -
   17.22 -/** @file
   17.23 - * An IOStream implementation using fds.
   17.24 - */
   17.25 -#ifndef __KERNEL__
   17.26 -
   17.27 -#include <stdio.h>
   17.28 -#include <stdlib.h>
   17.29 -#include <string.h>
   17.30 -#include <unistd.h>
   17.31 -#include <errno.h>
   17.32 -#include "allocate.h"
   17.33 -#include "fd_stream.h"
   17.34 -
   17.35 -#define MODULE_NAME "fd_stream"
   17.36 -#define DEBUG 1
   17.37 -//#undef DEBUG
   17.38 -#include "debug.h"
   17.39 -
   17.40 -static int fd_read(IOStream *s, void *buf, size_t n);
   17.41 -static int fd_write(IOStream *s, const void *buf, size_t n);
   17.42 -static int fd_error(IOStream *s);
   17.43 -static int fd_close(IOStream *s);
   17.44 -static void fd_free(IOStream *s);
   17.45 -static int fd_flush(IOStream *s);
   17.46 -
   17.47 -/** Methods used by a fd IOStream. */
   17.48 -static const IOMethods fd_methods = {
   17.49 -    read:  fd_read,
   17.50 -    write: fd_write,
   17.51 -    error: fd_error,
   17.52 -    close: fd_close,
   17.53 -    free:  fd_free,
   17.54 -    flush: fd_flush,
   17.55 -};
   17.56 -
   17.57 -/** Get the fd data.
   17.58 - * 
   17.59 - * @param io fd stream
   17.60 - * @return data
   17.61 - */
   17.62 -static inline FDData * fd_data(IOStream *io){
   17.63 -    return (FDData *)io->data;
   17.64 -}
   17.65 -
   17.66 -/** Test if a stream is a fd stream.
   17.67 - *
   17.68 - * @param io stream
   17.69 - * @return 0 if a fd stream, -EINVAL if not
   17.70 - */
   17.71 -int fd_stream_check(IOStream *io){
   17.72 -    return (io && io->methods == &fd_methods ? 0 : -EINVAL);
   17.73 -}
   17.74 -
   17.75 -/** Get the data for a fd stream.
   17.76 - *
   17.77 - * @param io stream
   17.78 - * @param data return value for the data
   17.79 - * @return 0 if a fd stream, -EINVAL if not
   17.80 - */
   17.81 -int fd_stream_data(IOStream *io, FDData **data){
   17.82 -    int err = fd_stream_check(io);
   17.83 -    if(err){
   17.84 -        *data = NULL;
   17.85 -    } else {
   17.86 -        *data = fd_data(io);
   17.87 -    }
   17.88 -    return err;
   17.89 -}
   17.90 -
   17.91 -
   17.92 -/** Write to the underlying fd.
   17.93 - *
   17.94 - * @param stream input
   17.95 - * @param buf where to put input
   17.96 - * @param n number of bytes to write
   17.97 - * @return number of bytes written
   17.98 - */
   17.99 -static int fd_write(IOStream *s, const void *buf, size_t n){
  17.100 -    FDData *data = fd_data(s);
  17.101 -    int k;
  17.102 -    k = write(data->fd, buf, n);
  17.103 -    return k;
  17.104 -}
  17.105 -
  17.106 -/** Read from the underlying stream;
  17.107 - *
  17.108 - * @param stream input
  17.109 - * @param buf where to put input
  17.110 - * @param n number of bytes to read
  17.111 - * @return number of bytes read
  17.112 - */
  17.113 -static int fd_read(IOStream *s, void *buf, size_t n){
  17.114 -    FDData *data = fd_data(s);
  17.115 -    int k;
  17.116 -    k = read(data->fd, buf, n);
  17.117 -    //printf("> fd_read> buf=%p n=%d --> k=%d\n", buf, n, k);
  17.118 -    return k;
  17.119 -}
  17.120 -
  17.121 -/** Flush the fd (no-op).
  17.122 - *
  17.123 - * @param s fd stream
  17.124 - * @return 0 on success, error code otherwise
  17.125 - */
  17.126 -static int fd_flush(IOStream *s){
  17.127 -    return 0;
  17.128 -}
  17.129 -
  17.130 -/** Check if a fd stream has an error (no-op).
  17.131 - *
  17.132 - * @param s fd stream
  17.133 - * @return 1 if has an error, 0 otherwise
  17.134 - */
  17.135 -static int fd_error(IOStream *s){
  17.136 -    return 0;
  17.137 -}
  17.138 -
  17.139 -/** Close a fd stream.
  17.140 - *
  17.141 - * @param s fd stream to close
  17.142 - * @return result of the close
  17.143 - */
  17.144 -static int fd_close(IOStream *s){
  17.145 -    FDData *data = fd_data(s);
  17.146 -    return close(data->fd);
  17.147 -}
  17.148 -
  17.149 -/** Free a fd stream.
  17.150 - *
  17.151 - * @param s fd stream
  17.152 - */
  17.153 -static void fd_free(IOStream *s){
  17.154 -    FDData *data = fd_data(s);
  17.155 -    deallocate(data);
  17.156 -}
  17.157 -
  17.158 -/** Create an IOStream for a fd.
  17.159 - *
  17.160 - * @param fd fd to wtap
  17.161 - * @return new IOStream using fd for i/o
  17.162 - */
  17.163 -IOStream *fd_stream_new(int fd){
  17.164 -    int err = -ENOMEM;
  17.165 -    IOStream *io = NULL;
  17.166 -    FDData *data = NULL;
  17.167 -
  17.168 -    io = ALLOCATE(IOStream);
  17.169 -    if(!io) goto exit;
  17.170 -    io->methods = &fd_methods;
  17.171 -    data = ALLOCATE(FDData);
  17.172 -    if(!data) goto exit;
  17.173 -    io->data = data;
  17.174 -    data->fd = fd;
  17.175 -    err = 0;
  17.176 -  exit:
  17.177 -    if(err){
  17.178 -        if(io){
  17.179 -            if(data) deallocate(data);
  17.180 -            deallocate(io);
  17.181 -            io = NULL;
  17.182 -        }
  17.183 -    }
  17.184 -    return io;
  17.185 -}
  17.186 -
  17.187 -#endif
    18.1 --- a/tools/libxutil/fd_stream.h	Tue May 24 21:10:23 2005 +0000
    18.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    18.3 @@ -1,36 +0,0 @@
    18.4 -/*
    18.5 - * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    18.6 - *
    18.7 - * This library is free software; you can redistribute it and/or modify
    18.8 - * it under the terms of the GNU Lesser General Public License as published by
    18.9 - * the Free Software Foundation; either version 2.1 of the License, or
   18.10 - * (at your option) any later version.
   18.11 - *
   18.12 - * This library is distributed in the hope that it will be useful,
   18.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   18.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   18.15 - * GNU Lesser General Public License for more details.
   18.16 - *
   18.17 - * You should have received a copy of the GNU Lesser General Public License
   18.18 - * along with this library; if not, write to the Free Software
   18.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   18.20 - */
   18.21 -
   18.22 -#ifndef _XMC_FD_STREAM_H_
   18.23 -#define _XMC_FD_STREAM_H_
   18.24 -
   18.25 -#ifndef __KERNEL__
   18.26 -#include "iostream.h"
   18.27 -
   18.28 -/** Data associated with a fd stream. */
   18.29 -typedef struct FDData {
   18.30 -    /** The socket file descriptor. */
   18.31 -    int fd;
   18.32 -} FDData;
   18.33 -
   18.34 -extern IOStream *fd_stream_new(int fd);
   18.35 -extern int fd_stream_data(IOStream *io, FDData **data);
   18.36 -extern int fd_stream_check(IOStream *io);
   18.37 -
   18.38 -#endif
   18.39 -#endif /* !_XMC_FD_STREAM_H_ */
    19.1 --- a/tools/libxutil/file_stream.c	Tue May 24 21:10:23 2005 +0000
    19.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    19.3 @@ -1,220 +0,0 @@
    19.4 -/*
    19.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    19.6 - *
    19.7 - * This library is free software; you can redistribute it and/or modify
    19.8 - * it under the terms of the GNU Lesser General Public License as published by
    19.9 - * the Free Software Foundation; either version 2.1 of the License, or
   19.10 - * (at your option) any later version.
   19.11 - *
   19.12 - * This library is distributed in the hope that it will be useful,
   19.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   19.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   19.15 - * GNU Lesser General Public License for more details.
   19.16 - *
   19.17 - * You should have received a copy of the GNU Lesser General Public License
   19.18 - * along with this library; if not, write to the Free Software
   19.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   19.20 - */
   19.21 -
   19.22 -/** @file
   19.23 - * An IOStream implementation using FILE*.
   19.24 - */
   19.25 -#ifndef __KERNEL__
   19.26 -#include <stdio.h>
   19.27 -#include <stdlib.h>
   19.28 -#include "allocate.h"
   19.29 -#include "file_stream.h"
   19.30 -
   19.31 -static int file_read(IOStream *s, void *buf, size_t n);
   19.32 -static int file_write(IOStream *s, const void *buf, size_t n);
   19.33 -static int file_error(IOStream *s);
   19.34 -static int file_close(IOStream *s);
   19.35 -static void file_free(IOStream *s);
   19.36 -static int file_flush(IOStream *s);
   19.37 -
   19.38 -/** Methods used by a FILE* IOStream. */
   19.39 -static const IOMethods file_methods = {
   19.40 -    read:  file_read,
   19.41 -    write: file_write,
   19.42 -    error: file_error,
   19.43 -    close: file_close,
   19.44 -    free:  file_free,
   19.45 -    flush: file_flush,
   19.46 -};
   19.47 -
   19.48 -/** IOStream for stdin. */
   19.49 -static IOStream _iostdin = {
   19.50 -    methods: &file_methods,
   19.51 -    data: (void*)1,
   19.52 -    nofree: 1,
   19.53 -};
   19.54 -
   19.55 -/** IOStream for stdout. */
   19.56 -static IOStream _iostdout = {
   19.57 -    methods: &file_methods,
   19.58 -    data: (void*)2,
   19.59 -    nofree: 1,
   19.60 -};
   19.61 -
   19.62 -/** IOStream for stderr. */
   19.63 -static IOStream _iostderr = {
   19.64 -    methods: &file_methods,
   19.65 -    data: (void*)3,
   19.66 -    nofree: 1,
   19.67 -};
   19.68 -
   19.69 -/** IOStream for stdin. */
   19.70 -IOStream *iostdin = &_iostdin;
   19.71 -
   19.72 -/** IOStream for stdout. */
   19.73 -IOStream *iostdout = &_iostdout;
   19.74 -
   19.75 -/** IOStream for stderr. */
   19.76 -IOStream *iostderr = &_iostderr;
   19.77 -
   19.78 -/* Get the underlying FILE*.
   19.79 - *
   19.80 - * @param s file stream
   19.81 - * @return the stream s wraps
   19.82 - */
   19.83 -static inline FILE *get_file(IOStream *s){
   19.84 -     FILE *data = NULL;
   19.85 -     switch((long)s->data){
   19.86 -     case 1:
   19.87 -         data = stdin;
   19.88 -         break;
   19.89 -     case 2:
   19.90 -         data = stdout;
   19.91 -         break;
   19.92 -     case 3:
   19.93 -         data = stderr;
   19.94 -         break;
   19.95 -     default:
   19.96 -         data = (FILE*)s->data;
   19.97 -         break;
   19.98 -     }
   19.99 -     return data;
  19.100 -}
  19.101 -
  19.102 -/** Control buffering on the underlying stream, like setvbuf().
  19.103 - *
  19.104 - * @param io file stream
  19.105 - * @param buf buffer
  19.106 - * @param mode buffering mode (see man setvbuf())
  19.107 - * @param size buffer size
  19.108 - * @return 0 on success, non-zero otherwise
  19.109 - */
  19.110 -int file_stream_setvbuf(IOStream *io, char *buf, int mode, size_t size){
  19.111 -    return setvbuf(get_file(io), buf, mode, size);
  19.112 -}
  19.113 -
  19.114 -/** Write to the underlying stream using fwrite();
  19.115 - *
  19.116 - * @param stream input
  19.117 - * @param buf where to put input
  19.118 - * @param n number of bytes to write
  19.119 - * @return number of bytes written
  19.120 - */
  19.121 -static int file_write(IOStream *s, const void *buf, size_t n){
  19.122 -    return fwrite(buf, 1, n, get_file(s));
  19.123 -}
  19.124 -
  19.125 -/** Read from the underlying stream using fread();
  19.126 - *
  19.127 - * @param stream input
  19.128 - * @param buf where to put input
  19.129 - * @param n number of bytes to read
  19.130 - * @return number of bytes read
  19.131 - */
  19.132 -static int file_read(IOStream *s, void *buf, size_t n){
  19.133 -    return fread(buf, 1, n, get_file(s));
  19.134 -}
  19.135 -
  19.136 -/** Fush the underlying stream using fflush().
  19.137 - *
  19.138 - * @param s file stream
  19.139 - * @return 0 on success, error code otherwise
  19.140 - */
  19.141 -static int file_flush(IOStream *s){
  19.142 -    return fflush(get_file(s));
  19.143 -}
  19.144 -
  19.145 -/** Check if a stream has an error.
  19.146 - *
  19.147 - * @param s file stream
  19.148 - * @return 1 if has an error, 0 otherwise
  19.149 - */
  19.150 -static int file_error(IOStream *s){
  19.151 -    return ferror(get_file(s));
  19.152 -}
  19.153 -
  19.154 -/** Close a file stream.
  19.155 - *
  19.156 - * @param s file stream to close
  19.157 - * @return result of the close
  19.158 - */
  19.159 -static int file_close(IOStream *s){
  19.160 -    int result = 0;
  19.161 -    result = fclose(get_file(s));
  19.162 -    return result;
  19.163 -}
  19.164 -
  19.165 -/** Free a file stream.
  19.166 - *
  19.167 - * @param s file stream
  19.168 - */
  19.169 -static void file_free(IOStream *s){
  19.170 -    // Nothing extra to do - close did it all.
  19.171 -}
  19.172 -
  19.173 -/** Create an IOStream for a stream.
  19.174 - *
  19.175 - * @param f stream to wrap
  19.176 - * @return new IOStream using f for i/o
  19.177 - */
  19.178 -IOStream *file_stream_new(FILE *f){
  19.179 -    IOStream *io = ALLOCATE(IOStream);
  19.180 -    if(io){
  19.181 -        io->methods = &file_methods;
  19.182 -        io->data = (void*)f;
  19.183 -    }
  19.184 -    return io;
  19.185 -}
  19.186 -
  19.187 -/** IOStream version of fopen().
  19.188 - *
  19.189 - * @param file name of the file to open
  19.190 - * @param flags giving the mode to open in (as for fopen())
  19.191 - * @return new stream for the open file, or 0 if failed
  19.192 - */
  19.193 -IOStream *file_stream_fopen(const char *file, const char *flags){
  19.194 -    IOStream *io = 0;
  19.195 -    FILE *fin = fopen(file, flags);
  19.196 -    if(fin){
  19.197 -        io = file_stream_new(fin);
  19.198 -        if(!io){
  19.199 -            fclose(fin);
  19.200 -        }
  19.201 -    }
  19.202 -    return io;
  19.203 -}
  19.204 -
  19.205 -/** IOStream version of fdopen().
  19.206 - *
  19.207 - * @param fd file descriptor
  19.208 - * @param flags giving the mode to open in (as for fdopen())
  19.209 - * @return new stream for the open file, or 0 if failed.  Always takes
  19.210 - *         ownership of fd.
  19.211 - */
  19.212 -IOStream *file_stream_fdopen(int fd, const char *flags){
  19.213 -    IOStream *io = 0;
  19.214 -    FILE *fin = fdopen(fd, flags);
  19.215 -    if(fin){
  19.216 -        io = file_stream_new(fin);
  19.217 -        if(!io){
  19.218 -            fclose(fin);
  19.219 -        }
  19.220 -    }
  19.221 -    return io;
  19.222 -}
  19.223 -#endif
    20.1 --- a/tools/libxutil/file_stream.h	Tue May 24 21:10:23 2005 +0000
    20.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    20.3 @@ -1,35 +0,0 @@
    20.4 -/*
    20.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    20.6 - *
    20.7 - * This library is free software; you can redistribute it and/or modify
    20.8 - * it under the terms of the GNU Lesser General Public License as published by
    20.9 - * the Free Software Foundation; either version 2.1 of the License, or
   20.10 - * (at your option) any later version.
   20.11 - *
   20.12 - * This library is distributed in the hope that it will be useful,
   20.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   20.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   20.15 - * GNU Lesser General Public License for more details.
   20.16 - *
   20.17 - * You should have received a copy of the GNU Lesser General Public License
   20.18 - * along with this library; if not, write to the Free Software
   20.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   20.20 - */
   20.21 -
   20.22 -#ifndef _XUTIL_FILE_STREAM_H_
   20.23 -#define _XUTIL_FILE_STREAM_H_
   20.24 -
   20.25 -#ifndef __KERNEL__
   20.26 -#include "iostream.h"
   20.27 -#include <stdio.h>
   20.28 -
   20.29 -extern IOStream *file_stream_new(FILE *f);
   20.30 -extern IOStream *file_stream_fopen(const char *file, const char *flags);
   20.31 -extern IOStream *file_stream_fdopen(int fd, const char *flags);
   20.32 -extern IOStream get_stream_stdout(void);
   20.33 -extern IOStream get_stream_stderr(void);
   20.34 -extern IOStream get_stream_stdin(void);
   20.35 -
   20.36 -extern int file_stream_setvbuf(IOStream *io, char *buf, int mode, size_t size);
   20.37 -#endif
   20.38 -#endif /* !_XUTIL_FILE_STREAM_H_ */
    21.1 --- a/tools/libxutil/gzip_stream.c	Tue May 24 21:10:23 2005 +0000
    21.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    21.3 @@ -1,174 +0,0 @@
    21.4 -/*
    21.5 - * Copyright (C) 2003 Hewlett-Packard Company.
    21.6 - *
    21.7 - * This library is free software; you can redistribute it and/or modify
    21.8 - * it under the terms of the GNU Lesser General Public License as published by
    21.9 - * the Free Software Foundation; either version 2.1 of the License, or
   21.10 - * (at your option) any later version.
   21.11 - *
   21.12 - * This library is distributed in the hope that it will be useful,
   21.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   21.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   21.15 - * GNU Lesser General Public License for more details.
   21.16 - *
   21.17 - * You should have received a copy of the GNU Lesser General Public License
   21.18 - * along with this library; if not, write to the Free Software
   21.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   21.20 - */
   21.21 -
   21.22 -/** @file
   21.23 - * An IOStream implementation using zlib gzFile to provide
   21.24 - * compression and decompression.
   21.25 - */
   21.26 -#ifndef __KERNEL__
   21.27 -
   21.28 -#include <stdio.h>
   21.29 -#include <stdlib.h>
   21.30 -
   21.31 -#include "zlib.h"
   21.32 -
   21.33 -#include "allocate.h"
   21.34 -#include "gzip_stream.h"
   21.35 -
   21.36 -static int gzip_read(IOStream *s, void *buf, size_t n);
   21.37 -static int gzip_write(IOStream *s, const void *buf, size_t n);
   21.38 -static int gzip_error(IOStream *s);
   21.39 -static int gzip_close(IOStream *s);
   21.40 -static void gzip_free(IOStream *s);
   21.41 -static int gzip_flush(IOStream *s);
   21.42 -
   21.43 -/** Methods used by a gzFile* IOStream. */
   21.44 -static const IOMethods gzip_methods = {
   21.45 -    read:  gzip_read,
   21.46 -    write: gzip_write,
   21.47 -    error: gzip_error,
   21.48 -    close: gzip_close,
   21.49 -    free:  gzip_free,
   21.50 -    flush: gzip_flush,
   21.51 -};
   21.52 -
   21.53 -/** Get the underlying gzFile*.
   21.54 - * 
   21.55 - * @param s gzip stream
   21.56 - * @return the stream s wraps
   21.57 - */
   21.58 -static inline gzFile get_gzfile(IOStream *s){
   21.59 -    return (gzFile)s->data;
   21.60 -}
   21.61 -
   21.62 -/** Write to the underlying stream.
   21.63 - *
   21.64 - * @param stream destination
   21.65 - * @param buf data
   21.66 - * @param n number of bytes to write
   21.67 - * @return number of bytes written
   21.68 - */
   21.69 -static int gzip_write(IOStream *s, const void *buf, size_t n){
   21.70 -    return gzwrite(get_gzfile(s), (void*)buf, n);
   21.71 -}
   21.72 -
   21.73 -/** Read from the underlying stream.
   21.74 - *
   21.75 - * @param stream input
   21.76 - * @param buf where to put input
   21.77 - * @param n number of bytes to read
   21.78 - * @return number of bytes read
   21.79 - */
   21.80 -static int gzip_read(IOStream *s, void *buf, size_t n){
   21.81 -    return gzread(get_gzfile(s), buf, n);
   21.82 -}
   21.83 -
   21.84 -/** Flush the underlying stream.
   21.85 - *
   21.86 - * @param s gzip stream
   21.87 - * @return 0 on success, error code otherwise
   21.88 - */
   21.89 -static int gzip_flush(IOStream *s){
   21.90 -    //return gzflush(get_gzfile(s), Z_NO_FLUSH);
   21.91 -    return gzflush(get_gzfile(s), Z_SYNC_FLUSH);
   21.92 -    //return gzflush(get_gzfile(s), Z_FULL_FLUSH);
   21.93 -}
   21.94 -
   21.95 -/** Check if a stream has an error.
   21.96 - *
   21.97 - * @param s gzip stream
   21.98 - * @return 1 if has an error, 0 otherwise
   21.99 - */
  21.100 -static int gzip_error(IOStream *s){
  21.101 -    int err;
  21.102 -    gzFile *gz = get_gzfile(s);
  21.103 -    gzerror(gz, &err);
  21.104 -    return (err == Z_ERRNO ? 1 /* ferror(gzfile(gz)) */ : err);
  21.105 -}
  21.106 -
  21.107 -/** Close a gzip stream.
  21.108 - *
  21.109 - * @param s gzip stream to close
  21.110 - * @return result of the close
  21.111 - */
  21.112 -static int gzip_close(IOStream *s){
  21.113 -    int result = 0;
  21.114 -    result = gzclose(get_gzfile(s));
  21.115 -    return result;
  21.116 -}
  21.117 -
  21.118 -/** Free a gzip stream.
  21.119 - *
  21.120 - * @param s gzip stream
  21.121 - */
  21.122 -static void gzip_free(IOStream *s){
  21.123 -    // Nothing to do - close did it all.
  21.124 -}
  21.125 -
  21.126 -/** Create an IOStream for a gzip stream.
  21.127 - *
  21.128 - * @param f stream to wrap
  21.129 - * @return new IOStream using f for i/o
  21.130 - */
  21.131 -IOStream *gzip_stream_new(gzFile *f){
  21.132 -    IOStream *io = ALLOCATE(IOStream);
  21.133 -    if(io){
  21.134 -        io->methods = &gzip_methods;
  21.135 -        io->data = (void*)f;
  21.136 -    }
  21.137 -    return io;
  21.138 -}
  21.139 -
  21.140 -/** IOStream version of fopen().
  21.141 - *
  21.142 - * @param file name of the file to open
  21.143 - * @param flags giving the mode to open in (as for fopen())
  21.144 - * @return new stream for the open file, or NULL if failed
  21.145 - */
  21.146 -IOStream *gzip_stream_fopen(const char *file, const char *flags){
  21.147 -    IOStream *io = NULL;
  21.148 -    gzFile *fgz;
  21.149 -    fgz = gzopen(file, flags);
  21.150 -    if(fgz){
  21.151 -        io = gzip_stream_new(fgz);
  21.152 -        if(!io){
  21.153 -            gzclose(fgz);
  21.154 -        }
  21.155 -    }
  21.156 -    return io;
  21.157 -}
  21.158 -
  21.159 -/** IOStream version of fdopen().
  21.160 - *
  21.161 - * @param fd file descriptor
  21.162 - * @param flags giving the mode to open in (as for fdopen())
  21.163 - * @return new stream for the open file, or NULL if failed.  Always takes
  21.164 - *         ownership of fd.
  21.165 - */
  21.166 -IOStream *gzip_stream_fdopen(int fd, const char *flags){
  21.167 -    IOStream *io = NULL;
  21.168 -    gzFile *fgz;
  21.169 -    fgz = gzdopen(fd, flags);
  21.170 -    if(fgz){
  21.171 -        io = gzip_stream_new(fgz);
  21.172 -        if(!io)
  21.173 -            gzclose(fgz);
  21.174 -    }
  21.175 -    return io;
  21.176 -}
  21.177 -#endif
    22.1 --- a/tools/libxutil/gzip_stream.h	Tue May 24 21:10:23 2005 +0000
    22.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    22.3 @@ -1,30 +0,0 @@
    22.4 -/*
    22.5 - * Copyright (C) 2003 Hewlett-Packard Company.
    22.6 - *
    22.7 - * This library is free software; you can redistribute it and/or modify
    22.8 - * it under the terms of the GNU Lesser General Public License as published by
    22.9 - * the Free Software Foundation; either version 2.1 of the License, or
   22.10 - * (at your option) any later version.
   22.11 - *
   22.12 - * This library is distributed in the hope that it will be useful,
   22.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   22.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   22.15 - * GNU Lesser General Public License for more details.
   22.16 - *
   22.17 - * You should have received a copy of the GNU Lesser General Public License
   22.18 - * along with this library; if not, write to the Free Software
   22.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   22.20 - */
   22.21 -
   22.22 -#ifndef _XUTIL_GZIP_STREAM_H_
   22.23 -#define _XUTIL_GZIP_STREAM_H_
   22.24 -
   22.25 -#ifndef __KERNEL__
   22.26 -#include "iostream.h"
   22.27 -#include "zlib.h"
   22.28 -
   22.29 -extern IOStream *gzip_stream_new(gzFile *f);
   22.30 -extern IOStream *gzip_stream_fopen(const char *file, const char *flags);
   22.31 -extern IOStream *gzip_stream_fdopen(int fd, const char *flags);
   22.32 -#endif
   22.33 -#endif /* !_XUTIL_GZIP_STREAM_H_ */
    23.1 --- a/tools/libxutil/hash_table.c	Tue May 24 21:10:23 2005 +0000
    23.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    23.3 @@ -1,640 +0,0 @@
    23.4 -/*
    23.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    23.6 - *
    23.7 - * This library is free software; you can redistribute it and/or modify
    23.8 - * it under the terms of the GNU Lesser General Public License as published by
    23.9 - * the Free Software Foundation; either version 2.1 of the License, or
   23.10 - * (at your option) any later version.
   23.11 - *
   23.12 - * This library is distributed in the hope that it will be useful,
   23.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   23.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   23.15 - * GNU Lesser General Public License for more details.
   23.16 - *
   23.17 - * You should have received a copy of the GNU Lesser General Public License
   23.18 - * along with this library; if not, write to the Free Software
   23.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   23.20 - */
   23.21 -
   23.22 -#ifdef __KERNEL__
   23.23 -#  include <linux/config.h>
   23.24 -#  include <linux/module.h>
   23.25 -#  include <linux/kernel.h>
   23.26 -#  include <linux/errno.h>
   23.27 -#else
   23.28 -#  include <errno.h>
   23.29 -#  include <stddef.h>
   23.30 -#endif
   23.31 -
   23.32 -//#include <limits.h>
   23.33 -
   23.34 -#include "allocate.h"
   23.35 -#include "hash_table.h"
   23.36 -
   23.37 -/** @file
   23.38 - * Base support for hashtables.
   23.39 - *
   23.40 - * Hash codes are reduced modulo the number of buckets to index tables,
   23.41 - * so there is no need for hash functions to limit the range of hashcodes.
   23.42 - * In fact it is assumed that hashcodes do not change when the number of
   23.43 - * buckets in the table changes.
   23.44 - */
   23.45 -
   23.46 -/*==========================================================================*/
   23.47 -/** Number of bits in half a word. */
   23.48 -//#if __WORDSIZE == 64
   23.49 -//#define HALF_WORD_BITS 32
   23.50 -//#else
   23.51 -#define HALF_WORD_BITS 16
   23.52 -//#endif
   23.53 -
   23.54 -/** Mask for lo half of a word. On 32-bit this is 
   23.55 - * (1<<16) - 1 = 65535 = 0xffff
   23.56 - * It's 4294967295 = 0xffffffff on 64-bit.
   23.57 - */
   23.58 -#define LO_HALF_MASK ((1 << HALF_WORD_BITS) - 1)
   23.59 -
   23.60 -/** Get the lo half of a word. */
   23.61 -#define LO_HALF(x) ((x) & LO_HALF_MASK)
   23.62 -
   23.63 -/** Get the hi half of a word. */
   23.64 -#define HI_HALF(x) ((x) >> HALF_WORD_BITS)
   23.65 -
   23.66 -/** Do a full hash on both inputs, using DES-style non-linear scrambling.
   23.67 - * Both inputs are replaced with the results of the hash.
   23.68 - *
   23.69 - * @param pleft input/output word
   23.70 - * @param pright input/output word
   23.71 - */
   23.72 -void pseudo_des(unsigned long *pleft, unsigned long *pright){
   23.73 -    // Bit-rich mixing constant.
   23.74 -    static const unsigned long a_mixer[] = {
   23.75 -        0xbaa96887L, 0x1e17d32cL, 0x03bcdc3cL, 0x0f33d1b2L, };
   23.76 -
   23.77 -    // Bit-rich mixing constant.
   23.78 -    static const unsigned long b_mixer[] = {
   23.79 -        0x4b0f3b58L, 0xe874f0c3L, 0x6955c5a6L, 0x55a7ca46L, };
   23.80 -
   23.81 -    // Number of iterations - must be 2 or 4.
   23.82 -    static const int ncycle = 4;
   23.83 -    //static const int ncycle = 2;
   23.84 -
   23.85 -    unsigned long left = *pleft, right = *pright;
   23.86 -    unsigned long v, v_hi, v_lo;
   23.87 -    int i;
   23.88 -
   23.89 -    for(i=0; i<ncycle; i++){
   23.90 -        // Flip some bits in right to get v.
   23.91 -        v = right;
   23.92 -        v ^= a_mixer[i];
   23.93 -        // Get lo and hi halves of v.
   23.94 -        v_lo = LO_HALF(v);
   23.95 -        v_hi = HI_HALF(v);
   23.96 -        // Non-linear mix of the halves of v.
   23.97 -        v = ((v_lo * v_lo) + ~(v_hi * v_hi));
   23.98 -        // Swap the halves of v.
   23.99 -        v = (HI_HALF(v) | (LO_HALF(v) << HALF_WORD_BITS));
  23.100 -        // Flip some bits.
  23.101 -        v ^= b_mixer[i];
  23.102 -        // More non-linear mixing.
  23.103 -        v += (v_lo * v_hi);
  23.104 -        v ^= left;
  23.105 -        left = right;
  23.106 -        right = v;
  23.107 -    }
  23.108 -    *pleft = left;
  23.109 -    *pright = right;
  23.110 -}
  23.111 -
  23.112 -/** Hash a string.
  23.113 - *
  23.114 - * @param s input to hash
  23.115 - * @return hashcode
  23.116 - */
  23.117 -Hashcode hash_string(char *s){
  23.118 -    Hashcode h = 0;
  23.119 -    if(s){
  23.120 -        for( ; *s; s++){
  23.121 -            h = hash_2ul(h, *s);
  23.122 -        }
  23.123 -    }
  23.124 -    return h;
  23.125 -}
  23.126 -
  23.127 -/** Get the bucket for a hashcode in a hash table.
  23.128 - *
  23.129 - * @param table to get bucket from
  23.130 - * @param hashcode to get bucket for
  23.131 - * @return bucket
  23.132 - */
  23.133 -inline HTBucket * get_bucket(HashTable *table, Hashcode hashcode){
  23.134 -    return table->buckets + (hashcode % table->buckets_n);
  23.135 -}
  23.136 -
  23.137 -/** Initialize a hash table.
  23.138 - * Can be safely called more than once.
  23.139 - *
  23.140 - * @param table to initialize
  23.141 - */
  23.142 -void HashTable_init(HashTable *table){
  23.143 -    int i;
  23.144 -
  23.145 -    if(!table->init_done){
  23.146 -        table->init_done = 1;
  23.147 -        table->next_id = 0;
  23.148 -        for(i=0; i<table->buckets_n; i++){
  23.149 -            HTBucket *bucket = get_bucket(table, i);
  23.150 -            bucket->head = 0;
  23.151 -            bucket->count = 0;
  23.152 -        }
  23.153 -        table->entry_count = 0;
  23.154 -    }
  23.155 -}
  23.156 -
  23.157 -/** Allocate a new hashtable.
  23.158 - * If the number of buckets is not positive the default is used.
  23.159 - * The number of buckets should usually be prime.
  23.160 - *
  23.161 - * @param buckets_n number of buckets
  23.162 - * @return new hashtable or null
  23.163 - */
  23.164 -HashTable *HashTable_new(int buckets_n){
  23.165 -    HashTable *z = ALLOCATE(HashTable);
  23.166 -    if(!z) goto exit;
  23.167 -    if(buckets_n <= 0){
  23.168 -        buckets_n = HT_BUCKETS_N;
  23.169 -    }
  23.170 -    z->buckets = (HTBucket*)allocate(buckets_n * sizeof(HTBucket));
  23.171 -    if(!z->buckets){
  23.172 -        deallocate(z);
  23.173 -        z = 0;
  23.174 -        goto exit;
  23.175 -    }
  23.176 -    z->buckets_n = buckets_n;
  23.177 -    HashTable_init(z);
  23.178 -  exit:
  23.179 -    return z;
  23.180 -}
  23.181 -
  23.182 -/** Free a hashtable.
  23.183 - * Any entries are removed and freed.
  23.184 - *
  23.185 - * @param h hashtable (ignored if null)
  23.186 - */
  23.187 -void HashTable_free(HashTable *h){
  23.188 -    if(h){
  23.189 -        HashTable_clear(h);
  23.190 -        deallocate(h->buckets);
  23.191 -        deallocate(h);
  23.192 -    }
  23.193 -}
  23.194 -
  23.195 -/** Push an entry on the list in the bucket for a given hashcode.
  23.196 - *
  23.197 - * @param table to add entry to
  23.198 - * @param hashcode for the entry
  23.199 - * @param entry to add
  23.200 - */
  23.201 -static inline void push_on_bucket(HashTable *table, Hashcode hashcode,
  23.202 -				  HTEntry *entry){
  23.203 -    HTBucket *bucket;
  23.204 -    HTEntry *old_head;
  23.205 -
  23.206 -    bucket = get_bucket(table, hashcode);
  23.207 -    old_head = bucket->head;
  23.208 -    bucket->count++;
  23.209 -    bucket->head = entry;
  23.210 -    entry->next = old_head;
  23.211 -}
  23.212 -
  23.213 -/** Change the number of buckets in a hashtable.
  23.214 - * No-op if the number of buckets is not positive.
  23.215 - * Existing entries are reallocated to buckets based on their hashcodes.
  23.216 - * The table is unmodified if the number of buckets cannot be changed.
  23.217 - *
  23.218 - * @param table hashtable
  23.219 - * @param buckets_n new number of buckets
  23.220 - * @return 0 on success, error code otherwise
  23.221 - */
  23.222 -int HashTable_set_buckets_n(HashTable *table, int buckets_n){
  23.223 -    int err = 0;
  23.224 -    HTBucket *old_buckets = table->buckets;
  23.225 -    int old_buckets_n = table->buckets_n;
  23.226 -    int i;
  23.227 -
  23.228 -    if(buckets_n <= 0){
  23.229 -        err = -EINVAL;
  23.230 -        goto exit;
  23.231 -    }
  23.232 -    table->buckets = (HTBucket*)allocate(buckets_n * sizeof(HTBucket));
  23.233 -    if(!table->buckets){
  23.234 -        err = -ENOMEM;
  23.235 -        table->buckets = old_buckets;
  23.236 -        goto exit;
  23.237 -    }
  23.238 -    table->buckets_n = buckets_n;
  23.239 -    for(i=0; i<old_buckets_n; i++){
  23.240 -        HTBucket *bucket = old_buckets + i;
  23.241 -        HTEntry *entry, *next;
  23.242 -        for(entry = bucket->head; entry; entry = next){
  23.243 -            next = entry->next;
  23.244 -            push_on_bucket(table, entry->hashcode, entry);
  23.245 -        }
  23.246 -    }
  23.247 -    deallocate(old_buckets);
  23.248 -  exit:
  23.249 -    return err;
  23.250 -}
  23.251 -
  23.252 -/** Adjust the number of buckets so the table is neither too full nor too empty.
  23.253 - * The table is unmodified if adjusting fails.
  23.254 - *
  23.255 - * @param table hash table
  23.256 - * @param buckets_min minimum number of buckets (use default if 0 or negative)
  23.257 - * @return 0 on success, error code otherwise
  23.258 - */
  23.259 -int HashTable_adjust(HashTable *table, int buckets_min){
  23.260 -    int buckets_n = 0;
  23.261 -    int err = 0;
  23.262 -    if(buckets_min <= 0) buckets_min = HT_BUCKETS_N;
  23.263 -    if(table->entry_count >= table->buckets_n){
  23.264 -        // The table is dense - expand it.
  23.265 -        buckets_n = 2 * table->buckets_n;
  23.266 -    } else if((table->buckets_n > buckets_min) &&
  23.267 -              (4 * table->entry_count < table->buckets_n)){
  23.268 -        // The table is more than minimum size and sparse - shrink it.
  23.269 -        buckets_n = 2 * table->entry_count;
  23.270 -        if(buckets_n < buckets_min) buckets_n = buckets_min;
  23.271 -    }
  23.272 -    if(buckets_n){
  23.273 -        err = HashTable_set_buckets_n(table, buckets_n);
  23.274 -    }
  23.275 -    return err;
  23.276 -}
  23.277 -
  23.278 -/** Allocate a new entry for a given value.
  23.279 - *
  23.280 - * @param value to put in the entry
  23.281 - * @return entry, or 0 on failure
  23.282 - */
  23.283 -HTEntry * HTEntry_new(Hashcode hashcode, void *key, void *value){
  23.284 -    HTEntry *z = ALLOCATE(HTEntry);
  23.285 -    if(z){
  23.286 -        z->hashcode = hashcode;
  23.287 -        z->key = key;
  23.288 -        z->value = value;
  23.289 -    }
  23.290 -    return z;
  23.291 -}
  23.292 -
  23.293 -/** Free an entry.
  23.294 - *
  23.295 - * @param z entry to free
  23.296 - */
  23.297 -inline void HTEntry_free(HTEntry *z){
  23.298 -    if(z){
  23.299 -        deallocate(z);
  23.300 -    }
  23.301 -}
  23.302 -
  23.303 -/** Free an entry in a hashtable.
  23.304 - * The table's entry_free_fn is used is defined, otherwise 
  23.305 - * the HTEntry itself is freed.
  23.306 - *
  23.307 - * @param table hashtable
  23.308 - * @param entry to free
  23.309 - */
  23.310 -inline void HashTable_free_entry(HashTable *table, HTEntry *entry){
  23.311 -    if(!entry)return;
  23.312 -    if(table && table->entry_free_fn){
  23.313 -        table->entry_free_fn(table, entry);
  23.314 -    } else {
  23.315 -        HTEntry_free(entry);
  23.316 -    }
  23.317 -}
  23.318 -
  23.319 -/** Get the first entry satisfying a test from the bucket for the
  23.320 - * given hashcode.
  23.321 - *
  23.322 - * @param table to look in
  23.323 - * @param hashcode indicates the bucket
  23.324 - * @param test_fn test to apply to elements
  23.325 - * @param arg first argument to calls to test_fn
  23.326 - * @return entry found, or 0
  23.327 - */
  23.328 -inline HTEntry * HashTable_find_entry(HashTable *table, Hashcode hashcode,
  23.329 -				      TableTestFn *test_fn, TableArg arg){
  23.330 -    HTBucket *bucket;
  23.331 -    HTEntry *entry = 0;
  23.332 -    HTEntry *next;
  23.333 -
  23.334 -    bucket = get_bucket(table, hashcode);
  23.335 -    for(entry = bucket->head; entry; entry = next){
  23.336 -        next = entry->next;
  23.337 -        if(test_fn(arg, table, entry)){
  23.338 -            break;
  23.339 -        }
  23.340 -    }
  23.341 -    return entry;
  23.342 -}
  23.343 -
  23.344 -/** Test hashtable keys for equality.
  23.345 - * Uses the table's key_equal_fn if defined, otherwise pointer equality.
  23.346 - *
  23.347 - * @param key1 key to compare
  23.348 - * @param key2 key to compare
  23.349 - * @return 1 if equal, 0 otherwise
  23.350 - */
  23.351 -inline int HashTable_key_equal(HashTable *table, void *key1, void *key2){
  23.352 -    return (table->key_equal_fn ? table->key_equal_fn(key1, key2) : key1==key2);
  23.353 -}
  23.354 -
  23.355 -/** Compute the hashcode of a hashtable key.
  23.356 - * The table's key_hash_fn is used if defined, otherwise the address of
  23.357 - * the key is hashed.
  23.358 - *
  23.359 - * @param table hashtable
  23.360 - * @param key to hash
  23.361 - * @return hashcode
  23.362 - */
  23.363 -inline Hashcode HashTable_key_hash(HashTable *table, void *key){
  23.364 -    return (table->key_hash_fn ? table->key_hash_fn(key) : hash_ul((unsigned long)key));
  23.365 -}
  23.366 -
  23.367 -/** Test if an entry has a given key.
  23.368 - *
  23.369 - * @param arg containing key to test for
  23.370 - * @param table the entry is in
  23.371 - * @param entry to test
  23.372 - * @return 1 if the entry has the key, 0 otherwise
  23.373 - */
  23.374 -static inline int has_key(TableArg arg, HashTable *table, HTEntry *entry){
  23.375 -    return HashTable_key_equal(table, arg.ptr, entry->key);
  23.376 -}
  23.377 -
  23.378 -/** Get an entry with a given key.
  23.379 - *
  23.380 - * @param table to search
  23.381 - * @param key to look for
  23.382 - * @return entry if found, null otherwise
  23.383 - */
  23.384 -#if 0
  23.385 -inline HTEntry * HashTable_get_entry(HashTable *table, void *key){
  23.386 -    TableArg arg = { ptr: key };
  23.387 -    return HashTable_find_entry(table, HashTable_key_hash(table, key), has_key, arg);
  23.388 -}
  23.389 -#else
  23.390 -inline HTEntry * HashTable_get_entry(HashTable *table, void *key){
  23.391 -    Hashcode hashcode;
  23.392 -    HTBucket *bucket;
  23.393 -    HTEntry *entry = 0;
  23.394 -    HTEntry *next;
  23.395 -
  23.396 -    hashcode = HashTable_key_hash(table, key);
  23.397 -    bucket = get_bucket(table, hashcode);
  23.398 -    for(entry = bucket->head; entry; entry = next){
  23.399 -        next = entry->next;
  23.400 -        if(HashTable_key_equal(table, key, entry->key)){
  23.401 -            break;
  23.402 -        }
  23.403 -    }
  23.404 -    return entry;
  23.405 -}
  23.406 -#endif
  23.407 -
  23.408 -/** Get the value of an entry with a given key.
  23.409 - *
  23.410 - * @param table to search
  23.411 - * @param key to look for
  23.412 - * @return value if an entry was found, null otherwise
  23.413 - */
  23.414 -inline void * HashTable_get(HashTable *table, void *key){
  23.415 -    HTEntry *entry = HashTable_get_entry(table, key);
  23.416 -    return (entry ? entry->value : 0);
  23.417 -}
  23.418 -
  23.419 -/** Print the buckets in a table.
  23.420 - *
  23.421 - * @param table to print
  23.422 - */
  23.423 -void show_buckets(HashTable *table, IOStream *io){
  23.424 -    int i,j ;
  23.425 -    IOStream_print(io, "entry_count=%d buckets_n=%d\n", table->entry_count, table->buckets_n);
  23.426 -    for(i=0; i<table->buckets_n; i++){
  23.427 -        if(0 || table->buckets[i].count>0){
  23.428 -            IOStream_print(io, "bucket %3d %3d %10p ", i,
  23.429 -                        table->buckets[i].count,
  23.430 -                        table->buckets[i].head);
  23.431 -            for(j = table->buckets[i].count; j>0; j--){
  23.432 -                IOStream_print(io, "+");
  23.433 -            }
  23.434 -            IOStream_print(io, "\n");
  23.435 -        }
  23.436 -    }
  23.437 -    HashTable_print(table, io); 
  23.438 -}
  23.439 -    
  23.440 -/** Print an entry in a table.
  23.441 - *
  23.442 - * @param entry to print
  23.443 - * @param arg a pointer to an IOStream to print to
  23.444 - * @return 0
  23.445 - */
  23.446 -static int print_entry(TableArg arg, HashTable *table, HTEntry *entry){
  23.447 -    IOStream *io = (IOStream*)arg.ptr;
  23.448 -    IOStream_print(io, " b=%4lx h=%08lx i=%08lx |-> e=%8p k=%8p v=%8p\n",
  23.449 -                entry->hashcode % table->buckets_n,
  23.450 -                entry->hashcode,
  23.451 -                entry->index,
  23.452 -                entry, entry->key, entry->value);
  23.453 -    return 0;
  23.454 -}
  23.455 -
  23.456 -/** Print a hash table.
  23.457 - *
  23.458 - * @param table to print
  23.459 - */
  23.460 -void HashTable_print(HashTable *table, IOStream *io){
  23.461 -    IOStream_print(io, "{\n");
  23.462 -    HashTable_map(table, print_entry, (TableArg){ ptr: io });
  23.463 -    IOStream_print(io, "}\n");
  23.464 -}
  23.465 -/*==========================================================================*/
  23.466 -
  23.467 -/** Get the next entry id to use for a table.
  23.468 - *
  23.469 - * @param table hash table
  23.470 - * @return non-zero entry id
  23.471 - */
  23.472 -static inline unsigned long get_next_id(HashTable *table){
  23.473 -    unsigned long id;
  23.474 -
  23.475 -    if(table->next_id == 0){
  23.476 -        table->next_id = 1;
  23.477 -    }
  23.478 -    id = table->next_id++;
  23.479 -    return id;
  23.480 -}
  23.481 -
  23.482 -/** Add an entry to the bucket for the
  23.483 - * given hashcode.
  23.484 - *
  23.485 - * @param table to insert in
  23.486 - * @param hashcode indicates the bucket
  23.487 - * @param key to add an entry for
  23.488 - * @param value to add an entry for
  23.489 - * @return entry on success, 0 on failure
  23.490 - */
  23.491 -inline HTEntry * HashTable_add_entry(HashTable *table, Hashcode hashcode, void *key, void *value){
  23.492 -    HTEntry *entry = HTEntry_new(hashcode, key, value);
  23.493 -    if(entry){
  23.494 -        entry->index = get_next_id(table);
  23.495 -        push_on_bucket(table, hashcode, entry);
  23.496 -        table->entry_count++;
  23.497 -    }
  23.498 -    return entry;
  23.499 -}
  23.500 -
  23.501 -/** Move the front entry for a bucket to the correct point in the bucket order as
  23.502 - * defined by the order function. If this is called every time a new entry is added
  23.503 - * the bucket will be maintained in sorted order.
  23.504 - *
  23.505 - * @param table to modify
  23.506 - * @param hashcode indicates the bucket
  23.507 - * @param order entry comparison function
  23.508 - * @return 0 if an entry was moved, 1 if not
  23.509 - */
  23.510 -int HashTable_order_bucket(HashTable *table, Hashcode hashcode, TableOrderFn *order){
  23.511 -    HTEntry *new_entry = NULL, *prev = NULL, *entry = NULL;
  23.512 -    HTBucket *bucket;
  23.513 -    int err = 1;
  23.514 -
  23.515 -    bucket = get_bucket(table, hashcode);
  23.516 -    new_entry = bucket->head;
  23.517 -    if(!new_entry || !new_entry->next) goto exit;
  23.518 -    for(entry = new_entry->next; entry; prev = entry, entry = entry->next){
  23.519 -        if(order(new_entry, entry) <= 0) break;
  23.520 -    }
  23.521 -    if(prev){
  23.522 -        err = 0;
  23.523 -        bucket->head = new_entry->next; 
  23.524 -        new_entry->next = entry;
  23.525 -        prev->next = new_entry;
  23.526 -    }
  23.527 -  exit:
  23.528 -    return err;
  23.529 -}
  23.530 -
  23.531 -/** Add an entry to a hashtable.
  23.532 - * The entry is added to the bucket for its key's hashcode.
  23.533 - *
  23.534 - * @param table to insert in
  23.535 - * @param key to add an entry for
  23.536 - * @param value to add an entry for
  23.537 - * @return entry on success, 0 on failure
  23.538 - */
  23.539 -inline HTEntry * HashTable_add(HashTable *table, void *key, void *value){
  23.540 -    return HashTable_add_entry(table, HashTable_key_hash(table, key), key, value);
  23.541 -}
  23.542 -
  23.543 -
  23.544 -/** Remove entries satisfying a test from the bucket for the
  23.545 - * given hashcode. 
  23.546 - *
  23.547 - * @param table to remove from
  23.548 - * @param hashcode indicates the bucket
  23.549 - * @param test_fn test to apply to elements
  23.550 - * @param arg first argument to calls to test_fn
  23.551 - * @return number of entries removed
  23.552 - */
  23.553 -inline int HashTable_remove_entry(HashTable *table, Hashcode hashcode,
  23.554 -				  TableTestFn *test_fn, TableArg arg){
  23.555 -    HTBucket *bucket;
  23.556 -    HTEntry *entry, *prev = 0, *next;
  23.557 -    int removed_count = 0;
  23.558 -
  23.559 -    bucket = get_bucket(table, hashcode);
  23.560 -    for(entry = bucket->head; entry; entry = next){
  23.561 -        next = entry->next;
  23.562 -        if(test_fn(arg, table, entry)){
  23.563 -            if(prev){
  23.564 -                prev->next = next;
  23.565 -            } else {
  23.566 -                bucket->head = next;
  23.567 -            }
  23.568 -            bucket->count--;
  23.569 -            table->entry_count--;
  23.570 -            removed_count++;
  23.571 -            HashTable_free_entry(table, entry);
  23.572 -            entry = 0;
  23.573 -        }
  23.574 -        prev = entry;
  23.575 -    }
  23.576 -    return removed_count;
  23.577 -}
  23.578 -
  23.579 -/** Remove entries with a given key. 
  23.580 - *
  23.581 - * @param table to remove from
  23.582 - * @param key of entries to remove
  23.583 - * @return number of entries removed
  23.584 - */
  23.585 -inline int HashTable_remove(HashTable *table, void *key){
  23.586 -#if 1
  23.587 -    Hashcode hashcode;
  23.588 -    HTBucket *bucket;
  23.589 -    HTEntry *entry, *prev = 0, *next;
  23.590 -    int removed_count = 0;
  23.591 -
  23.592 -    hashcode = HashTable_key_hash(table, key);
  23.593 -    bucket = get_bucket(table, hashcode);
  23.594 -    for(entry = bucket->head; entry; entry = next){
  23.595 -        next = entry->next;
  23.596 -        if(HashTable_key_equal(table, key, entry->key)){
  23.597 -            if(prev){
  23.598 -                prev->next = next;
  23.599 -            } else {
  23.600 -                bucket->head = next;
  23.601 -            }
  23.602 -            bucket->count--;
  23.603 -            table->entry_count--;
  23.604 -            removed_count++;
  23.605 -            HashTable_free_entry(table, entry);
  23.606 -            entry = 0;
  23.607 -        }
  23.608 -        prev = entry;
  23.609 -    }
  23.610 -    return removed_count;
  23.611 -#else
  23.612 -    return HashTable_remove_entry(table, HashTable_key_hash(table, key),
  23.613 -				  has_key, (TableArg){ ptr: key});
  23.614 -#endif
  23.615 -}
  23.616 -
  23.617 -/** Remove (and free) all the entries in a bucket.
  23.618 - *
  23.619 - * @param bucket to clear
  23.620 - */
  23.621 -static inline void bucket_clear(HashTable *table, HTBucket *bucket){
  23.622 -    HTEntry *entry, *next;
  23.623 -
  23.624 -    for(entry = bucket->head; entry; entry = next){
  23.625 -        next = entry->next;
  23.626 -        HashTable_free_entry(table, entry);
  23.627 -    }
  23.628 -    bucket->head = 0;
  23.629 -    table->entry_count -= bucket->count;
  23.630 -    bucket->count = 0;
  23.631 -}
  23.632 -
  23.633 -/** Remove (and free) all the entries in a table.
  23.634 - *
  23.635 - * @param table to clear
  23.636 - */
  23.637 -void HashTable_clear(HashTable *table){
  23.638 -    int i, n = table->buckets_n;
  23.639 -
  23.640 -    for(i=0; i<n; i++){
  23.641 -        bucket_clear(table, table->buckets + i);
  23.642 -    }
  23.643 -}
    24.1 --- a/tools/libxutil/hash_table.h	Tue May 24 21:10:23 2005 +0000
    24.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    24.3 @@ -1,294 +0,0 @@
    24.4 -/*
    24.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    24.6 - *
    24.7 - * This library is free software; you can redistribute it and/or modify
    24.8 - * it under the terms of the GNU Lesser General Public License as published by
    24.9 - * the Free Software Foundation; either version 2.1 of the License, or
   24.10 - * (at your option) any later version.
   24.11 - *
   24.12 - * This library is distributed in the hope that it will be useful,
   24.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   24.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   24.15 - * GNU Lesser General Public License for more details.
   24.16 - *
   24.17 - * You should have received a copy of the GNU Lesser General Public License
   24.18 - * along with this library; if not, write to the Free Software
   24.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   24.20 - */
   24.21 -
   24.22 -#ifndef _XUTIL_HASH_TABLE_H_
   24.23 -#define _XUTIL_HASH_TABLE_H_
   24.24 -
   24.25 -#include "iostream.h"
   24.26 -
   24.27 -typedef unsigned long Hashcode;
   24.28 -
   24.29 -/** Type used to pass parameters to table functions. */
   24.30 -typedef union TableArg {
   24.31 -    unsigned long ul;
   24.32 -    void *ptr;
   24.33 -} TableArg;
   24.34 -
   24.35 -/** An entry in a bucket list. */
   24.36 -typedef struct HTEntry {
   24.37 -    /** Hashcode of the entry's key. */
   24.38 -    Hashcode hashcode;
   24.39 -    /** Identifier for this entry in the table. */
   24.40 -    int index;
   24.41 -    /** The key for this entry. */
   24.42 -    void *key;
   24.43 -    /** The value in this entry. */
   24.44 -    void *value;
   24.45 -    /** The next entry in the list. */
   24.46 -    struct HTEntry *next;
   24.47 -} HTEntry;
   24.48 -
   24.49 -/** A bucket in a rule table. */
   24.50 -typedef struct HTBucket {
   24.51 -    /** Number of entries in the bucket. */
   24.52 -    int count;
   24.53 -    /** First entry in the bucket (may be null). */
   24.54 -    HTEntry *head;
   24.55 -} HTBucket;
   24.56 -
   24.57 -/** Default number of buckets in a hash table.
   24.58 - * You want enough buckets so the lists in the buckets will typically be short.
   24.59 - * It's a good idea if this is prime, since that will help to spread hashcodes
   24.60 - * around the table.
   24.61 - */
   24.62 -//#define HT_BUCKETS_N 1
   24.63 -//#define HT_BUCKETS_N 3
   24.64 -//#define HT_BUCKETS_N 7
   24.65 -//#define HT_BUCKETS_N 17
   24.66 -//#define HT_BUCKETS_N 97
   24.67 -//#define HT_BUCKETS_N 211
   24.68 -//#define HT_BUCKETS_N 401
   24.69 -#define HT_BUCKETS_N 1021
   24.70 -
   24.71 -typedef struct HashTable HashTable;
   24.72 -
   24.73 -/** Type for a function used to select table entries. */
   24.74 -typedef int TableTestFn(TableArg arg, HashTable *table, HTEntry *entry);
   24.75 -
   24.76 -/** Type for a function to map over table entries. */
   24.77 -typedef int TableMapFn(TableArg arg, HashTable *table, HTEntry *entry);
   24.78 -
   24.79 -/** Type for a function to free table entries. */
   24.80 -typedef void TableFreeFn(HashTable *table, HTEntry *entry);
   24.81 -
   24.82 -/** Type for a function to hash table keys. */
   24.83 -typedef Hashcode TableHashFn(void *key);
   24.84 -
   24.85 -/** Type for a function to test table keys for equality. */
   24.86 -typedef int TableEqualFn(void *key1, void *key2);
   24.87 -
   24.88 -/** Type for a function to order table entries. */
   24.89 -typedef int TableOrderFn(HTEntry *e1, HTEntry *e2);
   24.90 -
   24.91 -/** General hash table.
   24.92 - * A hash table with a list in each bucket.
   24.93 - * Functions can be supplied for freeing entries, hashing keys, and comparing keys.
   24.94 - * These all default to 0, when default behaviour treating keys as integers is used.
   24.95 - */
   24.96 -struct HashTable {
   24.97 -    /** Flag indicating whether the table has been initialised. */
   24.98 -    int init_done;
   24.99 -    /** Next value for the id field in inserted rules. */
  24.100 -    unsigned long next_id;
  24.101 -    /** Number of buckets in the bucket array. */
  24.102 -    int buckets_n;
  24.103 -    /** Array of buckets, each with its own list. */
  24.104 -    HTBucket *buckets;
  24.105 -    /** Number of entries in the table. */
  24.106 -    int entry_count;
  24.107 -    /** Function to free keys and values in entries. */
  24.108 -    TableFreeFn *entry_free_fn;
  24.109 -    /** Function to hash keys. */
  24.110 -    TableHashFn *key_hash_fn;
  24.111 -    /** Function to compare keys for equality. */
  24.112 -    TableEqualFn *key_equal_fn;
  24.113 -    /** Place for the user of the table to hang extra data. */
  24.114 -    void *user_data;
  24.115 -};
  24.116 -
  24.117 -extern HashTable *HashTable_new(int bucket_n);
  24.118 -extern void HashTable_free(HashTable *table);
  24.119 -extern HTEntry * HTEntry_new(Hashcode hashcode, void *key, void *value);
  24.120 -extern void HTEntry_free(HTEntry *entry);
  24.121 -extern int HashTable_set_bucket_n(HashTable *table, int bucket_n);
  24.122 -extern void HashTable_clear(HashTable *table);
  24.123 -extern HTEntry * HashTable_add_entry(HashTable *table, Hashcode hashcode, void *key, void *value);
  24.124 -extern HTEntry * HashTable_get_entry(HashTable *table, void *key);
  24.125 -extern HTEntry * HashTable_add(HashTable *table, void *key, void *value);
  24.126 -extern void * HashTable_get(HashTable *table, void *key);
  24.127 -extern int HashTable_remove(HashTable *table, void *key);
  24.128 -extern HTEntry * HashTable_find_entry(HashTable *table, Hashcode hashcode,
  24.129 -                                      TableTestFn *test_fn, TableArg arg);
  24.130 -extern int HashTable_remove_entry(HashTable *table, Hashcode hashcode,
  24.131 -                                   TableTestFn *test_fn, TableArg arg);
  24.132 -//extern int HashTable_map(HashTable *table, TableMapFn *map_fn, TableArg arg);
  24.133 -extern void HashTable_print(HashTable *table, IOStream *out);
  24.134 -extern int HashTable_set_buckets_n(HashTable *table, int buckets_n);
  24.135 -extern int HashTable_adjust(HashTable *table, int buckets_min);
  24.136 -extern void pseudo_des(unsigned long *pleft, unsigned long *pright);
  24.137 -extern Hashcode hash_string(char *s);
  24.138 -
  24.139 -extern int HashTable_order_bucket(HashTable *table, Hashcode hashcode, TableOrderFn *order);
  24.140 -
  24.141 -/** Control whether to use hashing based on DES or simple
  24.142 - * hashing. DES hashing is `more random' but much more expensive.
  24.143 - */
  24.144 -#define HASH_PSEUDO_DES 0
  24.145 -
  24.146 -/** Hash a long using a quick and dirty linear congruential random number generator.
  24.147 - *  See `Numerical Recipes in C', Chapter 7, "An Even Quicker Generator".
  24.148 - *
  24.149 - * @param a value to hash
  24.150 - * @return hashed input
  24.151 - */
  24.152 -static inline unsigned long lcrng_hash(unsigned long a){
  24.153 -    return (1664525L * a + 1013904223L);
  24.154 -}
  24.155 -
  24.156 -/** Hash an unsigned long.
  24.157 - *
  24.158 - * @param a input to hash
  24.159 - * @return hashcode
  24.160 - */
  24.161 -static inline Hashcode hash_ul(unsigned long a){
  24.162 -#if HASH_PSEUDO_DES
  24.163 -    unsigned long left = a;
  24.164 -    unsigned long right = 0L;
  24.165 -    pseudo_des(&left, &right);
  24.166 -    return right;
  24.167 -#else
  24.168 -    a = lcrng_hash(a);
  24.169 -    a = lcrng_hash(a);
  24.170 -    return a;
  24.171 -#endif
  24.172 -}
  24.173 -
  24.174 -/** Hash two unsigned longs together.
  24.175 - *
  24.176 - * @param a input to hash
  24.177 - * @param b input to hash
  24.178 - * @return hashcode
  24.179 - */
  24.180 -static inline Hashcode hash_2ul(unsigned long a, unsigned long b){
  24.181 -#if HASH_PSEUDO_DES
  24.182 -    unsigned long left = a;
  24.183 -    unsigned long right = b;
  24.184 -    pseudo_des(&left, &right);
  24.185 -    return right;
  24.186 -#else
  24.187 -    a = lcrng_hash(a);
  24.188 -    a ^= b;
  24.189 -    a = lcrng_hash(a);
  24.190 -    return a;
  24.191 -#endif
  24.192 -}
  24.193 -
  24.194 -/** Hash a hashcode and an unsigned long together.
  24.195 - *
  24.196 - * @param a input hashcode
  24.197 - * @param b input to hash
  24.198 - * @return hashcode
  24.199 - */
  24.200 -static inline Hashcode hash_hul(Hashcode a, unsigned long b){
  24.201 -#if HASH_PSEUDO_DES
  24.202 -    unsigned long left = a;
  24.203 -    unsigned long right = b;
  24.204 -    pseudo_des(&left, &right);
  24.205 -    return right;
  24.206 -#else
  24.207 -    a ^= b;
  24.208 -    a = lcrng_hash(a);
  24.209 -    return a;
  24.210 -#endif
  24.211 -}
  24.212 -
  24.213 -/** Macro to declare variables for HashTable_for_each() to use.
  24.214 - *
  24.215 - * @param entry variable that is set to entries in the table
  24.216 - */
  24.217 -#define HashTable_for_decl(entry) \
  24.218 -  HashTable *_var_table; \
  24.219 -  HTBucket *_var_bucket; \
  24.220 -  HTBucket *_var_end; \
  24.221 -  HTEntry *_var_next; \
  24.222 -  HTEntry *entry
  24.223 -
  24.224 -/** Macro to iterate over the entries in a hashtable.
  24.225 - * Must be in a scope where HashTable_for_decl() has been used to declare
  24.226 - * variables for it to use.
  24.227 - * The variable 'entry' is iterated over entries in the table.
  24.228 - * The code produced is syntactically a loop, so it must be followed by
  24.229 - * a loop body, typically some statements in braces:
  24.230 - * HashTable_for_each(entry, table){ ...loop body... }
  24.231 - *
  24.232 - * HashTable_for_each() and HashTable_for_decl() cannot be used for nested
  24.233 - * loops as variables will clash.
  24.234 - *
  24.235 - * @note The simplest way to code a direct loop over the entries in a hashtable
  24.236 - * is to use a loop over the buckets, with a nested loop over the entries
  24.237 - * in a bucket. Using this approach in a macro means the macro contains
  24.238 - * an opening brace, and calls to it must be followed by 2 braces!
  24.239 - * To avoid this the code has been restructured so that it is a for loop.
  24.240 - * So that statements could be used in the test expression of the for loop,
  24.241 - * we have used the gcc statement expression extension ({ ... }).
  24.242 - *
  24.243 - * @param entry variable to iterate over the entries
  24.244 - * @param table to iterate over (non-null)
  24.245 - */
  24.246 -#define HashTable_for_each(entry, table) \
  24.247 -  _var_table = table; \
  24.248 -  _var_bucket = _var_table->buckets; \
  24.249 -  _var_end = _var_bucket + _var_table->buckets_n; \
  24.250 -  for(entry=0, _var_next=0; \
  24.251 -      ({ if(_var_next){ \
  24.252 -             entry = _var_next; \
  24.253 -             _var_next = entry->next; \
  24.254 -          } else { \
  24.255 -             while(_var_bucket < _var_end){ \
  24.256 -                 entry = _var_bucket->head; \
  24.257 -                 _var_bucket++; \
  24.258 -                 if(entry){ \
  24.259 -                      _var_next = entry->next; \
  24.260 -                      break; \
  24.261 -                 } \
  24.262 -             } \
  24.263 -          }; \
  24.264 -         entry; }); \
  24.265 -      entry = _var_next )
  24.266 -
  24.267 -/** Map a function over the entries in a table.
  24.268 - * Mapping stops when the function returns a non-zero value.
  24.269 - * Uses the gcc statement expression extension ({ ... }).
  24.270 - *
  24.271 - * @param table to map over
  24.272 - * @param fn function to apply to entries
  24.273 - * @param arg first argument to call the function with
  24.274 - * @return 0 if fn always returned 0, first non-zero value otherwise
  24.275 - */
  24.276 -#define HashTable_map(table, fn, arg) \
  24.277 -  ({ HashTable_for_decl(_var_entry); \
  24.278 -    TableArg _var_arg = arg; \
  24.279 -    int _var_value = 0; \
  24.280 -    HashTable_for_each(_var_entry, table){ \
  24.281 -        if((_var_value = fn(_var_arg, _var_table, _var_entry))) break; \
  24.282 -    } \
  24.283 -    _var_value; })
  24.284 -
  24.285 -/** Cast x to the type for a key or value in a hash table.
  24.286 - * This avoids compiler warnings when using short integers
  24.287 - * as keys or values (especially on 64-bit platforms).
  24.288 - */
  24.289 -#define HKEY(x) ((void*)(unsigned long)(x))
  24.290 -
  24.291 -/** Cast x from the type for a key or value in a hash table.
  24.292 - * to an unsigned long. This avoids compiler warnings when using
  24.293 - * short integers as keys or values (especially on 64-bit platforms).
  24.294 - */
  24.295 -#define HVAL(x) ((unsigned long)(x))
  24.296 -
  24.297 -#endif /* !_XUTIL_HASH_TABLE_H_ */
    25.1 --- a/tools/libxutil/iostream.c	Tue May 24 21:10:23 2005 +0000
    25.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    25.3 @@ -1,55 +0,0 @@
    25.4 -/*
    25.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    25.6 - *
    25.7 - * This library is free software; you can redistribute it and/or modify
    25.8 - * it under the terms of the GNU Lesser General Public License as published by
    25.9 - * the Free Software Foundation; either version 2.1 of the License, or
   25.10 - * (at your option) any later version.
   25.11 - *
   25.12 - * This library is distributed in the hope that it will be useful,
   25.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   25.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   25.15 - * GNU Lesser General Public License for more details.
   25.16 - *
   25.17 - * You should have received a copy of the GNU Lesser General Public License
   25.18 - * along with this library; if not, write to the Free Software
   25.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   25.20 - */
   25.21 -
   25.22 -#include "iostream.h"
   25.23 -#include "sys_string.h"
   25.24 -
   25.25 -/** Print on a stream, like vfprintf().
   25.26 - *
   25.27 - * @param stream to print to
   25.28 - * @param format for the print (as fprintf())
   25.29 - * @param args arguments to print
   25.30 - * @return result code from the print
   25.31 - */
   25.32 -int IOStream_vprint(IOStream *stream, const char *format, va_list args){
   25.33 -  char buffer[1024];
   25.34 -  int k = sizeof(buffer), n;
   25.35 -
   25.36 -  n = vsnprintf(buffer, k, (char*)format, args);
   25.37 -  if(n < 0 || n > k ){
   25.38 -      n = k;
   25.39 -  }
   25.40 -  n = IOStream_write(stream, buffer, n);
   25.41 -  return n;
   25.42 -}
   25.43 -
   25.44 -/** Print on a stream, like fprintf().
   25.45 - *
   25.46 - * @param stream to print to
   25.47 - * @param format for the print (as fprintf())
   25.48 - * @return result code from the print
   25.49 - */
   25.50 -int IOStream_print(IOStream *stream, const char *format, ...){
   25.51 -  va_list args;
   25.52 -  int result = -1;
   25.53 -
   25.54 -  va_start(args, format);
   25.55 -  result = IOStream_vprint(stream, format, args);
   25.56 -  va_end(args);
   25.57 -  return result;
   25.58 -}
    26.1 --- a/tools/libxutil/iostream.h	Tue May 24 21:10:23 2005 +0000
    26.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    26.3 @@ -1,269 +0,0 @@
    26.4 -/*
    26.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    26.6 - *
    26.7 - * This library is free software; you can redistribute it and/or modify
    26.8 - * it under the terms of the GNU Lesser General Public License as published by
    26.9 - * the Free Software Foundation; either version 2.1 of the License, or
   26.10 - * (at your option) any later version.
   26.11 - *
   26.12 - * This library is distributed in the hope that it will be useful,
   26.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   26.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   26.15 - * GNU Lesser General Public License for more details.
   26.16 - *
   26.17 - * You should have received a copy of the GNU Lesser General Public License
   26.18 - * along with this library; if not, write to the Free Software
   26.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   26.20 - */
   26.21 -
   26.22 -#ifndef _XUTIL_IOSTREAM_H_
   26.23 -#define _XUTIL_IOSTREAM_H_
   26.24 -
   26.25 -#include <stdarg.h>
   26.26 -
   26.27 -#ifdef __KERNEL__
   26.28 -#include <linux/config.h>
   26.29 -#include <linux/types.h>
   26.30 -#include <linux/errno.h>
   26.31 -#else
   26.32 -#include <errno.h>
   26.33 -#include <stdint.h>
   26.34 -#include <stddef.h>
   26.35 -#endif
   26.36 -
   26.37 -#include "allocate.h"
   26.38 -
   26.39 -/** End of input return value (for getc). */
   26.40 -#define IOSTREAM_EOF -1
   26.41 -
   26.42 -/** An input/output abstraction.
   26.43 - */
   26.44 -typedef struct IOStream IOStream;
   26.45 -
   26.46 -/** Record of the functions to use for operations on an
   26.47 - * IOStream implementation.
   26.48 - */
   26.49 -typedef struct IOMethods {
   26.50 -    /** Read function.  Called with the user data, buffer to read into
   26.51 -     * and number of bytes to read.  Must return number of bytes read
   26.52 -     * on success, less than zero on error.
   26.53 -     */
   26.54 -    int (*read)(IOStream *stream, void *buf, size_t n);
   26.55 -
   26.56 -    /** Write function. Called with user data, buffer to write and
   26.57 -     * number of bytes to write. Must return number of bytes written on
   26.58 -     * success, less than zero otherwise.
   26.59 -     */
   26.60 -    int (*write)(IOStream *stream, const void *buf, size_t n);
   26.61 -
   26.62 -    int (*flush)(IOStream *s);
   26.63 -
   26.64 -    int (*error)(IOStream *s);
   26.65 -
   26.66 -    int (*close)(IOStream *s);
   26.67 -
   26.68 -    void (*free)(IOStream *s);
   26.69 -
   26.70 -    void (*lock)(IOStream *s);
   26.71 -    void (*unlock)(IOStream *s);
   26.72 -
   26.73 -} IOMethods;
   26.74 -
   26.75 -/** Abstract i/o object.
   26.76 - */
   26.77 -struct IOStream {
   26.78 -    /** Methods to use to implement operations. */
   26.79 -    const IOMethods *methods;
   26.80 -    /** Private state for the implementation. */
   26.81 -    const void *data;
   26.82 -    /** Flag indicating whether the stream is closed. */
   26.83 -    int closed;
   26.84 -    /** Number of bytes written. */
   26.85 -    int written;
   26.86 -    /** Number of bytes read. */
   26.87 -    int read;
   26.88 -    /** Flag indicating whether not to free when closed. */
   26.89 -    int nofree;
   26.90 -};
   26.91 -
   26.92 -
   26.93 -/** IOStream version of stdin. */
   26.94 -extern IOStream *iostdin;
   26.95 -
   26.96 -/** IOStream version of stdout, */
   26.97 -extern IOStream *iostdout;
   26.98 -
   26.99 -/** IOStream version of stderr. */
  26.100 -extern IOStream *iostderr;
  26.101 -
  26.102 -extern int IOStream_print(IOStream *io, const char *format, ...);
  26.103 -extern int IOStream_vprint(IOStream *io, const char *format, va_list args);
  26.104 -
  26.105 -/** Read from a stream.
  26.106 - *
  26.107 - * @param stream input
  26.108 - * @param buf where to put input
  26.109 - * @param n number of bytes to read
  26.110 - * @return if ok, number of bytes read, otherwise negative error code
  26.111 - */
  26.112 -static inline int IOStream_read(IOStream *stream, void *buf, size_t n){
  26.113 -    int result;
  26.114 -    if(stream->closed){
  26.115 -        result = -EIO;
  26.116 -        goto exit;
  26.117 -    }
  26.118 -    if(!stream->methods || !stream->methods->read){
  26.119 -        result = -EINVAL;
  26.120 -        goto exit;
  26.121 -    }
  26.122 -    result = (stream->methods->read)(stream, buf, n);
  26.123 -    if(result > 0){
  26.124 -        stream->read += result;
  26.125 -    }
  26.126 -  exit:
  26.127 -    return result;
  26.128 -}
  26.129 -
  26.130 -/** Write to a stream.
  26.131 - *
  26.132 - * @param stream input
  26.133 - * @param buf where to put input
  26.134 - * @param n number of bytes to write
  26.135 - * @return if ok, number of bytes written, otherwise negative error code
  26.136 - */
  26.137 -static inline int IOStream_write(IOStream *stream, const void *buf, size_t n){
  26.138 -    int result;
  26.139 -    if(stream->closed){
  26.140 -        result = -EIO;
  26.141 -        goto exit;
  26.142 -    }
  26.143 -    if(!stream->methods || !stream->methods->write){
  26.144 -        result = -EINVAL;
  26.145 -        goto exit;
  26.146 -    }
  26.147 -    result = (stream->methods->write)(stream, buf, n);
  26.148 -    if(result > 0){
  26.149 -        stream->written += result;
  26.150 -    }
  26.151 -  exit:
  26.152 -    return result;
  26.153 -}
  26.154 -
  26.155 -/** Flush the stream.
  26.156 - *
  26.157 - * @param stream stream
  26.158 - * @return 0 on success, negative error code otherwise
  26.159 - */
  26.160 -static inline int IOStream_flush(IOStream *stream){
  26.161 -    int result = 0;
  26.162 -    if(stream->closed){
  26.163 -        result = -EIO;
  26.164 -    } else if(stream->methods->flush){
  26.165 -        result = (stream->methods->flush)(stream);
  26.166 -    }
  26.167 -    return result;
  26.168 -}
  26.169 -
  26.170 -/** Check whether the stream has an error.
  26.171 - *
  26.172 - * @param stream to check
  26.173 - * @return 1 for error, 0 otherwise
  26.174 - */
  26.175 -static inline int IOStream_error(IOStream *stream){
  26.176 -    int err = 0;
  26.177 -    if(stream->methods && stream->methods->error){
  26.178 -       err = (stream->methods->error)(stream);
  26.179 -    }
  26.180 -    return err;
  26.181 -}
  26.182 -
  26.183 -/** Close the stream.
  26.184 - *
  26.185 - * @param stream to close
  26.186 - * @return 0 on success, negative error code otherwise
  26.187 - */
  26.188 -static inline int IOStream_close(IOStream *stream){
  26.189 -    int err = 0;
  26.190 -    if(!stream || stream->closed){
  26.191 -        err = -EIO;
  26.192 -        goto exit;
  26.193 -    }
  26.194 -    if(stream->methods && stream->methods->close){
  26.195 -        err = (stream->methods->close)(stream);
  26.196 -        stream->closed = 1;
  26.197 -    }
  26.198 -    if(stream->nofree) goto exit;
  26.199 -    if(stream->methods && stream->methods->free){
  26.200 -        (stream->methods->free)(stream);
  26.201 -    }
  26.202 -    *stream = (IOStream){};
  26.203 -    deallocate(stream);
  26.204 -  exit:
  26.205 -    return err;
  26.206 -}
  26.207 -
  26.208 -/** Test if the stream has been closed.
  26.209 - *
  26.210 - * @param stream to check
  26.211 - * @return 1 if closed, 0 otherwise
  26.212 - */
  26.213 -static inline int IOStream_is_closed(IOStream *stream){
  26.214 -    return stream->closed;
  26.215 -}
  26.216 -
  26.217 -/** Print a character to a stream, like fputc().
  26.218 - *
  26.219 - * @param stream to print to
  26.220 - * @param c character to print
  26.221 - * @return result code from the print
  26.222 - */
  26.223 -static inline int IOStream_putc(IOStream *stream, int c){
  26.224 -    int err;
  26.225 -    unsigned char b = (unsigned char)c;
  26.226 -    err = IOStream_write(stream, &b, 1);
  26.227 -    if(err < 1){
  26.228 -        err = IOSTREAM_EOF;
  26.229 -    } else {
  26.230 -        err = b;
  26.231 -    }
  26.232 -    return err;
  26.233 -}
  26.234 -
  26.235 -/** Read from a stream, like fgetc().
  26.236 - *
  26.237 - * @param stream to read from
  26.238 - * @return IOSTREAM_EOF on error, character read otherwise
  26.239 - */
  26.240 -static inline int IOStream_getc(IOStream *stream){
  26.241 -    int err, rc;
  26.242 -    unsigned char b;
  26.243 -
  26.244 -    err = IOStream_read(stream, &b, 1);
  26.245 -    if(err < 1){
  26.246 -        rc = IOSTREAM_EOF;
  26.247 -    } else {
  26.248 -        rc = b;
  26.249 -    }
  26.250 -    return rc;
  26.251 -}
  26.252 -
  26.253 -/** Get number of bytes read.
  26.254 - *
  26.255 - * @param stream to get from
  26.256 - * @return number of bytes read
  26.257 - */
  26.258 -static inline int IOStream_get_read(IOStream *stream){
  26.259 -    return stream->read;
  26.260 -}
  26.261 -
  26.262 -/** Get number of bytes written.
  26.263 - *
  26.264 - * @param stream to get from
  26.265 - * @return number of bytes written
  26.266 - */
  26.267 -static inline int IOStream_get_written(IOStream *stream){
  26.268 -    return stream->written;
  26.269 -}
  26.270 -
  26.271 -
  26.272 -#endif /* ! _XUTIL_IOSTREAM_H_ */
    27.1 --- a/tools/libxutil/kernel_stream.c	Tue May 24 21:10:23 2005 +0000
    27.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    27.3 @@ -1,178 +0,0 @@
    27.4 -/*
    27.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    27.6 - *
    27.7 - * This library is free software; you can redistribute it and/or modify
    27.8 - * it under the terms of the GNU Lesser General Public License as published by
    27.9 - * the Free Software Foundation; either version 2.1 of the License, or
   27.10 - * (at your option) any later version.
   27.11 - *
   27.12 - * This library is distributed in the hope that it will be useful,
   27.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   27.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   27.15 - * GNU Lesser General Public License for more details.
   27.16 - *
   27.17 - * You should have received a copy of the GNU Lesser General Public License
   27.18 - * along with this library; if not, write to the Free Software
   27.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   27.20 - */
   27.21 -
   27.22 -/** @file
   27.23 - * An IOStream implementation using printk() for output.
   27.24 - * Input is not implemented.
   27.25 - */
   27.26 -#ifdef __KERNEL__
   27.27 -
   27.28 -#include <linux/config.h>
   27.29 -#include <linux/module.h>
   27.30 -#include <linux/kernel.h>
   27.31 -#include <linux/types.h>
   27.32 -#include <linux/errno.h>
   27.33 -#include <linux/slab.h>
   27.34 -#include <linux/spinlock.h>
   27.35 -
   27.36 -#include "kernel_stream.h"
   27.37 -#include "allocate.h"
   27.38 -
   27.39 -/** Number of characters in the output buffer.
   27.40 - * The kernel uses 1024 for printk, so that should suffice.
   27.41 - */
   27.42 -#define BUF_N 1024
   27.43 -
   27.44 -/** State for a kernel stream. */
   27.45 -typedef struct KernelData {
   27.46 -    /** Stream lock. We need a lock to serialize access to the stream. */
   27.47 -    spinlock_t lock;
   27.48 -    /** Saved flags for locking. */
   27.49 -    unsigned long flags;
   27.50 -    /** Size of the output buffer. */
   27.51 -    int buf_n;
   27.52 -    /** Output buffer. */
   27.53 -    char buf[BUF_N];
   27.54 -} KernelData;
   27.55 -
   27.56 -static int kernel_write(IOStream *s, const void *msg, size_t n);
   27.57 -static void kernel_free(IOStream *s);
   27.58 -static void kernel_stream_lock(IOStream *s);
   27.59 -static void kernel_stream_unlock(IOStream *s);
   27.60 -
   27.61 -/** Methods for a kernel stream. Output only. */
   27.62 -static const IOMethods kernel_methods = {
   27.63 -    write:  kernel_write,
   27.64 -    free:   kernel_free,
   27.65 -    lock:   kernel_stream_lock,
   27.66 -    unlock: kernel_stream_unlock,
   27.67 -};
   27.68 -
   27.69 -/** Shared state for kernel streams.
   27.70 - * All implementations write using printk, so we can use
   27.71 - * shared state and avoid allocating it.
   27.72 - */
   27.73 -static const KernelData kernel_data = {
   27.74 -    lock:  SPIN_LOCK_UNLOCKED,
   27.75 -    flags: 0,
   27.76 -    buf_n: BUF_N,
   27.77 -};
   27.78 -
   27.79 -/** Stream for kernel printk. */
   27.80 -static IOStream iokernel = {
   27.81 -    methods: &kernel_methods,
   27.82 -    data:    &kernel_data,
   27.83 -    nofree:  1,
   27.84 -};
   27.85 -
   27.86 -/** Stream for kernel printk. */
   27.87 -IOStream *iostdout = &iokernel;
   27.88 -
   27.89 -/** Stream for kernel printk. */
   27.90 -IOStream *iostdin = &iokernel;
   27.91 -
   27.92 -/** Stream for kernel printk. */
   27.93 -IOStream *iostderr = &iokernel;
   27.94 -
   27.95 -/** Get an output-only stream implementation using
   27.96 - * printk(). The stream uses static storage, and must not be freed.
   27.97 - *
   27.98 - * @return kernel stream
   27.99 - */
  27.100 -IOStream get_stream_kernel(void){
  27.101 -    return iokernel;
  27.102 -}
  27.103 -
  27.104 -/** Obtain the lock on the stream state.
  27.105 - *
  27.106 - * @param kdata stream state
  27.107 - */
  27.108 -static inline void KernelData_lock(KernelData *kdata){
  27.109 -    spin_lock_irqsave(&kdata->lock, kdata->flags);
  27.110 -}
  27.111 -
  27.112 -/** Release the lock on the stream state.
  27.113 - *
  27.114 - * @param kdata stream state
  27.115 - */
  27.116 -static inline void KernelData_unlock(KernelData *kdata){
  27.117 -    spin_unlock_irqrestore(&kdata->lock, kdata->flags);
  27.118 -}
  27.119 -
  27.120 -/** Get the stream state.
  27.121 - *
  27.122 - * @param s kernel stream
  27.123 - * @return stream state
  27.124 - */
  27.125 -static inline KernelData *get_kernel_data(IOStream *s){
  27.126 -    return (KernelData*)s->data;
  27.127 -}
  27.128 -
  27.129 -/** Obtain the lock on the stream state.
  27.130 - *
  27.131 - * @param s stream
  27.132 - */
  27.133 -void kernel_stream_lock(IOStream *s){
  27.134 -    KernelData_lock(get_kernel_data(s));
  27.135 -}
  27.136 -
  27.137 -/** Release the lock on the stream state.
  27.138 - *
  27.139 - * @param s stream
  27.140 - */
  27.141 -void kernel_stream_unlock(IOStream *s){
  27.142 -    KernelData_unlock(get_kernel_data(s));
  27.143 -}
  27.144 -
  27.145 -/** Write to a kernel stream.
  27.146 - *
  27.147 - * @param stream kernel stream
  27.148 - * @param format print format
  27.149 - * @param args print arguments
  27.150 - * @return result of the print
  27.151 - */
  27.152 -static int kernel_write(IOStream *stream, const void *buf, size_t n){
  27.153 -    KernelData *kdata = get_kernel_data(stream);
  27.154 -    int k;
  27.155 -    k = kdata->buf_n - 1;
  27.156 -    if(n < k) k = n;
  27.157 -    memcpy(kdata->buf, buf, k);
  27.158 -    kdata->buf[k] = '\0';
  27.159 -    printk(kdata->buf);
  27.160 -    return k;
  27.161 -}
  27.162 -
  27.163 -/** Free a kernel stream.
  27.164 - * Frees the internal state of the stream.
  27.165 - * Do not call this unless the stream was dynamically allocated.
  27.166 - * Do not call this on a stream returned from get_stream_kernel().
  27.167 - *
  27.168 - * @param io stream to free
  27.169 - */
  27.170 -static void kernel_free(IOStream *io){
  27.171 -    KernelData *kdata;
  27.172 -    if(io == &iokernel) return;
  27.173 -    kdata = get_kernel_data(io);
  27.174 -    memset(kdata, 0, sizeof(*kdata));
  27.175 -    deallocate(kdata);
  27.176 -}
  27.177 -#endif /* __KERNEL__ */
  27.178 -
  27.179 -
  27.180 -
  27.181 -
    28.1 --- a/tools/libxutil/kernel_stream.h	Tue May 24 21:10:23 2005 +0000
    28.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    28.3 @@ -1,29 +0,0 @@
    28.4 -/*
    28.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    28.6 - *
    28.7 - * This library is free software; you can redistribute it and/or modify
    28.8 - * it under the terms of the GNU Lesser General Public License as published by
    28.9 - * the Free Software Foundation; either version 2.1 of the License, or
   28.10 - * (at your option) any later version.
   28.11 - *
   28.12 - * This library is distributed in the hope that it will be useful,
   28.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   28.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   28.15 - * GNU Lesser General Public License for more details.
   28.16 - *
   28.17 - * You should have received a copy of the GNU Lesser General Public License
   28.18 - * along with this library; if not, write to the Free Software
   28.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   28.20 - */
   28.21 -
   28.22 -#ifndef _XUTIL_KERNEL_STREAM_H_
   28.23 -#define _XUTIL_KERNEL_STREAM_H_
   28.24 -
   28.25 -#ifdef __KERNEL__
   28.26 -#include "iostream.h"
   28.27 -
   28.28 -extern IOStream get_stream_kernel(void);
   28.29 -#define get_stream_stdout get_stream_kernel
   28.30 -
   28.31 -#endif /* __KERNEL__ */
   28.32 -#endif /* !_XUTIL_KERNEL_STREAM_H_ */
    29.1 --- a/tools/libxutil/lexis.c	Tue May 24 21:10:23 2005 +0000
    29.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    29.3 @@ -1,94 +0,0 @@
    29.4 -/*
    29.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    29.6 - *
    29.7 - * This library is free software; you can redistribute it and/or modify
    29.8 - * it under the terms of the GNU Lesser General Public License as
    29.9 - * published by the Free Software Foundation; either version 2.1 of the
   29.10 - * License, or  (at your option) any later version. This library is 
   29.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   29.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   29.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   29.14 - * See the GNU Lesser General Public License for more details.
   29.15 - *
   29.16 - * You should have received a copy of the GNU Lesser General Public License
   29.17 - * along with this library; if not, write to the Free Software Foundation,
   29.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   29.19 - */
   29.20 -
   29.21 -/** @file
   29.22 - * Lexical analysis.
   29.23 - */
   29.24 -
   29.25 -#include "sys_string.h"
   29.26 -#include "lexis.h"
   29.27 -#include <errno.h>
   29.28 -
   29.29 -/** Check if a value lies in a (closed) range.
   29.30 - *
   29.31 - * @param x value to test
   29.32 - * @param lo low end of the range
   29.33 - * @param hi high end of the range
   29.34 - * @return 1 if x is in the interval [lo, hi], 0 otherwise
   29.35 - */
   29.36 -inline static int in_range(int x, int lo, int hi){
   29.37 -    return (lo <= x) && (x <= hi);
   29.38 -}
   29.39 -
   29.40 -/** Determine if a string is an (unsigned) decimal number.
   29.41 - * 
   29.42 - * @param s pointer to characters to test
   29.43 - * @param n length of string
   29.44 - * @return 1 if s is a decimal number, 0 otherwise.
   29.45 - */
   29.46 -int is_decimal_number(const char *s, int n){
   29.47 -    int i;
   29.48 -    if(n <= 0)return 0;
   29.49 -    for(i = 0; i < n; i++){
   29.50 -        if(!in_decimal_digit_class(s[i])) return 0;
   29.51 -    }
   29.52 -    return 1;
   29.53 -}
   29.54 -
   29.55 -/** Determine if a string is a hex number.
   29.56 - * Hex numbers are 0, or start with 0x or 0X followed
   29.57 - * by a non-zero number of hex digits (0-9,a-f,A-F).
   29.58 - * 
   29.59 - * @param s pointer to characters to test
   29.60 - * @param n length of string
   29.61 - * @return 1 if s is a hex number, 0 otherwise.
   29.62 - */
   29.63 -int is_hex_number(const char *s, int n){
   29.64 -    int i;
   29.65 -    if(n <= 0) return 0;
   29.66 -    if(n == 1){
   29.67 -        return s[0]=='0';
   29.68 -    }
   29.69 -    if(n <= 3) return 0;
   29.70 -    if(s[0] != '0' || (s[1] != 'x' && s[1] != 'X')) return 0;
   29.71 -    for(i = 2; i < n; i++){
   29.72 -        if(!in_hex_digit_class(s[i])) return 0;
   29.73 -    }
   29.74 -    return 1;
   29.75 -}
   29.76 -
   29.77 -/** Test if a string matches a keyword.
   29.78 - * The comparison is case-insensitive.
   29.79 - * The comparison fails if either argument is null.
   29.80 - *
   29.81 - * @param s string
   29.82 - * @param k keyword
   29.83 - * @return 1 if they match, 0 otherwise
   29.84 - */
   29.85 -int is_keyword(const char *s, const char *k){
   29.86 -  return s && k && !strcasecmp(s, k);
   29.87 -}
   29.88 -
   29.89 -/** Test if a string matches a character.
   29.90 - *
   29.91 - * @param s string
   29.92 - * @param c character (non-null)
   29.93 - * @return 1 if s contains exactly c, 0 otherwise
   29.94 - */
   29.95 -int is_keychar(const char *s, char c){
   29.96 -  return c && (s[0] == c) && !s[1];
   29.97 -}
    30.1 --- a/tools/libxutil/lexis.h	Tue May 24 21:10:23 2005 +0000
    30.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    30.3 @@ -1,128 +0,0 @@
    30.4 -/*
    30.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    30.6 - *
    30.7 - * This library is free software; you can redistribute it and/or modify
    30.8 - * it under the terms of the GNU Lesser General Public License as
    30.9 - * published by the Free Software Foundation; either version 2.1 of the
   30.10 - * License, or  (at your option) any later version. This library is 
   30.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   30.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   30.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   30.14 - * See the GNU Lesser General Public License for more details.
   30.15 - *
   30.16 - * You should have received a copy of the GNU Lesser General Public License
   30.17 - * along with this library; if not, write to the Free Software Foundation,
   30.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   30.19 - */
   30.20 -
   30.21 -#ifndef _XUTIL_LEXIS_H_
   30.22 -#define _XUTIL_LEXIS_H_
   30.23 -
   30.24 -#include "sys_string.h"
   30.25 -
   30.26 -#ifdef __KERNEL__
   30.27 -#  include <linux/ctype.h>
   30.28 -#else
   30.29 -#  include <ctype.h>
   30.30 -#endif
   30.31 -
   30.32 -/** @file
   30.33 - * Lexical analysis.
   30.34 - */
   30.35 -
   30.36 -/** Class of characters treated as space. */
   30.37 -#define space_class ((char []){ '\n', '\r', '\t', ' ', '\f' , 0 })
   30.38 -
   30.39 -/** Class of separator characters. */
   30.40 -#define sep_class "{}()<>[]!;\"'"
   30.41 -
   30.42 -#define comment_class "#"
   30.43 -
   30.44 -/** Determine if a character is in a given class.
   30.45 - * 
   30.46 - * @param c character to test
   30.47 - * @param s null-terminated string of characters in the class
   30.48 - * @return 1 if c is in the class, 0 otherwise.
   30.49 - */
   30.50 -static inline int in_class(int c, const char *s){
   30.51 -  return s && (strchr(s, c) != 0);
   30.52 -}
   30.53 -
   30.54 -/** Determine if a character is in the space class.
   30.55 - * 
   30.56 - * @param c character to test
   30.57 - * @return 1 if c is in the class, 0 otherwise.
   30.58 - */
   30.59 -static inline int in_space_class(int c){
   30.60 -    return in_class(c, space_class);
   30.61 -}
   30.62 -
   30.63 -static inline int in_comment_class(int c){
   30.64 -    return in_class(c, comment_class);
   30.65 -}
   30.66 -
   30.67 -/** Determine if a character is in the separator class.
   30.68 - * Separator characters terminate tokens, and do not need space
   30.69 - * to separate them.
   30.70 - * 
   30.71 - * @param c character to test
   30.72 - * @return 1 if c is in the class, 0 otherwise.
   30.73 - */
   30.74 -static inline int in_sep_class(int c){
   30.75 -    return in_class(c, sep_class);
   30.76 -}
   30.77 -
   30.78 -/** Determine if a character is in the alpha class.
   30.79 - * 
   30.80 - * @param c character to test
   30.81 - * @return 1 if c is in the class, 0 otherwise.
   30.82 - */
   30.83 -static inline int in_alpha_class(int c){
   30.84 -    return isalpha(c);
   30.85 -}
   30.86 -
   30.87 -/** Determine if a character is in the octal digit class.
   30.88 - * 
   30.89 - * @param c character to test
   30.90 - * @return 1 if c is in the class, 0 otherwise.
   30.91 - */
   30.92 -static inline int in_octal_digit_class(int c){
   30.93 -    return '0' <= c && c <= '7';
   30.94 -}
   30.95 -
   30.96 -/** Determine if a character is in the decimal digit class.
   30.97 - * 
   30.98 - * @param c character to test
   30.99 - * @return 1 if c is in the class, 0 otherwise.
  30.100 - */
  30.101 -static inline int in_decimal_digit_class(int c){
  30.102 -    return isdigit(c);
  30.103 -}
  30.104 -
  30.105 -/** Determine if a character is in the hex digit class.
  30.106 - * 
  30.107 - * @param c character to test
  30.108 - * @return 1 if c is in the class, 0 otherwise.
  30.109 - */
  30.110 -static inline int in_hex_digit_class(int c){
  30.111 -    return isdigit(c) || in_class(c, "abcdefABCDEF");
  30.112 -}
  30.113 -
  30.114 -
  30.115 -static inline int in_string_quote_class(int c){
  30.116 -    return in_class(c, "'\"");
  30.117 -}
  30.118 -
  30.119 -static inline int in_printable_class(int c){
  30.120 -    return ('A' <= c && c <= 'Z')
  30.121 -        || ('a' <= c && c <= 'z')
  30.122 -        || ('0' <= c && c <= '9')
  30.123 -        || in_class(c, "!$%&*+,-./:;<=>?@^_`{|}~");
  30.124 -}
  30.125 -
  30.126 -extern int is_decimal_number(const char *s, int n);
  30.127 -extern int is_hex_number(const char *s, int n);
  30.128 -extern int is_keyword(const char *s, const char *k);
  30.129 -extern int is_keychar(const char *s, char c);
  30.130 -
  30.131 -#endif /* !_XUTIL_LEXIS_H_ */
    31.1 --- a/tools/libxutil/socket_stream.c	Tue May 24 21:10:23 2005 +0000
    31.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    31.3 @@ -1,230 +0,0 @@
    31.4 -/*
    31.5 - * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    31.6 - *
    31.7 - * This library is free software; you can redistribute it and/or modify
    31.8 - * it under the terms of the GNU Lesser General Public License as published by
    31.9 - * the Free Software Foundation; either version 2.1 of the License, or
   31.10 - * (at your option) any later version.
   31.11 - *
   31.12 - * This library is distributed in the hope that it will be useful,
   31.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   31.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   31.15 - * GNU Lesser General Public License for more details.
   31.16 - *
   31.17 - * You should have received a copy of the GNU Lesser General Public License
   31.18 - * along with this library; if not, write to the Free Software
   31.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   31.20 - */
   31.21 -
   31.22 -/** @file
   31.23 - * An IOStream implementation using sockets.
   31.24 - */
   31.25 -#ifndef __KERNEL__
   31.26 -
   31.27 -#include <stdio.h>
   31.28 -#include <stdlib.h>
   31.29 -#include <string.h>
   31.30 -#include <unistd.h>
   31.31 -#include <errno.h>
   31.32 -#include "allocate.h"
   31.33 -#include "socket_stream.h"
   31.34 -
   31.35 -#define MODULE_NAME "sock"
   31.36 -#define DEBUG 0
   31.37 -//#undef DEBUG
   31.38 -#include "debug.h"
   31.39 -
   31.40 -static int socket_read(IOStream *s, void *buf, size_t n);
   31.41 -static int socket_write(IOStream *s, const void *buf, size_t n);
   31.42 -static int socket_error(IOStream *s);
   31.43 -static int socket_close(IOStream *s);
   31.44 -static void socket_free(IOStream *s);
   31.45 -static int socket_flush(IOStream *s);
   31.46 -
   31.47 -/** Methods used by a socket IOStream. */
   31.48 -static const IOMethods socket_methods = {
   31.49 -    read:  socket_read,
   31.50 -    write: socket_write,
   31.51 -    error: socket_error,
   31.52 -    close: socket_close,
   31.53 -    free:  socket_free,
   31.54 -    flush: socket_flush,
   31.55 -};
   31.56 -
   31.57 -/** Get the socket data.
   31.58 - * 
   31.59 - * @param io socket stream
   31.60 - * @return data
   31.61 - */
   31.62 -static inline SocketData * socket_data(IOStream *io){
   31.63 -    return (SocketData *)io->data;
   31.64 -}
   31.65 -
   31.66 -/** Test if a stream is a socket stream.
   31.67 - *
   31.68 - * @param io stream
   31.69 - * @return 0 if a socket stream, -EINVAL if not
   31.70 - */
   31.71 -int socket_stream_check(IOStream *io){
   31.72 -    return (io && io->methods == &socket_methods ? 0 : -EINVAL);
   31.73 -}
   31.74 -
   31.75 -/** Get the data for a socket stream.
   31.76 - *
   31.77 - * @param io stream
   31.78 - * @param data return value for the data
   31.79 - * @return 0 if a socket stream, -EINVAL if not
   31.80 - */
   31.81 -int socket_stream_data(IOStream *io, SocketData **data){
   31.82 -    int err = socket_stream_check(io);
   31.83 -    if(err){
   31.84 -        *data = NULL;
   31.85 -    } else {
   31.86 -        *data = socket_data(io);
   31.87 -    }
   31.88 -    return err;
   31.89 -}
   31.90 -
   31.91 -/** Set the destination address for a socket stream.
   31.92 - *
   31.93 - * @param io stream
   31.94 - * @param addr address
   31.95 - * @return 0 if a socket stream, -EINVAL if not
   31.96 - */
   31.97 -int socket_stream_set_addr(IOStream *io, struct sockaddr_in *addr){
   31.98 -    int err = 0;
   31.99 -    SocketData *data = NULL;
  31.100 -    err = socket_stream_data(io, &data);
  31.101 -    if(!err){
  31.102 -        data->daddr = *addr;
  31.103 -    }
  31.104 -    return err;
  31.105 -}
  31.106 -
  31.107 -/** Set the send flags for a socket stream.
  31.108 - *
  31.109 - * @param io stream
  31.110 - * @param flags flags
  31.111 - * @return 0 if a socket stream, -EINVAL if not
  31.112 - */
  31.113 -int socket_stream_set_flags(IOStream *io, int flags){
  31.114 -    int err = 0;
  31.115 -    SocketData *data = NULL;
  31.116 -    err = socket_stream_data(io, &data);
  31.117 -    if(!err){
  31.118 -        data->flags = flags;
  31.119 -    }
  31.120 -    return err;
  31.121 -}
  31.122 -
  31.123 -/** Write to the underlying socket using sendto.
  31.124 - *
  31.125 - * @param stream input
  31.126 - * @param buf where to put input
  31.127 - * @param n number of bytes to write
  31.128 - * @return number of bytes written
  31.129 - */
  31.130 -static int socket_write(IOStream *s, const void *buf, size_t n){
  31.131 -    SocketData *data = socket_data(s);
  31.132 -    struct sockaddr *daddr = (struct sockaddr *)&data->daddr;
  31.133 -    socklen_t daddr_n = sizeof(data->daddr);
  31.134 -    int k;
  31.135 -    dprintf("> sock=%d addr=%s:%d n=%d\n",
  31.136 -            data->fd, inet_ntoa(data->daddr.sin_addr), ntohs(data->daddr.sin_port), n);
  31.137 -    if(0){
  31.138 -        struct sockaddr_in self = {};
  31.139 -        socklen_t self_n;
  31.140 -        getsockname(data->fd, (struct sockaddr *)&self, &self_n);
  31.141 -        dprintf("> sockname sock=%d %s:%d\n",
  31.142 -                data->fd, inet_ntoa(self.sin_addr), ntohs(self.sin_port));
  31.143 -    }
  31.144 -    k = sendto(data->fd, buf, n, data->flags, daddr, daddr_n);
  31.145 -    dprintf("> sendto=%d\n", k);
  31.146 -    return k;
  31.147 -}
  31.148 -
  31.149 -/** Read from the underlying stream using recv();
  31.150 - *
  31.151 - * @param stream input
  31.152 - * @param buf where to put input
  31.153 - * @param n number of bytes to read
  31.154 - * @return number of bytes read
  31.155 - */
  31.156 -static int socket_read(IOStream *s, void *buf, size_t n){
  31.157 -    SocketData *data = socket_data(s);
  31.158 -    int k;
  31.159 -    struct sockaddr *saddr = (struct sockaddr *)&data->saddr;
  31.160 -    socklen_t saddr_n = sizeof(data->saddr);
  31.161 -    k = recvfrom(data->fd, buf, n, data->flags, saddr, &saddr_n);
  31.162 -    return k;
  31.163 -}
  31.164 -
  31.165 -/** Flush the socket (no-op).
  31.166 - *
  31.167 - * @param s socket stream
  31.168 - * @return 0 on success, error code otherwise
  31.169 - */
  31.170 -static int socket_flush(IOStream *s){
  31.171 -    return 0;
  31.172 -}
  31.173 -
  31.174 -/** Check if a socket stream has an error (no-op).
  31.175 - *
  31.176 - * @param s socket stream
  31.177 - * @return 1 if has an error, 0 otherwise
  31.178 - */
  31.179 -static int socket_error(IOStream *s){
  31.180 -    // Read SOL_SOCKET/SO_ERROR ?
  31.181 -    return 0;
  31.182 -}
  31.183 -
  31.184 -/** Close a socket stream.
  31.185 - *
  31.186 - * @param s socket stream to close
  31.187 - * @return result of the close
  31.188 - */
  31.189 -static int socket_close(IOStream *s){
  31.190 -    SocketData *data = socket_data(s);
  31.191 -    return close(data->fd);
  31.192 -}
  31.193 -
  31.194 -/** Free a socket stream.
  31.195 - *
  31.196 - * @param s socket stream
  31.197 - */
  31.198 -static void socket_free(IOStream *s){
  31.199 -    SocketData *data = socket_data(s);
  31.200 -    deallocate(data);
  31.201 -}
  31.202 -
  31.203 -/** Create an IOStream for a socket.
  31.204 - *
  31.205 - * @param fd socket to wtap
  31.206 - * @return new IOStream using fd for i/o
  31.207 - */
  31.208 -IOStream *socket_stream_new(int fd){
  31.209 -    int err = -ENOMEM;
  31.210 -    IOStream *io = NULL;
  31.211 -    SocketData *data = NULL;
  31.212 -
  31.213 -    io = ALLOCATE(IOStream);
  31.214 -    if(!io) goto exit;
  31.215 -    io->methods = &socket_methods;
  31.216 -    data = ALLOCATE(SocketData);
  31.217 -    if(!data) goto exit;
  31.218 -    io->data = data;
  31.219 -    data->fd = fd;
  31.220 -    data->buf_n = sizeof(data->buf);
  31.221 -    err = 0;
  31.222 -  exit:
  31.223 -    if(err){
  31.224 -        if(io){
  31.225 -            if(data) deallocate(data);
  31.226 -            deallocate(io);
  31.227 -            io = NULL;
  31.228 -        }
  31.229 -    }
  31.230 -    return io;
  31.231 -}
  31.232 -
  31.233 -#endif
    32.1 --- a/tools/libxutil/socket_stream.h	Tue May 24 21:10:23 2005 +0000
    32.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    32.3 @@ -1,53 +0,0 @@
    32.4 -/*
    32.5 - * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    32.6 - *
    32.7 - * This library is free software; you can redistribute it and/or modify
    32.8 - * it under the terms of the GNU Lesser General Public License as published by
    32.9 - * the Free Software Foundation; either version 2.1 of the License, or
   32.10 - * (at your option) any later version.
   32.11 - *
   32.12 - * This library is distributed in the hope that it will be useful,
   32.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   32.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   32.15 - * GNU Lesser General Public License for more details.
   32.16 - *
   32.17 - * You should have received a copy of the GNU Lesser General Public License
   32.18 - * along with this library; if not, write to the Free Software
   32.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   32.20 - */
   32.21 -
   32.22 -#ifndef _XEN_LIB_SOCKET_STREAM_H_
   32.23 -#define _XEN_LIB_SOCKET_STREAM_H_
   32.24 -
   32.25 -#ifndef __KERNEL__
   32.26 -#include "iostream.h"
   32.27 -#include <stdio.h>
   32.28 -
   32.29 -#include <sys/socket.h>
   32.30 -#include <netinet/in.h>
   32.31 -#include <arpa/inet.h>
   32.32 -
   32.33 -/** Data associated with a socket stream. */
   32.34 -typedef struct SocketData {
   32.35 -    /** The socket file descriptor. */
   32.36 -    int fd;
   32.37 -    /** Source address from last read (recvfrom). */
   32.38 -    struct sockaddr_in saddr;
   32.39 -    /** Destination address for writes (sendto). */
   32.40 -    struct sockaddr_in daddr;
   32.41 -    /** Write flags (sendto). */
   32.42 -    int flags;
   32.43 -    /** Buffer size. */
   32.44 -    int buf_n;
   32.45 -    /** Buffer for formatted printing. */
   32.46 -    char buf[1024];
   32.47 -} SocketData;
   32.48 -
   32.49 -extern IOStream *socket_stream_new(int fd);
   32.50 -extern int socket_stream_data(IOStream *io, SocketData **data);
   32.51 -extern int socket_stream_check(IOStream *io);
   32.52 -extern int socket_stream_set_addr(IOStream *io, struct sockaddr_in *addr);
   32.53 -extern int socket_stream_set_flags(IOStream *io, int flags);
   32.54 -
   32.55 -#endif
   32.56 -#endif /* !_XEN_LIB_SOCKET_STREAM_H_ */
    33.1 --- a/tools/libxutil/string_stream.c	Tue May 24 21:10:23 2005 +0000
    33.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    33.3 @@ -1,162 +0,0 @@
    33.4 -/*
    33.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    33.6 - *
    33.7 - * This library is free software; you can redistribute it and/or modify
    33.8 - * it under the terms of the GNU Lesser General Public License as published by
    33.9 - * the Free Software Foundation; either version 2.1 of the License, or
   33.10 - * (at your option) any later version.
   33.11 - *
   33.12 - * This library is distributed in the hope that it will be useful,
   33.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   33.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   33.15 - * GNU Lesser General Public License for more details.
   33.16 - *
   33.17 - * You should have received a copy of the GNU Lesser General Public License
   33.18 - * along with this library; if not, write to the Free Software
   33.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   33.20 - */
   33.21 -
   33.22 -/** @file
   33.23 - * IOStream subtype for input and output to strings.
   33.24 - * Usable from user or kernel code (with __KERNEL__ defined).
   33.25 - */
   33.26 -
   33.27 -#include "sys_string.h"
   33.28 -#include "string_stream.h"
   33.29 -#include "allocate.h"
   33.30 -
   33.31 -static int string_error(IOStream *io);
   33.32 -static int string_close(IOStream *io);
   33.33 -static void string_free(IOStream *io);
   33.34 -static int string_write(IOStream *io, const void *msg, size_t n);
   33.35 -static int string_read(IOStream *io, void *buf, size_t n);
   33.36 -
   33.37 -/** Methods for a string stream. */
   33.38 -static IOMethods string_methods = {
   33.39 -    read:  string_read,
   33.40 -    write: string_write,
   33.41 -    error: string_error,
   33.42 -    close: string_close,
   33.43 -    free:  string_free,
   33.44 -};
   33.45 -
   33.46 -/** Get the string stream state.
   33.47 - *
   33.48 - * @param io string stream
   33.49 - * @return state
   33.50 - */
   33.51 -static inline StringData *get_string_data(IOStream *io){
   33.52 -    return (StringData*)io->data;
   33.53 -}
   33.54 -
   33.55 -static int string_write(IOStream *io, const void *msg, size_t n){
   33.56 -    StringData *data = get_string_data(io);
   33.57 -    int k;
   33.58 -
   33.59 -    k = data->end - data->out;
   33.60 -    if(n > k) n = k;
   33.61 -    memcpy(data->out, msg, n);
   33.62 -    data->out += n;
   33.63 -    return n;
   33.64 -}
   33.65 -
   33.66 -static int string_read(IOStream *io, void *buf, size_t n){
   33.67 -    StringData *data = get_string_data(io);
   33.68 -    int k;
   33.69 -
   33.70 -    k = data->end - data->in;
   33.71 -    if(n > k) n = k;
   33.72 -    memcpy(buf, data->in, k);
   33.73 -    data->in += n;
   33.74 -    return n;
   33.75 -}
   33.76 -
   33.77 -/** Test if a string stream has an error.
   33.78 - *
   33.79 - * @param io string stream
   33.80 - * @return 0 if ok, error code otherwise
   33.81 - */
   33.82 -static int string_error(IOStream *io){
   33.83 -    StringData *data = get_string_data(io);
   33.84 -    return data->out == NULL;
   33.85 -}
   33.86 -
   33.87 -/** Close a string stream.
   33.88 - *
   33.89 - * @param io string stream
   33.90 - * @return 0
   33.91 - */
   33.92 -static int string_close(IOStream *io){
   33.93 -    StringData *data = get_string_data(io);
   33.94 -    data->in = NULL;
   33.95 -    data->out = NULL;
   33.96 -    return 0;
   33.97 -}
   33.98 -
   33.99 -/** Free a string stream.
  33.100 - * The stream state is freed, but the underlying string is not.
  33.101 - *
  33.102 - * @param io string stream
  33.103 - */
  33.104 -static void string_free(IOStream *io){
  33.105 -    StringData *data = get_string_data(io);
  33.106 -    memzero(data, sizeof(*data));
  33.107 -    deallocate(data);
  33.108 -}
  33.109 -
  33.110 -/** Get the methods to use for a string stream.
  33.111 - *
  33.112 - * @return methods
  33.113 - */
  33.114 -IOMethods *string_stream_get_methods(void){
  33.115 -    return &string_methods;
  33.116 -}
  33.117 -
  33.118 -/** Initialise a string stream, usually from static data.
  33.119 - * If the stream and StringData should be freed when
  33.120 - * the stream is closed, unset io->nofree.
  33.121 - * The string is not freed on close.
  33.122 - *
  33.123 - * @param io address of IOStream to fill in
  33.124 - * @param data address of StringData to fill in
  33.125 - * @param s string to use
  33.126 - * @param n length of the string
  33.127 - */
  33.128 -void string_stream_init(IOStream *io, StringData *data, char *s, int n){
  33.129 -    if(data && io){
  33.130 -        memzero(data, sizeof(*data));
  33.131 -        data->string = (char*)s;
  33.132 -        data->in = data->string;
  33.133 -        data->out = data->string;
  33.134 -        data->size = n;
  33.135 -        data->end = data->string + n;
  33.136 -        memzero(io, sizeof(*io));
  33.137 -        io->methods = &string_methods;
  33.138 -        io->data = data;
  33.139 -        io->nofree = 1;
  33.140 -    }
  33.141 -}
  33.142 -
  33.143 -/** Allocate and initialise a string stream.
  33.144 - * The stream is freed on close, but the string is not.
  33.145 - *
  33.146 - * @param s string to use
  33.147 - * @param n length of the string
  33.148 - * @return new stream (free using IOStream_free)
  33.149 - */
  33.150 -IOStream *string_stream_new(char *s, int n){
  33.151 -    int ok = 0;
  33.152 -    StringData *data = ALLOCATE(StringData);
  33.153 -    IOStream *io = ALLOCATE(IOStream);
  33.154 -    if(data && io){
  33.155 -        ok = 1;
  33.156 -        string_stream_init(io, data, s, n);
  33.157 -        io->nofree = 0;
  33.158 -    }
  33.159 -    if(!ok){
  33.160 -        deallocate(data);
  33.161 -        deallocate(io);
  33.162 -        io = NULL;
  33.163 -    }
  33.164 -    return io;
  33.165 -}
    34.1 --- a/tools/libxutil/string_stream.h	Tue May 24 21:10:23 2005 +0000
    34.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    34.3 @@ -1,45 +0,0 @@
    34.4 -/*
    34.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    34.6 - *
    34.7 - * This library is free software; you can redistribute it and/or modify
    34.8 - * it under the terms of the GNU Lesser General Public License as published by
    34.9 - * the Free Software Foundation; either version 2.1 of the License, or
   34.10 - * (at your option) any later version.
   34.11 - *
   34.12 - * This library is distributed in the hope that it will be useful,
   34.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   34.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   34.15 - * GNU Lesser General Public License for more details.
   34.16 - *
   34.17 - * You should have received a copy of the GNU Lesser General Public License
   34.18 - * along with this library; if not, write to the Free Software
   34.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   34.20 - */
   34.21 -
   34.22 -#ifndef _XUTIL_STRING_STREAM_H_
   34.23 -#define _XUTIL_STRING_STREAM_H_
   34.24 -
   34.25 -#include "iostream.h"
   34.26 -
   34.27 -/** Internal state for a string stream.
   34.28 - * Exposed here so that string streams can be statically created, using
   34.29 - * string_stream_init().
   34.30 - */
   34.31 -typedef struct {
   34.32 -    /** The string used for input and ouput. */
   34.33 -    char *string;
   34.34 -    /** Output pointer. */
   34.35 -    char *out;
   34.36 -    /** Input pointer. */
   34.37 -    char *in;
   34.38 -    /** Length of string. */
   34.39 -    int size;
   34.40 -    /** End marker. */
   34.41 -    char *end;
   34.42 -} StringData;
   34.43 -
   34.44 -extern IOMethods *string_stream_get_methods(void);
   34.45 -extern IOStream *string_stream_new(char *s, int n);
   34.46 -extern void string_stream_init(IOStream *stream, StringData *data, char *s, int n);
   34.47 -
   34.48 -#endif /* !_XUTIL_STRING_STREAM_H_ */
    35.1 --- a/tools/libxutil/sxpr.c	Tue May 24 21:10:23 2005 +0000
    35.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    35.3 @@ -1,1230 +0,0 @@
    35.4 -/*
    35.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    35.6 - *
    35.7 - * This library is free software; you can redistribute it and/or modify
    35.8 - * it under the terms of the GNU Lesser General Public License as
    35.9 - * published by the Free Software Foundation; either version 2.1 of the
   35.10 - * License, or  (at your option) any later version. This library is 
   35.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   35.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   35.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   35.14 - * See the GNU Lesser General Public License for more details.
   35.15 - *
   35.16 - * You should have received a copy of the GNU Lesser General Public License
   35.17 - * along with this library; if not, write to the Free Software Foundation,
   35.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   35.19 - */
   35.20 -
   35.21 -#include <stdarg.h>
   35.22 -#include "sys_string.h"
   35.23 -#include "lexis.h"
   35.24 -#include "sys_net.h"
   35.25 -#include "hash_table.h"
   35.26 -#include "sxpr.h"
   35.27 -
   35.28 -#ifdef __KERNEL__
   35.29 -#include <linux/errno.h>
   35.30 -#else
   35.31 -#include <errno.h>
   35.32 -#endif
   35.33 -
   35.34 -#ifdef __KERNEL__
   35.35 -#include <linux/random.h>
   35.36 -
   35.37 -int rand(void){
   35.38 -    int v;
   35.39 -    get_random_bytes(&v, sizeof(v));
   35.40 -    return v;
   35.41 -}
   35.42 -
   35.43 -#else
   35.44 -#include <stdlib.h>
   35.45 -#endif
   35.46 -
   35.47 -#undef free
   35.48 -
   35.49 -/** @file
   35.50 - * General representation of sxprs.
   35.51 - * Includes print, equal, and free functions for the sxpr types.
   35.52 - *
   35.53 - * Zero memory containing an Sxpr will have the value ONONE - this is intentional.
   35.54 - * When a function returning an sxpr cannot allocate memory we return ONOMEM.
   35.55 - *
   35.56 - */
   35.57 -
   35.58 -static int atom_print(IOStream *io, Sxpr obj, unsigned flags);
   35.59 -static int atom_equal(Sxpr x, Sxpr y);
   35.60 -static void atom_free(Sxpr obj);
   35.61 -static Sxpr atom_copy(Sxpr obj);
   35.62 -
   35.63 -static int string_print(IOStream *io, Sxpr obj, unsigned flags);
   35.64 -static int string_equal(Sxpr x, Sxpr y);
   35.65 -static void string_free(Sxpr obj);
   35.66 -static Sxpr string_copy(Sxpr obj);
   35.67 -
   35.68 -static int cons_print(IOStream *io, Sxpr obj, unsigned flags);
   35.69 -static int cons_equal(Sxpr x, Sxpr y);
   35.70 -static void cons_free(Sxpr obj);
   35.71 -static Sxpr cons_copy(Sxpr obj);
   35.72 -
   35.73 -static int null_print(IOStream *io, Sxpr obj, unsigned flags);
   35.74 -static int none_print(IOStream *io, Sxpr obj, unsigned flags);
   35.75 -static int int_print(IOStream *io, Sxpr obj, unsigned flags);
   35.76 -static int bool_print(IOStream *io, Sxpr obj, unsigned flags);
   35.77 -static int err_print(IOStream *io, Sxpr obj, unsigned flags);
   35.78 -static int nomem_print(IOStream *io, Sxpr obj, unsigned flags);
   35.79 -
   35.80 -/** Type definitions. */
   35.81 -static SxprType types[1024] = {
   35.82 -    [T_NONE]     { .type=    T_NONE,     .name= "none",       .print= none_print      },
   35.83 -    [T_NULL]     { .type=    T_NULL,     .name= "null",       .print= null_print      },
   35.84 -    [T_UINT]     { .type=    T_UINT,     .name= "int",        .print= int_print,      },
   35.85 -    [T_BOOL]     { .type=    T_BOOL,     .name= "bool",       .print= bool_print,     },
   35.86 -    [T_ERR]      { .type=    T_ERR,      .name= "err",        .print= err_print,      },
   35.87 -    [T_NOMEM]    { .type=    T_ERR,      .name= "nomem",      .print= nomem_print,    },
   35.88 -    [T_ATOM]     { .type=    T_ATOM,     .name= "atom",       .print= atom_print,
   35.89 -                   .pointer= TRUE,
   35.90 -                   .free=    atom_free,
   35.91 -                   .equal=   atom_equal,
   35.92 -                   .copy=    atom_copy,
   35.93 -                 },
   35.94 -    [T_STRING]   { .type=    T_STRING,   .name= "string",     .print= string_print,
   35.95 -                   .pointer= TRUE,
   35.96 -                   .free=    string_free,
   35.97 -                   .equal=   string_equal,
   35.98 -                   .copy=    string_copy,
   35.99 -                 },
  35.100 -    [T_CONS]     { .type=    T_CONS,     .name= "cons",       .print= cons_print,
  35.101 -                   .pointer= TRUE,
  35.102 -                   .free=    cons_free,
  35.103 -                   .equal=   cons_equal,
  35.104 -                   .copy=    cons_copy,
  35.105 -                 },
  35.106 -};
  35.107 -
  35.108 -/** Number of entries in the types array. */
  35.109 -static int type_sup = sizeof(types)/sizeof(types[0]);
  35.110 -
  35.111 -/** Define a type.
  35.112 - * The tydef must have a non-zero type code.
  35.113 - * It is an error if the type code is out of range or already defined.
  35.114 - *
  35.115 - * @param tydef type definition
  35.116 - * @return 0 on success, error code otherwise
  35.117 - */
  35.118 -int def_sxpr_type(SxprType *tydef){
  35.119 -    int err = 0;
  35.120 -    int ty = tydef->type;
  35.121 -    if(ty < 0 || ty >= type_sup){
  35.122 -        err = -EINVAL;
  35.123 -        goto exit;
  35.124 -    }
  35.125 -    if(types[ty].type){
  35.126 -        err = -EEXIST;
  35.127 -        goto exit;
  35.128 -    }
  35.129 -    types[ty] = *tydef;
  35.130 -  exit:
  35.131 -    return err;
  35.132 -    
  35.133 -}
  35.134 -
  35.135 -/** Get the type definition for a given type code.
  35.136 - *
  35.137 - * @param ty type code
  35.138 - * @return type definition or null
  35.139 - */
  35.140 -SxprType *get_sxpr_type(int ty){
  35.141 -    if(0 <= ty && ty < type_sup){
  35.142 -        return types+ty;
  35.143 -    }
  35.144 -    return NULL;
  35.145 -}
  35.146 -
  35.147 -/** The default print function.
  35.148 - *
  35.149 - * @param io stream to print to
  35.150 - * @param x sxpr to print
  35.151 - * @param flags print flags
  35.152 - * @return number of bytes written on success
  35.153 - */
  35.154 -int default_print(IOStream *io, Sxpr x, unsigned flags){
  35.155 -    return IOStream_print(io, "#<%u %lu>\n", get_type(x), get_ul(x));
  35.156 -}
  35.157 -
  35.158 -/** The default equal function.
  35.159 - * Uses eq().
  35.160 - *
  35.161 - * @param x sxpr to compare
  35.162 - * @param y sxpr to compare
  35.163 - * @return 1 if equal, 0 otherwise
  35.164 - */
  35.165 -int default_equal(Sxpr x, Sxpr y){
  35.166 -    return eq(x, y);
  35.167 -}
  35.168 -
  35.169 -/** General sxpr print function.
  35.170 - * Prints an sxpr on a stream using the print function for the sxpr type.
  35.171 - * Printing is controlled by flags from the PrintFlags enum.
  35.172 - * If PRINT_TYPE is in the flags the sxpr type is printed before the sxpr
  35.173 - * (for debugging).
  35.174 - *
  35.175 - * @param io stream to print to
  35.176 - * @param x sxpr to print
  35.177 - * @param flags print flags
  35.178 - * @return number of bytes written
  35.179 - */
  35.180 -int objprint(IOStream *io, Sxpr x, unsigned flags){
  35.181 -    SxprType *def = get_sxpr_type(get_type(x));
  35.182 -    ObjPrintFn *print_fn = (def && def->print ? def->print : default_print);
  35.183 -    int k = 0;
  35.184 -    if(!io) return k;
  35.185 -    if(flags & PRINT_TYPE){
  35.186 -        k += IOStream_print(io, "%s:", def->name);
  35.187 -    }
  35.188 -    if(def->pointer && (flags & PRINT_ADDR)){
  35.189 -        k += IOStream_print(io, "<%p>", get_ptr(x));
  35.190 -    }
  35.191 -    k += print_fn(io, x, flags);
  35.192 -    return k;
  35.193 -}
  35.194 -
  35.195 -Sxpr objcopy(Sxpr x){
  35.196 -    SxprType *def = get_sxpr_type(get_type(x));
  35.197 -    ObjCopyFn *copy_fn = (def ? def->copy : NULL);
  35.198 -    Sxpr v;
  35.199 -    if(copy_fn){
  35.200 -        v = copy_fn(x);
  35.201 -    } else if(def->pointer){
  35.202 -        v = ONOMEM;
  35.203 -    } else {
  35.204 -        v = x;
  35.205 -    }
  35.206 -    return v;
  35.207 -}
  35.208 -
  35.209 -/** General sxpr free function.
  35.210 - * Frees an sxpr using the free function for its type.
  35.211 - * Free functions must recursively free any subsxprs.
  35.212 - * If no function is defined then the default is to
  35.213 - * free sxprs whose type has pointer true.
  35.214 - * Sxprs must not be used after freeing.
  35.215 - *
  35.216 - * @param x sxpr to free
  35.217 - */
  35.218 -void objfree(Sxpr x){
  35.219 -    SxprType *def = get_sxpr_type(get_type(x));
  35.220 -
  35.221 -    if(def){
  35.222 -        if(def->free){
  35.223 -            def->free(x);
  35.224 -        } else if (def->pointer){
  35.225 -            hfree(x);
  35.226 -        }
  35.227 -    }
  35.228 -}
  35.229 -
  35.230 -/** General sxpr equality function.
  35.231 - * Compares x and y using the equal function for x.
  35.232 - * Uses default_equal() if x has no equal function.
  35.233 - *
  35.234 - * @param x sxpr to compare
  35.235 - * @param y sxpr to compare
  35.236 - * @return 1 if equal, 0 otherwise
  35.237 - */
  35.238 -int objequal(Sxpr x, Sxpr y){
  35.239 -    SxprType *def = get_sxpr_type(get_type(x));
  35.240 -    ObjEqualFn *equal_fn = (def && def->equal ? def->equal : default_equal);
  35.241 -    return equal_fn(x, y);
  35.242 -}
  35.243 -
  35.244 -/** Search for a key in an alist.
  35.245 - * An alist is a list of conses, where the cars
  35.246 - * of the conses are the keys. Compares keys using equality.
  35.247 - *
  35.248 - * @param k key
  35.249 - * @param l alist to search
  35.250 - * @return first element of l with car k, or ONULL
  35.251 - */
  35.252 -Sxpr assoc(Sxpr k, Sxpr l){
  35.253 -    for( ; CONSP(l) ; l = CDR(l)){
  35.254 -        Sxpr x = CAR(l);
  35.255 -        if(CONSP(x) && objequal(k, CAR(x))){
  35.256 -            return x;   
  35.257 -        }
  35.258 -    }
  35.259 -    return ONULL;
  35.260 -}
  35.261 -
  35.262 -/** Search for a key in an alist.
  35.263 - * An alist is a list of conses, where the cars
  35.264 - * of the conses are the keys. Compares keys using eq.
  35.265 - *
  35.266 - * @param k key
  35.267 - * @param l alist to search
  35.268 - * @return first element of l with car k, or ONULL
  35.269 - */
  35.270 -Sxpr assocq(Sxpr k, Sxpr l){
  35.271 -    for( ; CONSP(l); l = CDR(l)){
  35.272 -        Sxpr x = CAR(l);
  35.273 -        if(CONSP(x) && eq(k, CAR(x))){
  35.274 -            return x;
  35.275 -        }
  35.276 -    }
  35.277 -    return ONULL;
  35.278 -}
  35.279 -
  35.280 -/** Add a new key and value to an alist.
  35.281 - *
  35.282 - * @param k key
  35.283 - * @param l value
  35.284 - * @param l alist
  35.285 - * @return l with the new cell added to the front
  35.286 - */
  35.287 -Sxpr acons(Sxpr k, Sxpr v, Sxpr l){
  35.288 -    Sxpr x, y;
  35.289 -    x = cons_new(k, v);
  35.290 -    if(NOMEMP(x)) return x;
  35.291 -    y = cons_new(x, l);
  35.292 -    if(NOMEMP(y)) cons_free_cells(x);
  35.293 -    return y;
  35.294 -}
  35.295 -
  35.296 -/** Test if a list contains an element.
  35.297 - * Uses sxpr equality.
  35.298 - *
  35.299 - * @param l list
  35.300 - * @param x element to look for
  35.301 - * @return a tail of l with x as car, or ONULL
  35.302 - */
  35.303 -Sxpr cons_member(Sxpr l, Sxpr x){
  35.304 -    for( ; CONSP(l) && !eq(x, CAR(l)); l = CDR(l)){}
  35.305 -    return l;
  35.306 -}
  35.307 -
  35.308 -/** Test if a list contains an element satisfying a test.
  35.309 - * The test function is called with v and an element of the list.
  35.310 - *
  35.311 - * @param l list
  35.312 - * @param test_fn test function to use
  35.313 - * @param v value for first argument to the test
  35.314 - * @return a tail of l with car satisfying the test, or 0
  35.315 - */
  35.316 -Sxpr cons_member_if(Sxpr l, ObjEqualFn *test_fn, Sxpr v){
  35.317 -    for( ; CONSP(l) && !test_fn(v, CAR(l)); l = CDR(l)){ }
  35.318 -    return l;
  35.319 -}
  35.320 -
  35.321 -/** Test if the elements of list 't' are a subset of the elements
  35.322 - * of list 's'. Element order is not significant.
  35.323 - *
  35.324 - * @param s element list to check subset of
  35.325 - * @param t element list to check if is a subset
  35.326 - * @return 1 if is a subset, 0 otherwise
  35.327 - */
  35.328 -int cons_subset(Sxpr s, Sxpr t){
  35.329 -    for( ; CONSP(t); t = CDR(t)){
  35.330 -        if(!CONSP(cons_member(s, CAR(t)))){
  35.331 -            return 0;
  35.332 -        }
  35.333 -    }
  35.334 -    return 1;
  35.335 -}
  35.336 -
  35.337 -/** Test if two lists have equal sets of elements.
  35.338 - * Element order is not significant.
  35.339 - *
  35.340 - * @param s list to check
  35.341 - * @param t list to check
  35.342 - * @return 1 if equal, 0 otherwise
  35.343 - */
  35.344 -int cons_set_equal(Sxpr s, Sxpr t){
  35.345 -    return cons_subset(s, t) && cons_subset(t, s);
  35.346 -}
  35.347 -
  35.348 -#ifdef USE_GC
  35.349 -/*============================================================================*/
  35.350 -/* The functions inside this ifdef are only safe if GC is used.
  35.351 - * Otherwise they may leak memory.
  35.352 - */
  35.353 -
  35.354 -/** Remove an element from a list (GC only).
  35.355 - * Uses sxpr equality and removes all instances, even
  35.356 - * if there are more than one.
  35.357 - *
  35.358 - * @param l list to remove elements from
  35.359 - * @param x element to remove
  35.360 - * @return modified input list
  35.361 - */
  35.362 -Sxpr cons_remove(Sxpr l, Sxpr x){
  35.363 -    return cons_remove_if(l, eq, x);
  35.364 -}
  35.365 -
  35.366 -/** Remove elements satisfying a test (GC only).
  35.367 - * The test function is called with v and an element of the set.
  35.368 - *
  35.369 - * @param l list to remove elements from
  35.370 - * @param test_fn function to use to decide if an element should be removed
  35.371 - * @return modified input list
  35.372 - */
  35.373 -Sxpr cons_remove_if(Sxpr l, ObjEqualFn *test_fn, Sxpr v){
  35.374 -    Sxpr prev = ONULL, elt, next;
  35.375 -
  35.376 -    for(elt = l; CONSP(elt); elt = next){
  35.377 -        next = CDR(elt);
  35.378 -        if(test_fn(v, CAR(elt))){
  35.379 -            if(NULLP(prev)){
  35.380 -                l = next;
  35.381 -            } else {
  35.382 -                CDR(prev) = next;
  35.383 -            }
  35.384 -        }
  35.385 -    }
  35.386 -    return l;
  35.387 -}
  35.388 -
  35.389 -/** Set the value for a key in an alist (GC only).
  35.390 - * If the key is present, changes the value, otherwise
  35.391 - * adds a new cell.
  35.392 - *
  35.393 - * @param k key
  35.394 - * @param v value
  35.395 - * @param l alist
  35.396 - * @return modified or extended list
  35.397 - */
  35.398 -Sxpr setf(Sxpr k, Sxpr v, Sxpr l){
  35.399 -    Sxpr e = assoc(k, l);
  35.400 -    if(NULLP(e)){
  35.401 -        l = acons(k, v, l);
  35.402 -    } else {
  35.403 -        CAR(CDR(e)) = v;
  35.404 -    }
  35.405 -    return l;
  35.406 -}
  35.407 -/*============================================================================*/
  35.408 -#endif /* USE_GC */
  35.409 -
  35.410 -/** Create a new atom with the given name.
  35.411 - * Makes an integer sxpr if the name can be parsed as an int.
  35.412 - *
  35.413 - * @param name the name
  35.414 - * @return new atom
  35.415 - */
  35.416 -Sxpr atom_new(char *name){
  35.417 -    Sxpr n, obj = ONOMEM;
  35.418 -    long v;
  35.419 -
  35.420 -    if(convert_atol(name, &v) == 0){
  35.421 -        obj = OINT(v);
  35.422 -    } else {
  35.423 -        n = string_new(name);
  35.424 -        if(NOMEMP(n)) goto exit;
  35.425 -        obj = HALLOC(ObjAtom, T_ATOM);
  35.426 -        if(NOMEMP(obj)){
  35.427 -            string_free(n);
  35.428 -            goto exit;
  35.429 -        }
  35.430 -        OBJ_ATOM(obj)->name = n;
  35.431 -    }
  35.432 -  exit:
  35.433 -    return obj;
  35.434 -}
  35.435 -
  35.436 -/** Free an atom.
  35.437 - *
  35.438 - * @param obj to free
  35.439 - */
  35.440 -void atom_free(Sxpr obj){
  35.441 -    // Interned atoms are shared, so do not free.
  35.442 -    if(OBJ_ATOM(obj)->interned) return;
  35.443 -    objfree(OBJ_ATOM(obj)->name);
  35.444 -    hfree(obj);
  35.445 -}
  35.446 -
  35.447 -/** Copy an atom.
  35.448 - *
  35.449 - * @param obj to copy
  35.450 - */
  35.451 -Sxpr atom_copy(Sxpr obj){
  35.452 -    Sxpr v;
  35.453 -    if(OBJ_ATOM(obj)->interned){
  35.454 -        v = obj;
  35.455 -    } else {
  35.456 -        v = atom_new(atom_name(obj));
  35.457 -    }
  35.458 -    return v;
  35.459 -}
  35.460 -
  35.461 -/** Print an atom. Prints the atom name.
  35.462 - *
  35.463 - * @param io stream to print to
  35.464 - * @param obj to print
  35.465 - * @param flags print flags
  35.466 - * @return number of bytes printed
  35.467 - */
  35.468 -int atom_print(IOStream *io, Sxpr obj, unsigned flags){
  35.469 -    return objprint(io, OBJ_ATOM(obj)->name, flags);
  35.470 -}
  35.471 -
  35.472 -/** Atom equality.
  35.473 - *
  35.474 - * @param x to compare
  35.475 - * @param y to compare
  35.476 - * @return 1 if equal, 0 otherwise
  35.477 - */
  35.478 -int atom_equal(Sxpr x, Sxpr y){
  35.479 -    int ok;
  35.480 -    ok = eq(x, y);
  35.481 -    if(ok) goto exit;
  35.482 -    ok = ATOMP(y) && string_equal(OBJ_ATOM(x)->name, OBJ_ATOM(y)->name);
  35.483 -    if(ok) goto exit;
  35.484 -    ok = STRINGP(y) && string_equal(OBJ_ATOM(x)->name, y);
  35.485 -  exit:
  35.486 -    return ok;
  35.487 -}
  35.488 -
  35.489 -/** Get the name of an atom.
  35.490 - *
  35.491 - * @param obj atom
  35.492 - * @return name
  35.493 - */
  35.494 -char * atom_name(Sxpr obj){
  35.495 -    return string_string(OBJ_ATOM(obj)->name);
  35.496 -}
  35.497 -
  35.498 -int atom_length(Sxpr obj){
  35.499 -    return string_length(OBJ_ATOM(obj)->name);
  35.500 -}
  35.501 -
  35.502 -/** Get the C string from a string sxpr.
  35.503 - *
  35.504 - * @param obj string sxpr
  35.505 - * @return string
  35.506 - */
  35.507 -char * string_string(Sxpr obj){
  35.508 -    return OBJ_STRING(obj)->data;
  35.509 -}
  35.510 -
  35.511 -/** Get the length of a string.
  35.512 - *
  35.513 - * @param obj string
  35.514 - * @return length
  35.515 - */
  35.516 -int string_length(Sxpr obj){
  35.517 -    return OBJ_STRING(obj)->len;
  35.518 -}
  35.519 -
  35.520 -/** Create a new string. The input string is copied,
  35.521 - * and must be null-terminated.
  35.522 - *
  35.523 - * @param s characters to put in the string
  35.524 - * @return new sxpr
  35.525 - */
  35.526 -Sxpr string_new(char *s){
  35.527 -    int n = (s ? strlen(s) : 0);
  35.528 -    return string_new_n(s, n);
  35.529 -}
  35.530 -
  35.531 -/** Create a new string. The input string is copied,
  35.532 - * and need not be null-terminated.
  35.533 - *
  35.534 - * @param s characters to put in the string (may be null)
  35.535 - * @param n string length
  35.536 - * @return new sxpr
  35.537 - */
  35.538 -Sxpr string_new_n(char *s, int n){
  35.539 -    Sxpr obj;
  35.540 -    obj = halloc(sizeof(ObjString) + n + 1, T_STRING);
  35.541 -    if(!NOMEMP(obj)){
  35.542 -        char *str = OBJ_STRING(obj)->data;
  35.543 -        OBJ_STRING(obj)->len = n;
  35.544 -        if(s){
  35.545 -            memcpy(str, s, n);
  35.546 -            str[n] = '\0';
  35.547 -        } else {
  35.548 -            memset(str, 0, n + 1);
  35.549 -        }
  35.550 -    }
  35.551 -    return obj;
  35.552 -}
  35.553 -
  35.554 -/** Free a string.
  35.555 - *
  35.556 - * @param obj to free
  35.557 - */
  35.558 -void string_free(Sxpr obj){
  35.559 -    hfree(obj);
  35.560 -}
  35.561 -
  35.562 -/** Copy a string.
  35.563 - *
  35.564 - * @param obj to copy
  35.565 - */
  35.566 -Sxpr string_copy(Sxpr obj){
  35.567 -    return string_new_n(string_string(obj), string_length(obj));
  35.568 -}
  35.569 -
  35.570 -/** Determine if a string needs escapes when printed
  35.571 - * using the given flags.
  35.572 - *
  35.573 - * @param str string to check
  35.574 - * @param n string length
  35.575 - * @param flags print flags
  35.576 - * @return 1 if needs escapes, 0 otherwise
  35.577 - */
  35.578 -int needs_escapes(char *str, int n, unsigned flags){
  35.579 -    char *c;
  35.580 -    int i;
  35.581 -    int val = 0;
  35.582 -
  35.583 -    if(str){
  35.584 -        for(i=0, c=str; i<n; i++, c++){
  35.585 -            if(in_alpha_class(*c)) continue;
  35.586 -            if(in_decimal_digit_class(*c)) continue;
  35.587 -            if(in_class(*c, "/._+:@~-")) continue;
  35.588 -            val = 1;
  35.589 -            break;
  35.590 -        }
  35.591 -    }
  35.592 -    return val;
  35.593 -}
  35.594 -
  35.595 -char randchar(void){
  35.596 -    int r;
  35.597 -    char c;
  35.598 -    for( ; ; ){
  35.599 -        r = rand();
  35.600 -        c = (r >> 16) & 0xff;
  35.601 -        if('a' <= c && c <= 'z') break;
  35.602 -    }
  35.603 -    return c;
  35.604 -}
  35.605 -
  35.606 -int string_contains(char *s, int s_n, char *k, int k_n){
  35.607 -    int i, n = s_n - k_n;
  35.608 -    for(i=0; i < n; i++){
  35.609 -        if(!memcmp(s+i, k, k_n)) return 1;
  35.610 -    }
  35.611 -    return 0;
  35.612 -}
  35.613 -
  35.614 -int string_delim(char *s, int s_n, char *d, int d_n){
  35.615 -    int i;
  35.616 -    if(d_n < 4) return -1;
  35.617 -    memset(d, 0, d_n+1);
  35.618 -    for(i=0; i<3; i++){
  35.619 -        d[i] = randchar();
  35.620 -    }
  35.621 -    for( ; i < d_n; i++){
  35.622 -        if(!string_contains(s, s_n, d, i)){
  35.623 -            return i;
  35.624 -        }
  35.625 -        d[i] = randchar();
  35.626 -    }
  35.627 -    return -1;
  35.628 -}
  35.629 -
  35.630 -/** Print the bytes in a string as-is.
  35.631 - *
  35.632 - * @param io stream
  35.633 - * @param str string
  35.634 - * @param n length
  35.635 - * @return bytes written or error code
  35.636 - */
  35.637 -int _string_print_raw(IOStream *io, char *str, int n){
  35.638 -    int k = 0;
  35.639 -    k = IOStream_write(io, str, n);
  35.640 -    return k;
  35.641 -}
  35.642 -
  35.643 -/** Print a string in counted data format.
  35.644 - *
  35.645 - * @param io stream
  35.646 - * @param str string
  35.647 - * @param n length
  35.648 - * @return bytes written or error code
  35.649 - */
  35.650 -int _string_print_counted(IOStream *io, char *str, int n){
  35.651 -    int k = 0;
  35.652 -    k += IOStream_print(io, "%c%c%d%c",
  35.653 -                        c_data_open, c_data_count, n, c_data_count);
  35.654 -    k += IOStream_write(io, str, n);
  35.655 -    return k;
  35.656 -}
  35.657 -  
  35.658 -/** Print a string in quoted data format.
  35.659 - *
  35.660 - * @param io stream
  35.661 - * @param str string
  35.662 - * @param n length
  35.663 - * @return bytes written or error code
  35.664 - */
  35.665 -int _string_print_quoted(IOStream *io, char *str, int n){
  35.666 -    int k = 0;
  35.667 -    char d[10];
  35.668 -    int d_n;
  35.669 -    d_n = string_delim(str, n, d, sizeof(d) - 1);
  35.670 -    k += IOStream_print(io, "%c%c%s%c",
  35.671 -                        c_data_open, c_data_quote, d, c_data_quote);
  35.672 -    k += IOStream_write(io, str, n);
  35.673 -    k += IOStream_print(io, "%c%s%c", c_data_quote, d, c_data_quote);
  35.674 -    return k;
  35.675 -}
  35.676 -
  35.677 -/** Print a string as a quoted string.
  35.678 - *
  35.679 - * @param io stream
  35.680 - * @param str string
  35.681 - * @param n length
  35.682 - * @return bytes written or error code
  35.683 - */
  35.684 -int _string_print_string(IOStream *io, char *str, int n){
  35.685 -    int k = 0;
  35.686 -    
  35.687 -    k += IOStream_print(io, "\"");
  35.688 -    if(str){
  35.689 -        char *s, *t;
  35.690 -        for(s = str, t = str + n; s < t; s++){
  35.691 -            if(*s < ' ' || *s >= 127 ){
  35.692 -                switch(*s){
  35.693 -                case '\a': k += IOStream_print(io, "\\a");  break;
  35.694 -                case '\b': k += IOStream_print(io, "\\b");  break;
  35.695 -                case '\f': k += IOStream_print(io, "\\f");  break;
  35.696 -                case '\n': k += IOStream_print(io, "\\n");  break;
  35.697 -                case '\r': k += IOStream_print(io, "\\r");  break;
  35.698 -                case '\t': k += IOStream_print(io, "\\t");  break;
  35.699 -                case '\v': k += IOStream_print(io, "\\v");  break;
  35.700 -                default:
  35.701 -                    // Octal escape;
  35.702 -                    k += IOStream_print(io, "\\%o", *s);
  35.703 -                    break;
  35.704 -                }
  35.705 -            } else if(*s == c_double_quote ||
  35.706 -                      *s == c_single_quote ||
  35.707 -                      *s == c_escape){
  35.708 -                k += IOStream_print(io, "\\%c", *s);
  35.709 -            } else {
  35.710 -                k+= IOStream_print(io, "%c", *s);
  35.711 -            }
  35.712 -        }
  35.713 -    }
  35.714 -    k += IOStream_print(io, "\"");
  35.715 -    return k;
  35.716 -}
  35.717 -
  35.718 -/** Print a string to a stream, with escapes if necessary.
  35.719 - *
  35.720 - * @param io stream to print to
  35.721 - * @param str string
  35.722 - * @param n string length
  35.723 - * @param flags print flags
  35.724 - * @return number of bytes written
  35.725 - */
  35.726 -int _string_print(IOStream *io, char *str, int n, unsigned flags){
  35.727 -    int k = 0;
  35.728 -    if((flags & PRINT_COUNTED)){
  35.729 -        k = _string_print_counted(io, str, n);
  35.730 -    } else if((flags & PRINT_RAW) || !needs_escapes(str, n, flags)){
  35.731 -        k = _string_print_raw(io, str, n);
  35.732 -    } else if(n > 50){
  35.733 -        k = _string_print_quoted(io, str, n);
  35.734 -    } else {
  35.735 -        k = _string_print_string(io, str, n);
  35.736 -    }
  35.737 -    return k;
  35.738 -}
  35.739 -
  35.740 -/** Print a string to a stream, with escapes if necessary.
  35.741 - *
  35.742 - * @param io stream to print to
  35.743 - * @param obj string
  35.744 - * @param flags print flags
  35.745 - * @return number of bytes written
  35.746 - */
  35.747 -int string_print(IOStream *io, Sxpr obj, unsigned flags){
  35.748 -    return _string_print(io,
  35.749 -                         OBJ_STRING(obj)->data,
  35.750 -                         OBJ_STRING(obj)->len,
  35.751 -                         flags);
  35.752 -}
  35.753 -
  35.754 -int string_eq(char *s, int s_n, char *t, int t_n){
  35.755 -    return (s_n == t_n) && (memcmp(s, t, s_n) == 0);
  35.756 -}
  35.757 -
  35.758 -/** Compare an sxpr with a string for equality.
  35.759 - *
  35.760 - * @param x string to compare with
  35.761 - * @param y sxpr to compare
  35.762 - * @return 1 if equal, 0 otherwise
  35.763 - */
  35.764 -int string_equal(Sxpr x, Sxpr y){
  35.765 -    int ok = 0;
  35.766 -    ok = eq(x,y);
  35.767 -    if(ok) goto exit;
  35.768 -    ok = has_type(y, T_STRING) &&
  35.769 -        string_eq(OBJ_STRING(x)->data, OBJ_STRING(x)->len,
  35.770 -                  OBJ_STRING(y)->data, OBJ_STRING(y)->len);
  35.771 -    if(ok) goto exit;
  35.772 -    ok = has_type(y, T_ATOM) &&
  35.773 -        string_eq(OBJ_STRING(x)->data, OBJ_STRING(x)->len,
  35.774 -                  atom_name(y), atom_length(y));
  35.775 -  exit:
  35.776 -    return ok;
  35.777 -}
  35.778 -
  35.779 -/** Create a new cons cell.
  35.780 - * The cell is ONOMEM if either argument is.
  35.781 - *
  35.782 - * @param car sxpr for the car
  35.783 - * @param cdr sxpr for the cdr
  35.784 - * @return new cons
  35.785 - */
  35.786 -Sxpr cons_new(Sxpr car, Sxpr cdr){
  35.787 -    Sxpr obj;
  35.788 -    if(NOMEMP(car) || NOMEMP(cdr)){
  35.789 -        obj = ONOMEM;
  35.790 -    } else {
  35.791 -        obj = HALLOC(ObjCons, T_CONS);
  35.792 -        if(!NOMEMP(obj)){
  35.793 -            ObjCons *z = OBJ_CONS(obj);
  35.794 -            z->car = car;
  35.795 -            z->cdr = cdr;
  35.796 -        }
  35.797 -    }
  35.798 -    return obj;
  35.799 -}
  35.800 -
  35.801 -/** Push a new element onto a list.
  35.802 - *
  35.803 - * @param list list to add to
  35.804 - * @param elt element to add
  35.805 - * @return 0 if successful, error code otherwise
  35.806 - */
  35.807 -int cons_push(Sxpr *list, Sxpr elt){
  35.808 -    Sxpr l;
  35.809 -    l = cons_new(elt, *list);
  35.810 -    if(NOMEMP(l)) return -ENOMEM;
  35.811 -    *list = l;
  35.812 -    return 0;
  35.813 -}
  35.814 -
  35.815 -/** Free a cons. Recursively frees the car and cdr.
  35.816 - *
  35.817 - * @param obj to free
  35.818 - */
  35.819 -void cons_free(Sxpr obj){
  35.820 -    Sxpr next;
  35.821 -    for(; CONSP(obj); obj = next){
  35.822 -        next = CDR(obj);
  35.823 -        objfree(CAR(obj));
  35.824 -        hfree(obj);
  35.825 -    }
  35.826 -    if(!NULLP(obj)){
  35.827 -        objfree(obj);
  35.828 -    }
  35.829 -}
  35.830 -
  35.831 -/** Copy a cons. Recursively copies the car and cdr.
  35.832 - *
  35.833 - * @param obj to copy
  35.834 - */
  35.835 -Sxpr cons_copy(Sxpr obj){
  35.836 -    Sxpr v = ONULL;
  35.837 -    Sxpr l = ONULL, x = ONONE;
  35.838 -    for(l = obj; CONSP(l); l = CDR(l)){
  35.839 -        x = objcopy(CAR(l));
  35.840 -        if(NOMEMP(x)) goto exit;
  35.841 -        x = cons_new(x, v);
  35.842 -        if(NOMEMP(x)) goto exit;
  35.843 -        v = x;
  35.844 -    }
  35.845 -    v = nrev(v);
  35.846 -  exit:
  35.847 -    if(NOMEMP(x)){
  35.848 -        objfree(v);
  35.849 -        v = ONOMEM;
  35.850 -    }
  35.851 -    return v;
  35.852 -}
  35.853 -
  35.854 -/** Free a cons and its cdr cells, but not the car sxprs.
  35.855 - * Does nothing if called on something that is not a cons.
  35.856 - *
  35.857 - * @param obj to free
  35.858 - */
  35.859 -void cons_free_cells(Sxpr obj){
  35.860 -    Sxpr next;
  35.861 -    for(; CONSP(obj); obj = next){
  35.862 -        next = CDR(obj);
  35.863 -        hfree(obj);
  35.864 -    }
  35.865 -}
  35.866 -
  35.867 -/** Print a cons.
  35.868 - * Prints the cons in list format if the cdrs are conses.
  35.869 - * uses pair (dot) format if the last cdr is not a cons (or null).
  35.870 - *
  35.871 - * @param io stream to print to
  35.872 - * @param obj to print
  35.873 - * @param flags print flags
  35.874 - * @return number of bytes written
  35.875 - */
  35.876 -int cons_print(IOStream *io, Sxpr obj, unsigned flags){
  35.877 -    int first = 1;
  35.878 -    int k = 0;
  35.879 -    k += IOStream_print(io, "(");
  35.880 -    for( ; CONSP(obj) ; obj = CDR(obj)){
  35.881 -        if(first){ 
  35.882 -            first = 0;
  35.883 -        } else {
  35.884 -            k += IOStream_print(io, " ");
  35.885 -        }
  35.886 -        k += objprint(io, CAR(obj), flags);
  35.887 -    }
  35.888 -    if(!NULLP(obj)){
  35.889 -        k += IOStream_print(io, " . ");
  35.890 -        k += objprint(io, obj, flags);
  35.891 -    }
  35.892 -    k += IOStream_print(io, ")");
  35.893 -    return (IOStream_error(io) ? -1 : k);
  35.894 -}
  35.895 -
  35.896 -/** Compare a cons with another sxpr for equality.
  35.897 - * If y is a cons, compares the cars and cdrs recursively.
  35.898 - *
  35.899 - * @param x cons to compare
  35.900 - * @param y sxpr to compare
  35.901 - * @return 1 if equal, 0 otherwise
  35.902 - */
  35.903 -int cons_equal(Sxpr x, Sxpr y){
  35.904 -    return CONSP(y) &&
  35.905 -        objequal(CAR(x), CAR(y)) &&
  35.906 -        objequal(CDR(x), CDR(y));
  35.907 -}
  35.908 -
  35.909 -/** Return the length of a cons list.
  35.910 - *
  35.911 - * @param obj list
  35.912 - * @return length
  35.913 - */
  35.914 -int cons_length(Sxpr obj){
  35.915 -    int count = 0;
  35.916 -    for( ; CONSP(obj); obj = CDR(obj)){
  35.917 -        count++;
  35.918 -    }
  35.919 -    return count;
  35.920 -}
  35.921 -
  35.922 -/** Destructively reverse a cons list in-place.
  35.923 - * If the argument is not a cons it is returned unchanged.
  35.924 - * 
  35.925 - * @param l to reverse
  35.926 - * @return reversed list
  35.927 - */
  35.928 -Sxpr nrev(Sxpr l){
  35.929 -    if(CONSP(l)){
  35.930 -        // Iterate down the cells in the list making the cdr of
  35.931 -        // each cell point to the previous cell. The last cell 
  35.932 -        // is the head of the reversed list.
  35.933 -        Sxpr prev = ONULL;
  35.934 -        Sxpr cell = l;
  35.935 -        Sxpr next;
  35.936 -
  35.937 -        while(1){
  35.938 -            next = CDR(cell);
  35.939 -            CDR(cell) = prev;
  35.940 -            if(!CONSP(next)) break;
  35.941 -            prev = cell;
  35.942 -            cell = next;
  35.943 -        }
  35.944 -        l = cell;
  35.945 -    }
  35.946 -    return l;
  35.947 -}
  35.948 -
  35.949 -/** Print the null sxpr.        
  35.950 - *
  35.951 - * @param io stream to print to
  35.952 - * @param obj to print
  35.953 - * @param flags print flags
  35.954 - * @return number of bytes written
  35.955 - */
  35.956 -static int null_print(IOStream *io, Sxpr obj, unsigned flags){
  35.957 -    return IOStream_print(io, "()");
  35.958 -}
  35.959 -
  35.960 -/** Print the `unspecified' sxpr none.
  35.961 - *
  35.962 - * @param io stream to print to
  35.963 - * @param obj to print
  35.964 - * @param flags print flags
  35.965 - * @return number of bytes written
  35.966 - */
  35.967 -static int none_print(IOStream *io, Sxpr obj, unsigned flags){
  35.968 -    return IOStream_print(io, "<none>");
  35.969 -}
  35.970 -
  35.971 -/** Print an integer.
  35.972 - *
  35.973 - * @param io stream to print to
  35.974 - * @param obj to print
  35.975 - * @param flags print flags
  35.976 - * @return number of bytes written
  35.977 - */
  35.978 -static int int_print(IOStream *io, Sxpr obj, unsigned flags){
  35.979 -    return IOStream_print(io, "%d", OBJ_INT(obj));
  35.980 -}
  35.981 -
  35.982 -/** Print a boolean.
  35.983 - *
  35.984 - * @param io stream to print to
  35.985 - * @param obj to print
  35.986 - * @param flags print flags
  35.987 - * @return number of bytes written
  35.988 - */
  35.989 -static int bool_print(IOStream *io, Sxpr obj, unsigned flags){
  35.990 -    return IOStream_print(io, (OBJ_UINT(obj) ? k_true : k_false));
  35.991 -}
  35.992 -
  35.993 -/** Print an error.
  35.994 - *
  35.995 - * @param io stream to print to
  35.996 - * @param obj to print
  35.997 - * @param flags print flags
  35.998 - * @return number of bytes written
  35.999 - */
 35.1000 -static int err_print(IOStream *io, Sxpr obj, unsigned flags){
 35.1001 -    int err = OBJ_INT(obj);
 35.1002 -    if(err < 0) err = -err;
 35.1003 -    return IOStream_print(io, "[error:%d:%s]", err, strerror(err));
 35.1004 -}
 35.1005 -
 35.1006 -/** Print the 'nomem' sxpr.
 35.1007 - *
 35.1008 - * @param io stream to print to
 35.1009 - * @param obj to print
 35.1010 - * @param flags print flags
 35.1011 - * @return number of bytes written
 35.1012 - */
 35.1013 -static int nomem_print(IOStream *io, Sxpr obj, unsigned flags){
 35.1014 -    return IOStream_print(io, "[ENOMEM]");
 35.1015 -}
 35.1016 -
 35.1017 -int sxprp(Sxpr obj, Sxpr name){
 35.1018 -    return CONSP(obj) && objequal(CAR(obj), name);
 35.1019 -}
 35.1020 -
 35.1021 -/** Get the name of an element.
 35.1022 - * 
 35.1023 - * @param obj element
 35.1024 - * @return name
 35.1025 - */
 35.1026 -Sxpr sxpr_name(Sxpr obj){
 35.1027 -    Sxpr val = ONONE;
 35.1028 -    if(CONSP(obj)){
 35.1029 -        val = CAR(obj);
 35.1030 -    } else if(STRINGP(obj) || ATOMP(obj)){
 35.1031 -        val = obj;
 35.1032 -    }
 35.1033 -    return val;
 35.1034 -}
 35.1035 -
 35.1036 -int sxpr_is(Sxpr obj, char *s){
 35.1037 -    if(ATOMP(obj)) return string_eq(atom_name(obj), atom_length(obj), s, strlen(s));
 35.1038 -    if(STRINGP(obj)) return string_eq(string_string(obj), string_length(obj), s, strlen(s));
 35.1039 -    return 0;
 35.1040 -}
 35.1041 -
 35.1042 -int sxpr_elementp(Sxpr obj, Sxpr name){
 35.1043 -    int ok = 0;
 35.1044 -    ok = CONSP(obj) && objequal(CAR(obj), name);
 35.1045 -    return ok;
 35.1046 -}
 35.1047 -
 35.1048 -/** Get the attributes of an sxpr.
 35.1049 - * 
 35.1050 - * @param obj sxpr
 35.1051 - * @return attributes
 35.1052 - */
 35.1053 -Sxpr sxpr_attributes(Sxpr obj){
 35.1054 -    Sxpr val = ONULL;
 35.1055 -    if(CONSP(obj)){
 35.1056 -        obj = CDR(obj);
 35.1057 -        if(CONSP(obj)){
 35.1058 -            obj = CAR(obj);
 35.1059 -            if(sxprp(obj, intern("@"))){
 35.1060 -                val = CDR(obj);
 35.1061 -            }
 35.1062 -        }
 35.1063 -    }
 35.1064 -    return val;
 35.1065 -}
 35.1066 -
 35.1067 -Sxpr sxpr_attribute(Sxpr obj, Sxpr key, Sxpr def){
 35.1068 -    Sxpr val = ONONE;
 35.1069 -    val = assoc(sxpr_attributes(obj), key);
 35.1070 -    if(CONSP(val) && CONSP(CDR(val))){
 35.1071 -        val = CADR(def);
 35.1072 -    } else {
 35.1073 -        val = def;
 35.1074 -    }
 35.1075 -    return val;
 35.1076 -}
 35.1077 -
 35.1078 -/** Get the children of an sxpr.
 35.1079 - * 
 35.1080 - * @param obj sxpr
 35.1081 - * @return children
 35.1082 - */
 35.1083 -Sxpr sxpr_children(Sxpr obj){
 35.1084 -    Sxpr val = ONULL;
 35.1085 -    if(CONSP(obj)){
 35.1086 -        val = CDR(obj);
 35.1087 -        if(CONSP(val) && sxprp(CAR(val), intern("@"))){
 35.1088 -            val = CDR(val);
 35.1089 -        }
 35.1090 -    }
 35.1091 -    return val;
 35.1092 -}
 35.1093 -
 35.1094 -Sxpr sxpr_child(Sxpr obj, Sxpr name, Sxpr def){
 35.1095 -    Sxpr val = ONONE;
 35.1096 -    Sxpr l;
 35.1097 -    for(l = sxpr_children(obj); CONSP(l); l = CDR(l)){
 35.1098 -        if(sxprp(CAR(l), name)){
 35.1099 -            val = CAR(l);
 35.1100 -            break;
 35.1101 -        }
 35.1102 -    }
 35.1103 -    if(NONEP(val)) val = def;
 35.1104 -    return val;
 35.1105 -}
 35.1106 -
 35.1107 -Sxpr sxpr_child0(Sxpr obj, Sxpr def){
 35.1108 -    Sxpr val = ONONE;
 35.1109 -    Sxpr l = sxpr_children(obj);
 35.1110 -    if(CONSP(l)){
 35.1111 -        val = CAR(l);
 35.1112 -    } else {
 35.1113 -        val = def;
 35.1114 -    }
 35.1115 -    return val;
 35.1116 -}
 35.1117 -
 35.1118 -Sxpr sxpr_childN(Sxpr obj, int n, Sxpr def){
 35.1119 -    Sxpr val = def;
 35.1120 -    Sxpr l;
 35.1121 -    int i;
 35.1122 -    for (i = 0, l = sxpr_children(obj); CONSP(l); i++, l = CDR(l)){
 35.1123 -        if(i == n){
 35.1124 -            val = CAR(l);
 35.1125 -            break;
 35.1126 -        }
 35.1127 -    }
 35.1128 -    return val;
 35.1129 -}
 35.1130 -    
 35.1131 -Sxpr sxpr_child_value(Sxpr obj, Sxpr name, Sxpr def){
 35.1132 -    Sxpr val = ONONE;
 35.1133 -    val = sxpr_child(obj, name, ONONE);
 35.1134 -    if(NONEP(val)){
 35.1135 -        val = def;
 35.1136 -    } else {
 35.1137 -        val = sxpr_child0(val, def);
 35.1138 -    }
 35.1139 -    return val;
 35.1140 -}
 35.1141 -
 35.1142 -/** Table of interned symbols. Indexed by symbol name. */
 35.1143 -static HashTable *symbols = NULL;
 35.1144 -
 35.1145 -/** Hash function for entries in the symbol table.
 35.1146 - *
 35.1147 - * @param key to hash
 35.1148 - * @return hashcode
 35.1149 - */
 35.1150 -static Hashcode sym_hash_fn(void *key){
 35.1151 -    return hash_string((char*)key);
 35.1152 -}
 35.1153 -
 35.1154 -/** Key equality function for the symbol table.
 35.1155 - *
 35.1156 - * @param x to compare
 35.1157 - * @param y to compare
 35.1158 - * @return 1 if equal, 0 otherwise
 35.1159 - */
 35.1160 -static int sym_equal_fn(void *x, void *y){
 35.1161 -    return !strcmp((char*)x, (char*)y);
 35.1162 -}
 35.1163 -
 35.1164 -/** Entry free function for the symbol table.
 35.1165 - *
 35.1166 - * @param table the entry is in
 35.1167 - * @param entry being freed
 35.1168 - */
 35.1169 -static void sym_free_fn(HashTable *table, HTEntry *entry){
 35.1170 -    if(entry){
 35.1171 -        objfree(((ObjAtom*)entry->value)->name);
 35.1172 -        HTEntry_free(entry);
 35.1173 -    }
 35.1174 -}
 35.1175 -        
 35.1176 -/** Initialize the symbol table.
 35.1177 - *
 35.1178 - * @return 0 on sucess, error code otherwise
 35.1179 - */
 35.1180 -static int init_symbols(void){
 35.1181 -    symbols = HashTable_new(100);
 35.1182 -    if(symbols){
 35.1183 -        symbols->key_hash_fn = sym_hash_fn;
 35.1184 -        symbols->key_equal_fn = sym_equal_fn;
 35.1185 -        symbols->entry_free_fn = sym_free_fn;
 35.1186 -        return 0;
 35.1187 -    }
 35.1188 -    return -1;
 35.1189 -}
 35.1190 -
 35.1191 -/** Cleanup the symbol table. Frees the table and all its symbols.
 35.1192 - */
 35.1193 -void cleanup_symbols(void){
 35.1194 -    HashTable_free(symbols);
 35.1195 -    symbols = NULL;
 35.1196 -}
 35.1197 -
 35.1198 -/** Get the interned symbol with the given name.
 35.1199 - * No new symbol is created.
 35.1200 - *
 35.1201 - * @return symbol or null
 35.1202 - */
 35.1203 -Sxpr get_symbol(char *sym){
 35.1204 -    HTEntry *entry;
 35.1205 -    if(!symbols){
 35.1206 -        if(init_symbols()) return ONOMEM;
 35.1207 -        return ONULL;
 35.1208 -    }
 35.1209 -    entry = HashTable_get_entry(symbols, sym);
 35.1210 -    if(entry){
 35.1211 -        return OBJP(T_ATOM, entry->value);
 35.1212 -    } else {
 35.1213 -        return ONULL;
 35.1214 -    }
 35.1215 -}
 35.1216 -
 35.1217 -/** Get the interned symbol with the given name.
 35.1218 - * Creates a new symbol if necessary.
 35.1219 - *
 35.1220 - * @return symbol
 35.1221 - */
 35.1222 -Sxpr intern(char *sym){
 35.1223 -    Sxpr symbol = get_symbol(sym);
 35.1224 -    if(NULLP(symbol)){
 35.1225 -        if(!symbols) return ONOMEM;
 35.1226 -        symbol = atom_new(sym);
 35.1227 -        if(!NOMEMP(symbol)){
 35.1228 -            OBJ_ATOM(symbol)->interned = TRUE;
 35.1229 -            HashTable_add(symbols, atom_name(symbol), get_ptr(symbol));
 35.1230 -        }
 35.1231 -    }
 35.1232 -    return symbol;
 35.1233 -}
    36.1 --- a/tools/libxutil/sxpr.h	Tue May 24 21:10:23 2005 +0000
    36.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    36.3 @@ -1,437 +0,0 @@
    36.4 -/*
    36.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    36.6 - *
    36.7 - * This library is free software; you can redistribute it and/or modify
    36.8 - * it under the terms of the GNU Lesser General Public License as
    36.9 - * published by the Free Software Foundation; either version 2.1 of the
   36.10 - * License, or  (at your option) any later version. This library is 
   36.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   36.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   36.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   36.14 - * See the GNU Lesser General Public License for more details.
   36.15 - *
   36.16 - * You should have received a copy of the GNU Lesser General Public License
   36.17 - * along with this library; if not, write to the Free Software Foundation,
   36.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   36.19 - */
   36.20 -#ifndef _XUTIL_SXPR_H_
   36.21 -#define _XUTIL_SXPR_H_
   36.22 -
   36.23 -#ifdef __KERNEL__
   36.24 -#include <linux/config.h>
   36.25 -#include <linux/types.h>
   36.26 -#else
   36.27 -#include <stdint.h>
   36.28 -#endif
   36.29 -
   36.30 -#include "hash_table.h"
   36.31 -#include "iostream.h"
   36.32 -#include "allocate.h"
   36.33 -
   36.34 -/** @file
   36.35 - * Definitions for rules and sxprs.
   36.36 - */
   36.37 -
   36.38 -#ifndef NULL
   36.39 -#define NULL 0
   36.40 -#endif
   36.41 -
   36.42 -#ifndef TRUE
   36.43 -#define TRUE 1
   36.44 -#endif
   36.45 -
   36.46 -#ifndef FALSE
   36.47 -#define FALSE 0
   36.48 -#endif
   36.49 -
   36.50 -/** Sxpr type. */
   36.51 -typedef int16_t TypeCode;
   36.52 -
   36.53 -/** A typed sxpr handle.*/
   36.54 -typedef struct Sxpr {
   36.55 -    /** Sxpr type. */
   36.56 -    TypeCode type;
   36.57 -    union {
   36.58 -        /** Sxpr value. */
   36.59 -        unsigned long ul;
   36.60 -        /** Pointer. */
   36.61 -        void *ptr;
   36.62 -    } v;
   36.63 -} Sxpr;
   36.64 -
   36.65 -/** Get the integer value from an sxpr.
   36.66 - *
   36.67 - * @param obj sxpr
   36.68 - * @return value
   36.69 - */
   36.70 -static inline unsigned long get_ul(Sxpr obj){
   36.71 -    return obj.v.ul;
   36.72 -}
   36.73 -
   36.74 -/** Get the pointer value from an sxpr.
   36.75 - *
   36.76 - * @param obj sxpr
   36.77 - * @return value
   36.78 - */
   36.79 -static inline void * get_ptr(Sxpr obj){
   36.80 -    return obj.v.ptr;
   36.81 -}
   36.82 -
   36.83 -/** Create an sxpr containing a pointer.
   36.84 - *
   36.85 - * @param ty typecode
   36.86 - * @param val pointer
   36.87 - * @return sxpr
   36.88 - */
   36.89 -static inline Sxpr obj_ptr(TypeCode ty, void *val){
   36.90 -    return (Sxpr){ .type= ty, .v= { .ptr= val } };
   36.91 -}
   36.92 -
   36.93 -/** Create an sxpr containing an integer.
   36.94 - *
   36.95 - * @param ty typecode
   36.96 - * @param val integer
   36.97 - * @return sxpr
   36.98 - */
   36.99 -static inline Sxpr obj_ul(TypeCode ty, unsigned long val){
  36.100 -    return (Sxpr){ .type= ty, .v= { .ul= val } };
  36.101 -}
  36.102 -
  36.103 -/** Get the type of an sxpr.
  36.104 - *
  36.105 - * @param obj sxpr
  36.106 - * @return type
  36.107 - */
  36.108 -static inline TypeCode get_type(Sxpr obj){
  36.109 -    return obj.type;
  36.110 -}
  36.111 -
  36.112 -/** Check the type of an sxpr.
  36.113 - *
  36.114 - * @param obj sxpr
  36.115 - * @param type to check
  36.116 - * @return 1 if has the type, 0 otherwise
  36.117 - */
  36.118 -static inline int has_type(Sxpr obj, TypeCode type){
  36.119 -    return get_type(obj) == type;
  36.120 -}
  36.121 -
  36.122 -/** Compare sxprs for literal equality of type and value.
  36.123 - *
  36.124 - * @param x sxpr to compare
  36.125 - * @param y sxpr to compare
  36.126 - * @return 1 if equal, 0 otherwise
  36.127 - */
  36.128 -static inline int eq(Sxpr x, Sxpr y){
  36.129 -    return ((get_type(x) == get_type(y)) && (get_ul(x) == get_ul(y)));
  36.130 -}
  36.131 -
  36.132 -/** The 'unspecified' sxpr. */
  36.133 -#define T_NONE       ((TypeCode)0)
  36.134 -/** The empty list. */
  36.135 -#define T_NULL       ((TypeCode)1)
  36.136 -/** Unsigned integer. */
  36.137 -#define T_UINT       ((TypeCode)2)
  36.138 -/** A string. */
  36.139 -#define T_STRING     ((TypeCode)3)
  36.140 -/** An atom. */
  36.141 -#define T_ATOM       ((TypeCode)4)
  36.142 -/** A boolean. */
  36.143 -#define T_BOOL       ((TypeCode)5)
  36.144 -
  36.145 -/** A cons (pair or list). */
  36.146 -#define T_CONS       ((TypeCode)10)
  36.147 -
  36.148 -/** An error. */
  36.149 -#define T_ERR        ((TypeCode)40)
  36.150 -/** Sxpr type to indicate out of memory. */
  36.151 -#define T_NOMEM      ((TypeCode)41)
  36.152 -
  36.153 -typedef struct ObjString {
  36.154 -    int len;
  36.155 -    char data[];
  36.156 -} ObjString;
  36.157 -
  36.158 -/** An atom. */
  36.159 -typedef struct ObjAtom {
  36.160 -    Sxpr name;
  36.161 -    Hashcode hashcode;
  36.162 -    int interned;
  36.163 -} ObjAtom;
  36.164 -
  36.165 -/** A cons (pair). */
  36.166 -typedef struct ObjCons {
  36.167 -    Sxpr car;
  36.168 -    Sxpr cdr;
  36.169 -} ObjCons;
  36.170 -
  36.171 -/** Flags for sxpr printing. */
  36.172 -enum PrintFlags {
  36.173 -    PRINT_RAW           = 0x001,
  36.174 -    PRINT_TYPE          = 0x002,
  36.175 -    PRINT_PRETTY        = 0x004,
  36.176 -    PRINT_COUNTED       = 0x008,
  36.177 -    PRINT_ADDR          = 0x010,
  36.178 -};
  36.179 -
  36.180 -extern int _string_print(IOStream *io, char *str, int n, unsigned flags);
  36.181 -extern int _string_print_raw(IOStream *io, char *str, int n);
  36.182 -extern int _string_print_counted(IOStream *io, char *str, int n);
  36.183 -extern int _string_print_quoted(IOStream *io, char *str, int n);
  36.184 -extern int _string_print_string(IOStream *io, char *str, int n);
  36.185 -
  36.186 -/** An integer sxpr.
  36.187 - *
  36.188 - * @param ty type
  36.189 - * @param val integer value
  36.190 - */
  36.191 -#define OBJI(ty, val) obj_ul(ty, val)
  36.192 -
  36.193 -/** Make an integer sxpr.
  36.194 - * @param x value
  36.195 - */
  36.196 -#define OINT(x)       OBJI(T_UINT,  x)
  36.197 -
  36.198 -/** Make an error sxpr.
  36.199 - *
  36.200 - * @param x value
  36.201 - */
  36.202 -#define OERR(x)       OBJI(T_ERR,   x)
  36.203 -
  36.204 -/** Out of memory constant. */
  36.205 -#define ONOMEM        OBJI(T_NOMEM, 0)
  36.206 -
  36.207 -/** The `unspecified' constant. */
  36.208 -#define ONONE         OBJI(T_NONE,  0)
  36.209 -
  36.210 -/** Empty list constant. */
  36.211 -#define ONULL         OBJI(T_NULL,  0)
  36.212 -
  36.213 -/** False constant. */
  36.214 -#define OFALSE        OBJI(T_BOOL,  0)
  36.215 -
  36.216 -/** True constant. */
  36.217 -#define OTRUE         OBJI(T_BOOL,  1)
  36.218 -
  36.219 -/** A pointer sxpr.
  36.220 - * If the pointer is non-null, returns an sxpr containing it.
  36.221 - * If the pointer is null, returns ONOMEM.
  36.222 - *
  36.223 - * @param ty type
  36.224 - * @param val pointer
  36.225 - */
  36.226 -static inline Sxpr OBJP(int ty, void *val){
  36.227 -    return (val ? obj_ptr(ty, val) : ONOMEM);
  36.228 -}
  36.229 -
  36.230 -/** Make an integer sxpr containing a pointer.
  36.231 - *
  36.232 - * @param val pointer
  36.233 - */
  36.234 -#define PTR(val) OBJP(T_UINT, (void*)(val))
  36.235 -
  36.236 -/** Allocate some memory and return an sxpr containing it.
  36.237 - * Returns ONOMEM if allocation failed.
  36.238 - *
  36.239 - * @param n number of bytes to allocate
  36.240 - * @param ty typecode
  36.241 - * @return sxpr
  36.242 - */
  36.243 -#define halloc(_n, _ty) OBJP(_ty, allocate(_n))
  36.244 -
  36.245 -/** Allocate an sxpr containing a pointer to the given type.
  36.246 - *
  36.247 - * @param _ctype type (uses sizeof to determine how many bytes to allocate)
  36.248 - * @param _tycode typecode
  36.249 - * @return sxpr, ONOMEM if allocation failed
  36.250 - */
  36.251 -#define HALLOC(_ctype, _tycode) halloc(sizeof(_ctype), _tycode)
  36.252 -
  36.253 -/* Recognizers for the various sxpr types.  */
  36.254 -#define ATOMP(obj)        has_type(obj, T_ATOM)
  36.255 -#define BOOLP(obj)        has_type(obj, T_BOOL)
  36.256 -#define CONSP(obj)        has_type(obj, T_CONS)
  36.257 -#define ERRP(obj)         has_type(obj, T_ERR)
  36.258 -#define INTP(obj)         has_type(obj, T_UINT)
  36.259 -#define NOMEMP(obj)       has_type(obj, T_NOMEM)
  36.260 -#define NONEP(obj)        has_type(obj, T_NONE)
  36.261 -#define NULLP(obj)        has_type(obj, T_NULL)
  36.262 -#define STRINGP(obj)      has_type(obj, T_STRING)
  36.263 -
  36.264 -#define TRUEP(obj)    get_ul(obj)
  36.265 -
  36.266 -/** Convert an sxpr to an unsigned integer. */
  36.267 -#define OBJ_UINT(x)   get_ul(x)
  36.268 -/** Convert an sxpr to an integer. */
  36.269 -#define OBJ_INT(x)    (int)get_ul(x)
  36.270 -
  36.271 -/* Conversions of sxprs to their values.
  36.272 - * No checking is done.
  36.273 - */
  36.274 -#define OBJ_STRING(x)  ((ObjString*)get_ptr(x))
  36.275 -#define OBJ_CONS(x)    ((ObjCons*)get_ptr(x))
  36.276 -#define OBJ_ATOM(x)    ((ObjAtom*)get_ptr(x))
  36.277 -#define OBJ_SET(x)     ((ObjSet*)get_ptr(x))
  36.278 -#define CAR(x)         (OBJ_CONS(x)->car)
  36.279 -#define CDR(x)         (OBJ_CONS(x)->cdr)
  36.280 -
  36.281 -#define CAAR(x)        (CAR(CAR(x)))
  36.282 -#define CADR(x)        (CAR(CDR(x)))
  36.283 -#define CDAR(x)        (CDR(CAR(x)))
  36.284 -#define CDDR(x)        (CDR(CDR(x)))
  36.285 -
  36.286 -/** Checked version of CAR
  36.287 - *
  36.288 - * @param x sxpr
  36.289 - * @return CAR if a cons, x otherwise
  36.290 - */
  36.291 -static inline Sxpr car(Sxpr x){
  36.292 -    return (CONSP(x) ? CAR(x) : x);
  36.293 -}
  36.294 -
  36.295 -/** Checked version of CDR.
  36.296 - *
  36.297 - * @param x sxpr
  36.298 - * @return CDR if a cons, null otherwise
  36.299 - */
  36.300 -static inline Sxpr cdr(Sxpr x){
  36.301 -    return (CONSP(x) ? CDR(x) : ONULL);
  36.302 -}
  36.303 -
  36.304 -typedef int ObjPrintFn(IOStream *io, Sxpr obj, unsigned flags);
  36.305 -typedef int ObjEqualFn(Sxpr obj, Sxpr other);
  36.306 -typedef void ObjFreeFn(Sxpr obj);
  36.307 -typedef Sxpr ObjCopyFn(Sxpr obj);
  36.308 -
  36.309 -/** An sxpr type definition. */
  36.310 -typedef struct SxprType {
  36.311 -    TypeCode type;
  36.312 -    char *name;
  36.313 -    int pointer;
  36.314 -    ObjPrintFn *print;
  36.315 -    ObjEqualFn *equal;
  36.316 -    ObjFreeFn *free;
  36.317 -    ObjCopyFn *copy;
  36.318 -} SxprType;
  36.319 -
  36.320 -
  36.321 -extern int def_sxpr_type(SxprType *tydef);
  36.322 -extern SxprType *get_sxpr_type(int ty);
  36.323 -
  36.324 -/** Free the pointer in an sxpr.
  36.325 - *
  36.326 - * @param x sxpr containing a pointer
  36.327 - */
  36.328 -static inline void hfree(Sxpr x){
  36.329 -    deallocate(get_ptr(x));
  36.330 -}
  36.331 -
  36.332 -extern int objprint(IOStream *io, Sxpr x, unsigned flags);
  36.333 -extern int objequal(Sxpr x, Sxpr y);
  36.334 -extern void objfree(Sxpr x);
  36.335 -extern Sxpr objcopy(Sxpr x);
  36.336 -
  36.337 -extern void cons_free_cells(Sxpr obj);
  36.338 -extern Sxpr intern(char *s);
  36.339 -
  36.340 -extern Sxpr assoc(Sxpr k, Sxpr l);
  36.341 -extern Sxpr assocq(Sxpr k, Sxpr l);
  36.342 -extern Sxpr acons(Sxpr k, Sxpr v, Sxpr l);
  36.343 -extern Sxpr nrev(Sxpr l);
  36.344 -extern Sxpr cons_member(Sxpr l, Sxpr x);
  36.345 -extern Sxpr cons_member_if(Sxpr l, ObjEqualFn *test_fn, Sxpr v);
  36.346 -extern int cons_subset(Sxpr s, Sxpr t);
  36.347 -extern int cons_set_equal(Sxpr s, Sxpr t);
  36.348 -
  36.349 -#ifdef USE_GC
  36.350 -extern Sxpr cons_remove(Sxpr l, Sxpr x);
  36.351 -extern Sxpr cons_remove_if(Sxpr l, ObjEqualFn *test_fn, Sxpr v);
  36.352 -#endif
  36.353 -
  36.354 -extern Sxpr atom_new(char *name);
  36.355 -extern char * atom_name(Sxpr obj);
  36.356 -extern int atom_length(Sxpr obj);
  36.357 -
  36.358 -extern Sxpr string_new(char *s);
  36.359 -extern Sxpr string_new_n(char *s, int n);
  36.360 -extern char * string_string(Sxpr obj);
  36.361 -extern int string_length(Sxpr obj);
  36.362 -
  36.363 -extern Sxpr cons_new(Sxpr car, Sxpr cdr);
  36.364 -extern int cons_push(Sxpr *list, Sxpr elt);
  36.365 -extern int cons_length(Sxpr obj);
  36.366 -
  36.367 -Sxpr sxpr_name(Sxpr obj);
  36.368 -int sxpr_is(Sxpr obj, char *s);
  36.369 -int sxpr_elementp(Sxpr obj, Sxpr name);
  36.370 -Sxpr sxpr_attributes(Sxpr obj);
  36.371 -Sxpr sxpr_attribute(Sxpr obj, Sxpr key, Sxpr def);
  36.372 -Sxpr sxpr_children(Sxpr obj);
  36.373 -Sxpr sxpr_child(Sxpr obj, Sxpr name, Sxpr def);
  36.374 -Sxpr sxpr_childN(Sxpr obj, int n, Sxpr def);
  36.375 -Sxpr sxpr_child0(Sxpr obj, Sxpr def);
  36.376 -Sxpr sxpr_child_value(Sxpr obj, Sxpr name, Sxpr def);
  36.377 -
  36.378 -/** Create a new atom.
  36.379 - *
  36.380 - * @param s atom name
  36.381 - * @return new atom
  36.382 - */
  36.383 -static inline Sxpr mkatom(char *s){
  36.384 -    return atom_new(s);
  36.385 -}
  36.386 -
  36.387 -/** Create a new string sxpr.
  36.388 - *
  36.389 - * @param s string bytes (copied)
  36.390 - * @return new string
  36.391 - */
  36.392 -static inline Sxpr mkstring(char *s){
  36.393 -    return string_new(s);
  36.394 -}
  36.395 -
  36.396 -/** Create an integer sxpr.
  36.397 - *
  36.398 - * @param i value
  36.399 - * @return sxpr
  36.400 - */
  36.401 -static inline Sxpr mkint(int i){
  36.402 -    return OBJI(T_UINT, i);
  36.403 -}
  36.404 -
  36.405 -/** Create a boolean sxpr.
  36.406 - *
  36.407 - * @param b value
  36.408 - * @return sxpr
  36.409 - */
  36.410 -static inline Sxpr mkbool(int b){
  36.411 -    return OBJI(T_BOOL, (b ? 1 : 0));
  36.412 -}
  36.413 -
  36.414 -/* Constants used in parsing and printing. */
  36.415 -#define k_list_open    "("
  36.416 -#define c_list_open    '('
  36.417 -#define k_list_close   ")"
  36.418 -#define c_list_close   ')'
  36.419 -#define k_true         "true"
  36.420 -#define k_false        "false"
  36.421 -
  36.422 -#define c_escape       '\\'
  36.423 -#define c_single_quote '\''
  36.424 -#define c_double_quote '"'
  36.425 -#define c_string_open  c_double_quote
  36.426 -#define c_string_close c_double_quote
  36.427 -
  36.428 -#define c_data_open    '<'
  36.429 -#define c_data_quote   '<'
  36.430 -#define c_data_count   '*'
  36.431 -//#define c_data_open    '['
  36.432 -//#define c_data_close   ']'
  36.433 -//#define c_binary       '*'
  36.434 -
  36.435 -#define c_var          '$'
  36.436 -#define c_eval         '!'
  36.437 -#define c_concat_open  '{'
  36.438 -#define c_concat_close '}'
  36.439 -
  36.440 -#endif /* ! _XUTIL_SXPR_H_ */
    37.1 --- a/tools/libxutil/sxpr_parser.c	Tue May 24 21:10:23 2005 +0000
    37.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    37.3 @@ -1,991 +0,0 @@
    37.4 -/*
    37.5 - * Copyright (C) 2001 - 2005 Mike Wray <mike.wray@hp.com>
    37.6 - *
    37.7 - * This library is free software; you can redistribute it and/or modify
    37.8 - * it under the terms of the GNU Lesser General Public License as
    37.9 - * published by the Free Software Foundation; either version 2.1 of the
   37.10 - * License, or  (at your option) any later version. This library is 
   37.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   37.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   37.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   37.14 - * See the GNU Lesser General Public License for more details.
   37.15 - *
   37.16 - * You should have received a copy of the GNU Lesser General Public License
   37.17 - * along with this library; if not, write to the Free Software Foundation,
   37.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   37.19 - */
   37.20 -
   37.21 -#ifdef __KERNEL__
   37.22 -#  include <linux/config.h>
   37.23 -#  include <linux/module.h>
   37.24 -#  include <linux/kernel.h>
   37.25 -#  include <linux/string.h>
   37.26 -#  include <linux/errno.h>
   37.27 -#else
   37.28 -#  include <stdlib.h>
   37.29 -#  include <errno.h>
   37.30 -#endif
   37.31 -
   37.32 -#include "sys_net.h"
   37.33 -
   37.34 -#include "iostream.h"
   37.35 -#include "lexis.h"
   37.36 -#include "sxpr_parser.h"
   37.37 -#include "sys_string.h"
   37.38 -#include "enum.h"
   37.39 -
   37.40 -/** @file
   37.41 - * Sxpr parsing.
   37.42 - *
   37.43 - * So that the parser does not leak memory, all sxprs constructed by
   37.44 - * the parser must be freed on error.  On successful parse the sxpr
   37.45 - * returned becomes the responsibility of the caller.
   37.46 - *
   37.47 - * @author Mike Wray <mike.wray@hpl.hp.com>
   37.48 - */
   37.49 -
   37.50 -#ifdef DEBUG
   37.51 -#define dprintf(fmt, args...) IOStream_print(iostdout, "[DEBUG] %s" fmt, __FUNCTION__, ##args)
   37.52 -#else
   37.53 -#define dprintf(fmt, args...) do{ }while(0)
   37.54 -#endif
   37.55 -
   37.56 -#undef printf
   37.57 -#define printf(fmt, args...)   IOStream_print(iostdout, fmt, ##args)
   37.58 -
   37.59 -static int state_start(Parser *p, char c);
   37.60 -static int begin_start(Parser *p, char c);
   37.61 -
   37.62 -#if 0
   37.63 -/** Print a parse error.
   37.64 - *
   37.65 - * @param in parser
   37.66 - * @param msg format followed by printf arguments
   37.67 - */
   37.68 -static void eprintf(Parser *in, char *msg, ...){
   37.69 -    va_list args;
   37.70 -    if(in->error_out){
   37.71 -        va_start(args, msg);
   37.72 -        IOStream_vprint(in->error_out, msg, args);
   37.73 -        va_end(args);
   37.74 -    }
   37.75 -}
   37.76 -
   37.77 -/** Print a parse warning.
   37.78 - *
   37.79 - * @param in parser
   37.80 - * @param msg format followed by printf arguments
   37.81 - */
   37.82 -static void wprintf(Parser *in, char *msg, ...){
   37.83 -    va_list args;
   37.84 -    if(in->error_out){
   37.85 -        va_start(args, msg);
   37.86 -        IOStream_vprint(in->error_out, msg, args);
   37.87 -        va_end(args);
   37.88 -    }
   37.89 -}
   37.90 -#endif
   37.91 -
   37.92 -
   37.93 -/*============================================================================*/
   37.94 -
   37.95 -/** Record defining the message for a parse error. */
   37.96 -typedef struct {
   37.97 -    ParseErrorId id;
   37.98 -    char *message;
   37.99 -} ParseError;
  37.100 -
  37.101 -/** Format for printing parse error messages. */
  37.102 -#define PARSE_ERR_FMT "parse error> line %3d, column %2d: %s"
  37.103 -
  37.104 -/** Message catalog for the parse error codes. */
  37.105 -static ParseError catalog[] = {
  37.106 -    { PARSE_ERR_UNSPECIFIED,            "unspecified error" },
  37.107 -    { PARSE_ERR_NOMEM,                  "out of memory" },
  37.108 -    { PARSE_ERR_UNEXPECTED_EOF,         "unexpected end of input" },
  37.109 -    { PARSE_ERR_TOKEN_TOO_LONG,         "token too long" },
  37.110 -    { PARSE_ERR_INVALID_SYNTAX,         "syntax error" },
  37.111 -    { PARSE_ERR_INVALID_ESCAPE,         "invalid escape" },
  37.112 -    { 0, NULL }
  37.113 -};
  37.114 -
  37.115 -/** Number of entries in the message catalog. */
  37.116 -const static int catalog_n = sizeof(catalog)/sizeof(ParseError);
  37.117 -
  37.118 -/** Set the parser error stream.
  37.119 - * Parse errors are reported on the the error stream if it is non-null.
  37.120 - * 
  37.121 - * @param z parser
  37.122 - * @param error_out error stream
  37.123 - */
  37.124 -void Parser_set_error_stream(Parser *z, IOStream *error_out){
  37.125 -    z->error_out = error_out;
  37.126 -}
  37.127 -
  37.128 -/** Get the parser error message for an error code.
  37.129 - *
  37.130 - * @param id error code
  37.131 - * @return error message (empty string if the code is unknown)
  37.132 - */
  37.133 -static char *get_message(ParseErrorId id){
  37.134 -    int i;
  37.135 -    for(i = 0; i < catalog_n; i++){
  37.136 -        if(id == catalog[i].id){
  37.137 -            return catalog[i].message;
  37.138 -        }
  37.139 -    }
  37.140 -    return "";
  37.141 -}
  37.142 -
  37.143 -#if 0
  37.144 -/** Get the line number.
  37.145 - *
  37.146 - * @param in parser
  37.147 - */
  37.148 -static int get_line(Parser *in){
  37.149 -    return in->line_no;
  37.150 -}
  37.151 -
  37.152 -/** Get the column number.
  37.153 - *
  37.154 - * @param in parser
  37.155 - */
  37.156 -static int get_column(Parser *in){
  37.157 -    return in->char_no;
  37.158 -}
  37.159 -#endif
  37.160 -
  37.161 -/** Get the line number the current token started on.
  37.162 - *
  37.163 - * @param in parser
  37.164 - */
  37.165 -static int get_tok_line(Parser *in){
  37.166 -    return in->tok_begin_line;
  37.167 -}
  37.168 -
  37.169 -/** Get the column number the current token started on.
  37.170 - *
  37.171 - * @param in parser
  37.172 - */
  37.173 -static int get_tok_column(Parser *in){
  37.174 -    return in->tok_begin_char;
  37.175 -}
  37.176 -
  37.177 -/** Return the current token.
  37.178 - * The return value points at the internal buffer, so
  37.179 - * it must not be modified (or freed). Use copy_token() if you need a copy.
  37.180 - *
  37.181 - * @param p parser
  37.182 - * @return token
  37.183 - */
  37.184 -char *peek_token(Parser *p){
  37.185 -    return p->tok;
  37.186 -}
  37.187 -
  37.188 -int token_len(Parser *p){
  37.189 -    return p->tok_end - p->tok;
  37.190 -}
  37.191 -
  37.192 -/** Return a copy of the current token.
  37.193 - * The returned value should be freed when finished with.
  37.194 - *
  37.195 - * @param p parser
  37.196 - * @return copy of token
  37.197 - */
  37.198 -char *copy_token(Parser *p){
  37.199 -    int n = token_len(p);
  37.200 -    char *buf = allocate(n + 1);
  37.201 -    if(buf){
  37.202 -        memcpy(buf, peek_token(p), n);
  37.203 -        buf[n] = '\0';
  37.204 -    }
  37.205 -    return buf;
  37.206 -}
  37.207 -
  37.208 -void new_token(Parser *p){
  37.209 -    memset(p->buf, 0, p->buf_end - p->buf);
  37.210 -    p->tok = p->buf;
  37.211 -    p->tok_end = p->tok;
  37.212 -    p->tok_begin_line = p->line_no;
  37.213 -    p->tok_begin_char = p->char_no;
  37.214 -}
  37.215 -
  37.216 -/** Report a parse error.
  37.217 - * Does nothing if the error stream is null or there is no error.
  37.218 - *
  37.219 - * @param in parser
  37.220 - */
  37.221 -static void report_error(Parser *in){
  37.222 -    if(in->error_out && in->err){
  37.223 -        char *msg = get_message(in->err);
  37.224 -        char *tok = peek_token(in);
  37.225 -        IOStream_print(in->error_out, PARSE_ERR_FMT,
  37.226 -                       get_tok_line(in), get_tok_column(in), msg);
  37.227 -        if(tok && tok[0]){
  37.228 -            IOStream_print(in->error_out, " '%s'", tok);
  37.229 -        }
  37.230 -        IOStream_print(in->error_out, "\n");
  37.231 -    }
  37.232 -}
  37.233 -
  37.234 -/** Get the error message for the current parse error code.
  37.235 - * Does nothing if there is no error.
  37.236 - *
  37.237 - * @param in parser
  37.238 - * @param buf where to place the message
  37.239 - * @param n maximum number of characters to place in buf
  37.240 - * @return current error code (zero for no error)
  37.241 - */
  37.242 -int Parser_error_message(Parser *in, char *buf, int n){
  37.243 -    if(in->err){
  37.244 -        char *msg = get_message(in->err);
  37.245 -        snprintf(buf, n, PARSE_ERR_FMT, get_tok_line(in),
  37.246 -                 get_tok_column(in), msg);
  37.247 -    }
  37.248 -    return in->err;
  37.249 -}
  37.250 -
  37.251 -/** Flag a parse error. All subsequent reads will fail.
  37.252 - * Does not change the parser error code if it is already set.
  37.253 - *
  37.254 - * @param in parser
  37.255 - * @param id error code
  37.256 - */
  37.257 -int Parser_error_id(Parser *in, ParseErrorId id){
  37.258 -    if(!in->err){
  37.259 -        in->err = id;
  37.260 -        report_error(in);
  37.261 -    }
  37.262 -    return -EINVAL;
  37.263 -}
  37.264 -
  37.265 -/** Flag an unspecified parse error.
  37.266 - *
  37.267 - * @param in parser
  37.268 - */
  37.269 -int Parser_error(Parser *in){
  37.270 -    return Parser_error_id(in, PARSE_ERR_INVALID_SYNTAX);
  37.271 -}
  37.272 -
  37.273 -/** Test if the parser's error flag is set.
  37.274 - *
  37.275 - * @param in parser
  37.276 - * @return 1 if set, 0 otherwise
  37.277 - */
  37.278 -int Parser_has_error(Parser *in){
  37.279 -    return (in->err > 0);
  37.280 -}
  37.281 -
  37.282 -/** Test if the parser is at end of input.
  37.283 - *
  37.284 - * @param in parser
  37.285 - * @return 1 if at EOF, 0 otherwise
  37.286 - */
  37.287 -int Parser_at_eof(Parser *p){
  37.288 -    return p->eof;
  37.289 -}
  37.290 -
  37.291 -void ParserState_free(ParserState *z){
  37.292 -    if(!z) return;
  37.293 -    objfree(z->val);
  37.294 -    deallocate(z);
  37.295 -}
  37.296 -
  37.297 -int ParserState_new(ParserStateFn *fn, char *name,
  37.298 -                    ParserState *parent, ParserState **val){
  37.299 -    int err = -ENOMEM;
  37.300 -    ParserState *z;
  37.301 -    z = ALLOCATE(ParserState);
  37.302 -    if(!z) goto exit;
  37.303 -    z->name = name;
  37.304 -    z->fn = fn;
  37.305 -    z->parent = parent;
  37.306 -    z->val = ONULL;
  37.307 -    err = 0;
  37.308 -  exit:
  37.309 -    *val = (err ? NULL : z);
  37.310 -    return err;
  37.311 -}
  37.312 -
  37.313 -void Parser_pop(Parser *p){
  37.314 -    ParserState *s = p->state;
  37.315 -    if(!s) return;
  37.316 -    p->state = s->parent;
  37.317 -    if (p->start_state == s) {
  37.318 -        p->start_state = NULL;
  37.319 -    }
  37.320 -    ParserState_free(s);
  37.321 -}
  37.322 -
  37.323 -/** Free a parser.
  37.324 - * No-op if the parser is null.
  37.325 - *
  37.326 - * @param z parser 
  37.327 - */
  37.328 -void Parser_free(Parser *z){
  37.329 -    if(!z) return;
  37.330 -    // Hmmm. Need to free states, but careful about double free of values.
  37.331 -    while(z->state){
  37.332 -        objfree(z->state->val);
  37.333 -        Parser_pop(z);
  37.334 -    }
  37.335 -    if(z->buf) deallocate(z->buf);
  37.336 -    objfree(z->val);
  37.337 -    z->val = ONONE;
  37.338 -    deallocate(z);
  37.339 -}
  37.340 -
  37.341 -int Parser_push(Parser *p, ParserStateFn *fn, char *name){
  37.342 -    return ParserState_new(fn, name, p->state, &p->state);
  37.343 -}
  37.344 -        
  37.345 -int Parser_return(Parser *p){
  37.346 -    int err = 0;
  37.347 -    Sxpr val = ONONE;
  37.348 -    if(!p->state){
  37.349 -        err = -EINVAL;
  37.350 -        goto exit;
  37.351 -    }
  37.352 -    val = p->state->val;
  37.353 -    p->state->val = ONONE;
  37.354 -    Parser_pop(p);
  37.355 -    if(p->state){
  37.356 -        err = cons_push(&p->state->val, val);
  37.357 -    } else {
  37.358 -        val = nrev(val);
  37.359 -        p->val = val;
  37.360 -    }
  37.361 -  exit:
  37.362 -    if(err){
  37.363 -        objfree(val);
  37.364 -    }
  37.365 -    return err;
  37.366 -}
  37.367 -
  37.368 -/** Reset the fields of a parser to initial values.
  37.369 - *
  37.370 - * @param z parser
  37.371 - */
  37.372 -static void reset(Parser *z){
  37.373 -    // leave flags
  37.374 -    // leave error_out
  37.375 -    while(z->state){
  37.376 -        Parser_pop(z);
  37.377 -    }
  37.378 -    z->val = ONONE;
  37.379 -    z->eof = 0;
  37.380 -    z->err = 0;
  37.381 -    z->line_no = 1;
  37.382 -    z->char_no = 0;
  37.383 -    memset(z->buf, 0, z->buf_end - z->buf);
  37.384 -    z->tok = z->buf;
  37.385 -    z->tok_end = z->tok;
  37.386 -    z->tok_begin_line = 0;
  37.387 -    z->tok_begin_char = 0;
  37.388 -    z->start_state = NULL;
  37.389 -}
  37.390 -
  37.391 -/** Create a new parser. The error stream defaults to null.
  37.392 - */
  37.393 -Parser * Parser_new(void){
  37.394 -    Parser *z = ALLOCATE(Parser);
  37.395 -    int n = PARSER_BUF_SIZE;
  37.396 -    int err = -ENOMEM;
  37.397 -  
  37.398 -    if(!z) goto exit;
  37.399 -    z->buf = allocate(n);
  37.400 -    if(!z->buf) goto exit;
  37.401 -    err = 0;
  37.402 -    z->buf_end = z->buf + n;
  37.403 -    z->begin = begin_start;
  37.404 -    reset(z);
  37.405 -  exit:
  37.406 -    if(err){
  37.407 -        Parser_free(z);
  37.408 -        z = NULL;
  37.409 -    }
  37.410 -    return z;
  37.411 -}
  37.412 -
  37.413 -/** Get the next character.
  37.414 - * Records the character read in the parser,
  37.415 - * and sets the line and character counts.
  37.416 - *
  37.417 - * @param p parser
  37.418 - * @return error flag: 0 on success, non-zero on error
  37.419 - */
  37.420 -static int input_char(Parser *p, char c){
  37.421 -    int err = 0;
  37.422 -    if(c=='\n'){
  37.423 -        p->line_no++;
  37.424 -        p->char_no = 0;
  37.425 -    } else {
  37.426 -        p->char_no++;
  37.427 -    }
  37.428 -    return err;
  37.429 -}
  37.430 -
  37.431 -int save_char(Parser *p, char c){
  37.432 -    int err = 0;
  37.433 -    if(p->tok_end >= p->buf_end){
  37.434 -        int buf_n = (p->buf_end - p->buf) + PARSER_BUF_INCREMENT;
  37.435 -        char *buf = allocate(buf_n);
  37.436 -        if(!buf){
  37.437 -            err = -ENOMEM;
  37.438 -            goto exit;
  37.439 -        }
  37.440 -        memcpy(buf, p->buf, p->tok_end - p->buf);
  37.441 -        p->buf_end = buf + buf_n;
  37.442 -        p->tok     = buf + (p->tok     - p->buf);
  37.443 -        p->tok_end = buf + (p->tok_end - p->buf);
  37.444 -        deallocate(p->buf);
  37.445 -        p->buf = buf;
  37.446 -    }
  37.447 -    *p->tok_end++ = c;
  37.448 -  exit:
  37.449 -    return err;
  37.450 -}
  37.451 -
  37.452 -/** Determine if a character is a separator.
  37.453 - *
  37.454 - * @param p parser
  37.455 - * @param c character to test
  37.456 - * @return 1 if a separator, 0 otherwise
  37.457 - */
  37.458 -static int is_separator(Parser *p, char c){
  37.459 -    return in_sep_class(c);
  37.460 -}
  37.461 -
  37.462 -int Parser_set_value(Parser *p, Sxpr obj){
  37.463 -    int err = 0;
  37.464 -    if(NOMEMP(obj)){
  37.465 -        err = -ENOMEM;
  37.466 -    } else {
  37.467 -        p->state->val = obj;
  37.468 -    }
  37.469 -    return err;
  37.470 -}
  37.471 -    
  37.472 -int Parser_intern(Parser *p){
  37.473 -    Sxpr obj = intern(peek_token(p));
  37.474 -    return Parser_set_value(p, obj);
  37.475 -}
  37.476 -
  37.477 -int Parser_atom(Parser *p){
  37.478 -    Sxpr obj = atom_new(peek_token(p));
  37.479 -    return Parser_set_value(p, obj);
  37.480 -}
  37.481 -
  37.482 -int Parser_string(Parser *p){
  37.483 -    Sxpr obj = string_new_n(peek_token(p), token_len(p));
  37.484 -    return Parser_set_value(p, obj);
  37.485 -}
  37.486 -
  37.487 -int Parser_data(Parser *p){
  37.488 -    Sxpr obj = string_new_n(peek_token(p), token_len(p));
  37.489 -    return Parser_set_value(p, obj);
  37.490 -}
  37.491 -
  37.492 -int Parser_uint(Parser *p){
  37.493 -    unsigned int x = htonl(*(unsigned int *)peek_token(p));
  37.494 -    return Parser_set_value(p, OINT(x));
  37.495 -}
  37.496 -
  37.497 -static int get_escape(char c, char *d){
  37.498 -    int err = 0;
  37.499 -    switch(c){
  37.500 -    case 'a':            *d = '\a'; break;
  37.501 -    case 'b':            *d = '\b'; break;
  37.502 -    case 'f':            *d = '\f'; break;
  37.503 -    case 'n':            *d = '\n'; break;
  37.504 -    case 'r':            *d = '\r'; break;
  37.505 -    case 't':            *d = '\t'; break;
  37.506 -    case 'v':            *d = '\v'; break;
  37.507 -    case c_escape:       *d = c_escape; break;
  37.508 -    case c_single_quote: *d = c_single_quote; break;
  37.509 -    case c_double_quote: *d = c_double_quote; break;
  37.510 -    default:
  37.511 -        err = -EINVAL;
  37.512 -    }
  37.513 -    return err;
  37.514 -}
  37.515 -
  37.516 -int Parser_ready(Parser *p){
  37.517 -    return CONSP(p->val) || (p->start_state && CONSP(p->start_state->val));
  37.518 -}
  37.519 -
  37.520 -Sxpr Parser_get_val(Parser *p){
  37.521 -    Sxpr v = ONONE;
  37.522 -    if(CONSP(p->val)){
  37.523 -    } else if (p->start_state && CONSP(p->start_state->val)){
  37.524 -        p->val = p->start_state->val;
  37.525 -        p->val = nrev(p->val);
  37.526 -        p->start_state->val = ONULL;
  37.527 -    }  else {
  37.528 -        goto exit;
  37.529 -    }
  37.530 -    Sxpr w = p->val;
  37.531 -    v = CAR(w);
  37.532 -    p->val = CDR(w);
  37.533 -    hfree(w);
  37.534 -  exit:
  37.535 -    return v;
  37.536 -}
  37.537 -
  37.538 -Sxpr Parser_get_all(Parser *p){
  37.539 -    Sxpr v = ONULL;
  37.540 -    if(CONSP(p->val)){
  37.541 -        v = p->val;
  37.542 -        p->val = ONONE;
  37.543 -    } else if(p->start_state && CONSP(p->start_state->val)){
  37.544 -        v = p->start_state->val;
  37.545 -        p->start_state->val = ONULL;
  37.546 -        v = nrev(v);
  37.547 -    }
  37.548 -    return v;
  37.549 -}
  37.550 -
  37.551 -static int state_comment(Parser *p, char c){
  37.552 -    int err = 0;
  37.553 -    if(c == '\n' || Parser_at_eof(p)){
  37.554 -        Parser_pop(p);
  37.555 -    } else {
  37.556 -        err = input_char(p, c);
  37.557 -    }
  37.558 -    return err;
  37.559 -}
  37.560 -
  37.561 -static int begin_comment(Parser *p, char c){
  37.562 -    int err = 0;
  37.563 -    err = Parser_push(p, state_comment, "comment");
  37.564 -    if(err) goto exit;
  37.565 -    err = input_char(p, c);
  37.566 -  exit:
  37.567 -    return err;
  37.568 -}
  37.569 -
  37.570 -static int end_string(Parser *p){
  37.571 -    int err = 0;
  37.572 -    err = Parser_string(p);
  37.573 -    if(err) goto exit;
  37.574 -    err = Parser_return(p);
  37.575 -  exit:
  37.576 -    return err;
  37.577 -}
  37.578 -
  37.579 -static int octaldone(Parser *p){
  37.580 -    int err = 0;
  37.581 -    char d = (char)(p->state->ival & 0xff);
  37.582 -    Parser_pop(p);
  37.583 -    err = Parser_input_char(p, d);
  37.584 -    return err;
  37.585 -}
  37.586 -
  37.587 -static int octaldigit(Parser *p, int d){
  37.588 -    int err = 0;
  37.589 -    p->state->ival *= 8;
  37.590 -    p->state->ival += d; 
  37.591 -    p->state->count++;
  37.592 -    if(err) goto exit;
  37.593 -    if(p->state->ival < 0 || p->state->ival > 0xff){
  37.594 -        err = Parser_error(p);
  37.595 -        goto exit;
  37.596 -    }
  37.597 -    if(p->state->count == 3){
  37.598 -        err = octaldone(p);
  37.599 -    }
  37.600 -  exit:
  37.601 -    return err;
  37.602 -}
  37.603 -
  37.604 -static int state_octal(Parser *p, char c){
  37.605 -    int err = 0;
  37.606 -    if(Parser_at_eof(p)){
  37.607 -        err = Parser_error_id(p, PARSE_ERR_UNEXPECTED_EOF);
  37.608 -        goto exit;
  37.609 -    } else if('0' <= c && c <= '7'){
  37.610 -        err = octaldigit(p, c - '0');
  37.611 -    } else {
  37.612 -        err = octaldone(p);
  37.613 -        if(err) goto exit;
  37.614 -        Parser_input_char(p, c);
  37.615 -    }
  37.616 -  exit:
  37.617 -    return err;
  37.618 -}
  37.619 -
  37.620 -static int hexdone(Parser *p){
  37.621 -    int err = 0;
  37.622 -    char d = (char)(p->state->ival & 0xff);
  37.623 -    Parser_pop(p);
  37.624 -    err = Parser_input_char(p, d);
  37.625 -    return err;
  37.626 -}
  37.627 -    
  37.628 -static int hexdigit(Parser *p, int d){
  37.629 -    int err = 0;
  37.630 -    p->state->ival *= 16;
  37.631 -    p->state->ival += d; 
  37.632 -    p->state->count++;
  37.633 -    if(err) goto exit;
  37.634 -    if(p->state->ival < 0 || p->state->ival > 0xff){
  37.635 -        err = Parser_error(p);
  37.636 -        goto exit;
  37.637 -    }
  37.638 -    if(p->state->count == 2){
  37.639 -        err = hexdone(p);
  37.640 -    }
  37.641 -  exit:
  37.642 -    return err;
  37.643 -}
  37.644 -    
  37.645 -static int state_hex(Parser *p, char c){
  37.646 -    int err = 0;
  37.647 -    if(Parser_at_eof(p)){
  37.648 -        err = Parser_error_id(p, PARSE_ERR_UNEXPECTED_EOF);
  37.649 -        goto exit;
  37.650 -    } else if('0' <= c && c <= '9'){
  37.651 -        err = hexdigit(p, c - '0');
  37.652 -    } else if('A' <= c && c <= 'F'){
  37.653 -        err = hexdigit(p, c - 'A' + 10);
  37.654 -    } else if('a' <= c && c <= 'f'){
  37.655 -        err = hexdigit(p, c - 'a' + 10);
  37.656 -    } else if(p->state->count){
  37.657 -        err = hexdone(p);
  37.658 -        if(err) goto exit;
  37.659 -        Parser_input_char(p, c);
  37.660 -    }
  37.661 -  exit:
  37.662 -    return err;
  37.663 -}
  37.664 -
  37.665 -static int state_escape(Parser *p, char c){
  37.666 -    int err = 0;
  37.667 -    char d;
  37.668 -    if(Parser_at_eof(p)){
  37.669 -        err = Parser_error_id(p, PARSE_ERR_UNEXPECTED_EOF);
  37.670 -        goto exit;
  37.671 -    }
  37.672 -    if(get_escape(c, &d) == 0){
  37.673 -        err = save_char(p, d);
  37.674 -        if(err) goto exit;
  37.675 -        Parser_pop(p);
  37.676 -    } else if(c == 'x'){
  37.677 -        p->state->fn = state_hex;
  37.678 -        p->state->ival = 0;
  37.679 -        p->state->count = 0;
  37.680 -    } else {
  37.681 -        p->state->fn = state_octal;
  37.682 -        p->state->ival = 0;
  37.683 -        p->state->count = 0;
  37.684 -        err = Parser_input_char(p, c);
  37.685 -    }
  37.686 -  exit:
  37.687 -    return err;
  37.688 -}
  37.689 -
  37.690 -static int state_string(Parser *p, char c){
  37.691 -    int err = 0;
  37.692 -    if(Parser_at_eof(p)){
  37.693 -        err = Parser_error_id(p, PARSE_ERR_UNEXPECTED_EOF);
  37.694 -    } else if(c == p->state->delim){
  37.695 -        err = end_string(p);
  37.696 -    } else if(c == '\\'){
  37.697 -        err = Parser_push(p, state_escape, "escape");
  37.698 -    } else {
  37.699 -        err = save_char(p, c);
  37.700 -    }
  37.701 -    return err;
  37.702 -}
  37.703 -
  37.704 -static int begin_string(Parser *p, char c){
  37.705 -    int err = 0;
  37.706 -    err = Parser_push(p, state_string, "string");
  37.707 -    if(err) goto exit;
  37.708 -    new_token(p);
  37.709 -    p->state->delim = c;
  37.710 -  exit:
  37.711 -    return err;
  37.712 -}
  37.713 -
  37.714 -static int end_atom(Parser *p){
  37.715 -    int err = 0;
  37.716 -    err = Parser_atom(p);
  37.717 -    if(err) goto exit;
  37.718 -    err = Parser_return(p);
  37.719 -  exit:
  37.720 -    return err;
  37.721 -}
  37.722 -
  37.723 -static int state_atom(Parser *p, char c){
  37.724 -    int err = 0;
  37.725 -    if(Parser_at_eof(p)){
  37.726 -        err = end_atom(p);
  37.727 -    } else if(is_separator(p, c) ||
  37.728 -              in_space_class(c) ||
  37.729 -              in_comment_class(c)){
  37.730 -        err = end_atom(p);
  37.731 -        if(err) goto exit;
  37.732 -        err = Parser_input_char(p, c);
  37.733 -    } else {
  37.734 -        err = save_char(p, c);
  37.735 -    }
  37.736 -  exit:
  37.737 -    return err;
  37.738 -}
  37.739 -
  37.740 -static int begin_atom(Parser *p, char c){
  37.741 -    int err = 0;
  37.742 -    err = Parser_push(p, state_atom, "atom");
  37.743 -    if(err) goto exit;
  37.744 -    new_token(p);
  37.745 -    err = save_char(p, c);
  37.746 -  exit:
  37.747 -    return err;
  37.748 -}
  37.749 -
  37.750 -static int end_data(Parser *p){
  37.751 -    int err = 0;
  37.752 -    err = Parser_data(p);
  37.753 -    if(err) goto exit;
  37.754 -    err = Parser_return(p);
  37.755 -  exit:
  37.756 -    return err;
  37.757 -}
  37.758 -
  37.759 -static int counted_data(Parser *p, char c){
  37.760 -    int err = 0;
  37.761 -    err = save_char(p, c);
  37.762 -    if(err) goto exit;
  37.763 -    if(token_len(p) == p->state->count){
  37.764 -        err = end_data(p);
  37.765 -    }
  37.766 -  exit:
  37.767 -    return err;
  37.768 -}
  37.769 -
  37.770 -static int counted_data_count(Parser *p, char c){
  37.771 -    int err = 0;
  37.772 -    if(c == p->state->delim){
  37.773 -        new_token(p);
  37.774 -        p->state->count = p->state->ival;
  37.775 -        p->state->fn = counted_data;
  37.776 -    } else if('0' <= c && c <= '9'){
  37.777 -        p->state->ival *= 10;
  37.778 -        p->state->ival += c - '0';
  37.779 -    } else {
  37.780 -        err = -EINVAL;
  37.781 -    }
  37.782 -    return err;
  37.783 -}
  37.784 -
  37.785 -static int quoted_data(Parser *p, char c){
  37.786 -    int err = 0;
  37.787 -    int count = p->state->count;
  37.788 -    err = save_char(p, c);
  37.789 -    if(err) goto exit;
  37.790 -    // Check that buf is longer than delim and
  37.791 -    // ends with delim. If so, trim delim off and return.
  37.792 -    if((token_len(p) >= count) &&
  37.793 -       !memcmp(p->tok_end - count, p->buf, count)){
  37.794 -        p->tok_end -= count;
  37.795 -        end_data(p);
  37.796 -    }
  37.797 -  exit:
  37.798 -    return err;
  37.799 -}
  37.800 -
  37.801 -static int quoted_data_delim(Parser *p, char c){
  37.802 -    // Saves the delim in the token buffer.
  37.803 -    int err = 0;
  37.804 -    err = save_char(p, c);
  37.805 -    if(err) goto exit;
  37.806 -    if(c == p->state->delim){
  37.807 -        p->state->fn = quoted_data;
  37.808 -        p->state->count = token_len(p);
  37.809 -        // Advance the token pointer past the delim.
  37.810 -        p->tok = p->tok_end;
  37.811 -    }
  37.812 -  exit:
  37.813 -    return err;
  37.814 -}
  37.815 -
  37.816 -static int state_data(Parser *p, char c){
  37.817 -    // Quoted data:
  37.818 -    // <<delim< anything not containing delimiter<delim<
  37.819 -    // Where 'delim' is anything not containing '<'.
  37.820 -    // Counted data:
  37.821 -    // <*nnn..* N bytes
  37.822 -    // Where nnn... is N in decimal (
  37.823 -    int err = 0;
  37.824 -    switch(c){
  37.825 -    case c_data_count:
  37.826 -        p->state->delim = c;
  37.827 -        p->state->fn = counted_data_count;
  37.828 -        p->state->ival = 0;
  37.829 -        new_token(p);
  37.830 -        break;
  37.831 -    case c_data_quote:
  37.832 -        p->state->delim = c;
  37.833 -        p->state->fn = quoted_data_delim;
  37.834 -        new_token(p);
  37.835 -        err = save_char(p, c);
  37.836 -        break;
  37.837 -    default:
  37.838 -        err = Parser_error(p);
  37.839 -        break;
  37.840 -    }
  37.841 -    return err;
  37.842 -}
  37.843 -
  37.844 -static int begin_data(Parser *p, char c){
  37.845 -    int err = 0;
  37.846 -    err = Parser_push(p, state_data, "data");
  37.847 -    if(err) goto exit;
  37.848 -    new_token(p);
  37.849 -  exit:
  37.850 -    return err;
  37.851 -}
  37.852 -
  37.853 -static int state_list(Parser *p, char c){
  37.854 -    int err = 0;
  37.855 -    dprintf(">\n");
  37.856 -    if(Parser_at_eof(p)){
  37.857 -        err = Parser_error_id(p, PARSE_ERR_UNEXPECTED_EOF);
  37.858 -    } else if(c == c_list_close){
  37.859 -        p->state->val = nrev(p->state->val);
  37.860 -        err = Parser_return(p);
  37.861 -    } else {
  37.862 -        err = state_start(p, c);
  37.863 -    }
  37.864 -    dprintf("< err=%d\n", err);
  37.865 -    return err;
  37.866 -    
  37.867 -}
  37.868 -
  37.869 -static int begin_list(Parser *p, char c){
  37.870 -    return Parser_push(p, state_list, "list");
  37.871 -}
  37.872 -
  37.873 -static int state_start(Parser *p, char c){
  37.874 -    int err = 0;
  37.875 -    dprintf(">\n");
  37.876 -    if(Parser_at_eof(p)){
  37.877 -        err = Parser_return(p);
  37.878 -    } else if(in_space_class(c)){
  37.879 -        //skip
  37.880 -    } else if(in_comment_class(c)){
  37.881 -        begin_comment(p, c);
  37.882 -    } else if(c == c_list_open){
  37.883 -        begin_list(p, c);
  37.884 -    } else if(c == c_list_close){
  37.885 -        err = Parser_error(p);
  37.886 -    } else if(in_string_quote_class(c)){
  37.887 -        begin_string(p, c);
  37.888 -    } else if(c == c_data_open){
  37.889 -        begin_data(p, c);
  37.890 -    } else if(in_printable_class(c)){
  37.891 -        begin_atom(p, c);
  37.892 -    } else if(c == 0x04){
  37.893 -        //ctrl-D, EOT: end-of-text.
  37.894 -        Parser_input_eof(p);
  37.895 -    } else {
  37.896 -        err = Parser_error(p);
  37.897 -    }
  37.898 -    dprintf("< err=%d\n", err);
  37.899 -    return err;
  37.900 -}
  37.901 -
  37.902 -int begin_start(Parser *p, char c){
  37.903 -    int err = 0;
  37.904 -    dprintf(">\n");
  37.905 -    err = Parser_push(p, state_start, "start");
  37.906 -    if(err) goto exit;
  37.907 -    p->start_state = p->state;
  37.908 -  exit:
  37.909 -    dprintf("< err=%d\n", err);
  37.910 -    return err;
  37.911 -}
  37.912 -
  37.913 -int Parser_input_char(Parser *p, char c){
  37.914 -    int err = 0;
  37.915 -    if(Parser_at_eof(p)){
  37.916 -        //skip;
  37.917 -    } else {
  37.918 -        input_char(p, c);
  37.919 -    }
  37.920 -    if(!p->state){
  37.921 -        err = p->begin(p, c);
  37.922 -        if(err) goto exit;
  37.923 -    }
  37.924 -    err = p->state->fn(p, c);
  37.925 -  exit:
  37.926 -    return err;
  37.927 -}
  37.928 -
  37.929 -int Parser_input_eof(Parser *p){
  37.930 -    int err = 0;
  37.931 -    p->eof = 1;
  37.932 -    err = Parser_input_char(p, IOSTREAM_EOF);
  37.933 -    return err;
  37.934 -}
  37.935 -
  37.936 -int Parser_input(Parser *p, char *buf, int buf_n){
  37.937 -    int err = 0;
  37.938 -    int i = 0;
  37.939 -    dprintf("> |%s|\n", buf);
  37.940 -    if(buf_n <= 0){
  37.941 -        err = Parser_input_eof(p);
  37.942 -        goto exit;
  37.943 -    }
  37.944 -    for(i = 0; i < buf_n; i++){
  37.945 -        err = Parser_input_char(p, buf[i]);
  37.946 -        if(err) goto exit;
  37.947 -    }
  37.948 -  exit:
  37.949 -    err = (err < 0 ? err : buf_n);
  37.950 -    dprintf("< err=%d\n", err);
  37.951 -    return err;
  37.952 -}
  37.953 -
  37.954 -#ifdef SXPR_PARSER_MAIN
  37.955 -/* Stuff for standalone testing. */
  37.956 -
  37.957 -#include "file_stream.h"
  37.958 -//#include "string_stream.h"
  37.959 -
  37.960 -/** Main program for testing.
  37.961 - * Parses input and prints it.
  37.962 - *
  37.963 - * @param argc number of arguments
  37.964 - * @param argv arguments
  37.965 - * @return error code
  37.966 - */
  37.967 -int main(int argc, char *argv[]){
  37.968 -    Parser *pin;
  37.969 -    int err = 0;
  37.970 -    char buf[1024];
  37.971 -    int k;
  37.972 -    Sxpr obj;
  37.973 -    int i = 0;
  37.974 -
  37.975 -    pin = Parser_new();
  37.976 -    Parser_set_error_stream(pin, iostdout);
  37.977 -    dprintf("> parse...\n");
  37.978 -    while(1){
  37.979 -        k = fread(buf, 1, 100, stdin);
  37.980 -        if(k>=0){
  37.981 -            buf[k+1] = '\0';
  37.982 -        }
  37.983 -        err = Parser_input(pin, buf, k);
  37.984 -        while(Parser_ready(pin)){
  37.985 -            obj = Parser_get_val(pin);
  37.986 -            printf("obj %d\n", i++);
  37.987 -            objprint(iostdout, obj, 0); printf("\n");
  37.988 -        }
  37.989 -        if(k <= 0) break;
  37.990 -    }
  37.991 -    dprintf("> err=%d\n", err);
  37.992 -    return 0;
  37.993 -}
  37.994 -#endif
    38.1 --- a/tools/libxutil/sxpr_parser.h	Tue May 24 21:10:23 2005 +0000
    38.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    38.3 @@ -1,154 +0,0 @@
    38.4 -/*
    38.5 - * Copyright (C) 2001 - 2005 Mike Wray <mike.wray@hp.com>
    38.6 - *
    38.7 - * This library is free software; you can redistribute it and/or modify
    38.8 - * it under the terms of the GNU Lesser General Public License as
    38.9 - * published by the Free Software Foundation; either version 2.1 of the
   38.10 - * License, or  (at your option) any later version. This library is 
   38.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   38.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   38.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   38.14 - * See the GNU Lesser General Public License for more details.
   38.15 - *
   38.16 - * You should have received a copy of the GNU Lesser General Public License
   38.17 - * along with this library; if not, write to the Free Software Foundation,
   38.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   38.19 - */
   38.20 -
   38.21 -#ifndef _XUTIL_SXPR_PARSER_H_
   38.22 -#define _XUTIL_SXPR_PARSER_H_
   38.23 -
   38.24 -#include "sxpr.h"
   38.25 -#include "iostream.h"
   38.26 -
   38.27 -/** @file
   38.28 - * Sxpr parsing definitions.
   38.29 - */
   38.30 -
   38.31 -/** Initial size of a parser input buffer.
   38.32 - */
   38.33 -#define PARSER_BUF_SIZE 512
   38.34 -
   38.35 -/** Input buffer size increment (when it's full).
   38.36 - */
   38.37 -#define PARSER_BUF_INCREMENT 512
   38.38 -
   38.39 -struct Parser;
   38.40 -typedef int ParserStateFn(struct Parser *, char c);
   38.41 -
   38.42 -typedef struct ParserState {
   38.43 -    struct ParserState *parent;
   38.44 -    Sxpr val;
   38.45 -    int ival;
   38.46 -    int count;
   38.47 -    char delim;
   38.48 -    ParserStateFn *fn;
   38.49 -    char *name;
   38.50 -} ParserState;
   38.51 -
   38.52 -typedef struct Parser {
   38.53 -    /** Initial state function. */
   38.54 -    ParserStateFn *begin;
   38.55 -    /** Parse value. */
   38.56 -    Sxpr val;
   38.57 -    /** Error reporting stream (null for no reports). */
   38.58 -    IOStream *error_out;
   38.59 -    /** End-of-file flag, */
   38.60 -    int eof;
   38.61 -    /** Error flag. Non-zero if there has been a read error. */
   38.62 -    int err;
   38.63 -    /** Line number on input (from 1). */
   38.64 -    int line_no;
   38.65 -    /** Column number of input (reset on new line). */
   38.66 -    int char_no;
   38.67 -    /** Buffer for reading tokens. */
   38.68 -    char *buf;
   38.69 -    char *buf_end;
   38.70 -    char *tok;
   38.71 -    char *tok_end;
   38.72 -    /** Line the last token started on. */
   38.73 -    int tok_begin_line;
   38.74 -    /** Character number the last token started on. */
   38.75 -    int tok_begin_char;
   38.76 -    /** Parsing flags. */
   38.77 -    int flags;
   38.78 -    ParserState *state;
   38.79 -    ParserState *start_state;
   38.80 -} Parser;
   38.81 -
   38.82 -/** Parser error codes. */
   38.83 -typedef enum {
   38.84 -    PARSE_ERR_NONE=0,
   38.85 -    PARSE_ERR_UNSPECIFIED,
   38.86 -    PARSE_ERR_NOMEM,
   38.87 -    PARSE_ERR_UNEXPECTED_EOF,
   38.88 -    PARSE_ERR_TOKEN_TOO_LONG,
   38.89 -    PARSE_ERR_INVALID_SYNTAX,
   38.90 -    PARSE_ERR_INVALID_ESCAPE,
   38.91 -} ParseErrorId;
   38.92 -
   38.93 -
   38.94 -/** Parser flags. */
   38.95 -//enum {
   38.96 -//};
   38.97 -
   38.98 -/** Raise some parser flags.
   38.99 - *
  38.100 - * @param in parser
  38.101 - * @param flags flags mask
  38.102 - */
  38.103 -inline static void Parser_flags_raise(Parser *in, int flags){
  38.104 -    in->flags |= flags;
  38.105 -}
  38.106 -
  38.107 -/** Lower some parser flags.
  38.108 - *
  38.109 - * @param in parser
  38.110 - * @param flags flags mask
  38.111 - */
  38.112 -inline static void Parser_flags_lower(Parser *in, int flags){
  38.113 -    in->flags &= ~flags;
  38.114 -}
  38.115 -
  38.116 -/** Clear all parser flags.
  38.117 - *
  38.118 - * @param in parser
  38.119 - */
  38.120 -inline static void Parser_flags_clear(Parser *in){
  38.121 -    in->flags = 0;
  38.122 -}
  38.123 -
  38.124 -extern void Parser_free(Parser *z);
  38.125 -extern Parser * Parser_new(void);
  38.126 -extern int Parser_input(Parser *p, char *buf, int buf_n);
  38.127 -extern int Parser_input_eof(Parser *p);
  38.128 -extern int Parser_input_char(Parser *p, char c);
  38.129 -extern void Parser_set_error_stream(Parser *z, IOStream *error_out);
  38.130 -
  38.131 -extern int Parser_error_message(Parser *in, char *buf, int n);
  38.132 -extern int Parser_has_error(Parser *in);
  38.133 -extern int Parser_at_eof(Parser *in);
  38.134 -
  38.135 -extern int Parser_ready(Parser *p);
  38.136 -extern Sxpr Parser_get_val(Parser *p);
  38.137 -extern Sxpr Parser_get_all(Parser *p);
  38.138 -
  38.139 -/* Internal parser api. */
  38.140 -void Parser_pop(Parser *p);
  38.141 -int Parser_push(Parser *p, ParserStateFn *fn, char *name);
  38.142 -int Parser_return(Parser *p);
  38.143 -int Parser_at_eof(Parser *p);
  38.144 -int Parser_error(Parser *in);
  38.145 -int Parser_set_value(Parser *p, Sxpr val);
  38.146 -int Parser_intern(Parser *p);
  38.147 -int Parser_string(Parser *p);
  38.148 -int Parser_data(Parser *p);
  38.149 -int Parser_uint(Parser *p);
  38.150 -
  38.151 -char *peek_token(Parser *p);
  38.152 -char *copy_token(Parser *p);
  38.153 -void new_token(Parser *p);
  38.154 -int save_char(Parser *p, char c);
  38.155 -int token_len(Parser *p);
  38.156 -
  38.157 -#endif /* ! _XUTIL_SXPR_PARSER_H_ */
    39.1 --- a/tools/libxutil/sys_net.c	Tue May 24 21:10:23 2005 +0000
    39.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    39.3 @@ -1,319 +0,0 @@
    39.4 -/*
    39.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    39.6 - *
    39.7 - * This library is free software; you can redistribute it and/or modify
    39.8 - * it under the terms of the GNU Lesser General Public License as
    39.9 - * published by the Free Software Foundation; either version 2.1 of the
   39.10 - * License, or  (at your option) any later version. This library is 
   39.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   39.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   39.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   39.14 - * See the GNU Lesser General Public License for more details.
   39.15 - *
   39.16 - * You should have received a copy of the GNU Lesser General Public License
   39.17 - * along with this library; if not, write to the Free Software Foundation,
   39.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   39.19 - */
   39.20 -
   39.21 -#include "sys_net.h"
   39.22 -#include "sys_string.h"
   39.23 -
   39.24 -#ifdef __KERNEL__
   39.25 -#  include <linux/errno.h>
   39.26 -#else
   39.27 -#  include <errno.h>
   39.28 -#endif
   39.29 -
   39.30 -/** @file
   39.31 - * All network data are kept in network order and only converted to
   39.32 - * host order for display. Network data includes IP addresses, port numbers and
   39.33 - * network masks.
   39.34 - */
   39.35 -
   39.36 -/** Maximum value for a port. */
   39.37 -#define PORT_MAX 0xffff
   39.38 -
   39.39 -/** Convert a number of bits to a network mask
   39.40 - * for IP addresses. The number of bits must
   39.41 - * be in the range 1-31.
   39.42 - *
   39.43 - * @param n number of bits to set in the mask
   39.44 - * @return value with n high bits set (in network order)
   39.45 - */
   39.46 -unsigned long bits_to_mask(int n){
   39.47 -    unsigned long mask = (n ? (1 << 31) : 0);
   39.48 -    int i;
   39.49 -    for(i=1; i<n; i++){
   39.50 -        mask |= (mask >> 1);
   39.51 -    }
   39.52 -    return htonl(mask);
   39.53 -}
   39.54 -
   39.55 -/** Convert a network mask to a number of bits.
   39.56 - *
   39.57 - * @param mask network mask in network order
   39.58 - * @return number of bits in mask
   39.59 - */
   39.60 -int mask_to_bits(unsigned long mask){
   39.61 -    // Start with n set to the number of bits in the mask. Then reduce n by
   39.62 -    // the number of low zero bits in the mask.
   39.63 -    int n = 32;
   39.64 -    for(mask = ntohl(mask);
   39.65 -        (mask & 1)==0 && n>0;
   39.66 -        mask >>= 1){
   39.67 -        n--;
   39.68 -    }
   39.69 -    return n;
   39.70 -}
   39.71 -
   39.72 -/** Get the index of the first occurrence of a character in a string.
   39.73 - * Stops at end of string or after n characters.
   39.74 - *
   39.75 - * @param s input string
   39.76 - * @param n maximum number of charactes to search
   39.77 - * @param c character to look for
   39.78 - * @return index of first occurrence, -1 if not found
   39.79 - */
   39.80 -inline static int indexof(const char *s, int n, char c){
   39.81 -    int i;
   39.82 -    for(i=0; i<n && *s; i++, s++){
   39.83 -        if(*s == c) return i;
   39.84 -    }
   39.85 -    return -1;
   39.86 -}
   39.87 -
   39.88 -/** Convert an IPv4 address in dot notation into an unsigned long (in network order).
   39.89 - *
   39.90 - * @param s input string
   39.91 - * @param address where to put the address
   39.92 - * @return 0 on success, negative on error
   39.93 - */
   39.94 -int get_inet_addr(const char *s, unsigned long *address){
   39.95 -    // Number of bits in a byte.
   39.96 -    const int BYTE_BITS = 8;
   39.97 -    // Number of bytes in a word.
   39.98 -    const int WORD_BYTES = 4;
   39.99 -    // Max value for a component of an address.
  39.100 -    const int ADDR_MAX  = 255;
  39.101 -    // Separator for components of an address.
  39.102 -    const char dot = '.';
  39.103 -
  39.104 -    int n;
  39.105 -    unsigned long addr = 0;
  39.106 -    unsigned long v;
  39.107 -    int i;
  39.108 -    int err = -EINVAL;
  39.109 -    // Bit shift for the current byte.
  39.110 -    int shift = BYTE_BITS * (WORD_BYTES - 1);
  39.111 -    char buf[64];
  39.112 -
  39.113 -    n = strlen(s);
  39.114 -    if(n >= sizeof(buf)){
  39.115 -        goto exit;
  39.116 -    }
  39.117 -    for(i=0; i < WORD_BYTES; i++){
  39.118 -        int idx = indexof(s, n, dot);
  39.119 -        idx = (idx < 0 ? strlen(s) : idx);
  39.120 -        strncpy(buf, s, idx); buf[idx]='\0';
  39.121 -        if(convert_atoul(buf, &v)){
  39.122 -            goto exit;
  39.123 -        }
  39.124 -        if(v < 0 || v > ADDR_MAX){
  39.125 -            goto exit;
  39.126 -        }
  39.127 -        addr |= (v << shift);
  39.128 -        if(idx == n) break;
  39.129 -        shift -= BYTE_BITS;
  39.130 -        s += idx+1;
  39.131 -    }
  39.132 -    err = 0;
  39.133 -  exit:
  39.134 -    addr = htonl(addr);
  39.135 -    *address = (err ? 0 : addr);
  39.136 -    return err;
  39.137 -}
  39.138 -
  39.139 -#ifdef __KERNEL__
  39.140 -/** Convert an address in network order to IPv4 dot notation.
  39.141 - * The return value is a static buffer which is overwritten on each call.
  39.142 - *
  39.143 - * @param inaddr address (in network order)
  39.144 - * @return address in dot notation
  39.145 - */
  39.146 -char *inet_ntoa(struct in_addr inaddr){
  39.147 -    static char address[16] = {};
  39.148 -    uint32_t addr = ntohl(inaddr.s_addr);
  39.149 -    snprintf(address, sizeof(address), "%d.%d.%d.%d",
  39.150 -            (unsigned)((addr >> 24) & 0xff),
  39.151 -            (unsigned)((addr >> 16) & 0xff),
  39.152 -            (unsigned)((addr >>  8) & 0xff),
  39.153 -            (unsigned)((addr      ) & 0xff));
  39.154 -    return address;
  39.155 -}
  39.156 -
  39.157 -
  39.158 -/** Convert a string in IPv4 dot notation to an int in network order.
  39.159 - *
  39.160 - * @param address address in dot notation
  39.161 - * @param inp result of conversion (in network order)
  39.162 - * @return 0 on success, error code on error
  39.163 - */
  39.164 -int inet_aton(const char *address, struct in_addr *inp){
  39.165 -    int err = 0; 
  39.166 -    unsigned long addr;
  39.167 -    
  39.168 -    err = get_inet_addr(address, &addr);
  39.169 -    if(err) goto exit;
  39.170 -    inp->s_addr = addr;
  39.171 -  exit:
  39.172 -    return err;
  39.173 -}
  39.174 -#endif
  39.175 -
  39.176 -/** Convert a hostname or IPv4 address string to an address in network order.
  39.177 - *
  39.178 - * @param name input hostname or address string
  39.179 - * @param address where to put the address
  39.180 - * @return 0 if address found OK, nonzero otherwise
  39.181 - */
  39.182 -int get_host_address(const char *name, unsigned long *address){
  39.183 -#ifdef __KERNEL__
  39.184 -    return get_inet_addr(name, address);
  39.185 -#else
  39.186 -    struct hostent *host = gethostbyname(name);
  39.187 -    if(!host){
  39.188 -        return -EINVAL;
  39.189 -    }
  39.190 -    *address = ((struct in_addr *)(host->h_addr))->s_addr;
  39.191 -    return 0;
  39.192 -#endif
  39.193 -}
  39.194 -
  39.195 -/** Convert a service name to a port (in network order).
  39.196 - *
  39.197 - * @param name service name
  39.198 - * @param port where to put the port
  39.199 - * @return 0 if service port found OK, negative otherwise
  39.200 - */
  39.201 -int get_service_port(const char *name, unsigned long *port){
  39.202 -#ifdef __KERNEL__
  39.203 -    return -ENOSYS;
  39.204 -#else
  39.205 -    struct servent *service;
  39.206 -    service = getservbyname(name, 0);
  39.207 -    if(!service){
  39.208 -        return -EINVAL;
  39.209 -    }
  39.210 -    *port = service->s_port;
  39.211 -    return 0;
  39.212 -#endif
  39.213 -}
  39.214 -
  39.215 -/** Convert a port number (in network order) to a service name.
  39.216 - *
  39.217 - * @param port the port number
  39.218 - * @return service name if found OK, NULL otherwise
  39.219 - */
  39.220 -char *get_port_service(unsigned long port){
  39.221 -#ifdef __KERNEL__
  39.222 -    return NULL;
  39.223 -#else
  39.224 -    struct servent *service = getservbyport(port, 0);
  39.225 -    return (service ? service->s_name : NULL);
  39.226 -#endif
  39.227 -}
  39.228 -
  39.229 -/** Convert a decimal integer or service name to a port (in network order).
  39.230 - *
  39.231 - * @param s input to convert
  39.232 - * @param port where to put the port
  39.233 - * @return 0 if port found OK, -1 otherwise
  39.234 - */
  39.235 -int convert_service_to_port(const char *s, unsigned long *port){
  39.236 -    int err = 0;
  39.237 -    unsigned long value;
  39.238 -    if(convert_atoul(s, &value) == 0){
  39.239 -        int ok = (0 <= value) && (value <= PORT_MAX);
  39.240 -        if(ok){
  39.241 -            value = htons((unsigned short)value);
  39.242 -        } else {
  39.243 -            err = -EINVAL;
  39.244 -        }
  39.245 -    } else {
  39.246 -        err = get_service_port(s, &value);
  39.247 -    }
  39.248 -    *port = (err ? 0: value);
  39.249 -    return err;
  39.250 -}
  39.251 -
  39.252 -#define MAC_ELEMENT_N  6 // Number of elements in a MAC address.
  39.253 -#define MAC_DIGIT_N    2 // Number of digits in an element in a MAC address.
  39.254 -#define MAC_LENGTH    17 //((MAC_ELEMENT_N * MAC_DIGIT_N) + MAC_ELEMENT_N - 1)
  39.255 -
  39.256 -/** Convert a mac address from a string of the form
  39.257 - * XX:XX:XX:XX:XX:XX to numerical form (an array of 6 unsigned chars).
  39.258 - * Each X denotes a hex digit: 0..9, a..f, A..F.
  39.259 - * Also supports using '-' as the separator instead of ':'.
  39.260 - *
  39.261 - * @param mac_in string to convert
  39.262 - * @param mac destination for the value
  39.263 - * @return 0 on success, -1 on error
  39.264 - */
  39.265 -int mac_aton(const char *mac_in, unsigned char *mac){
  39.266 -    int err = 0;
  39.267 -    int i, j;
  39.268 -    const char *p;
  39.269 -    char sep = 0;
  39.270 -    unsigned char d;
  39.271 -    if(!mac_in || strlen(mac_in) != MAC_LENGTH){
  39.272 -        err = -1;
  39.273 -        goto exit;
  39.274 -    }
  39.275 -    for(i = 0, p = mac_in; i < MAC_ELEMENT_N; i++){
  39.276 -        d = 0;
  39.277 -        if(i){
  39.278 -            if(!sep){
  39.279 -                if(*p == ':' || *p == '-') sep = *p;
  39.280 -            }
  39.281 -            if(sep && *p == sep){
  39.282 -                p++;
  39.283 -            } else {
  39.284 -                err = -1;
  39.285 -                goto exit;
  39.286 -            }
  39.287 -        }
  39.288 -        for(j = 0; j < MAC_DIGIT_N; j++, p++){
  39.289 -            if(j) d <<= 4;
  39.290 -            if(*p >= '0' && *p <= '9'){
  39.291 -                d += (*p - '0');
  39.292 -            } else if(*p >= 'A' && *p <= 'F'){
  39.293 -                d += (*p - 'A') + 10;
  39.294 -            } else if(*p >= 'a' && *p <= 'f'){
  39.295 -                d += (*p - 'a') + 10;
  39.296 -            } else {
  39.297 -                err = -1;
  39.298 -                goto exit;
  39.299 -            }
  39.300 -        }
  39.301 -        mac[i] = d;
  39.302 -    }
  39.303 -  exit:
  39.304 -    return err;
  39.305 -}
  39.306 -
  39.307 -/** Convert a MAC address from numerical form to a string.
  39.308 - *
  39.309 - * @param mac address to convert
  39.310 - * @return static string value
  39.311 - */
  39.312 -char *mac_ntoa(const unsigned char *mac){
  39.313 -    static char buf[MAC_LENGTH + 1];
  39.314 -    int buf_n = sizeof(buf);
  39.315 -
  39.316 -    memset(buf, 0, buf_n);
  39.317 -    snprintf(buf, buf_n, "%02x:%02x:%02x:%02x:%02x:%02x",
  39.318 -             mac[0], mac[1], mac[2],
  39.319 -             mac[3], mac[4], mac[5]);
  39.320 -    buf[buf_n - 1] = '\0';
  39.321 -    return buf;
  39.322 -}
    40.1 --- a/tools/libxutil/sys_net.h	Tue May 24 21:10:23 2005 +0000
    40.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    40.3 @@ -1,78 +0,0 @@
    40.4 -/*
    40.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    40.6 - *
    40.7 - * This library is free software; you can redistribute it and/or modify
    40.8 - * it under the terms of the GNU Lesser General Public License as published by
    40.9 - * the Free Software Foundation; either version 2.1 of the License, or
   40.10 - * (at your option) any later version.
   40.11 - *
   40.12 - * This library is distributed in the hope that it will be useful,
   40.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   40.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   40.15 - * GNU Lesser General Public License for more details.
   40.16 - *
   40.17 - * You should have received a copy of the GNU Lesser General Public License
   40.18 - * along with this library; if not, write to the Free Software
   40.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   40.20 - */
   40.21 -
   40.22 -#ifndef _XUTIL_SYS_NET_H_
   40.23 -#define _XUTIL_SYS_NET_H_
   40.24 -/** @file
   40.25 - *
   40.26 - * Replacement for standard network includes.
   40.27 - * Works in user or kernel code.
   40.28 - */
   40.29 -
   40.30 -extern int get_inet_addr(const char *s, unsigned long *address);
   40.31 -extern unsigned long bits_to_mask(int n);
   40.32 -extern int mask_to_bits(unsigned long mask);
   40.33 -extern int get_host_address(const char *name, unsigned long *address);
   40.34 -extern int get_service_port(const char *name, unsigned long *port);
   40.35 -extern char *get_port_service(unsigned long port);
   40.36 -extern int convert_service_to_port(const char *s, unsigned long *port);
   40.37 -
   40.38 -#ifdef __KERNEL__
   40.39 -#include <linux/kernel.h>
   40.40 -#include <linux/types.h>
   40.41 -#include <linux/errno.h>
   40.42 -#include <linux/slab.h>
   40.43 -#include <asm/byteorder.h> 
   40.44 -
   40.45 -#ifndef htonl
   40.46 -#define htonl(x) __constant_htonl(x)
   40.47 -#endif
   40.48 -
   40.49 -#ifndef ntohl
   40.50 -#define ntohl(x) __constant_ntohl(x)
   40.51 -#endif
   40.52 -
   40.53 -#ifndef htons
   40.54 -#define htons(x) __constant_htons(x)
   40.55 -#endif
   40.56 -
   40.57 -#ifndef ntohs
   40.58 -#define ntohs(x) __constant_ntohs(x)
   40.59 -#endif
   40.60 -
   40.61 -#include <linux/in.h>
   40.62 -extern char *inet_ntoa(struct in_addr inaddr);
   40.63 -extern int inet_aton(const char *address, struct in_addr *inp);
   40.64 -
   40.65 -#else
   40.66 -
   40.67 -#include <limits.h>
   40.68 -#include <sys/socket.h>
   40.69 -#include <netinet/in.h>
   40.70 -#include <netdb.h>
   40.71 -#include <arpa/inet.h>
   40.72 -
   40.73 -#endif
   40.74 -
   40.75 -extern char *mac_ntoa(const unsigned char *macaddr);
   40.76 -extern int mac_aton(const char *addr, unsigned char *macaddr);
   40.77 -
   40.78 -#endif /* !_XUTIL_SYS_NET_H_ */
   40.79 -
   40.80 -
   40.81 -
    41.1 --- a/tools/libxutil/sys_string.c	Tue May 24 21:10:23 2005 +0000
    41.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    41.3 @@ -1,193 +0,0 @@
    41.4 -/*
    41.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    41.6 - *
    41.7 - * This library is free software; you can redistribute it and/or modify
    41.8 - * it under the terms of the GNU Lesser General Public License as published by
    41.9 - * the Free Software Foundation; either version 2.1 of the License, or
   41.10 - * (at your option) any later version.
   41.11 - *
   41.12 - * This library is distributed in the hope that it will be useful,
   41.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   41.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   41.15 - * GNU Lesser General Public License for more details.
   41.16 - *
   41.17 - * You should have received a copy of the GNU Lesser General Public License
   41.18 - * along with this library; if not, write to the Free Software
   41.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   41.20 - */
   41.21 -
   41.22 -#ifdef __KERNEL__
   41.23 -#  include <linux/config.h>
   41.24 -#  include <linux/module.h>
   41.25 -#  include <linux/kernel.h>
   41.26 -#  include <linux/errno.h>
   41.27 -#else
   41.28 -#  include <errno.h>
   41.29 -#endif
   41.30 -
   41.31 -#include "allocate.h"
   41.32 -#include "sys_string.h"
   41.33 -
   41.34 -/** Set the base to use for converting a string to a number.  Base is
   41.35 - * hex if starts with 0x, otherwise decimal.
   41.36 - *
   41.37 - * @param s input string
   41.38 - * @param base where to put the base
   41.39 - * @return rest of s to parse as a number
   41.40 - */
   41.41 -inline static const char * convert_set_base(const char *s, int *base){
   41.42 -    *base = 10;
   41.43 -    if(s){
   41.44 -        if(*s=='0'){
   41.45 -            s++;
   41.46 -            if(*s=='x' || *s=='X'){
   41.47 -                *base = 16;
   41.48 -                s++;
   41.49 -            }
   41.50 -        }
   41.51 -    }
   41.52 -    return s;
   41.53 -}
   41.54 -
   41.55 -/** Set the sign to use for converting a string to a number.
   41.56 - * Value is 1 for positive, -1 for negative.
   41.57 - *
   41.58 - * @param s input string
   41.59 - * @param sign where to put the sign
   41.60 - * @return rest of s to parse as a number
   41.61 - */
   41.62 -inline static const char * convert_set_sign(const char *s, int *sign){
   41.63 -    *sign = 1;
   41.64 -    if(s){
   41.65 -        if(*s == '+'){
   41.66 -            *sign = 1;
   41.67 -            s++;
   41.68 -        } else if (*s == '-'){
   41.69 -            *sign = -1;
   41.70 -            s++;
   41.71 -        }
   41.72 -    }
   41.73 -    return s;
   41.74 -}
   41.75 -
   41.76 -/** Get the numerical value of a digit in the given base.
   41.77 - *
   41.78 - * @param c digit character
   41.79 - * @param base to use
   41.80 - * @return numerical value of digit in range 0..base-1 or
   41.81 - * -1 if not in range for the base
   41.82 - */
   41.83 -inline static int convert_get_digit(char c, int base){
   41.84 -    int d;
   41.85 -
   41.86 -    if('0'<=c  && c<='9'){
   41.87 -        d = c - '0';
   41.88 -    } else if('a'<=c && c<='f'){
   41.89 -        d = c - 'a' + 10;
   41.90 -    } else if('A'<=c && c<='F'){
   41.91 -        d = c - 'A' + 10;
   41.92 -    } else {
   41.93 -        d = -1;
   41.94 -    }
   41.95 -    return (d < base ? d : -1);
   41.96 -}
   41.97 -
   41.98 -/** Convert a string to an unsigned long by parsing it as a number.
   41.99 - * Will accept hex or decimal in usual C syntax.
  41.100 - *
  41.101 - * @param str input string
  41.102 - * @param val where to put the result
  41.103 - * @return 0 if converted OK, negative otherwise
  41.104 - */
  41.105 -int convert_atoul(const char *str, unsigned long *val){
  41.106 -    int err = 0;
  41.107 -    unsigned long v = 0;
  41.108 -    int base;
  41.109 -    const char *s = str;
  41.110 -
  41.111 -    if(!s) {
  41.112 -        err = -EINVAL;
  41.113 -        goto exit;
  41.114 -    }
  41.115 -    s = convert_set_base(s, &base);
  41.116 -    for( ; !err && *s; s++){
  41.117 -        int digit = convert_get_digit(*s, base);
  41.118 -        if(digit<0){
  41.119 -            err = -EINVAL;
  41.120 -            goto exit;
  41.121 -        }
  41.122 -        v *= base;
  41.123 -        v += digit;
  41.124 -    } 
  41.125 -  exit:
  41.126 -    *val = (err ? 0 : v);
  41.127 -    return err;
  41.128 -}
  41.129 -
  41.130 -/** Convert a string to a long by parsing it as a number.
  41.131 - * Will accept hex or decimal in usual C syntax.
  41.132 - *
  41.133 - * @param str input string
  41.134 - * @param val where to put the result
  41.135 - * @return 0 if converted OK, negative otherwise
  41.136 - */
  41.137 -int convert_atol(const char *str, long *val){
  41.138 -    int err = 0;
  41.139 -    unsigned long v = 0;
  41.140 -    int base, sign = 1;
  41.141 -    const char *s = str;
  41.142 -
  41.143 -    if(!s) {
  41.144 -        err = -EINVAL;
  41.145 -        goto exit;
  41.146 -    }
  41.147 -    s = convert_set_sign(s, &sign);
  41.148 -    s = convert_set_base(s, &base);
  41.149 -    for( ; !err && *s; s++){
  41.150 -        int digit = convert_get_digit(*s, base);
  41.151 -        if(digit<0){
  41.152 -            err = -EINVAL;
  41.153 -            goto exit;
  41.154 -        }
  41.155 -        v *= base;
  41.156 -        v += digit;
  41.157 -    } 
  41.158 -    if(sign < 0) v = -v;
  41.159 -  exit:
  41.160 -    *val = (err ? 0 : v);
  41.161 -    return err;
  41.162 -}
  41.163 -
  41.164 -/** Combine a directory path with a relative path to produce
  41.165 - * a new path.
  41.166 - *
  41.167 - * @param s directory path
  41.168 - * @param t relative path
  41.169 - * @return new combined path s/t
  41.170 - */
  41.171 -int path_concat(char *s, char *t, char **val){
  41.172 -    int err = 0;
  41.173 -    int sn, tn, vn;
  41.174 -    char *v;
  41.175 -    sn = strlen(s);
  41.176 -    if(sn > 0 && s[sn-1] == '/'){
  41.177 -        sn--;
  41.178 -    }
  41.179 -    tn = strlen(t);
  41.180 -    if(tn > 0 && t[0] == '/'){
  41.181 -        tn--;
  41.182 -    }
  41.183 -    vn = sn+tn+1;
  41.184 -    v = (char*)allocate(vn+1);
  41.185 -    if(!v){
  41.186 -        err = -ENOMEM;
  41.187 -        goto exit;
  41.188 -    }
  41.189 -    strncpy(v, s, sn);
  41.190 -    v[sn] = '/';
  41.191 -    strncpy(v+sn+1, t, tn);
  41.192 -    v[vn] = '\0';
  41.193 -  exit:
  41.194 -    *val = (err ? NULL : v);
  41.195 -    return err;    
  41.196 -}
    42.1 --- a/tools/libxutil/sys_string.h	Tue May 24 21:10:23 2005 +0000
    42.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    42.3 @@ -1,92 +0,0 @@
    42.4 -/*
    42.5 - * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    42.6 - *
    42.7 - * This library is free software; you can redistribute it and/or modify
    42.8 - * it under the terms of the GNU Lesser General Public License as published by
    42.9 - * the Free Software Foundation; either version 2.1 of the License, or
   42.10 - * (at your option) any later version.
   42.11 - *
   42.12 - * This library is distributed in the hope that it will be useful,
   42.13 - * but WITHOUT ANY WARRANTY; without even the implied warranty of
   42.14 - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   42.15 - * GNU Lesser General Public License for more details.
   42.16 - *
   42.17 - * You should have received a copy of the GNU Lesser General Public License
   42.18 - * along with this library; if not, write to the Free Software
   42.19 - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   42.20 - */
   42.21 -
   42.22 -#ifndef _XUTIL_SYS_STRING_H_
   42.23 -#define _XUTIL_SYS_STRING_H_
   42.24 -/** @file
   42.25 - * Replacement for standard string includes.
   42.26 - * Works in user or kernel code.
   42.27 - */
   42.28 -/*============================================================================*/
   42.29 -#ifdef __KERNEL__
   42.30 -
   42.31 -#include <linux/config.h>
   42.32 -#include <linux/kernel.h>
   42.33 -#include <linux/string.h>
   42.34 -#include <linux/types.h>
   42.35 -#include <stdarg.h>
   42.36 -#include "allocate.h"
   42.37 -
   42.38 -#if 0
   42.39 -static inline int tolower(int c){
   42.40 -    return (c>='A' && c<='Z' ? (c-'A')+'a' : c);
   42.41 -}
   42.42 -#endif
   42.43 -
   42.44 -static inline int isalpha(int c){
   42.45 -    return (c>='A' && c<='Z') || (c>='a' && c<='z');
   42.46 -}
   42.47 -
   42.48 -static inline int isdigit(int c){
   42.49 -   return (c>='0' && c<='9');
   42.50 -}
   42.51 -
   42.52 -#if 0
   42.53 -static inline int strcasecmp(const char *s1, const char *s2){
   42.54 -	int c1, c2;
   42.55 -
   42.56 -	do {
   42.57 -		c1 = tolower(*s1++);
   42.58 -		c2 = tolower(*s2++);
   42.59 -	} while (c1 && c1 == c2);
   42.60 -	return c1 - c2;
   42.61 -}
   42.62 -#endif
   42.63 -
   42.64 -static inline char * strdup(const char *s){
   42.65 -    int n = (s ? 1+strlen(s) : 0);
   42.66 -    char *copy = (n ? allocate(n) : NULL);
   42.67 -    if(copy){
   42.68 -        strcpy(copy, s);
   42.69 -    }
   42.70 -    return copy;
   42.71 -}
   42.72 -
   42.73 -/*============================================================================*/
   42.74 -#else
   42.75 -#include <string.h>
   42.76 -#include <stdio.h>
   42.77 -
   42.78 -#ifndef _GNU_SOURCE
   42.79 -static inline size_t strnlen(const char *s, size_t n){
   42.80 -    int k = 0;
   42.81 -    if(s){
   42.82 -	for(k=0; *s && k<n; s++, k++){}
   42.83 -    }
   42.84 -    return k;
   42.85 -}
   42.86 -#endif
   42.87 -
   42.88 -#endif
   42.89 -/*============================================================================*/
   42.90 -
   42.91 -extern int convert_atoul(const char *s, unsigned long *v);
   42.92 -extern int convert_atol(const char *s, long *v);
   42.93 -extern int path_concat(char *s, char *t, char **val);
   42.94 -
   42.95 -#endif /* !_XUTIL_SYS_STRING_H_ */
    43.1 --- a/tools/libxutil/util.c	Tue May 24 21:10:23 2005 +0000
    43.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    43.3 @@ -1,106 +0,0 @@
    43.4 -/*
    43.5 - * Copyright (C) 2002 - 2004 Mike Wray <mike.wray@hp.com>.
    43.6 - *
    43.7 - * This library is free software; you can redistribute it and/or modify
    43.8 - * it under the terms of the GNU Lesser General Public License as
    43.9 - * published by the Free Software Foundation; either version 2.1 of the
   43.10 - * License, or  (at your option) any later version. This library is 
   43.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   43.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   43.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   43.14 - * See the GNU Lesser General Public License for more details.
   43.15 - *
   43.16 - * You should have received a copy of the GNU Lesser General Public License
   43.17 - * along with this library; if not, write to the Free Software Foundation,
   43.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   43.19 - */
   43.20 -
   43.21 -#include "sys_net.h"
   43.22 -#include "sys_string.h"
   43.23 -
   43.24 -#ifndef __KERNEL__
   43.25 -#  include <grp.h>   
   43.26 -#  include <pwd.h>  
   43.27 -#endif
   43.28 -
   43.29 -#include "util.h"
   43.30 -
   43.31 -
   43.32 -/** @file Various utility functions.
   43.33 - */
   43.34 -
   43.35 -/** Print an address (in network order) as an IPv4 address string
   43.36 - * in dot notation.
   43.37 - *
   43.38 - * @param io where to print address
   43.39 - * @param address to print (in network order)
   43.40 - * @return bytes printed
   43.41 - */
   43.42 -int print_address(IOStream *io, unsigned long address){
   43.43 -#ifdef __KERNEL__
   43.44 -    address = ntohl(address);
   43.45 -    return IOStream_print(io, "%u.%u.%u.%u", 
   43.46 -                          (unsigned)((address >> 24) & 0xff),
   43.47 -                          (unsigned)((address >> 16) & 0xff),
   43.48 -                          (unsigned)((address >>  8) & 0xff),
   43.49 -                          (unsigned)((address      ) & 0xff));
   43.50 -#else
   43.51 -    struct in_addr inaddr = { s_addr: address };
   43.52 -    return IOStream_print(io, inet_ntoa(inaddr));
   43.53 -#endif
   43.54 -}
   43.55 -
   43.56 -/** Get the protocol number for a protocol.
   43.57 - *
   43.58 - * @param name protocol name
   43.59 - * @param protocol where to put the protocol number
   43.60 - * @return 0 if OK, error otherwise
   43.61 - */  
   43.62 -int get_protocol_number(char *name, unsigned long *protocol){
   43.63 -#ifdef __KERNEL__
   43.64 -    return -1;
   43.65 -#else
   43.66 -    struct protoent *proto = getprotobyname(name);
   43.67 -    if(!proto){
   43.68 -	return -1;
   43.69 -    }
   43.70 -    *protocol = proto->p_proto;
   43.71 -    return 0;
   43.72 -#endif
   43.73 -}
   43.74 -
   43.75 -/** Get the protocol name for a protocol number.
   43.76 - *
   43.77 - * @param protocol number
   43.78 - * @return name or null
   43.79 - */
   43.80 -char *get_protocol_name(unsigned long protocol){
   43.81 -#ifdef __KERNEL__
   43.82 -    return 0;
   43.83 -#else
   43.84 -    struct protoent *proto = getprotobynumber(protocol);
   43.85 -    if(!proto){
   43.86 -	return 0;
   43.87 -    }
   43.88 -    return proto->p_name;
   43.89 -#endif
   43.90 -}
   43.91 -
   43.92 -/** Get the host name for an address.
   43.93 - *
   43.94 - * @param addr address
   43.95 - * @return host name or null
   43.96 - */
   43.97 -char *get_host_name(unsigned long addr){
   43.98 -#ifdef __KERNEL__
   43.99 -    return 0;
  43.100 -#else
  43.101 -    struct in_addr inaddr;
  43.102 -    struct hostent *host = 0;
  43.103 -
  43.104 -    inaddr.s_addr = addr;
  43.105 -    host = gethostbyaddr((char*)&inaddr, sizeof(inaddr), AF_INET);
  43.106 -    if(!host) return NULL;
  43.107 -    return host->h_name;
  43.108 -#endif
  43.109 -}
    44.1 --- a/tools/libxutil/util.h	Tue May 24 21:10:23 2005 +0000
    44.2 +++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
    44.3 @@ -1,28 +0,0 @@
    44.4 -/*
    44.5 - * Copyright (C) 2002 - 2004 Mike Wray <mike.wray@hp.com>.
    44.6 - *
    44.7 - * This library is free software; you can redistribute it and/or modify
    44.8 - * it under the terms of the GNU Lesser General Public License as
    44.9 - * published by the Free Software Foundation; either version 2.1 of the
   44.10 - * License, or  (at your option) any later version. This library is 
   44.11 - * distributed in the  hope that it will be useful, but WITHOUT ANY
   44.12 - * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   44.13 - * FITNESS FOR A PARTICULAR PURPOSE.
   44.14 - * See the GNU Lesser General Public License for more details.
   44.15 - *
   44.16 - * You should have received a copy of the GNU Lesser General Public License
   44.17 - * along with this library; if not, write to the Free Software Foundation,
   44.18 - * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   44.19 - */
   44.20 -
   44.21 -#ifndef _XEN_LIB_UTIL_H_
   44.22 -#define _XEN_LIB_UTIL_H_
   44.23 -
   44.24 -#include "iostream.h"
   44.25 -
   44.26 -extern int print_address(IOStream *io, unsigned long address);
   44.27 -extern int get_protocol_number(char *name, unsigned long *protocol);
   44.28 -extern char *get_protocol_name(unsigned long protocol);
   44.29 -extern char *get_host_name(unsigned long addr);
   44.30 -
   44.31 -#endif /* ! _XEN_LIB_UTIL_H_ */
    45.1 --- a/tools/misc/Makefile	Tue May 24 21:10:23 2005 +0000
    45.2 +++ b/tools/misc/Makefile	Tue May 24 21:17:29 2005 +0000
    45.3 @@ -45,4 +45,4 @@ clean:
    45.4  	$(CC) -c $(CFLAGS) -o $@ $<
    45.5  
    45.6  $(TARGETS): %: %.o Makefile
    45.7 -	$(CC) $(CFLAGS) -o $@ $< -L$(XEN_LIBXC) -lxc -L$(XEN_LIBXUTIL) -lxutil
    45.8 +	$(CC) $(CFLAGS) -o $@ $< -L$(XEN_LIBXC) -lxc
    46.1 --- a/tools/misc/cpuperf/Makefile	Tue May 24 21:10:23 2005 +0000
    46.2 +++ b/tools/misc/cpuperf/Makefile	Tue May 24 21:17:29 2005 +0000
    46.3 @@ -38,7 +38,7 @@ clean:
    46.4  	$(CC) $(CFLAGS) -o $@ $<
    46.5  
    46.6  cpuperf-xen: cpuperf.c $(HDRS) Makefile
    46.7 -	$(CC) $(CFLAGS) -I $(XEN_LIBXC) -L$(XEN_LIBXC) -lxc -L$(XEN_LIBXUTIL) -lxutil -DXENO -o $@ $<
    46.8 +	$(CC) $(CFLAGS) -I $(XEN_LIBXC) -L$(XEN_LIBXC) -lxc -DXENO -o $@ $<
    46.9  
   46.10  cpuperf-perfcntr: cpuperf.c $(HDRS) Makefile
   46.11  	$(CC) $(CFLAGS) -DPERFCNTR -o $@ $<
    47.1 --- a/tools/python/setup.py	Tue May 24 21:10:23 2005 +0000
    47.2 +++ b/tools/python/setup.py	Tue May 24 21:17:29 2005 +0000
    47.3 @@ -9,15 +9,13 @@ extra_compile_args  = [ "-fno-strict-ali
    47.4  
    47.5  include_dirs = [ XEN_ROOT + "/tools/python/xen/lowlevel/xu",
    47.6                   XEN_ROOT + "/tools/libxc",
    47.7 -                 XEN_ROOT + "/tools/libxutil",
    47.8                   XEN_ROOT + "/tools/xcs",
    47.9                   ]
   47.10  
   47.11  library_dirs = [ XEN_ROOT + "/tools/libxc",
   47.12 -                 XEN_ROOT + "/tools/libxutil",
   47.13                   ]
   47.14  
   47.15 -libraries = [ "xc", "xutil" ]
   47.16 +libraries = [ "xc" ]
   47.17  
   47.18  xc = Extension("xc",
   47.19                 extra_compile_args = extra_compile_args,
    48.1 --- a/tools/python/xen/lowlevel/xc/xc.c	Tue May 24 21:10:23 2005 +0000
    48.2 +++ b/tools/python/xen/lowlevel/xc/xc.c	Tue May 24 21:17:29 2005 +0000
    48.3 @@ -15,7 +15,6 @@
    48.4  #include <netdb.h>
    48.5  #include <arpa/inet.h>
    48.6  #include "xc_private.h"
    48.7 -#include "gzip_stream.h"
    48.8  #include "linux_boot_params.h"
    48.9  
   48.10  /* Needed for Python versions earlier than 2.3. */
    49.1 --- a/tools/vnet/Makefile	Tue May 24 21:10:23 2005 +0000
    49.2 +++ b/tools/vnet/Makefile	Tue May 24 21:17:29 2005 +0000
    49.3 @@ -7,11 +7,11 @@ export prefix?=$(shell cd ../../dist/ins
    49.4  
    49.5  .PHONY: all compile
    49.6  .PHONY: gc-install gc-clean gc-prstine
    49.7 -.PHONY: vnetd vnet-module install dist clean pristine
    49.8 +.PHONY: libxutil vnetd vnet-module install dist clean pristine
    49.9  
   49.10  all: compile
   49.11  
   49.12 -compile: vnetd vnet-module
   49.13 +compile: libxutil vnetd vnet-module
   49.14  #compile: vnet-module
   49.15  
   49.16  gc.tar.gz:
   49.17 @@ -32,6 +32,9 @@ gc-clean:
   49.18  gc-pristine:
   49.19  	-rm -rf gc?.? gc
   49.20  
   49.21 +libxutil:
   49.22 +	$(MAKE) -C libxutil
   49.23 +
   49.24  vnetd: gc-install
   49.25  	$(MAKE) -C vnetd
   49.26  
   49.27 @@ -39,13 +42,15 @@ vnet-module:
   49.28  	$(MAKE) -C vnet-module
   49.29  
   49.30  install: compile
   49.31 +	$(MAKE) -C libxutil install
   49.32  	$(MAKE) -C vnetd install
   49.33  	$(MAKE) -C vnet-module install
   49.34  	$(MAKE) -C examples install
   49.35  
   49.36  clean:
   49.37 +	-$(MAKE) -C libxutil clean
   49.38  	-$(MAKE) -C vnetd clean
   49.39  	-$(MAKE) -C vnet-module clean
   49.40  	-rm -rf gc?.? gc
   49.41 -	
   49.42 +
   49.43  pristine: clean gc-pristine
    50.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    50.2 +++ b/tools/vnet/libxutil/Makefile	Tue May 24 21:17:29 2005 +0000
    50.3 @@ -0,0 +1,77 @@
    50.4 +
    50.5 +XEN_ROOT = ../../..
    50.6 +INSTALL		= install
    50.7 +INSTALL_DATA	= $(INSTALL) -m0644
    50.8 +INSTALL_PROG	= $(INSTALL) -m0755
    50.9 +INSTALL_DIR	= $(INSTALL) -d -m0755
   50.10 +
   50.11 +include $(XEN_ROOT)/tools/Rules.mk
   50.12 +
   50.13 +LIB_SRCS :=
   50.14 +LIB_SRCS += allocate.c
   50.15 +LIB_SRCS += enum.c
   50.16 +LIB_SRCS += file_stream.c
   50.17 +LIB_SRCS += gzip_stream.c
   50.18 +LIB_SRCS += hash_table.c
   50.19 +LIB_SRCS += iostream.c
   50.20 +LIB_SRCS += lexis.c
   50.21 +LIB_SRCS += string_stream.c
   50.22 +LIB_SRCS += sxpr.c
   50.23 +LIB_SRCS += sxpr_parser.c
   50.24 +LIB_SRCS += sys_net.c
   50.25 +LIB_SRCS += sys_string.c
   50.26 +LIB_SRCS += util.c
   50.27 +
   50.28 +LIB_OBJS := $(LIB_SRCS:.c=.o)
   50.29 +PIC_OBJS := $(LIB_SRCS:.c=.opic)
   50.30 +
   50.31 +CFLAGS   += -Wall -Werror -O3 -fno-strict-aliasing
   50.32 +
   50.33 +# Get gcc to generate the dependencies for us.
   50.34 +CFLAGS   += -Wp,-MD,.$(@F).d
   50.35 +DEPS     = .*.d
   50.36 +
   50.37 +MAJOR    := 3.0
   50.38 +MINOR    := 0
   50.39 +LIB      := libxutil.so 
   50.40 +LIB      += libxutil.so.$(MAJOR)
   50.41 +LIB      += libxutil.so.$(MAJOR).$(MINOR)
   50.42 +LIB      += libxutil.a
   50.43 +
   50.44 +all: build
   50.45 +build: check-for-zlib
   50.46 +	$(MAKE) $(LIB)
   50.47 +
   50.48 +libxutil.so: libxutil.so.$(MAJOR)
   50.49 +	ln -sf $^ $@
   50.50 +
   50.51 +libxutil.so.$(MAJOR): libxutil.so.$(MAJOR).$(MINOR)
   50.52 +	ln -sf $^ $@
   50.53 +
   50.54 +libxutil.so.$(MAJOR).$(MINOR): $(PIC_OBJS)
   50.55 +	$(CC) $(CFLAGS) -Wl,-soname -Wl,libxutil.so.$(MAJOR) -shared -o $@ $^
   50.56 +
   50.57 +libxutil.a: $(LIB_OBJS)
   50.58 +	$(AR) rc $@ $^
   50.59 +
   50.60 +check-for-zlib:
   50.61 +	@if [ ! -e /usr/include/zlib.h ]; then \
   50.62 +	echo "***********************************************************"; \
   50.63 +	echo "ERROR: install zlib header files (http://www.gzip.org/zlib)"; \
   50.64 +	echo "***********************************************************"; \
   50.65 +	false; \
   50.66 +	fi
   50.67 +
   50.68 +install: build
   50.69 +	[ -d $(DESTDIR)/usr/$(LIBDIR) ] || $(INSTALL_DIR) -p $(DESTDIR)/usr/$(LIBDIR)
   50.70 +	$(INSTALL_PROG) libxutil.so.$(MAJOR).$(MINOR) $(DESTDIR)/usr/$(LIBDIR)
   50.71 +	$(INSTALL_DATA) libxutil.a $(DESTDIR)/usr/$(LIBDIR)
   50.72 +	ln -sf libxutil.so.$(MAJOR).$(MINOR) $(DESTDIR)/usr/$(LIBDIR)/libxutil.so.$(MAJOR)
   50.73 +	ln -sf libxutil.so.$(MAJOR) $(DESTDIR)/usr/$(LIBDIR)/libxutil.so
   50.74 +
   50.75 +clean:
   50.76 +	$(RM) *.a *.so* *.o *.opic *.rpm 
   50.77 +	$(RM) *~
   50.78 +	$(RM) $(DEPS)
   50.79 +
   50.80 +-include $(DEPS)
    51.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    51.2 +++ b/tools/vnet/libxutil/allocate.c	Tue May 24 21:17:29 2005 +0000
    51.3 @@ -0,0 +1,116 @@
    51.4 +/*
    51.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    51.6 + *
    51.7 + * This library is free software; you can redistribute it and/or modify
    51.8 + * it under the terms of the GNU Lesser General Public License as published by
    51.9 + * the Free Software Foundation; either version 2.1 of the License, or
   51.10 + * (at your option) any later version.
   51.11 + *
   51.12 + * This library is distributed in the hope that it will be useful,
   51.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   51.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   51.15 + * GNU Lesser General Public License for more details.
   51.16 + *
   51.17 + * You should have received a copy of the GNU Lesser General Public License
   51.18 + * along with this library; if not, write to the Free Software
   51.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   51.20 + */
   51.21 +
   51.22 +#include "allocate.h"
   51.23 +
   51.24 +/** @file
   51.25 + * Support for allocating memory.
   51.26 + * Usable from user code or kernel code (with __KERNEL__ defined).
   51.27 + * In user code will use GC if USE_GC is defined.
   51.28 + */
   51.29 +
   51.30 +#ifdef __KERNEL__
   51.31 +/*----------------------------------------------------------------------------*/
   51.32 +#  include <linux/config.h>
   51.33 +#  include <linux/slab.h>
   51.34 +#  include <linux/string.h>
   51.35 +#  include <linux/types.h>
   51.36 +
   51.37 +#  define DEFAULT_TYPE    0
   51.38 +#  define MALLOC(n, type) kmalloc(n, type)
   51.39 +#  define FREE(ptr)       kfree(ptr)
   51.40 +
   51.41 +/*----------------------------------------------------------------------------*/
   51.42 +#else /* ! __KERNEL__ */
   51.43 +
   51.44 +#  include <stdlib.h>
   51.45 +#  include <string.h>
   51.46 +
   51.47 +#  define DEFAULT_TYPE    0
   51.48 +
   51.49 +#ifdef USE_GC
   51.50 +#  include "gc.h"
   51.51 +#  define MALLOC(n, typ)  GC_malloc(n)
   51.52 +#  define FREE(ptr)       (ptr=NULL)
   51.53 +//typedef void *GC_PTR;
   51.54 +//GC_PTR (*GC_oom_fn)(size_t n);
   51.55 +#else
   51.56 +#  define MALLOC(n, type) malloc(n)
   51.57 +#  define FREE(ptr)       free(ptr)
   51.58 +#endif
   51.59 +
   51.60 +/*----------------------------------------------------------------------------*/
   51.61 +#endif
   51.62 +
   51.63 +/** Function to call when memory cannot be allocated. */
   51.64 +AllocateFailedFn *allocate_failed_fn = NULL;
   51.65 +
   51.66 +/** Allocate memory and zero it.
   51.67 + * The type is only relevant when calling from kernel code,
   51.68 + * from user code it is ignored.
   51.69 + * In kernel code the values accepted by kmalloc can be used:
   51.70 + * GFP_USER, GFP_ATOMIC, GFP_KERNEL.
   51.71 + *
   51.72 + * @param size number of bytes to allocate
   51.73 + * @param type memory type to allocate (kernel only)
   51.74 + * @return pointer to the allocated memory or zero
   51.75 + * if malloc failed
   51.76 + */
   51.77 +void *allocate_type(int size, int type){
   51.78 +    void *p = MALLOC(size, type);
   51.79 +    if(p){
   51.80 +        memzero(p, size);
   51.81 +    } else if(allocate_failed_fn){
   51.82 +        allocate_failed_fn(size, type);
   51.83 +    }
   51.84 +    return p;
   51.85 +}
   51.86 +
   51.87 +/** Allocate memory and zero it.
   51.88 + *
   51.89 + * @param size number of bytes to allocate
   51.90 + * @return pointer to the allocated memory or zero
   51.91 + * if malloc failed
   51.92 + */
   51.93 +void *allocate(int size){
   51.94 +    return allocate_type(size, DEFAULT_TYPE);
   51.95 +}
   51.96 +
   51.97 +/** Free memory allocated by allocate().
   51.98 + * No-op if 'p' is null.
   51.99 + *
  51.100 + * @param p memory to free
  51.101 + */
  51.102 +void deallocate(void *p){
  51.103 +    if(p){
  51.104 +        FREE(p);
  51.105 +    }
  51.106 +}
  51.107 +
  51.108 +/** Set bytes to zero.
  51.109 + * No-op if 'p' is null.
  51.110 + *
  51.111 + * @param p memory to zero
  51.112 + * @param size number of bytes to zero
  51.113 + */
  51.114 +void memzero(void *p, int size){
  51.115 +    if(p){
  51.116 +        memset(p, 0, (size_t)size);
  51.117 +    }
  51.118 +}
  51.119 +
    52.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    52.2 +++ b/tools/vnet/libxutil/allocate.h	Tue May 24 21:17:29 2005 +0000
    52.3 @@ -0,0 +1,45 @@
    52.4 +/*
    52.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    52.6 + *
    52.7 + * This library is free software; you can redistribute it and/or modify
    52.8 + * it under the terms of the GNU Lesser General Public License as published by
    52.9 + * the Free Software Foundation; either version 2.1 of the License, or
   52.10 + * (at your option) any later version.
   52.11 + *
   52.12 + * This library is distributed in the hope that it will be useful,
   52.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   52.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   52.15 + * GNU Lesser General Public License for more details.
   52.16 + *
   52.17 + * You should have received a copy of the GNU Lesser General Public License
   52.18 + * along with this library; if not, write to the Free Software
   52.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   52.20 + */
   52.21 +
   52.22 +#ifndef _XUTIL_ALLOCATE_H_
   52.23 +#define _XUTIL_ALLOCATE_H_
   52.24 +
   52.25 +/** Allocate memory for a given type, and cast. */
   52.26 +#define ALLOCATE(ctype) (ctype *)allocate(sizeof(ctype))
   52.27 +
   52.28 +/** Allocate memory for a given type, and cast. */
   52.29 +#define ALLOCATE_TYPE(ctype, type) (ctype *)allocate(sizeof(ctype))
   52.30 +
   52.31 +extern void *allocate_type(int size, int type);
   52.32 +extern void *allocate(int size);
   52.33 +extern void deallocate(void *);
   52.34 +extern void memzero(void *p, int size);
   52.35 +
   52.36 +typedef void AllocateFailedFn(int size, int type);
   52.37 +extern AllocateFailedFn *allocate_failed_fn;
   52.38 +
   52.39 +#endif /* _XUTIL_ALLOCATE_H_ */
   52.40 +
   52.41 +
   52.42 +
   52.43 +
   52.44 +
   52.45 +
   52.46 +
   52.47 +
   52.48 +
    53.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    53.2 +++ b/tools/vnet/libxutil/debug.h	Tue May 24 21:17:29 2005 +0000
    53.3 @@ -0,0 +1,72 @@
    53.4 +/*
    53.5 + * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    53.6 + *
    53.7 + * This library is free software; you can redistribute it and/or modify
    53.8 + * it under the terms of the GNU Lesser General Public License as published by
    53.9 + * the Free Software Foundation; either version 2.1 of the License, or
   53.10 + * (at your option) any later version.
   53.11 + *
   53.12 + * This library is distributed in the hope that it will be useful,
   53.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   53.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   53.15 + * GNU Lesser General Public License for more details.
   53.16 + *
   53.17 + * You should have received a copy of the GNU Lesser General Public License
   53.18 + * along with this library; if not, write to the Free Software
   53.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   53.20 + */
   53.21 +#ifndef _XUTIL_DEBUG_H_
   53.22 +#define _XUTIL_DEBUG_H_
   53.23 +
   53.24 +#ifndef MODULE_NAME
   53.25 +#define MODULE_NAME ""
   53.26 +#endif
   53.27 +
   53.28 +#ifdef __KERNEL__
   53.29 +#include <linux/config.h>
   53.30 +#include <linux/kernel.h>
   53.31 +
   53.32 +#ifdef DEBUG
   53.33 +
   53.34 +#define dprintf(fmt, args...) printk(KERN_DEBUG   "[DBG] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   53.35 +#define wprintf(fmt, args...) printk(KERN_WARNING "[WRN] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   53.36 +#define iprintf(fmt, args...) printk(KERN_INFO    "[INF] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   53.37 +#define eprintf(fmt, args...) printk(KERN_ERR     "[ERR] " MODULE_NAME ">%s" fmt, __FUNCTION__, ##args)
   53.38 +
   53.39 +#else
   53.40 +
   53.41 +#define dprintf(fmt, args...) do {} while(0)
   53.42 +#define wprintf(fmt, args...) printk(KERN_WARNING "[WRN] " MODULE_NAME fmt, ##args)
   53.43 +#define iprintf(fmt, args...) printk(KERN_INFO    "[INF] " MODULE_NAME fmt, ##args)
   53.44 +#define eprintf(fmt, args...) printk(KERN_ERR     "[ERR] " MODULE_NAME fmt, ##args)
   53.45 +
   53.46 +#endif
   53.47 +
   53.48 +#else
   53.49 +
   53.50 +#include <stdio.h>
   53.51 +
   53.52 +#ifdef DEBUG
   53.53 +
   53.54 +#define dprintf(fmt, args...) fprintf(stdout, "%d [DBG] " MODULE_NAME ">%s" fmt, getpid(), __FUNCTION__, ##args)
   53.55 +#define wprintf(fmt, args...) fprintf(stderr, "%d [WRN] " MODULE_NAME ">%s" fmt, getpid(),__FUNCTION__, ##args)
   53.56 +#define iprintf(fmt, args...) fprintf(stderr, "%d [INF] " MODULE_NAME ">%s" fmt, getpid(),__FUNCTION__, ##args)
   53.57 +#define eprintf(fmt, args...) fprintf(stderr, "%d [ERR] " MODULE_NAME ">%s" fmt, getpid(),__FUNCTION__, ##args)
   53.58 +
   53.59 +#else
   53.60 +
   53.61 +#define dprintf(fmt, args...) do {} while(0)
   53.62 +#define wprintf(fmt, args...) fprintf(stderr, "%d [WRN] " MODULE_NAME fmt, getpid(), ##args)
   53.63 +#define iprintf(fmt, args...) fprintf(stderr, "%d [INF] " MODULE_NAME fmt, getpid(), ##args)
   53.64 +#define eprintf(fmt, args...) fprintf(stderr, "%d [ERR] " MODULE_NAME fmt, getpid(), ##args)
   53.65 +
   53.66 +#endif
   53.67 +
   53.68 +#endif
   53.69 +
   53.70 +/** Print format for an IP address.
   53.71 + * See NIPQUAD(), HIPQUAD()
   53.72 + */
   53.73 +#define IPFMT "%u.%u.%u.%u"
   53.74 +
   53.75 +#endif /* ! _XUTIL_DEBUG_H_ */
    54.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    54.2 +++ b/tools/vnet/libxutil/enum.c	Tue May 24 21:17:29 2005 +0000
    54.3 @@ -0,0 +1,61 @@
    54.4 +/*
    54.5 + * Copyright (C) 2002, 2004 Mike Wray <mike.wray@hp.com>
    54.6 + *
    54.7 + * This library is free software; you can redistribute it and/or modify
    54.8 + * it under the terms of the GNU Lesser General Public License as
    54.9 + * published by the Free Software Foundation; either version 2.1 of the
   54.10 + * License, or  (at your option) any later version. This library is 
   54.11 + * distributed in the  hope that it will be useful, but WITHOUT ANY
   54.12 + * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   54.13 + * FITNESS FOR A PARTICULAR PURPOSE.
   54.14 + * See the GNU Lesser General Public License for more details.
   54.15 + *
   54.16 + * You should have received a copy of the GNU Lesser General Public License
   54.17 + * along with this library; if not, write to the Free Software Foundation,
   54.18 + * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   54.19 + */
   54.20 +
   54.21 +#ifdef __KERNEL__
   54.22 +#include <linux/errno.h>
   54.23 +#else
   54.24 +#include <errno.h>
   54.25 +#endif
   54.26 +
   54.27 +#include "sys_string.h"
   54.28 +#include "enum.h"
   54.29 +
   54.30 +/** Map an enum name to its value using a table.
   54.31 + *
   54.32 + * @param name enum name
   54.33 + * @param defs enum definitions
   54.34 + * @return enum value or -1 if not known
   54.35 + */
   54.36 +int enum_name_to_val(char *name, EnumDef *defs){
   54.37 +    int val = -1;
   54.38 +    for(; defs->name; defs++){
   54.39 +	if(!strcmp(defs->name, name)){
   54.40 +	    val = defs->val;
   54.41 +	    break;
   54.42 +	}
   54.43 +    }
   54.44 +    return val;
   54.45 +}
   54.46 +
   54.47 +/** Map an enum value to its name using a table.
   54.48 + *
   54.49 + * @param val enum value
   54.50 + * @param defs enum definitions
   54.51 + * @param defs_n number of definitions
   54.52 + * @return enum name or NULL if not known
   54.53 + */
   54.54 +char *enum_val_to_name(int val, EnumDef *defs){
   54.55 +    char *name = NULL;
   54.56 +    for(; defs->name; defs++){
   54.57 +	if(val == defs->val){
   54.58 +	    name = defs->name;
   54.59 +	    break;
   54.60 +	}
   54.61 +    }
   54.62 +    return name;
   54.63 +}
   54.64 +
    55.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    55.2 +++ b/tools/vnet/libxutil/enum.h	Tue May 24 21:17:29 2005 +0000
    55.3 @@ -0,0 +1,30 @@
    55.4 +/*
    55.5 + * Copyright (C) 2002, 2004 Mike Wray <mike.wray@hp.com>
    55.6 + *
    55.7 + * This library is free software; you can redistribute it and/or modify
    55.8 + * it under the terms of the GNU Lesser General Public License as
    55.9 + * published by the Free Software Foundation; either version 2.1 of the
   55.10 + * License, or  (at your option) any later version. This library is 
   55.11 + * distributed in the  hope that it will be useful, but WITHOUT ANY
   55.12 + * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   55.13 + * FITNESS FOR A PARTICULAR PURPOSE.
   55.14 + * See the GNU Lesser General Public License for more details.
   55.15 + *
   55.16 + * You should have received a copy of the GNU Lesser General Public License
   55.17 + * along with this library; if not, write to the Free Software Foundation,
   55.18 + * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   55.19 + */
   55.20 +
   55.21 +#ifndef _XUTIL_ENUM_H_
   55.22 +#define _XUTIL_ENUM_H_
   55.23 +
   55.24 +/** Mapping of an enum value to a name. */
   55.25 +typedef struct EnumDef {
   55.26 +    int val;
   55.27 +    char *name;
   55.28 +} EnumDef;
   55.29 +
   55.30 +extern int enum_name_to_val(char *name, EnumDef *defs);
   55.31 +extern char *enum_val_to_name(int val, EnumDef *defs);
   55.32 +
   55.33 +#endif /* _XUTIL_ENUM_H_ */
    56.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    56.2 +++ b/tools/vnet/libxutil/fd_stream.c	Tue May 24 21:17:29 2005 +0000
    56.3 @@ -0,0 +1,184 @@
    56.4 +/*
    56.5 + * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    56.6 + *
    56.7 + * This library is free software; you can redistribute it and/or modify
    56.8 + * it under the terms of the GNU Lesser General Public License as published by
    56.9 + * the Free Software Foundation; either version 2.1 of the License, or
   56.10 + * (at your option) any later version.
   56.11 + *
   56.12 + * This library is distributed in the hope that it will be useful,
   56.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   56.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   56.15 + * GNU Lesser General Public License for more details.
   56.16 + *
   56.17 + * You should have received a copy of the GNU Lesser General Public License
   56.18 + * along with this library; if not, write to the Free Software
   56.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   56.20 + */
   56.21 +
   56.22 +/** @file
   56.23 + * An IOStream implementation using fds.
   56.24 + */
   56.25 +#ifndef __KERNEL__
   56.26 +
   56.27 +#include <stdio.h>
   56.28 +#include <stdlib.h>
   56.29 +#include <string.h>
   56.30 +#include <unistd.h>
   56.31 +#include <errno.h>
   56.32 +#include "allocate.h"
   56.33 +#include "fd_stream.h"
   56.34 +
   56.35 +#define MODULE_NAME "fd_stream"
   56.36 +#define DEBUG 1
   56.37 +//#undef DEBUG
   56.38 +#include "debug.h"
   56.39 +
   56.40 +static int fd_read(IOStream *s, void *buf, size_t n);
   56.41 +static int fd_write(IOStream *s, const void *buf, size_t n);
   56.42 +static int fd_error(IOStream *s);
   56.43 +static int fd_close(IOStream *s);
   56.44 +static void fd_free(IOStream *s);
   56.45 +static int fd_flush(IOStream *s);
   56.46 +
   56.47 +/** Methods used by a fd IOStream. */
   56.48 +static const IOMethods fd_methods = {
   56.49 +    read:  fd_read,
   56.50 +    write: fd_write,
   56.51 +    error: fd_error,
   56.52 +    close: fd_close,
   56.53 +    free:  fd_free,
   56.54 +    flush: fd_flush,
   56.55 +};
   56.56 +
   56.57 +/** Get the fd data.
   56.58 + * 
   56.59 + * @param io fd stream
   56.60 + * @return data
   56.61 + */
   56.62 +static inline FDData * fd_data(IOStream *io){
   56.63 +    return (FDData *)io->data;
   56.64 +}
   56.65 +
   56.66 +/** Test if a stream is a fd stream.
   56.67 + *
   56.68 + * @param io stream
   56.69 + * @return 0 if a fd stream, -EINVAL if not
   56.70 + */
   56.71 +int fd_stream_check(IOStream *io){
   56.72 +    return (io && io->methods == &fd_methods ? 0 : -EINVAL);
   56.73 +}
   56.74 +
   56.75 +/** Get the data for a fd stream.
   56.76 + *
   56.77 + * @param io stream
   56.78 + * @param data return value for the data
   56.79 + * @return 0 if a fd stream, -EINVAL if not
   56.80 + */
   56.81 +int fd_stream_data(IOStream *io, FDData **data){
   56.82 +    int err = fd_stream_check(io);
   56.83 +    if(err){
   56.84 +        *data = NULL;
   56.85 +    } else {
   56.86 +        *data = fd_data(io);
   56.87 +    }
   56.88 +    return err;
   56.89 +}
   56.90 +
   56.91 +
   56.92 +/** Write to the underlying fd.
   56.93 + *
   56.94 + * @param stream input
   56.95 + * @param buf where to put input
   56.96 + * @param n number of bytes to write
   56.97 + * @return number of bytes written
   56.98 + */
   56.99 +static int fd_write(IOStream *s, const void *buf, size_t n){
  56.100 +    FDData *data = fd_data(s);
  56.101 +    int k;
  56.102 +    k = write(data->fd, buf, n);
  56.103 +    return k;
  56.104 +}
  56.105 +
  56.106 +/** Read from the underlying stream;
  56.107 + *
  56.108 + * @param stream input
  56.109 + * @param buf where to put input
  56.110 + * @param n number of bytes to read
  56.111 + * @return number of bytes read
  56.112 + */
  56.113 +static int fd_read(IOStream *s, void *buf, size_t n){
  56.114 +    FDData *data = fd_data(s);
  56.115 +    int k;
  56.116 +    k = read(data->fd, buf, n);
  56.117 +    //printf("> fd_read> buf=%p n=%d --> k=%d\n", buf, n, k);
  56.118 +    return k;
  56.119 +}
  56.120 +
  56.121 +/** Flush the fd (no-op).
  56.122 + *
  56.123 + * @param s fd stream
  56.124 + * @return 0 on success, error code otherwise
  56.125 + */
  56.126 +static int fd_flush(IOStream *s){
  56.127 +    return 0;
  56.128 +}
  56.129 +
  56.130 +/** Check if a fd stream has an error (no-op).
  56.131 + *
  56.132 + * @param s fd stream
  56.133 + * @return 1 if has an error, 0 otherwise
  56.134 + */
  56.135 +static int fd_error(IOStream *s){
  56.136 +    return 0;
  56.137 +}
  56.138 +
  56.139 +/** Close a fd stream.
  56.140 + *
  56.141 + * @param s fd stream to close
  56.142 + * @return result of the close
  56.143 + */
  56.144 +static int fd_close(IOStream *s){
  56.145 +    FDData *data = fd_data(s);
  56.146 +    return close(data->fd);
  56.147 +}
  56.148 +
  56.149 +/** Free a fd stream.
  56.150 + *
  56.151 + * @param s fd stream
  56.152 + */
  56.153 +static void fd_free(IOStream *s){
  56.154 +    FDData *data = fd_data(s);
  56.155 +    deallocate(data);
  56.156 +}
  56.157 +
  56.158 +/** Create an IOStream for a fd.
  56.159 + *
  56.160 + * @param fd fd to wtap
  56.161 + * @return new IOStream using fd for i/o
  56.162 + */
  56.163 +IOStream *fd_stream_new(int fd){
  56.164 +    int err = -ENOMEM;
  56.165 +    IOStream *io = NULL;
  56.166 +    FDData *data = NULL;
  56.167 +
  56.168 +    io = ALLOCATE(IOStream);
  56.169 +    if(!io) goto exit;
  56.170 +    io->methods = &fd_methods;
  56.171 +    data = ALLOCATE(FDData);
  56.172 +    if(!data) goto exit;
  56.173 +    io->data = data;
  56.174 +    data->fd = fd;
  56.175 +    err = 0;
  56.176 +  exit:
  56.177 +    if(err){
  56.178 +        if(io){
  56.179 +            if(data) deallocate(data);
  56.180 +            deallocate(io);
  56.181 +            io = NULL;
  56.182 +        }
  56.183 +    }
  56.184 +    return io;
  56.185 +}
  56.186 +
  56.187 +#endif
    57.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    57.2 +++ b/tools/vnet/libxutil/fd_stream.h	Tue May 24 21:17:29 2005 +0000
    57.3 @@ -0,0 +1,36 @@
    57.4 +/*
    57.5 + * Copyright (C) 2004 Mike Wray <mike.wray@hp.com>
    57.6 + *
    57.7 + * This library is free software; you can redistribute it and/or modify
    57.8 + * it under the terms of the GNU Lesser General Public License as published by
    57.9 + * the Free Software Foundation; either version 2.1 of the License, or
   57.10 + * (at your option) any later version.
   57.11 + *
   57.12 + * This library is distributed in the hope that it will be useful,
   57.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   57.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   57.15 + * GNU Lesser General Public License for more details.
   57.16 + *
   57.17 + * You should have received a copy of the GNU Lesser General Public License
   57.18 + * along with this library; if not, write to the Free Software
   57.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   57.20 + */
   57.21 +
   57.22 +#ifndef _XMC_FD_STREAM_H_
   57.23 +#define _XMC_FD_STREAM_H_
   57.24 +
   57.25 +#ifndef __KERNEL__
   57.26 +#include "iostream.h"
   57.27 +
   57.28 +/** Data associated with a fd stream. */
   57.29 +typedef struct FDData {
   57.30 +    /** The socket file descriptor. */
   57.31 +    int fd;
   57.32 +} FDData;
   57.33 +
   57.34 +extern IOStream *fd_stream_new(int fd);
   57.35 +extern int fd_stream_data(IOStream *io, FDData **data);
   57.36 +extern int fd_stream_check(IOStream *io);
   57.37 +
   57.38 +#endif
   57.39 +#endif /* !_XMC_FD_STREAM_H_ */
    58.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    58.2 +++ b/tools/vnet/libxutil/file_stream.c	Tue May 24 21:17:29 2005 +0000
    58.3 @@ -0,0 +1,220 @@
    58.4 +/*
    58.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    58.6 + *
    58.7 + * This library is free software; you can redistribute it and/or modify
    58.8 + * it under the terms of the GNU Lesser General Public License as published by
    58.9 + * the Free Software Foundation; either version 2.1 of the License, or
   58.10 + * (at your option) any later version.
   58.11 + *
   58.12 + * This library is distributed in the hope that it will be useful,
   58.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   58.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   58.15 + * GNU Lesser General Public License for more details.
   58.16 + *
   58.17 + * You should have received a copy of the GNU Lesser General Public License
   58.18 + * along with this library; if not, write to the Free Software
   58.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   58.20 + */
   58.21 +
   58.22 +/** @file
   58.23 + * An IOStream implementation using FILE*.
   58.24 + */
   58.25 +#ifndef __KERNEL__
   58.26 +#include <stdio.h>
   58.27 +#include <stdlib.h>
   58.28 +#include "allocate.h"
   58.29 +#include "file_stream.h"
   58.30 +
   58.31 +static int file_read(IOStream *s, void *buf, size_t n);
   58.32 +static int file_write(IOStream *s, const void *buf, size_t n);
   58.33 +static int file_error(IOStream *s);
   58.34 +static int file_close(IOStream *s);
   58.35 +static void file_free(IOStream *s);
   58.36 +static int file_flush(IOStream *s);
   58.37 +
   58.38 +/** Methods used by a FILE* IOStream. */
   58.39 +static const IOMethods file_methods = {
   58.40 +    read:  file_read,
   58.41 +    write: file_write,
   58.42 +    error: file_error,
   58.43 +    close: file_close,
   58.44 +    free:  file_free,
   58.45 +    flush: file_flush,
   58.46 +};
   58.47 +
   58.48 +/** IOStream for stdin. */
   58.49 +static IOStream _iostdin = {
   58.50 +    methods: &file_methods,
   58.51 +    data: (void*)1,
   58.52 +    nofree: 1,
   58.53 +};
   58.54 +
   58.55 +/** IOStream for stdout. */
   58.56 +static IOStream _iostdout = {
   58.57 +    methods: &file_methods,
   58.58 +    data: (void*)2,
   58.59 +    nofree: 1,
   58.60 +};
   58.61 +
   58.62 +/** IOStream for stderr. */
   58.63 +static IOStream _iostderr = {
   58.64 +    methods: &file_methods,
   58.65 +    data: (void*)3,
   58.66 +    nofree: 1,
   58.67 +};
   58.68 +
   58.69 +/** IOStream for stdin. */
   58.70 +IOStream *iostdin = &_iostdin;
   58.71 +
   58.72 +/** IOStream for stdout. */
   58.73 +IOStream *iostdout = &_iostdout;
   58.74 +
   58.75 +/** IOStream for stderr. */
   58.76 +IOStream *iostderr = &_iostderr;
   58.77 +
   58.78 +/* Get the underlying FILE*.
   58.79 + *
   58.80 + * @param s file stream
   58.81 + * @return the stream s wraps
   58.82 + */
   58.83 +static inline FILE *get_file(IOStream *s){
   58.84 +     FILE *data = NULL;
   58.85 +     switch((long)s->data){
   58.86 +     case 1:
   58.87 +         data = stdin;
   58.88 +         break;
   58.89 +     case 2:
   58.90 +         data = stdout;
   58.91 +         break;
   58.92 +     case 3:
   58.93 +         data = stderr;
   58.94 +         break;
   58.95 +     default:
   58.96 +         data = (FILE*)s->data;
   58.97 +         break;
   58.98 +     }
   58.99 +     return data;
  58.100 +}
  58.101 +
  58.102 +/** Control buffering on the underlying stream, like setvbuf().
  58.103 + *
  58.104 + * @param io file stream
  58.105 + * @param buf buffer
  58.106 + * @param mode buffering mode (see man setvbuf())
  58.107 + * @param size buffer size
  58.108 + * @return 0 on success, non-zero otherwise
  58.109 + */
  58.110 +int file_stream_setvbuf(IOStream *io, char *buf, int mode, size_t size){
  58.111 +    return setvbuf(get_file(io), buf, mode, size);
  58.112 +}
  58.113 +
  58.114 +/** Write to the underlying stream using fwrite();
  58.115 + *
  58.116 + * @param stream input
  58.117 + * @param buf where to put input
  58.118 + * @param n number of bytes to write
  58.119 + * @return number of bytes written
  58.120 + */
  58.121 +static int file_write(IOStream *s, const void *buf, size_t n){
  58.122 +    return fwrite(buf, 1, n, get_file(s));
  58.123 +}
  58.124 +
  58.125 +/** Read from the underlying stream using fread();
  58.126 + *
  58.127 + * @param stream input
  58.128 + * @param buf where to put input
  58.129 + * @param n number of bytes to read
  58.130 + * @return number of bytes read
  58.131 + */
  58.132 +static int file_read(IOStream *s, void *buf, size_t n){
  58.133 +    return fread(buf, 1, n, get_file(s));
  58.134 +}
  58.135 +
  58.136 +/** Fush the underlying stream using fflush().
  58.137 + *
  58.138 + * @param s file stream
  58.139 + * @return 0 on success, error code otherwise
  58.140 + */
  58.141 +static int file_flush(IOStream *s){
  58.142 +    return fflush(get_file(s));
  58.143 +}
  58.144 +
  58.145 +/** Check if a stream has an error.
  58.146 + *
  58.147 + * @param s file stream
  58.148 + * @return 1 if has an error, 0 otherwise
  58.149 + */
  58.150 +static int file_error(IOStream *s){
  58.151 +    return ferror(get_file(s));
  58.152 +}
  58.153 +
  58.154 +/** Close a file stream.
  58.155 + *
  58.156 + * @param s file stream to close
  58.157 + * @return result of the close
  58.158 + */
  58.159 +static int file_close(IOStream *s){
  58.160 +    int result = 0;
  58.161 +    result = fclose(get_file(s));
  58.162 +    return result;
  58.163 +}
  58.164 +
  58.165 +/** Free a file stream.
  58.166 + *
  58.167 + * @param s file stream
  58.168 + */
  58.169 +static void file_free(IOStream *s){
  58.170 +    // Nothing extra to do - close did it all.
  58.171 +}
  58.172 +
  58.173 +/** Create an IOStream for a stream.
  58.174 + *
  58.175 + * @param f stream to wrap
  58.176 + * @return new IOStream using f for i/o
  58.177 + */
  58.178 +IOStream *file_stream_new(FILE *f){
  58.179 +    IOStream *io = ALLOCATE(IOStream);
  58.180 +    if(io){
  58.181 +        io->methods = &file_methods;
  58.182 +        io->data = (void*)f;
  58.183 +    }
  58.184 +    return io;
  58.185 +}
  58.186 +
  58.187 +/** IOStream version of fopen().
  58.188 + *
  58.189 + * @param file name of the file to open
  58.190 + * @param flags giving the mode to open in (as for fopen())
  58.191 + * @return new stream for the open file, or 0 if failed
  58.192 + */
  58.193 +IOStream *file_stream_fopen(const char *file, const char *flags){
  58.194 +    IOStream *io = 0;
  58.195 +    FILE *fin = fopen(file, flags);
  58.196 +    if(fin){
  58.197 +        io = file_stream_new(fin);
  58.198 +        if(!io){
  58.199 +            fclose(fin);
  58.200 +        }
  58.201 +    }
  58.202 +    return io;
  58.203 +}
  58.204 +
  58.205 +/** IOStream version of fdopen().
  58.206 + *
  58.207 + * @param fd file descriptor
  58.208 + * @param flags giving the mode to open in (as for fdopen())
  58.209 + * @return new stream for the open file, or 0 if failed.  Always takes
  58.210 + *         ownership of fd.
  58.211 + */
  58.212 +IOStream *file_stream_fdopen(int fd, const char *flags){
  58.213 +    IOStream *io = 0;
  58.214 +    FILE *fin = fdopen(fd, flags);
  58.215 +    if(fin){
  58.216 +        io = file_stream_new(fin);
  58.217 +        if(!io){
  58.218 +            fclose(fin);
  58.219 +        }
  58.220 +    }
  58.221 +    return io;
  58.222 +}
  58.223 +#endif
    59.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    59.2 +++ b/tools/vnet/libxutil/file_stream.h	Tue May 24 21:17:29 2005 +0000
    59.3 @@ -0,0 +1,35 @@
    59.4 +/*
    59.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    59.6 + *
    59.7 + * This library is free software; you can redistribute it and/or modify
    59.8 + * it under the terms of the GNU Lesser General Public License as published by
    59.9 + * the Free Software Foundation; either version 2.1 of the License, or
   59.10 + * (at your option) any later version.
   59.11 + *
   59.12 + * This library is distributed in the hope that it will be useful,
   59.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   59.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   59.15 + * GNU Lesser General Public License for more details.
   59.16 + *
   59.17 + * You should have received a copy of the GNU Lesser General Public License
   59.18 + * along with this library; if not, write to the Free Software
   59.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   59.20 + */
   59.21 +
   59.22 +#ifndef _XUTIL_FILE_STREAM_H_
   59.23 +#define _XUTIL_FILE_STREAM_H_
   59.24 +
   59.25 +#ifndef __KERNEL__
   59.26 +#include "iostream.h"
   59.27 +#include <stdio.h>
   59.28 +
   59.29 +extern IOStream *file_stream_new(FILE *f);
   59.30 +extern IOStream *file_stream_fopen(const char *file, const char *flags);
   59.31 +extern IOStream *file_stream_fdopen(int fd, const char *flags);
   59.32 +extern IOStream get_stream_stdout(void);
   59.33 +extern IOStream get_stream_stderr(void);
   59.34 +extern IOStream get_stream_stdin(void);
   59.35 +
   59.36 +extern int file_stream_setvbuf(IOStream *io, char *buf, int mode, size_t size);
   59.37 +#endif
   59.38 +#endif /* !_XUTIL_FILE_STREAM_H_ */
    60.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    60.2 +++ b/tools/vnet/libxutil/gzip_stream.c	Tue May 24 21:17:29 2005 +0000
    60.3 @@ -0,0 +1,174 @@
    60.4 +/*
    60.5 + * Copyright (C) 2003 Hewlett-Packard Company.
    60.6 + *
    60.7 + * This library is free software; you can redistribute it and/or modify
    60.8 + * it under the terms of the GNU Lesser General Public License as published by
    60.9 + * the Free Software Foundation; either version 2.1 of the License, or
   60.10 + * (at your option) any later version.
   60.11 + *
   60.12 + * This library is distributed in the hope that it will be useful,
   60.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   60.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   60.15 + * GNU Lesser General Public License for more details.
   60.16 + *
   60.17 + * You should have received a copy of the GNU Lesser General Public License
   60.18 + * along with this library; if not, write to the Free Software
   60.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   60.20 + */
   60.21 +
   60.22 +/** @file
   60.23 + * An IOStream implementation using zlib gzFile to provide
   60.24 + * compression and decompression.
   60.25 + */
   60.26 +#ifndef __KERNEL__
   60.27 +
   60.28 +#include <stdio.h>
   60.29 +#include <stdlib.h>
   60.30 +
   60.31 +#include "zlib.h"
   60.32 +
   60.33 +#include "allocate.h"
   60.34 +#include "gzip_stream.h"
   60.35 +
   60.36 +static int gzip_read(IOStream *s, void *buf, size_t n);
   60.37 +static int gzip_write(IOStream *s, const void *buf, size_t n);
   60.38 +static int gzip_error(IOStream *s);
   60.39 +static int gzip_close(IOStream *s);
   60.40 +static void gzip_free(IOStream *s);
   60.41 +static int gzip_flush(IOStream *s);
   60.42 +
   60.43 +/** Methods used by a gzFile* IOStream. */
   60.44 +static const IOMethods gzip_methods = {
   60.45 +    read:  gzip_read,
   60.46 +    write: gzip_write,
   60.47 +    error: gzip_error,
   60.48 +    close: gzip_close,
   60.49 +    free:  gzip_free,
   60.50 +    flush: gzip_flush,
   60.51 +};
   60.52 +
   60.53 +/** Get the underlying gzFile*.
   60.54 + * 
   60.55 + * @param s gzip stream
   60.56 + * @return the stream s wraps
   60.57 + */
   60.58 +static inline gzFile get_gzfile(IOStream *s){
   60.59 +    return (gzFile)s->data;
   60.60 +}
   60.61 +
   60.62 +/** Write to the underlying stream.
   60.63 + *
   60.64 + * @param stream destination
   60.65 + * @param buf data
   60.66 + * @param n number of bytes to write
   60.67 + * @return number of bytes written
   60.68 + */
   60.69 +static int gzip_write(IOStream *s, const void *buf, size_t n){
   60.70 +    return gzwrite(get_gzfile(s), (void*)buf, n);
   60.71 +}
   60.72 +
   60.73 +/** Read from the underlying stream.
   60.74 + *
   60.75 + * @param stream input
   60.76 + * @param buf where to put input
   60.77 + * @param n number of bytes to read
   60.78 + * @return number of bytes read
   60.79 + */
   60.80 +static int gzip_read(IOStream *s, void *buf, size_t n){
   60.81 +    return gzread(get_gzfile(s), buf, n);
   60.82 +}
   60.83 +
   60.84 +/** Flush the underlying stream.
   60.85 + *
   60.86 + * @param s gzip stream
   60.87 + * @return 0 on success, error code otherwise
   60.88 + */
   60.89 +static int gzip_flush(IOStream *s){
   60.90 +    //return gzflush(get_gzfile(s), Z_NO_FLUSH);
   60.91 +    return gzflush(get_gzfile(s), Z_SYNC_FLUSH);
   60.92 +    //return gzflush(get_gzfile(s), Z_FULL_FLUSH);
   60.93 +}
   60.94 +
   60.95 +/** Check if a stream has an error.
   60.96 + *
   60.97 + * @param s gzip stream
   60.98 + * @return 1 if has an error, 0 otherwise
   60.99 + */
  60.100 +static int gzip_error(IOStream *s){
  60.101 +    int err;
  60.102 +    gzFile *gz = get_gzfile(s);
  60.103 +    gzerror(gz, &err);
  60.104 +    return (err == Z_ERRNO ? 1 /* ferror(gzfile(gz)) */ : err);
  60.105 +}
  60.106 +
  60.107 +/** Close a gzip stream.
  60.108 + *
  60.109 + * @param s gzip stream to close
  60.110 + * @return result of the close
  60.111 + */
  60.112 +static int gzip_close(IOStream *s){
  60.113 +    int result = 0;
  60.114 +    result = gzclose(get_gzfile(s));
  60.115 +    return result;
  60.116 +}
  60.117 +
  60.118 +/** Free a gzip stream.
  60.119 + *
  60.120 + * @param s gzip stream
  60.121 + */
  60.122 +static void gzip_free(IOStream *s){
  60.123 +    // Nothing to do - close did it all.
  60.124 +}
  60.125 +
  60.126 +/** Create an IOStream for a gzip stream.
  60.127 + *
  60.128 + * @param f stream to wrap
  60.129 + * @return new IOStream using f for i/o
  60.130 + */
  60.131 +IOStream *gzip_stream_new(gzFile *f){
  60.132 +    IOStream *io = ALLOCATE(IOStream);
  60.133 +    if(io){
  60.134 +        io->methods = &gzip_methods;
  60.135 +        io->data = (void*)f;
  60.136 +    }
  60.137 +    return io;
  60.138 +}
  60.139 +
  60.140 +/** IOStream version of fopen().
  60.141 + *
  60.142 + * @param file name of the file to open
  60.143 + * @param flags giving the mode to open in (as for fopen())
  60.144 + * @return new stream for the open file, or NULL if failed
  60.145 + */
  60.146 +IOStream *gzip_stream_fopen(const char *file, const char *flags){
  60.147 +    IOStream *io = NULL;
  60.148 +    gzFile *fgz;
  60.149 +    fgz = gzopen(file, flags);
  60.150 +    if(fgz){
  60.151 +        io = gzip_stream_new(fgz);
  60.152 +        if(!io){
  60.153 +            gzclose(fgz);
  60.154 +        }
  60.155 +    }
  60.156 +    return io;
  60.157 +}
  60.158 +
  60.159 +/** IOStream version of fdopen().
  60.160 + *
  60.161 + * @param fd file descriptor
  60.162 + * @param flags giving the mode to open in (as for fdopen())
  60.163 + * @return new stream for the open file, or NULL if failed.  Always takes
  60.164 + *         ownership of fd.
  60.165 + */
  60.166 +IOStream *gzip_stream_fdopen(int fd, const char *flags){
  60.167 +    IOStream *io = NULL;
  60.168 +    gzFile *fgz;
  60.169 +    fgz = gzdopen(fd, flags);
  60.170 +    if(fgz){
  60.171 +        io = gzip_stream_new(fgz);
  60.172 +        if(!io)
  60.173 +            gzclose(fgz);
  60.174 +    }
  60.175 +    return io;
  60.176 +}
  60.177 +#endif
    61.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    61.2 +++ b/tools/vnet/libxutil/gzip_stream.h	Tue May 24 21:17:29 2005 +0000
    61.3 @@ -0,0 +1,30 @@
    61.4 +/*
    61.5 + * Copyright (C) 2003 Hewlett-Packard Company.
    61.6 + *
    61.7 + * This library is free software; you can redistribute it and/or modify
    61.8 + * it under the terms of the GNU Lesser General Public License as published by
    61.9 + * the Free Software Foundation; either version 2.1 of the License, or
   61.10 + * (at your option) any later version.
   61.11 + *
   61.12 + * This library is distributed in the hope that it will be useful,
   61.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   61.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   61.15 + * GNU Lesser General Public License for more details.
   61.16 + *
   61.17 + * You should have received a copy of the GNU Lesser General Public License
   61.18 + * along with this library; if not, write to the Free Software
   61.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   61.20 + */
   61.21 +
   61.22 +#ifndef _XUTIL_GZIP_STREAM_H_
   61.23 +#define _XUTIL_GZIP_STREAM_H_
   61.24 +
   61.25 +#ifndef __KERNEL__
   61.26 +#include "iostream.h"
   61.27 +#include "zlib.h"
   61.28 +
   61.29 +extern IOStream *gzip_stream_new(gzFile *f);
   61.30 +extern IOStream *gzip_stream_fopen(const char *file, const char *flags);
   61.31 +extern IOStream *gzip_stream_fdopen(int fd, const char *flags);
   61.32 +#endif
   61.33 +#endif /* !_XUTIL_GZIP_STREAM_H_ */
    62.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    62.2 +++ b/tools/vnet/libxutil/hash_table.c	Tue May 24 21:17:29 2005 +0000
    62.3 @@ -0,0 +1,640 @@
    62.4 +/*
    62.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    62.6 + *
    62.7 + * This library is free software; you can redistribute it and/or modify
    62.8 + * it under the terms of the GNU Lesser General Public License as published by
    62.9 + * the Free Software Foundation; either version 2.1 of the License, or
   62.10 + * (at your option) any later version.
   62.11 + *
   62.12 + * This library is distributed in the hope that it will be useful,
   62.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   62.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   62.15 + * GNU Lesser General Public License for more details.
   62.16 + *
   62.17 + * You should have received a copy of the GNU Lesser General Public License
   62.18 + * along with this library; if not, write to the Free Software
   62.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   62.20 + */
   62.21 +
   62.22 +#ifdef __KERNEL__
   62.23 +#  include <linux/config.h>
   62.24 +#  include <linux/module.h>
   62.25 +#  include <linux/kernel.h>
   62.26 +#  include <linux/errno.h>
   62.27 +#else
   62.28 +#  include <errno.h>
   62.29 +#  include <stddef.h>
   62.30 +#endif
   62.31 +
   62.32 +//#include <limits.h>
   62.33 +
   62.34 +#include "allocate.h"
   62.35 +#include "hash_table.h"
   62.36 +
   62.37 +/** @file
   62.38 + * Base support for hashtables.
   62.39 + *
   62.40 + * Hash codes are reduced modulo the number of buckets to index tables,
   62.41 + * so there is no need for hash functions to limit the range of hashcodes.
   62.42 + * In fact it is assumed that hashcodes do not change when the number of
   62.43 + * buckets in the table changes.
   62.44 + */
   62.45 +
   62.46 +/*==========================================================================*/
   62.47 +/** Number of bits in half a word. */
   62.48 +//#if __WORDSIZE == 64
   62.49 +//#define HALF_WORD_BITS 32
   62.50 +//#else
   62.51 +#define HALF_WORD_BITS 16
   62.52 +//#endif
   62.53 +
   62.54 +/** Mask for lo half of a word. On 32-bit this is 
   62.55 + * (1<<16) - 1 = 65535 = 0xffff
   62.56 + * It's 4294967295 = 0xffffffff on 64-bit.
   62.57 + */
   62.58 +#define LO_HALF_MASK ((1 << HALF_WORD_BITS) - 1)
   62.59 +
   62.60 +/** Get the lo half of a word. */
   62.61 +#define LO_HALF(x) ((x) & LO_HALF_MASK)
   62.62 +
   62.63 +/** Get the hi half of a word. */
   62.64 +#define HI_HALF(x) ((x) >> HALF_WORD_BITS)
   62.65 +
   62.66 +/** Do a full hash on both inputs, using DES-style non-linear scrambling.
   62.67 + * Both inputs are replaced with the results of the hash.
   62.68 + *
   62.69 + * @param pleft input/output word
   62.70 + * @param pright input/output word
   62.71 + */
   62.72 +void pseudo_des(unsigned long *pleft, unsigned long *pright){
   62.73 +    // Bit-rich mixing constant.
   62.74 +    static const unsigned long a_mixer[] = {
   62.75 +        0xbaa96887L, 0x1e17d32cL, 0x03bcdc3cL, 0x0f33d1b2L, };
   62.76 +
   62.77 +    // Bit-rich mixing constant.
   62.78 +    static const unsigned long b_mixer[] = {
   62.79 +        0x4b0f3b58L, 0xe874f0c3L, 0x6955c5a6L, 0x55a7ca46L, };
   62.80 +
   62.81 +    // Number of iterations - must be 2 or 4.
   62.82 +    static const int ncycle = 4;
   62.83 +    //static const int ncycle = 2;
   62.84 +
   62.85 +    unsigned long left = *pleft, right = *pright;
   62.86 +    unsigned long v, v_hi, v_lo;
   62.87 +    int i;
   62.88 +
   62.89 +    for(i=0; i<ncycle; i++){
   62.90 +        // Flip some bits in right to get v.
   62.91 +        v = right;
   62.92 +        v ^= a_mixer[i];
   62.93 +        // Get lo and hi halves of v.
   62.94 +        v_lo = LO_HALF(v);
   62.95 +        v_hi = HI_HALF(v);
   62.96 +        // Non-linear mix of the halves of v.
   62.97 +        v = ((v_lo * v_lo) + ~(v_hi * v_hi));
   62.98 +        // Swap the halves of v.
   62.99 +        v = (HI_HALF(v) | (LO_HALF(v) << HALF_WORD_BITS));
  62.100 +        // Flip some bits.
  62.101 +        v ^= b_mixer[i];
  62.102 +        // More non-linear mixing.
  62.103 +        v += (v_lo * v_hi);
  62.104 +        v ^= left;
  62.105 +        left = right;
  62.106 +        right = v;
  62.107 +    }
  62.108 +    *pleft = left;
  62.109 +    *pright = right;
  62.110 +}
  62.111 +
  62.112 +/** Hash a string.
  62.113 + *
  62.114 + * @param s input to hash
  62.115 + * @return hashcode
  62.116 + */
  62.117 +Hashcode hash_string(char *s){
  62.118 +    Hashcode h = 0;
  62.119 +    if(s){
  62.120 +        for( ; *s; s++){
  62.121 +            h = hash_2ul(h, *s);
  62.122 +        }
  62.123 +    }
  62.124 +    return h;
  62.125 +}
  62.126 +
  62.127 +/** Get the bucket for a hashcode in a hash table.
  62.128 + *
  62.129 + * @param table to get bucket from
  62.130 + * @param hashcode to get bucket for
  62.131 + * @return bucket
  62.132 + */
  62.133 +inline HTBucket * get_bucket(HashTable *table, Hashcode hashcode){
  62.134 +    return table->buckets + (hashcode % table->buckets_n);
  62.135 +}
  62.136 +
  62.137 +/** Initialize a hash table.
  62.138 + * Can be safely called more than once.
  62.139 + *
  62.140 + * @param table to initialize
  62.141 + */
  62.142 +void HashTable_init(HashTable *table){
  62.143 +    int i;
  62.144 +
  62.145 +    if(!table->init_done){
  62.146 +        table->init_done = 1;
  62.147 +        table->next_id = 0;
  62.148 +        for(i=0; i<table->buckets_n; i++){
  62.149 +            HTBucket *bucket = get_bucket(table, i);
  62.150 +            bucket->head = 0;
  62.151 +            bucket->count = 0;
  62.152 +        }
  62.153 +        table->entry_count = 0;
  62.154 +    }
  62.155 +}
  62.156 +
  62.157 +/** Allocate a new hashtable.
  62.158 + * If the number of buckets is not positive the default is used.
  62.159 + * The number of buckets should usually be prime.
  62.160 + *
  62.161 + * @param buckets_n number of buckets
  62.162 + * @return new hashtable or null
  62.163 + */
  62.164 +HashTable *HashTable_new(int buckets_n){
  62.165 +    HashTable *z = ALLOCATE(HashTable);
  62.166 +    if(!z) goto exit;
  62.167 +    if(buckets_n <= 0){
  62.168 +        buckets_n = HT_BUCKETS_N;
  62.169 +    }
  62.170 +    z->buckets = (HTBucket*)allocate(buckets_n * sizeof(HTBucket));
  62.171 +    if(!z->buckets){
  62.172 +        deallocate(z);
  62.173 +        z = 0;
  62.174 +        goto exit;
  62.175 +    }
  62.176 +    z->buckets_n = buckets_n;
  62.177 +    HashTable_init(z);
  62.178 +  exit:
  62.179 +    return z;
  62.180 +}
  62.181 +
  62.182 +/** Free a hashtable.
  62.183 + * Any entries are removed and freed.
  62.184 + *
  62.185 + * @param h hashtable (ignored if null)
  62.186 + */
  62.187 +void HashTable_free(HashTable *h){
  62.188 +    if(h){
  62.189 +        HashTable_clear(h);
  62.190 +        deallocate(h->buckets);
  62.191 +        deallocate(h);
  62.192 +    }
  62.193 +}
  62.194 +
  62.195 +/** Push an entry on the list in the bucket for a given hashcode.
  62.196 + *
  62.197 + * @param table to add entry to
  62.198 + * @param hashcode for the entry
  62.199 + * @param entry to add
  62.200 + */
  62.201 +static inline void push_on_bucket(HashTable *table, Hashcode hashcode,
  62.202 +				  HTEntry *entry){
  62.203 +    HTBucket *bucket;
  62.204 +    HTEntry *old_head;
  62.205 +
  62.206 +    bucket = get_bucket(table, hashcode);
  62.207 +    old_head = bucket->head;
  62.208 +    bucket->count++;
  62.209 +    bucket->head = entry;
  62.210 +    entry->next = old_head;
  62.211 +}
  62.212 +
  62.213 +/** Change the number of buckets in a hashtable.
  62.214 + * No-op if the number of buckets is not positive.
  62.215 + * Existing entries are reallocated to buckets based on their hashcodes.
  62.216 + * The table is unmodified if the number of buckets cannot be changed.
  62.217 + *
  62.218 + * @param table hashtable
  62.219 + * @param buckets_n new number of buckets
  62.220 + * @return 0 on success, error code otherwise
  62.221 + */
  62.222 +int HashTable_set_buckets_n(HashTable *table, int buckets_n){
  62.223 +    int err = 0;
  62.224 +    HTBucket *old_buckets = table->buckets;
  62.225 +    int old_buckets_n = table->buckets_n;
  62.226 +    int i;
  62.227 +
  62.228 +    if(buckets_n <= 0){
  62.229 +        err = -EINVAL;
  62.230 +        goto exit;
  62.231 +    }
  62.232 +    table->buckets = (HTBucket*)allocate(buckets_n * sizeof(HTBucket));
  62.233 +    if(!table->buckets){
  62.234 +        err = -ENOMEM;
  62.235 +        table->buckets = old_buckets;
  62.236 +        goto exit;
  62.237 +    }
  62.238 +    table->buckets_n = buckets_n;
  62.239 +    for(i=0; i<old_buckets_n; i++){
  62.240 +        HTBucket *bucket = old_buckets + i;
  62.241 +        HTEntry *entry, *next;
  62.242 +        for(entry = bucket->head; entry; entry = next){
  62.243 +            next = entry->next;
  62.244 +            push_on_bucket(table, entry->hashcode, entry);
  62.245 +        }
  62.246 +    }
  62.247 +    deallocate(old_buckets);
  62.248 +  exit:
  62.249 +    return err;
  62.250 +}
  62.251 +
  62.252 +/** Adjust the number of buckets so the table is neither too full nor too empty.
  62.253 + * The table is unmodified if adjusting fails.
  62.254 + *
  62.255 + * @param table hash table
  62.256 + * @param buckets_min minimum number of buckets (use default if 0 or negative)
  62.257 + * @return 0 on success, error code otherwise
  62.258 + */
  62.259 +int HashTable_adjust(HashTable *table, int buckets_min){
  62.260 +    int buckets_n = 0;
  62.261 +    int err = 0;
  62.262 +    if(buckets_min <= 0) buckets_min = HT_BUCKETS_N;
  62.263 +    if(table->entry_count >= table->buckets_n){
  62.264 +        // The table is dense - expand it.
  62.265 +        buckets_n = 2 * table->buckets_n;
  62.266 +    } else if((table->buckets_n > buckets_min) &&
  62.267 +              (4 * table->entry_count < table->buckets_n)){
  62.268 +        // The table is more than minimum size and sparse - shrink it.
  62.269 +        buckets_n = 2 * table->entry_count;
  62.270 +        if(buckets_n < buckets_min) buckets_n = buckets_min;
  62.271 +    }
  62.272 +    if(buckets_n){
  62.273 +        err = HashTable_set_buckets_n(table, buckets_n);
  62.274 +    }
  62.275 +    return err;
  62.276 +}
  62.277 +
  62.278 +/** Allocate a new entry for a given value.
  62.279 + *
  62.280 + * @param value to put in the entry
  62.281 + * @return entry, or 0 on failure
  62.282 + */
  62.283 +HTEntry * HTEntry_new(Hashcode hashcode, void *key, void *value){
  62.284 +    HTEntry *z = ALLOCATE(HTEntry);
  62.285 +    if(z){
  62.286 +        z->hashcode = hashcode;
  62.287 +        z->key = key;
  62.288 +        z->value = value;
  62.289 +    }
  62.290 +    return z;
  62.291 +}
  62.292 +
  62.293 +/** Free an entry.
  62.294 + *
  62.295 + * @param z entry to free
  62.296 + */
  62.297 +inline void HTEntry_free(HTEntry *z){
  62.298 +    if(z){
  62.299 +        deallocate(z);
  62.300 +    }
  62.301 +}
  62.302 +
  62.303 +/** Free an entry in a hashtable.
  62.304 + * The table's entry_free_fn is used is defined, otherwise 
  62.305 + * the HTEntry itself is freed.
  62.306 + *
  62.307 + * @param table hashtable
  62.308 + * @param entry to free
  62.309 + */
  62.310 +inline void HashTable_free_entry(HashTable *table, HTEntry *entry){
  62.311 +    if(!entry)return;
  62.312 +    if(table && table->entry_free_fn){
  62.313 +        table->entry_free_fn(table, entry);
  62.314 +    } else {
  62.315 +        HTEntry_free(entry);
  62.316 +    }
  62.317 +}
  62.318 +
  62.319 +/** Get the first entry satisfying a test from the bucket for the
  62.320 + * given hashcode.
  62.321 + *
  62.322 + * @param table to look in
  62.323 + * @param hashcode indicates the bucket
  62.324 + * @param test_fn test to apply to elements
  62.325 + * @param arg first argument to calls to test_fn
  62.326 + * @return entry found, or 0
  62.327 + */
  62.328 +inline HTEntry * HashTable_find_entry(HashTable *table, Hashcode hashcode,
  62.329 +				      TableTestFn *test_fn, TableArg arg){
  62.330 +    HTBucket *bucket;
  62.331 +    HTEntry *entry = 0;
  62.332 +    HTEntry *next;
  62.333 +
  62.334 +    bucket = get_bucket(table, hashcode);
  62.335 +    for(entry = bucket->head; entry; entry = next){
  62.336 +        next = entry->next;
  62.337 +        if(test_fn(arg, table, entry)){
  62.338 +            break;
  62.339 +        }
  62.340 +    }
  62.341 +    return entry;
  62.342 +}
  62.343 +
  62.344 +/** Test hashtable keys for equality.
  62.345 + * Uses the table's key_equal_fn if defined, otherwise pointer equality.
  62.346 + *
  62.347 + * @param key1 key to compare
  62.348 + * @param key2 key to compare
  62.349 + * @return 1 if equal, 0 otherwise
  62.350 + */
  62.351 +inline int HashTable_key_equal(HashTable *table, void *key1, void *key2){
  62.352 +    return (table->key_equal_fn ? table->key_equal_fn(key1, key2) : key1==key2);
  62.353 +}
  62.354 +
  62.355 +/** Compute the hashcode of a hashtable key.
  62.356 + * The table's key_hash_fn is used if defined, otherwise the address of
  62.357 + * the key is hashed.
  62.358 + *
  62.359 + * @param table hashtable
  62.360 + * @param key to hash
  62.361 + * @return hashcode
  62.362 + */
  62.363 +inline Hashcode HashTable_key_hash(HashTable *table, void *key){
  62.364 +    return (table->key_hash_fn ? table->key_hash_fn(key) : hash_ul((unsigned long)key));
  62.365 +}
  62.366 +
  62.367 +/** Test if an entry has a given key.
  62.368 + *
  62.369 + * @param arg containing key to test for
  62.370 + * @param table the entry is in
  62.371 + * @param entry to test
  62.372 + * @return 1 if the entry has the key, 0 otherwise
  62.373 + */
  62.374 +static inline int has_key(TableArg arg, HashTable *table, HTEntry *entry){
  62.375 +    return HashTable_key_equal(table, arg.ptr, entry->key);
  62.376 +}
  62.377 +
  62.378 +/** Get an entry with a given key.
  62.379 + *
  62.380 + * @param table to search
  62.381 + * @param key to look for
  62.382 + * @return entry if found, null otherwise
  62.383 + */
  62.384 +#if 0
  62.385 +inline HTEntry * HashTable_get_entry(HashTable *table, void *key){
  62.386 +    TableArg arg = { ptr: key };
  62.387 +    return HashTable_find_entry(table, HashTable_key_hash(table, key), has_key, arg);
  62.388 +}
  62.389 +#else
  62.390 +inline HTEntry * HashTable_get_entry(HashTable *table, void *key){
  62.391 +    Hashcode hashcode;
  62.392 +    HTBucket *bucket;
  62.393 +    HTEntry *entry = 0;
  62.394 +    HTEntry *next;
  62.395 +
  62.396 +    hashcode = HashTable_key_hash(table, key);
  62.397 +    bucket = get_bucket(table, hashcode);
  62.398 +    for(entry = bucket->head; entry; entry = next){
  62.399 +        next = entry->next;
  62.400 +        if(HashTable_key_equal(table, key, entry->key)){
  62.401 +            break;
  62.402 +        }
  62.403 +    }
  62.404 +    return entry;
  62.405 +}
  62.406 +#endif
  62.407 +
  62.408 +/** Get the value of an entry with a given key.
  62.409 + *
  62.410 + * @param table to search
  62.411 + * @param key to look for
  62.412 + * @return value if an entry was found, null otherwise
  62.413 + */
  62.414 +inline void * HashTable_get(HashTable *table, void *key){
  62.415 +    HTEntry *entry = HashTable_get_entry(table, key);
  62.416 +    return (entry ? entry->value : 0);
  62.417 +}
  62.418 +
  62.419 +/** Print the buckets in a table.
  62.420 + *
  62.421 + * @param table to print
  62.422 + */
  62.423 +void show_buckets(HashTable *table, IOStream *io){
  62.424 +    int i,j ;
  62.425 +    IOStream_print(io, "entry_count=%d buckets_n=%d\n", table->entry_count, table->buckets_n);
  62.426 +    for(i=0; i<table->buckets_n; i++){
  62.427 +        if(0 || table->buckets[i].count>0){
  62.428 +            IOStream_print(io, "bucket %3d %3d %10p ", i,
  62.429 +                        table->buckets[i].count,
  62.430 +                        table->buckets[i].head);
  62.431 +            for(j = table->buckets[i].count; j>0; j--){
  62.432 +                IOStream_print(io, "+");
  62.433 +            }
  62.434 +            IOStream_print(io, "\n");
  62.435 +        }
  62.436 +    }
  62.437 +    HashTable_print(table, io); 
  62.438 +}
  62.439 +    
  62.440 +/** Print an entry in a table.
  62.441 + *
  62.442 + * @param entry to print
  62.443 + * @param arg a pointer to an IOStream to print to
  62.444 + * @return 0
  62.445 + */
  62.446 +static int print_entry(TableArg arg, HashTable *table, HTEntry *entry){
  62.447 +    IOStream *io = (IOStream*)arg.ptr;
  62.448 +    IOStream_print(io, " b=%4lx h=%08lx i=%08lx |-> e=%8p k=%8p v=%8p\n",
  62.449 +                entry->hashcode % table->buckets_n,
  62.450 +                entry->hashcode,
  62.451 +                entry->index,
  62.452 +                entry, entry->key, entry->value);
  62.453 +    return 0;
  62.454 +}
  62.455 +
  62.456 +/** Print a hash table.
  62.457 + *
  62.458 + * @param table to print
  62.459 + */
  62.460 +void HashTable_print(HashTable *table, IOStream *io){
  62.461 +    IOStream_print(io, "{\n");
  62.462 +    HashTable_map(table, print_entry, (TableArg){ ptr: io });
  62.463 +    IOStream_print(io, "}\n");
  62.464 +}
  62.465 +/*==========================================================================*/
  62.466 +
  62.467 +/** Get the next entry id to use for a table.
  62.468 + *
  62.469 + * @param table hash table
  62.470 + * @return non-zero entry id
  62.471 + */
  62.472 +static inline unsigned long get_next_id(HashTable *table){
  62.473 +    unsigned long id;
  62.474 +
  62.475 +    if(table->next_id == 0){
  62.476 +        table->next_id = 1;
  62.477 +    }
  62.478 +    id = table->next_id++;
  62.479 +    return id;
  62.480 +}
  62.481 +
  62.482 +/** Add an entry to the bucket for the
  62.483 + * given hashcode.
  62.484 + *
  62.485 + * @param table to insert in
  62.486 + * @param hashcode indicates the bucket
  62.487 + * @param key to add an entry for
  62.488 + * @param value to add an entry for
  62.489 + * @return entry on success, 0 on failure
  62.490 + */
  62.491 +inline HTEntry * HashTable_add_entry(HashTable *table, Hashcode hashcode, void *key, void *value){
  62.492 +    HTEntry *entry = HTEntry_new(hashcode, key, value);
  62.493 +    if(entry){
  62.494 +        entry->index = get_next_id(table);
  62.495 +        push_on_bucket(table, hashcode, entry);
  62.496 +        table->entry_count++;
  62.497 +    }
  62.498 +    return entry;
  62.499 +}
  62.500 +
  62.501 +/** Move the front entry for a bucket to the correct point in the bucket order as
  62.502 + * defined by the order function. If this is called every time a new entry is added
  62.503 + * the bucket will be maintained in sorted order.
  62.504 + *
  62.505 + * @param table to modify
  62.506 + * @param hashcode indicates the bucket
  62.507 + * @param order entry comparison function
  62.508 + * @return 0 if an entry was moved, 1 if not
  62.509 + */
  62.510 +int HashTable_order_bucket(HashTable *table, Hashcode hashcode, TableOrderFn *order){
  62.511 +    HTEntry *new_entry = NULL, *prev = NULL, *entry = NULL;
  62.512 +    HTBucket *bucket;
  62.513 +    int err = 1;
  62.514 +
  62.515 +    bucket = get_bucket(table, hashcode);
  62.516 +    new_entry = bucket->head;
  62.517 +    if(!new_entry || !new_entry->next) goto exit;
  62.518 +    for(entry = new_entry->next; entry; prev = entry, entry = entry->next){
  62.519 +        if(order(new_entry, entry) <= 0) break;
  62.520 +    }
  62.521 +    if(prev){
  62.522 +        err = 0;
  62.523 +        bucket->head = new_entry->next; 
  62.524 +        new_entry->next = entry;
  62.525 +        prev->next = new_entry;
  62.526 +    }
  62.527 +  exit:
  62.528 +    return err;
  62.529 +}
  62.530 +
  62.531 +/** Add an entry to a hashtable.
  62.532 + * The entry is added to the bucket for its key's hashcode.
  62.533 + *
  62.534 + * @param table to insert in
  62.535 + * @param key to add an entry for
  62.536 + * @param value to add an entry for
  62.537 + * @return entry on success, 0 on failure
  62.538 + */
  62.539 +inline HTEntry * HashTable_add(HashTable *table, void *key, void *value){
  62.540 +    return HashTable_add_entry(table, HashTable_key_hash(table, key), key, value);
  62.541 +}
  62.542 +
  62.543 +
  62.544 +/** Remove entries satisfying a test from the bucket for the
  62.545 + * given hashcode. 
  62.546 + *
  62.547 + * @param table to remove from
  62.548 + * @param hashcode indicates the bucket
  62.549 + * @param test_fn test to apply to elements
  62.550 + * @param arg first argument to calls to test_fn
  62.551 + * @return number of entries removed
  62.552 + */
  62.553 +inline int HashTable_remove_entry(HashTable *table, Hashcode hashcode,
  62.554 +				  TableTestFn *test_fn, TableArg arg){
  62.555 +    HTBucket *bucket;
  62.556 +    HTEntry *entry, *prev = 0, *next;
  62.557 +    int removed_count = 0;
  62.558 +
  62.559 +    bucket = get_bucket(table, hashcode);
  62.560 +    for(entry = bucket->head; entry; entry = next){
  62.561 +        next = entry->next;
  62.562 +        if(test_fn(arg, table, entry)){
  62.563 +            if(prev){
  62.564 +                prev->next = next;
  62.565 +            } else {
  62.566 +                bucket->head = next;
  62.567 +            }
  62.568 +            bucket->count--;
  62.569 +            table->entry_count--;
  62.570 +            removed_count++;
  62.571 +            HashTable_free_entry(table, entry);
  62.572 +            entry = 0;
  62.573 +        }
  62.574 +        prev = entry;
  62.575 +    }
  62.576 +    return removed_count;
  62.577 +}
  62.578 +
  62.579 +/** Remove entries with a given key. 
  62.580 + *
  62.581 + * @param table to remove from
  62.582 + * @param key of entries to remove
  62.583 + * @return number of entries removed
  62.584 + */
  62.585 +inline int HashTable_remove(HashTable *table, void *key){
  62.586 +#if 1
  62.587 +    Hashcode hashcode;
  62.588 +    HTBucket *bucket;
  62.589 +    HTEntry *entry, *prev = 0, *next;
  62.590 +    int removed_count = 0;
  62.591 +
  62.592 +    hashcode = HashTable_key_hash(table, key);
  62.593 +    bucket = get_bucket(table, hashcode);
  62.594 +    for(entry = bucket->head; entry; entry = next){
  62.595 +        next = entry->next;
  62.596 +        if(HashTable_key_equal(table, key, entry->key)){
  62.597 +            if(prev){
  62.598 +                prev->next = next;
  62.599 +            } else {
  62.600 +                bucket->head = next;
  62.601 +            }
  62.602 +            bucket->count--;
  62.603 +            table->entry_count--;
  62.604 +            removed_count++;
  62.605 +            HashTable_free_entry(table, entry);
  62.606 +            entry = 0;
  62.607 +        }
  62.608 +        prev = entry;
  62.609 +    }
  62.610 +    return removed_count;
  62.611 +#else
  62.612 +    return HashTable_remove_entry(table, HashTable_key_hash(table, key),
  62.613 +				  has_key, (TableArg){ ptr: key});
  62.614 +#endif
  62.615 +}
  62.616 +
  62.617 +/** Remove (and free) all the entries in a bucket.
  62.618 + *
  62.619 + * @param bucket to clear
  62.620 + */
  62.621 +static inline void bucket_clear(HashTable *table, HTBucket *bucket){
  62.622 +    HTEntry *entry, *next;
  62.623 +
  62.624 +    for(entry = bucket->head; entry; entry = next){
  62.625 +        next = entry->next;
  62.626 +        HashTable_free_entry(table, entry);
  62.627 +    }
  62.628 +    bucket->head = 0;
  62.629 +    table->entry_count -= bucket->count;
  62.630 +    bucket->count = 0;
  62.631 +}
  62.632 +
  62.633 +/** Remove (and free) all the entries in a table.
  62.634 + *
  62.635 + * @param table to clear
  62.636 + */
  62.637 +void HashTable_clear(HashTable *table){
  62.638 +    int i, n = table->buckets_n;
  62.639 +
  62.640 +    for(i=0; i<n; i++){
  62.641 +        bucket_clear(table, table->buckets + i);
  62.642 +    }
  62.643 +}
    63.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    63.2 +++ b/tools/vnet/libxutil/hash_table.h	Tue May 24 21:17:29 2005 +0000
    63.3 @@ -0,0 +1,294 @@
    63.4 +/*
    63.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    63.6 + *
    63.7 + * This library is free software; you can redistribute it and/or modify
    63.8 + * it under the terms of the GNU Lesser General Public License as published by
    63.9 + * the Free Software Foundation; either version 2.1 of the License, or
   63.10 + * (at your option) any later version.
   63.11 + *
   63.12 + * This library is distributed in the hope that it will be useful,
   63.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   63.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   63.15 + * GNU Lesser General Public License for more details.
   63.16 + *
   63.17 + * You should have received a copy of the GNU Lesser General Public License
   63.18 + * along with this library; if not, write to the Free Software
   63.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   63.20 + */
   63.21 +
   63.22 +#ifndef _XUTIL_HASH_TABLE_H_
   63.23 +#define _XUTIL_HASH_TABLE_H_
   63.24 +
   63.25 +#include "iostream.h"
   63.26 +
   63.27 +typedef unsigned long Hashcode;
   63.28 +
   63.29 +/** Type used to pass parameters to table functions. */
   63.30 +typedef union TableArg {
   63.31 +    unsigned long ul;
   63.32 +    void *ptr;
   63.33 +} TableArg;
   63.34 +
   63.35 +/** An entry in a bucket list. */
   63.36 +typedef struct HTEntry {
   63.37 +    /** Hashcode of the entry's key. */
   63.38 +    Hashcode hashcode;
   63.39 +    /** Identifier for this entry in the table. */
   63.40 +    int index;
   63.41 +    /** The key for this entry. */
   63.42 +    void *key;
   63.43 +    /** The value in this entry. */
   63.44 +    void *value;
   63.45 +    /** The next entry in the list. */
   63.46 +    struct HTEntry *next;
   63.47 +} HTEntry;
   63.48 +
   63.49 +/** A bucket in a rule table. */
   63.50 +typedef struct HTBucket {
   63.51 +    /** Number of entries in the bucket. */
   63.52 +    int count;
   63.53 +    /** First entry in the bucket (may be null). */
   63.54 +    HTEntry *head;
   63.55 +} HTBucket;
   63.56 +
   63.57 +/** Default number of buckets in a hash table.
   63.58 + * You want enough buckets so the lists in the buckets will typically be short.
   63.59 + * It's a good idea if this is prime, since that will help to spread hashcodes
   63.60 + * around the table.
   63.61 + */
   63.62 +//#define HT_BUCKETS_N 1
   63.63 +//#define HT_BUCKETS_N 3
   63.64 +//#define HT_BUCKETS_N 7
   63.65 +//#define HT_BUCKETS_N 17
   63.66 +//#define HT_BUCKETS_N 97
   63.67 +//#define HT_BUCKETS_N 211
   63.68 +//#define HT_BUCKETS_N 401
   63.69 +#define HT_BUCKETS_N 1021
   63.70 +
   63.71 +typedef struct HashTable HashTable;
   63.72 +
   63.73 +/** Type for a function used to select table entries. */
   63.74 +typedef int TableTestFn(TableArg arg, HashTable *table, HTEntry *entry);
   63.75 +
   63.76 +/** Type for a function to map over table entries. */
   63.77 +typedef int TableMapFn(TableArg arg, HashTable *table, HTEntry *entry);
   63.78 +
   63.79 +/** Type for a function to free table entries. */
   63.80 +typedef void TableFreeFn(HashTable *table, HTEntry *entry);
   63.81 +
   63.82 +/** Type for a function to hash table keys. */
   63.83 +typedef Hashcode TableHashFn(void *key);
   63.84 +
   63.85 +/** Type for a function to test table keys for equality. */
   63.86 +typedef int TableEqualFn(void *key1, void *key2);
   63.87 +
   63.88 +/** Type for a function to order table entries. */
   63.89 +typedef int TableOrderFn(HTEntry *e1, HTEntry *e2);
   63.90 +
   63.91 +/** General hash table.
   63.92 + * A hash table with a list in each bucket.
   63.93 + * Functions can be supplied for freeing entries, hashing keys, and comparing keys.
   63.94 + * These all default to 0, when default behaviour treating keys as integers is used.
   63.95 + */
   63.96 +struct HashTable {
   63.97 +    /** Flag indicating whether the table has been initialised. */
   63.98 +    int init_done;
   63.99 +    /** Next value for the id field in inserted rules. */
  63.100 +    unsigned long next_id;
  63.101 +    /** Number of buckets in the bucket array. */
  63.102 +    int buckets_n;
  63.103 +    /** Array of buckets, each with its own list. */
  63.104 +    HTBucket *buckets;
  63.105 +    /** Number of entries in the table. */
  63.106 +    int entry_count;
  63.107 +    /** Function to free keys and values in entries. */
  63.108 +    TableFreeFn *entry_free_fn;
  63.109 +    /** Function to hash keys. */
  63.110 +    TableHashFn *key_hash_fn;
  63.111 +    /** Function to compare keys for equality. */
  63.112 +    TableEqualFn *key_equal_fn;
  63.113 +    /** Place for the user of the table to hang extra data. */
  63.114 +    void *user_data;
  63.115 +};
  63.116 +
  63.117 +extern HashTable *HashTable_new(int bucket_n);
  63.118 +extern void HashTable_free(HashTable *table);
  63.119 +extern HTEntry * HTEntry_new(Hashcode hashcode, void *key, void *value);
  63.120 +extern void HTEntry_free(HTEntry *entry);
  63.121 +extern int HashTable_set_bucket_n(HashTable *table, int bucket_n);
  63.122 +extern void HashTable_clear(HashTable *table);
  63.123 +extern HTEntry * HashTable_add_entry(HashTable *table, Hashcode hashcode, void *key, void *value);
  63.124 +extern HTEntry * HashTable_get_entry(HashTable *table, void *key);
  63.125 +extern HTEntry * HashTable_add(HashTable *table, void *key, void *value);
  63.126 +extern void * HashTable_get(HashTable *table, void *key);
  63.127 +extern int HashTable_remove(HashTable *table, void *key);
  63.128 +extern HTEntry * HashTable_find_entry(HashTable *table, Hashcode hashcode,
  63.129 +                                      TableTestFn *test_fn, TableArg arg);
  63.130 +extern int HashTable_remove_entry(HashTable *table, Hashcode hashcode,
  63.131 +                                   TableTestFn *test_fn, TableArg arg);
  63.132 +//extern int HashTable_map(HashTable *table, TableMapFn *map_fn, TableArg arg);
  63.133 +extern void HashTable_print(HashTable *table, IOStream *out);
  63.134 +extern int HashTable_set_buckets_n(HashTable *table, int buckets_n);
  63.135 +extern int HashTable_adjust(HashTable *table, int buckets_min);
  63.136 +extern void pseudo_des(unsigned long *pleft, unsigned long *pright);
  63.137 +extern Hashcode hash_string(char *s);
  63.138 +
  63.139 +extern int HashTable_order_bucket(HashTable *table, Hashcode hashcode, TableOrderFn *order);
  63.140 +
  63.141 +/** Control whether to use hashing based on DES or simple
  63.142 + * hashing. DES hashing is `more random' but much more expensive.
  63.143 + */
  63.144 +#define HASH_PSEUDO_DES 0
  63.145 +
  63.146 +/** Hash a long using a quick and dirty linear congruential random number generator.
  63.147 + *  See `Numerical Recipes in C', Chapter 7, "An Even Quicker Generator".
  63.148 + *
  63.149 + * @param a value to hash
  63.150 + * @return hashed input
  63.151 + */
  63.152 +static inline unsigned long lcrng_hash(unsigned long a){
  63.153 +    return (1664525L * a + 1013904223L);
  63.154 +}
  63.155 +
  63.156 +/** Hash an unsigned long.
  63.157 + *
  63.158 + * @param a input to hash
  63.159 + * @return hashcode
  63.160 + */
  63.161 +static inline Hashcode hash_ul(unsigned long a){
  63.162 +#if HASH_PSEUDO_DES
  63.163 +    unsigned long left = a;
  63.164 +    unsigned long right = 0L;
  63.165 +    pseudo_des(&left, &right);
  63.166 +    return right;
  63.167 +#else
  63.168 +    a = lcrng_hash(a);
  63.169 +    a = lcrng_hash(a);
  63.170 +    return a;
  63.171 +#endif
  63.172 +}
  63.173 +
  63.174 +/** Hash two unsigned longs together.
  63.175 + *
  63.176 + * @param a input to hash
  63.177 + * @param b input to hash
  63.178 + * @return hashcode
  63.179 + */
  63.180 +static inline Hashcode hash_2ul(unsigned long a, unsigned long b){
  63.181 +#if HASH_PSEUDO_DES
  63.182 +    unsigned long left = a;
  63.183 +    unsigned long right = b;
  63.184 +    pseudo_des(&left, &right);
  63.185 +    return right;
  63.186 +#else
  63.187 +    a = lcrng_hash(a);
  63.188 +    a ^= b;
  63.189 +    a = lcrng_hash(a);
  63.190 +    return a;
  63.191 +#endif
  63.192 +}
  63.193 +
  63.194 +/** Hash a hashcode and an unsigned long together.
  63.195 + *
  63.196 + * @param a input hashcode
  63.197 + * @param b input to hash
  63.198 + * @return hashcode
  63.199 + */
  63.200 +static inline Hashcode hash_hul(Hashcode a, unsigned long b){
  63.201 +#if HASH_PSEUDO_DES
  63.202 +    unsigned long left = a;
  63.203 +    unsigned long right = b;
  63.204 +    pseudo_des(&left, &right);
  63.205 +    return right;
  63.206 +#else
  63.207 +    a ^= b;
  63.208 +    a = lcrng_hash(a);
  63.209 +    return a;
  63.210 +#endif
  63.211 +}
  63.212 +
  63.213 +/** Macro to declare variables for HashTable_for_each() to use.
  63.214 + *
  63.215 + * @param entry variable that is set to entries in the table
  63.216 + */
  63.217 +#define HashTable_for_decl(entry) \
  63.218 +  HashTable *_var_table; \
  63.219 +  HTBucket *_var_bucket; \
  63.220 +  HTBucket *_var_end; \
  63.221 +  HTEntry *_var_next; \
  63.222 +  HTEntry *entry
  63.223 +
  63.224 +/** Macro to iterate over the entries in a hashtable.
  63.225 + * Must be in a scope where HashTable_for_decl() has been used to declare
  63.226 + * variables for it to use.
  63.227 + * The variable 'entry' is iterated over entries in the table.
  63.228 + * The code produced is syntactically a loop, so it must be followed by
  63.229 + * a loop body, typically some statements in braces:
  63.230 + * HashTable_for_each(entry, table){ ...loop body... }
  63.231 + *
  63.232 + * HashTable_for_each() and HashTable_for_decl() cannot be used for nested
  63.233 + * loops as variables will clash.
  63.234 + *
  63.235 + * @note The simplest way to code a direct loop over the entries in a hashtable
  63.236 + * is to use a loop over the buckets, with a nested loop over the entries
  63.237 + * in a bucket. Using this approach in a macro means the macro contains
  63.238 + * an opening brace, and calls to it must be followed by 2 braces!
  63.239 + * To avoid this the code has been restructured so that it is a for loop.
  63.240 + * So that statements could be used in the test expression of the for loop,
  63.241 + * we have used the gcc statement expression extension ({ ... }).
  63.242 + *
  63.243 + * @param entry variable to iterate over the entries
  63.244 + * @param table to iterate over (non-null)
  63.245 + */
  63.246 +#define HashTable_for_each(entry, table) \
  63.247 +  _var_table = table; \
  63.248 +  _var_bucket = _var_table->buckets; \
  63.249 +  _var_end = _var_bucket + _var_table->buckets_n; \
  63.250 +  for(entry=0, _var_next=0; \
  63.251 +      ({ if(_var_next){ \
  63.252 +             entry = _var_next; \
  63.253 +             _var_next = entry->next; \
  63.254 +          } else { \
  63.255 +             while(_var_bucket < _var_end){ \
  63.256 +                 entry = _var_bucket->head; \
  63.257 +                 _var_bucket++; \
  63.258 +                 if(entry){ \
  63.259 +                      _var_next = entry->next; \
  63.260 +                      break; \
  63.261 +                 } \
  63.262 +             } \
  63.263 +          }; \
  63.264 +         entry; }); \
  63.265 +      entry = _var_next )
  63.266 +
  63.267 +/** Map a function over the entries in a table.
  63.268 + * Mapping stops when the function returns a non-zero value.
  63.269 + * Uses the gcc statement expression extension ({ ... }).
  63.270 + *
  63.271 + * @param table to map over
  63.272 + * @param fn function to apply to entries
  63.273 + * @param arg first argument to call the function with
  63.274 + * @return 0 if fn always returned 0, first non-zero value otherwise
  63.275 + */
  63.276 +#define HashTable_map(table, fn, arg) \
  63.277 +  ({ HashTable_for_decl(_var_entry); \
  63.278 +    TableArg _var_arg = arg; \
  63.279 +    int _var_value = 0; \
  63.280 +    HashTable_for_each(_var_entry, table){ \
  63.281 +        if((_var_value = fn(_var_arg, _var_table, _var_entry))) break; \
  63.282 +    } \
  63.283 +    _var_value; })
  63.284 +
  63.285 +/** Cast x to the type for a key or value in a hash table.
  63.286 + * This avoids compiler warnings when using short integers
  63.287 + * as keys or values (especially on 64-bit platforms).
  63.288 + */
  63.289 +#define HKEY(x) ((void*)(unsigned long)(x))
  63.290 +
  63.291 +/** Cast x from the type for a key or value in a hash table.
  63.292 + * to an unsigned long. This avoids compiler warnings when using
  63.293 + * short integers as keys or values (especially on 64-bit platforms).
  63.294 + */
  63.295 +#define HVAL(x) ((unsigned long)(x))
  63.296 +
  63.297 +#endif /* !_XUTIL_HASH_TABLE_H_ */
    64.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    64.2 +++ b/tools/vnet/libxutil/iostream.c	Tue May 24 21:17:29 2005 +0000
    64.3 @@ -0,0 +1,55 @@
    64.4 +/*
    64.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    64.6 + *
    64.7 + * This library is free software; you can redistribute it and/or modify
    64.8 + * it under the terms of the GNU Lesser General Public License as published by
    64.9 + * the Free Software Foundation; either version 2.1 of the License, or
   64.10 + * (at your option) any later version.
   64.11 + *
   64.12 + * This library is distributed in the hope that it will be useful,
   64.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   64.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   64.15 + * GNU Lesser General Public License for more details.
   64.16 + *
   64.17 + * You should have received a copy of the GNU Lesser General Public License
   64.18 + * along with this library; if not, write to the Free Software
   64.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   64.20 + */
   64.21 +
   64.22 +#include "iostream.h"
   64.23 +#include "sys_string.h"
   64.24 +
   64.25 +/** Print on a stream, like vfprintf().
   64.26 + *
   64.27 + * @param stream to print to
   64.28 + * @param format for the print (as fprintf())
   64.29 + * @param args arguments to print
   64.30 + * @return result code from the print
   64.31 + */
   64.32 +int IOStream_vprint(IOStream *stream, const char *format, va_list args){
   64.33 +  char buffer[1024];
   64.34 +  int k = sizeof(buffer), n;
   64.35 +
   64.36 +  n = vsnprintf(buffer, k, (char*)format, args);
   64.37 +  if(n < 0 || n > k ){
   64.38 +      n = k;
   64.39 +  }
   64.40 +  n = IOStream_write(stream, buffer, n);
   64.41 +  return n;
   64.42 +}
   64.43 +
   64.44 +/** Print on a stream, like fprintf().
   64.45 + *
   64.46 + * @param stream to print to
   64.47 + * @param format for the print (as fprintf())
   64.48 + * @return result code from the print
   64.49 + */
   64.50 +int IOStream_print(IOStream *stream, const char *format, ...){
   64.51 +  va_list args;
   64.52 +  int result = -1;
   64.53 +
   64.54 +  va_start(args, format);
   64.55 +  result = IOStream_vprint(stream, format, args);
   64.56 +  va_end(args);
   64.57 +  return result;
   64.58 +}
    65.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    65.2 +++ b/tools/vnet/libxutil/iostream.h	Tue May 24 21:17:29 2005 +0000
    65.3 @@ -0,0 +1,269 @@
    65.4 +/*
    65.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    65.6 + *
    65.7 + * This library is free software; you can redistribute it and/or modify
    65.8 + * it under the terms of the GNU Lesser General Public License as published by
    65.9 + * the Free Software Foundation; either version 2.1 of the License, or
   65.10 + * (at your option) any later version.
   65.11 + *
   65.12 + * This library is distributed in the hope that it will be useful,
   65.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   65.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   65.15 + * GNU Lesser General Public License for more details.
   65.16 + *
   65.17 + * You should have received a copy of the GNU Lesser General Public License
   65.18 + * along with this library; if not, write to the Free Software
   65.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   65.20 + */
   65.21 +
   65.22 +#ifndef _XUTIL_IOSTREAM_H_
   65.23 +#define _XUTIL_IOSTREAM_H_
   65.24 +
   65.25 +#include <stdarg.h>
   65.26 +
   65.27 +#ifdef __KERNEL__
   65.28 +#include <linux/config.h>
   65.29 +#include <linux/types.h>
   65.30 +#include <linux/errno.h>
   65.31 +#else
   65.32 +#include <errno.h>
   65.33 +#include <stdint.h>
   65.34 +#include <stddef.h>
   65.35 +#endif
   65.36 +
   65.37 +#include "allocate.h"
   65.38 +
   65.39 +/** End of input return value (for getc). */
   65.40 +#define IOSTREAM_EOF -1
   65.41 +
   65.42 +/** An input/output abstraction.
   65.43 + */
   65.44 +typedef struct IOStream IOStream;
   65.45 +
   65.46 +/** Record of the functions to use for operations on an
   65.47 + * IOStream implementation.
   65.48 + */
   65.49 +typedef struct IOMethods {
   65.50 +    /** Read function.  Called with the user data, buffer to read into
   65.51 +     * and number of bytes to read.  Must return number of bytes read
   65.52 +     * on success, less than zero on error.
   65.53 +     */
   65.54 +    int (*read)(IOStream *stream, void *buf, size_t n);
   65.55 +
   65.56 +    /** Write function. Called with user data, buffer to write and
   65.57 +     * number of bytes to write. Must return number of bytes written on
   65.58 +     * success, less than zero otherwise.
   65.59 +     */
   65.60 +    int (*write)(IOStream *stream, const void *buf, size_t n);
   65.61 +
   65.62 +    int (*flush)(IOStream *s);
   65.63 +
   65.64 +    int (*error)(IOStream *s);
   65.65 +
   65.66 +    int (*close)(IOStream *s);
   65.67 +
   65.68 +    void (*free)(IOStream *s);
   65.69 +
   65.70 +    void (*lock)(IOStream *s);
   65.71 +    void (*unlock)(IOStream *s);
   65.72 +
   65.73 +} IOMethods;
   65.74 +
   65.75 +/** Abstract i/o object.
   65.76 + */
   65.77 +struct IOStream {
   65.78 +    /** Methods to use to implement operations. */
   65.79 +    const IOMethods *methods;
   65.80 +    /** Private state for the implementation. */
   65.81 +    const void *data;
   65.82 +    /** Flag indicating whether the stream is closed. */
   65.83 +    int closed;
   65.84 +    /** Number of bytes written. */
   65.85 +    int written;
   65.86 +    /** Number of bytes read. */
   65.87 +    int read;
   65.88 +    /** Flag indicating whether not to free when closed. */
   65.89 +    int nofree;
   65.90 +};
   65.91 +
   65.92 +
   65.93 +/** IOStream version of stdin. */
   65.94 +extern IOStream *iostdin;
   65.95 +
   65.96 +/** IOStream version of stdout, */
   65.97 +extern IOStream *iostdout;
   65.98 +
   65.99 +/** IOStream version of stderr. */
  65.100 +extern IOStream *iostderr;
  65.101 +
  65.102 +extern int IOStream_print(IOStream *io, const char *format, ...);
  65.103 +extern int IOStream_vprint(IOStream *io, const char *format, va_list args);
  65.104 +
  65.105 +/** Read from a stream.
  65.106 + *
  65.107 + * @param stream input
  65.108 + * @param buf where to put input
  65.109 + * @param n number of bytes to read
  65.110 + * @return if ok, number of bytes read, otherwise negative error code
  65.111 + */
  65.112 +static inline int IOStream_read(IOStream *stream, void *buf, size_t n){
  65.113 +    int result;
  65.114 +    if(stream->closed){
  65.115 +        result = -EIO;
  65.116 +        goto exit;
  65.117 +    }
  65.118 +    if(!stream->methods || !stream->methods->read){
  65.119 +        result = -EINVAL;
  65.120 +        goto exit;
  65.121 +    }
  65.122 +    result = (stream->methods->read)(stream, buf, n);
  65.123 +    if(result > 0){
  65.124 +        stream->read += result;
  65.125 +    }
  65.126 +  exit:
  65.127 +    return result;
  65.128 +}
  65.129 +
  65.130 +/** Write to a stream.
  65.131 + *
  65.132 + * @param stream input
  65.133 + * @param buf where to put input
  65.134 + * @param n number of bytes to write
  65.135 + * @return if ok, number of bytes written, otherwise negative error code
  65.136 + */
  65.137 +static inline int IOStream_write(IOStream *stream, const void *buf, size_t n){
  65.138 +    int result;
  65.139 +    if(stream->closed){
  65.140 +        result = -EIO;
  65.141 +        goto exit;
  65.142 +    }
  65.143 +    if(!stream->methods || !stream->methods->write){
  65.144 +        result = -EINVAL;
  65.145 +        goto exit;
  65.146 +    }
  65.147 +    result = (stream->methods->write)(stream, buf, n);
  65.148 +    if(result > 0){
  65.149 +        stream->written += result;
  65.150 +    }
  65.151 +  exit:
  65.152 +    return result;
  65.153 +}
  65.154 +
  65.155 +/** Flush the stream.
  65.156 + *
  65.157 + * @param stream stream
  65.158 + * @return 0 on success, negative error code otherwise
  65.159 + */
  65.160 +static inline int IOStream_flush(IOStream *stream){
  65.161 +    int result = 0;
  65.162 +    if(stream->closed){
  65.163 +        result = -EIO;
  65.164 +    } else if(stream->methods->flush){
  65.165 +        result = (stream->methods->flush)(stream);
  65.166 +    }
  65.167 +    return result;
  65.168 +}
  65.169 +
  65.170 +/** Check whether the stream has an error.
  65.171 + *
  65.172 + * @param stream to check
  65.173 + * @return 1 for error, 0 otherwise
  65.174 + */
  65.175 +static inline int IOStream_error(IOStream *stream){
  65.176 +    int err = 0;
  65.177 +    if(stream->methods && stream->methods->error){
  65.178 +       err = (stream->methods->error)(stream);
  65.179 +    }
  65.180 +    return err;
  65.181 +}
  65.182 +
  65.183 +/** Close the stream.
  65.184 + *
  65.185 + * @param stream to close
  65.186 + * @return 0 on success, negative error code otherwise
  65.187 + */
  65.188 +static inline int IOStream_close(IOStream *stream){
  65.189 +    int err = 0;
  65.190 +    if(!stream || stream->closed){
  65.191 +        err = -EIO;
  65.192 +        goto exit;
  65.193 +    }
  65.194 +    if(stream->methods && stream->methods->close){
  65.195 +        err = (stream->methods->close)(stream);
  65.196 +        stream->closed = 1;
  65.197 +    }
  65.198 +    if(stream->nofree) goto exit;
  65.199 +    if(stream->methods && stream->methods->free){
  65.200 +        (stream->methods->free)(stream);
  65.201 +    }
  65.202 +    *stream = (IOStream){};
  65.203 +    deallocate(stream);
  65.204 +  exit:
  65.205 +    return err;
  65.206 +}
  65.207 +
  65.208 +/** Test if the stream has been closed.
  65.209 + *
  65.210 + * @param stream to check
  65.211 + * @return 1 if closed, 0 otherwise
  65.212 + */
  65.213 +static inline int IOStream_is_closed(IOStream *stream){
  65.214 +    return stream->closed;
  65.215 +}
  65.216 +
  65.217 +/** Print a character to a stream, like fputc().
  65.218 + *
  65.219 + * @param stream to print to
  65.220 + * @param c character to print
  65.221 + * @return result code from the print
  65.222 + */
  65.223 +static inline int IOStream_putc(IOStream *stream, int c){
  65.224 +    int err;
  65.225 +    unsigned char b = (unsigned char)c;
  65.226 +    err = IOStream_write(stream, &b, 1);
  65.227 +    if(err < 1){
  65.228 +        err = IOSTREAM_EOF;
  65.229 +    } else {
  65.230 +        err = b;
  65.231 +    }
  65.232 +    return err;
  65.233 +}
  65.234 +
  65.235 +/** Read from a stream, like fgetc().
  65.236 + *
  65.237 + * @param stream to read from
  65.238 + * @return IOSTREAM_EOF on error, character read otherwise
  65.239 + */
  65.240 +static inline int IOStream_getc(IOStream *stream){
  65.241 +    int err, rc;
  65.242 +    unsigned char b;
  65.243 +
  65.244 +    err = IOStream_read(stream, &b, 1);
  65.245 +    if(err < 1){
  65.246 +        rc = IOSTREAM_EOF;
  65.247 +    } else {
  65.248 +        rc = b;
  65.249 +    }
  65.250 +    return rc;
  65.251 +}
  65.252 +
  65.253 +/** Get number of bytes read.
  65.254 + *
  65.255 + * @param stream to get from
  65.256 + * @return number of bytes read
  65.257 + */
  65.258 +static inline int IOStream_get_read(IOStream *stream){
  65.259 +    return stream->read;
  65.260 +}
  65.261 +
  65.262 +/** Get number of bytes written.
  65.263 + *
  65.264 + * @param stream to get from
  65.265 + * @return number of bytes written
  65.266 + */
  65.267 +static inline int IOStream_get_written(IOStream *stream){
  65.268 +    return stream->written;
  65.269 +}
  65.270 +
  65.271 +
  65.272 +#endif /* ! _XUTIL_IOSTREAM_H_ */
    66.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    66.2 +++ b/tools/vnet/libxutil/kernel_stream.c	Tue May 24 21:17:29 2005 +0000
    66.3 @@ -0,0 +1,178 @@
    66.4 +/*
    66.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    66.6 + *
    66.7 + * This library is free software; you can redistribute it and/or modify
    66.8 + * it under the terms of the GNU Lesser General Public License as published by
    66.9 + * the Free Software Foundation; either version 2.1 of the License, or
   66.10 + * (at your option) any later version.
   66.11 + *
   66.12 + * This library is distributed in the hope that it will be useful,
   66.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   66.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   66.15 + * GNU Lesser General Public License for more details.
   66.16 + *
   66.17 + * You should have received a copy of the GNU Lesser General Public License
   66.18 + * along with this library; if not, write to the Free Software
   66.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   66.20 + */
   66.21 +
   66.22 +/** @file
   66.23 + * An IOStream implementation using printk() for output.
   66.24 + * Input is not implemented.
   66.25 + */
   66.26 +#ifdef __KERNEL__
   66.27 +
   66.28 +#include <linux/config.h>
   66.29 +#include <linux/module.h>
   66.30 +#include <linux/kernel.h>
   66.31 +#include <linux/types.h>
   66.32 +#include <linux/errno.h>
   66.33 +#include <linux/slab.h>
   66.34 +#include <linux/spinlock.h>
   66.35 +
   66.36 +#include "kernel_stream.h"
   66.37 +#include "allocate.h"
   66.38 +
   66.39 +/** Number of characters in the output buffer.
   66.40 + * The kernel uses 1024 for printk, so that should suffice.
   66.41 + */
   66.42 +#define BUF_N 1024
   66.43 +
   66.44 +/** State for a kernel stream. */
   66.45 +typedef struct KernelData {
   66.46 +    /** Stream lock. We need a lock to serialize access to the stream. */
   66.47 +    spinlock_t lock;
   66.48 +    /** Saved flags for locking. */
   66.49 +    unsigned long flags;
   66.50 +    /** Size of the output buffer. */
   66.51 +    int buf_n;
   66.52 +    /** Output buffer. */
   66.53 +    char buf[BUF_N];
   66.54 +} KernelData;
   66.55 +
   66.56 +static int kernel_write(IOStream *s, const void *msg, size_t n);
   66.57 +static void kernel_free(IOStream *s);
   66.58 +static void kernel_stream_lock(IOStream *s);
   66.59 +static void kernel_stream_unlock(IOStream *s);
   66.60 +
   66.61 +/** Methods for a kernel stream. Output only. */
   66.62 +static const IOMethods kernel_methods = {
   66.63 +    write:  kernel_write,
   66.64 +    free:   kernel_free,
   66.65 +    lock:   kernel_stream_lock,
   66.66 +    unlock: kernel_stream_unlock,
   66.67 +};
   66.68 +
   66.69 +/** Shared state for kernel streams.
   66.70 + * All implementations write using printk, so we can use
   66.71 + * shared state and avoid allocating it.
   66.72 + */
   66.73 +static const KernelData kernel_data = {
   66.74 +    lock:  SPIN_LOCK_UNLOCKED,
   66.75 +    flags: 0,
   66.76 +    buf_n: BUF_N,
   66.77 +};
   66.78 +
   66.79 +/** Stream for kernel printk. */
   66.80 +static IOStream iokernel = {
   66.81 +    methods: &kernel_methods,
   66.82 +    data:    &kernel_data,
   66.83 +    nofree:  1,
   66.84 +};
   66.85 +
   66.86 +/** Stream for kernel printk. */
   66.87 +IOStream *iostdout = &iokernel;
   66.88 +
   66.89 +/** Stream for kernel printk. */
   66.90 +IOStream *iostdin = &iokernel;
   66.91 +
   66.92 +/** Stream for kernel printk. */
   66.93 +IOStream *iostderr = &iokernel;
   66.94 +
   66.95 +/** Get an output-only stream implementation using
   66.96 + * printk(). The stream uses static storage, and must not be freed.
   66.97 + *
   66.98 + * @return kernel stream
   66.99 + */
  66.100 +IOStream get_stream_kernel(void){
  66.101 +    return iokernel;
  66.102 +}
  66.103 +
  66.104 +/** Obtain the lock on the stream state.
  66.105 + *
  66.106 + * @param kdata stream state
  66.107 + */
  66.108 +static inline void KernelData_lock(KernelData *kdata){
  66.109 +    spin_lock_irqsave(&kdata->lock, kdata->flags);
  66.110 +}
  66.111 +
  66.112 +/** Release the lock on the stream state.
  66.113 + *
  66.114 + * @param kdata stream state
  66.115 + */
  66.116 +static inline void KernelData_unlock(KernelData *kdata){
  66.117 +    spin_unlock_irqrestore(&kdata->lock, kdata->flags);
  66.118 +}
  66.119 +
  66.120 +/** Get the stream state.
  66.121 + *
  66.122 + * @param s kernel stream
  66.123 + * @return stream state
  66.124 + */
  66.125 +static inline KernelData *get_kernel_data(IOStream *s){
  66.126 +    return (KernelData*)s->data;
  66.127 +}
  66.128 +
  66.129 +/** Obtain the lock on the stream state.
  66.130 + *
  66.131 + * @param s stream
  66.132 + */
  66.133 +void kernel_stream_lock(IOStream *s){
  66.134 +    KernelData_lock(get_kernel_data(s));
  66.135 +}
  66.136 +
  66.137 +/** Release the lock on the stream state.
  66.138 + *
  66.139 + * @param s stream
  66.140 + */
  66.141 +void kernel_stream_unlock(IOStream *s){
  66.142 +    KernelData_unlock(get_kernel_data(s));
  66.143 +}
  66.144 +
  66.145 +/** Write to a kernel stream.
  66.146 + *
  66.147 + * @param stream kernel stream
  66.148 + * @param format print format
  66.149 + * @param args print arguments
  66.150 + * @return result of the print
  66.151 + */
  66.152 +static int kernel_write(IOStream *stream, const void *buf, size_t n){
  66.153 +    KernelData *kdata = get_kernel_data(stream);
  66.154 +    int k;
  66.155 +    k = kdata->buf_n - 1;
  66.156 +    if(n < k) k = n;
  66.157 +    memcpy(kdata->buf, buf, k);
  66.158 +    kdata->buf[k] = '\0';
  66.159 +    printk(kdata->buf);
  66.160 +    return k;
  66.161 +}
  66.162 +
  66.163 +/** Free a kernel stream.
  66.164 + * Frees the internal state of the stream.
  66.165 + * Do not call this unless the stream was dynamically allocated.
  66.166 + * Do not call this on a stream returned from get_stream_kernel().
  66.167 + *
  66.168 + * @param io stream to free
  66.169 + */
  66.170 +static void kernel_free(IOStream *io){
  66.171 +    KernelData *kdata;
  66.172 +    if(io == &iokernel) return;
  66.173 +    kdata = get_kernel_data(io);
  66.174 +    memset(kdata, 0, sizeof(*kdata));
  66.175 +    deallocate(kdata);
  66.176 +}
  66.177 +#endif /* __KERNEL__ */
  66.178 +
  66.179 +
  66.180 +
  66.181 +
    67.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    67.2 +++ b/tools/vnet/libxutil/kernel_stream.h	Tue May 24 21:17:29 2005 +0000
    67.3 @@ -0,0 +1,29 @@
    67.4 +/*
    67.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    67.6 + *
    67.7 + * This library is free software; you can redistribute it and/or modify
    67.8 + * it under the terms of the GNU Lesser General Public License as published by
    67.9 + * the Free Software Foundation; either version 2.1 of the License, or
   67.10 + * (at your option) any later version.
   67.11 + *
   67.12 + * This library is distributed in the hope that it will be useful,
   67.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
   67.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   67.15 + * GNU Lesser General Public License for more details.
   67.16 + *
   67.17 + * You should have received a copy of the GNU Lesser General Public License
   67.18 + * along with this library; if not, write to the Free Software
   67.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   67.20 + */
   67.21 +
   67.22 +#ifndef _XUTIL_KERNEL_STREAM_H_
   67.23 +#define _XUTIL_KERNEL_STREAM_H_
   67.24 +
   67.25 +#ifdef __KERNEL__
   67.26 +#include "iostream.h"
   67.27 +
   67.28 +extern IOStream get_stream_kernel(void);
   67.29 +#define get_stream_stdout get_stream_kernel
   67.30 +
   67.31 +#endif /* __KERNEL__ */
   67.32 +#endif /* !_XUTIL_KERNEL_STREAM_H_ */
    68.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    68.2 +++ b/tools/vnet/libxutil/lexis.c	Tue May 24 21:17:29 2005 +0000
    68.3 @@ -0,0 +1,94 @@
    68.4 +/*
    68.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    68.6 + *
    68.7 + * This library is free software; you can redistribute it and/or modify
    68.8 + * it under the terms of the GNU Lesser General Public License as
    68.9 + * published by the Free Software Foundation; either version 2.1 of the
   68.10 + * License, or  (at your option) any later version. This library is 
   68.11 + * distributed in the  hope that it will be useful, but WITHOUT ANY
   68.12 + * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   68.13 + * FITNESS FOR A PARTICULAR PURPOSE.
   68.14 + * See the GNU Lesser General Public License for more details.
   68.15 + *
   68.16 + * You should have received a copy of the GNU Lesser General Public License
   68.17 + * along with this library; if not, write to the Free Software Foundation,
   68.18 + * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   68.19 + */
   68.20 +
   68.21 +/** @file
   68.22 + * Lexical analysis.
   68.23 + */
   68.24 +
   68.25 +#include "sys_string.h"
   68.26 +#include "lexis.h"
   68.27 +#include <errno.h>
   68.28 +
   68.29 +/** Check if a value lies in a (closed) range.
   68.30 + *
   68.31 + * @param x value to test
   68.32 + * @param lo low end of the range
   68.33 + * @param hi high end of the range
   68.34 + * @return 1 if x is in the interval [lo, hi], 0 otherwise
   68.35 + */
   68.36 +inline static int in_range(int x, int lo, int hi){
   68.37 +    return (lo <= x) && (x <= hi);
   68.38 +}
   68.39 +
   68.40 +/** Determine if a string is an (unsigned) decimal number.
   68.41 + * 
   68.42 + * @param s pointer to characters to test
   68.43 + * @param n length of string
   68.44 + * @return 1 if s is a decimal number, 0 otherwise.
   68.45 + */
   68.46 +int is_decimal_number(const char *s, int n){
   68.47 +    int i;
   68.48 +    if(n <= 0)return 0;
   68.49 +    for(i = 0; i < n; i++){
   68.50 +        if(!in_decimal_digit_class(s[i])) return 0;
   68.51 +    }
   68.52 +    return 1;
   68.53 +}
   68.54 +
   68.55 +/** Determine if a string is a hex number.
   68.56 + * Hex numbers are 0, or start with 0x or 0X followed
   68.57 + * by a non-zero number of hex digits (0-9,a-f,A-F).
   68.58 + * 
   68.59 + * @param s pointer to characters to test
   68.60 + * @param n length of string
   68.61 + * @return 1 if s is a hex number, 0 otherwise.
   68.62 + */
   68.63 +int is_hex_number(const char *s, int n){
   68.64 +    int i;
   68.65 +    if(n <= 0) return 0;
   68.66 +    if(n == 1){
   68.67 +        return s[0]=='0';
   68.68 +    }
   68.69 +    if(n <= 3) return 0;
   68.70 +    if(s[0] != '0' || (s[1] != 'x' && s[1] != 'X')) return 0;
   68.71 +    for(i = 2; i < n; i++){
   68.72 +        if(!in_hex_digit_class(s[i])) return 0;
   68.73 +    }
   68.74 +    return 1;
   68.75 +}
   68.76 +
   68.77 +/** Test if a string matches a keyword.
   68.78 + * The comparison is case-insensitive.
   68.79 + * The comparison fails if either argument is null.
   68.80 + *
   68.81 + * @param s string
   68.82 + * @param k keyword
   68.83 + * @return 1 if they match, 0 otherwise
   68.84 + */
   68.85 +int is_keyword(const char *s, const char *k){
   68.86 +  return s && k && !strcasecmp(s, k);
   68.87 +}
   68.88 +
   68.89 +/** Test if a string matches a character.
   68.90 + *
   68.91 + * @param s string
   68.92 + * @param c character (non-null)
   68.93 + * @return 1 if s contains exactly c, 0 otherwise
   68.94 + */
   68.95 +int is_keychar(const char *s, char c){
   68.96 +  return c && (s[0] == c) && !s[1];
   68.97 +}
    69.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
    69.2 +++ b/tools/vnet/libxutil/lexis.h	Tue May 24 21:17:29 2005 +0000
    69.3 @@ -0,0 +1,128 @@
    69.4 +/*
    69.5 + * Copyright (C) 2001 - 2004 Mike Wray <mike.wray@hp.com>
    69.6 + *
    69.7 + * This library is free software; you can redistribute it and/or modify
    69.8 + * it under the terms of the GNU Lesser General Public License as
    69.9 + * published by the Free Software Foundation; either version 2.1 of the
   69.10 + * License, or  (at your option) any later version. This library is 
   69.11 + * distributed in the  hope that it will be useful, but WITHOUT ANY
   69.12 + * WARRANTY; without even the implied warranty of MERCHANTABILITY or
   69.13 + * FITNESS FOR A PARTICULAR PURPOSE.
   69.14 + * See the GNU Lesser General Public License for more details.
   69.15 + *
   69.16 + * You should have received a copy of the GNU Lesser General Public License
   69.17 + * along with this library; if not, write to the Free Software Foundation,
   69.18 + * Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
   69.19 + */
   69.20 +
   69.21 +#ifndef _XUTIL_LEXIS_H_
   69.22 +#define _XUTIL_LEXIS_H_
   69.23 +
   69.24 +#include "sys_string.h"
   69.25 +
   69.26 +#ifdef __KERNEL__
   69.27