]> sourceware.org Git - systemtap.git/commitdiff
rebased unwind_branch on top of current master
authorFrank Ch. Eigler <fche@elastic.org>
Tue, 25 Mar 2008 15:32:58 +0000 (11:32 -0400)
committerFrank Ch. Eigler <fche@elastic.org>
Tue, 25 Mar 2008 15:32:58 +0000 (11:32 -0400)
63 files changed:
.gitignore
ChangeLog
Makefile.am
Makefile.in
doc/ChangeLog
doc/langref.tex
runtime/.gitignore [new file with mode: 0644]
runtime/Makefile [deleted file]
runtime/bench2/Makefile [deleted file]
runtime/debug.h
runtime/lket/b2a/.cvsignore [deleted file]
runtime/lket/b2a/Makefile.am [deleted file]
runtime/lket/b2a/Makefile.in [deleted file]
runtime/lket/b2a/lket_b2a.c [deleted file]
runtime/lket/b2a/lket_b2a.h [deleted file]
runtime/map.c
runtime/probes.c
runtime/probes/bench/Makefile [deleted file]
runtime/runtime.h
runtime/stack-x86_64.c
runtime/stack.c
runtime/staprun/mainloop.c
runtime/staprun/staprun.c
runtime/staprun/staprun.h
runtime/staprun/staprun_funcs.c
runtime/staprun/unwind_data.c [new file with mode: 0644]
runtime/sym.c
runtime/sym.h
runtime/tests/Makefile [deleted file]
runtime/tests/agg/Makefile [deleted file]
runtime/tests/maps/Makefile [deleted file]
runtime/tests/math/Makefile [deleted file]
runtime/tests/pmaps/Makefile [deleted file]
runtime/tests/string/Makefile [deleted file]
runtime/transport/control.c
runtime/transport/procfs.c
runtime/transport/symbols.c
runtime/transport/transport.c
runtime/transport/transport.h
runtime/transport/transport_msgs.h
runtime/unwind.c [new file with mode: 0644]
runtime/uprobes/Makefile [deleted file]
safety/README [deleted file]
safety/data/opcodes-i686 [deleted file]
safety/data/opcodes-ia64 [deleted file]
safety/data/opcodes-x86_64 [deleted file]
safety/data/references [deleted file]
safety/safety.py [deleted file]
stap.1.in
stapfuncs.5.in
tapset/ChangeLog
tapset/conversions.stp
testsuite/ChangeLog
testsuite/buildok/conversions-embedded.stp
testsuite/buildok/conversions.stp
testsuite/lib/stap_run.exp
testsuite/lib/systemtap.exp
testsuite/systemtap.stress/conversions.stp
translate.cxx
vim/filetype.vim [deleted file]
vim/ftplugin/stap.vim [deleted file]
vim/indent/stap.vim [deleted file]
vim/syntax/stap.vim [deleted file]

index 69bd5e97941fe7e770ed57cbf9282c7b973734b1..1c02452bc4cef469d4ff0742e076ac364ee55721 100644 (file)
@@ -18,3 +18,9 @@ systemtap.spec
 testresults
 stapio
 stap_merge
+CVS
+.checkstyle
+.cproject
+.metadata
+.project
+.settings
index 046804c76ebba607517c781d3e2aa404c6f96703..c7bb82c338cb28b29dffa605a47e352b46aa4b0d 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,19 +1,3 @@
-2008-03-25  Frank Ch. Eigler  <fche@elastic.org>
-
-       * stap.1.in: Clarify utility of epilogue type probe aliases.
-
-2008-03-21  Eugene Teo  <eugeneteo@kernel.sg>
-
-       PR 5528
-       * tapset/conversions.stp (user_string_n, user_string_n2,
-       user_string_n_warn, user_string_n_quoted, user_short, user_short_warn,
-       user_int, user_int_warn, user_long, user_long_warn, user_char,
-       user_char_warn): New user_* functions.
-       * stapfuncs.5.in: Documented the new functions.
-       * testsuite/systemtap.stress/conversions.stp: Test new functions.
-       * testsuite/buildok/conversions.stp: Test new functions.
-       * testsuite/buildok/conversions-embedded.stp: Test new functions.
-
 2008-03-20  Frank Ch. Eigler  <fche@elastic.org>
 
        PR 5975.
index 1fc4dbec913771044480f75af7163f0a852300fe..a53fdba0f79bf333e6667357241ce7eabfd96f8e 100644 (file)
@@ -53,19 +53,19 @@ endif
 
 staprun_SOURCES = runtime/staprun/staprun.c runtime/staprun/staprun_funcs.c\
        runtime/staprun/ctl.c runtime/staprun/common.c \
-       runtime/staprun/cap.c runtime/staprun/symbols.c
+       runtime/staprun/cap.c
 
 staprun_CPPFLAGS = $(AM_CPPFLAGS)
-staprun_CFLAGS = @PROCFLAGS@ $(AM_CFLAGS)
-staprun_LDADD = @PROCFLAGS@ @cap_LIBS@ -lpthread
+staprun_CFLAGS = @PROCFLAGS@ $(AM_CFLAGS) -DSINGLE_THREADED
+staprun_LDADD = @PROCFLAGS@ @cap_LIBS@
 
 stapio_SOURCES = runtime/staprun/stapio.c \
        runtime/staprun/mainloop.c runtime/staprun/common.c \
-       runtime/staprun/ctl.c \
+       runtime/staprun/ctl.c runtime/staprun/unwind_data.c \
        runtime/staprun/relay.c runtime/staprun/relay_old.c 
 
 stapio_CFLAGS = @PROCFLAGS@ $(AM_CFLAGS)
-stapio_LDADD = @PROCFLAGS@ -lpthread
+stapio_LDADD = @PROCFLAGS@ -ldw -lpthread
 
 install-exec-hook:
        if [ `id -u` -eq 0 ]; then chmod 04111 "$(DESTDIR)$(bindir)/staprun"; fi
@@ -127,8 +127,9 @@ dist-hook: dist-add-samples
        find $(distdir) -name 'stap' -o -name '*.log' -o -name '*.sum' -o -name 'site.exp' | xargs rm -rf
 
 install-data-local:
-#      mkdir -p $(DESTDIR)$(pkgdatadir)/runtime/transport $(DESTDIR)$(pkgdatadir)/tapset
        (cd $(srcdir)/runtime; for f in *.[ch]; do $(INSTALL_DATA) -D $$f $(DESTDIR)$(pkgdatadir)/runtime/$$f; done)
+       (cd $(srcdir)/runtime/unwind; find . \( -name '*.[ch]' \) -print \
+               | while read f; do $(INSTALL_DATA) -D $$f $(DESTDIR)$(pkgdatadir)/runtime/unwind/$$f; done)
        (cd $(srcdir)/runtime/transport; for f in *.[ch]; \
                do $(INSTALL_DATA) -D $$f $(DESTDIR)$(pkgdatadir)/runtime/transport/$$f; done)
        (cd $(srcdir)/runtime/uprobes; for f in Makefile *.[ch]; \
index e82d66a3c801ea78205046741b3f906b699c4f52..9fc103d31ba40af586ad8d96202c5d8df7dccfdf 100644 (file)
@@ -102,15 +102,15 @@ stap_LINK = $(CXXLD) $(stap_CXXFLAGS) $(CXXFLAGS) $(stap_LDFLAGS) \
        $(LDFLAGS) -o $@
 am_stapio_OBJECTS = stapio-stapio.$(OBJEXT) stapio-mainloop.$(OBJEXT) \
        stapio-common.$(OBJEXT) stapio-ctl.$(OBJEXT) \
-       stapio-relay.$(OBJEXT) stapio-relay_old.$(OBJEXT)
+       stapio-unwind_data.$(OBJEXT) stapio-relay.$(OBJEXT) \
+       stapio-relay_old.$(OBJEXT)
 stapio_OBJECTS = $(am_stapio_OBJECTS)
 stapio_DEPENDENCIES =
 stapio_LINK = $(CCLD) $(stapio_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \
        $(LDFLAGS) -o $@
 am_staprun_OBJECTS = staprun-staprun.$(OBJEXT) \
        staprun-staprun_funcs.$(OBJEXT) staprun-ctl.$(OBJEXT) \
-       staprun-common.$(OBJEXT) staprun-cap.$(OBJEXT) \
-       staprun-symbols.$(OBJEXT)
+       staprun-common.$(OBJEXT) staprun-cap.$(OBJEXT)
 staprun_OBJECTS = $(am_staprun_OBJECTS)
 staprun_DEPENDENCIES =
 staprun_LINK = $(CCLD) $(staprun_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \
@@ -286,18 +286,18 @@ CLEANFILES = $(am__append_3) $(pkglibexec_PROGRAMS)
 @BUILD_ELFUTILS_TRUE@stap_DEPENDENCIES = lib-elfutils/libdw.so
 staprun_SOURCES = runtime/staprun/staprun.c runtime/staprun/staprun_funcs.c\
        runtime/staprun/ctl.c runtime/staprun/common.c \
-       runtime/staprun/cap.c runtime/staprun/symbols.c
+       runtime/staprun/cap.c
 
 staprun_CPPFLAGS = $(AM_CPPFLAGS)
-staprun_CFLAGS = @PROCFLAGS@ $(AM_CFLAGS)
-staprun_LDADD = @PROCFLAGS@ @cap_LIBS@ -lpthread
+staprun_CFLAGS = @PROCFLAGS@ $(AM_CFLAGS) -DSINGLE_THREADED
+staprun_LDADD = @PROCFLAGS@ @cap_LIBS@
 stapio_SOURCES = runtime/staprun/stapio.c \
        runtime/staprun/mainloop.c runtime/staprun/common.c \
-       runtime/staprun/ctl.c \
+       runtime/staprun/ctl.c runtime/staprun/unwind_data.c \
        runtime/staprun/relay.c runtime/staprun/relay_old.c 
 
 stapio_CFLAGS = @PROCFLAGS@ $(AM_CFLAGS)
-stapio_LDADD = @PROCFLAGS@ -lpthread
+stapio_LDADD = @PROCFLAGS@ -ldw -lpthread
 loc2c_test_SOURCES = loc2c-test.c loc2c.c
 loc2c_test_CPPFLAGS = $(stap_CPPFLAGS)
 loc2c_test_LDFLAGS = $(stap_LDFLAGS)
@@ -505,12 +505,12 @@ distclean-compile:
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/stapio-relay.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/stapio-relay_old.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/stapio-stapio.Po@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/stapio-unwind_data.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/staprun-cap.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/staprun-common.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/staprun-ctl.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/staprun-staprun.Po@am__quote@
 @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/staprun-staprun_funcs.Po@am__quote@
-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/staprun-symbols.Po@am__quote@
 
 .c.o:
 @am__fastdepCC_TRUE@   $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $<
@@ -638,6 +638,20 @@ stapio-ctl.obj: runtime/staprun/ctl.c
 @AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
 @am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(stapio_CFLAGS) $(CFLAGS) -c -o stapio-ctl.obj `if test -f 'runtime/staprun/ctl.c'; then $(CYGPATH_W) 'runtime/staprun/ctl.c'; else $(CYGPATH_W) '$(srcdir)/runtime/staprun/ctl.c'; fi`
 
+stapio-unwind_data.o: runtime/staprun/unwind_data.c
+@am__fastdepCC_TRUE@   $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(stapio_CFLAGS) $(CFLAGS) -MT stapio-unwind_data.o -MD -MP -MF $(DEPDIR)/stapio-unwind_data.Tpo -c -o stapio-unwind_data.o `test -f 'runtime/staprun/unwind_data.c' || echo '$(srcdir)/'`runtime/staprun/unwind_data.c
+@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/stapio-unwind_data.Tpo $(DEPDIR)/stapio-unwind_data.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='runtime/staprun/unwind_data.c' object='stapio-unwind_data.o' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(stapio_CFLAGS) $(CFLAGS) -c -o stapio-unwind_data.o `test -f 'runtime/staprun/unwind_data.c' || echo '$(srcdir)/'`runtime/staprun/unwind_data.c
+
+stapio-unwind_data.obj: runtime/staprun/unwind_data.c
+@am__fastdepCC_TRUE@   $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(stapio_CFLAGS) $(CFLAGS) -MT stapio-unwind_data.obj -MD -MP -MF $(DEPDIR)/stapio-unwind_data.Tpo -c -o stapio-unwind_data.obj `if test -f 'runtime/staprun/unwind_data.c'; then $(CYGPATH_W) 'runtime/staprun/unwind_data.c'; else $(CYGPATH_W) '$(srcdir)/runtime/staprun/unwind_data.c'; fi`
+@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/stapio-unwind_data.Tpo $(DEPDIR)/stapio-unwind_data.Po
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='runtime/staprun/unwind_data.c' object='stapio-unwind_data.obj' libtool=no @AMDEPBACKSLASH@
+@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
+@am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(stapio_CFLAGS) $(CFLAGS) -c -o stapio-unwind_data.obj `if test -f 'runtime/staprun/unwind_data.c'; then $(CYGPATH_W) 'runtime/staprun/unwind_data.c'; else $(CYGPATH_W) '$(srcdir)/runtime/staprun/unwind_data.c'; fi`
+
 stapio-relay.o: runtime/staprun/relay.c
 @am__fastdepCC_TRUE@   $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(stapio_CFLAGS) $(CFLAGS) -MT stapio-relay.o -MD -MP -MF $(DEPDIR)/stapio-relay.Tpo -c -o stapio-relay.o `test -f 'runtime/staprun/relay.c' || echo '$(srcdir)/'`runtime/staprun/relay.c
 @am__fastdepCC_TRUE@   mv -f $(DEPDIR)/stapio-relay.Tpo $(DEPDIR)/stapio-relay.Po
@@ -736,20 +750,6 @@ staprun-cap.obj: runtime/staprun/cap.c
 @AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
 @am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(staprun_CPPFLAGS) $(CPPFLAGS) $(staprun_CFLAGS) $(CFLAGS) -c -o staprun-cap.obj `if test -f 'runtime/staprun/cap.c'; then $(CYGPATH_W) 'runtime/staprun/cap.c'; else $(CYGPATH_W) '$(srcdir)/runtime/staprun/cap.c'; fi`
 
-staprun-symbols.o: runtime/staprun/symbols.c
-@am__fastdepCC_TRUE@   $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(staprun_CPPFLAGS) $(CPPFLAGS) $(staprun_CFLAGS) $(CFLAGS) -MT staprun-symbols.o -MD -MP -MF $(DEPDIR)/staprun-symbols.Tpo -c -o staprun-symbols.o `test -f 'runtime/staprun/symbols.c' || echo '$(srcdir)/'`runtime/staprun/symbols.c
-@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/staprun-symbols.Tpo $(DEPDIR)/staprun-symbols.Po
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='runtime/staprun/symbols.c' object='staprun-symbols.o' libtool=no @AMDEPBACKSLASH@
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
-@am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(staprun_CPPFLAGS) $(CPPFLAGS) $(staprun_CFLAGS) $(CFLAGS) -c -o staprun-symbols.o `test -f 'runtime/staprun/symbols.c' || echo '$(srcdir)/'`runtime/staprun/symbols.c
-
-staprun-symbols.obj: runtime/staprun/symbols.c
-@am__fastdepCC_TRUE@   $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(staprun_CPPFLAGS) $(CPPFLAGS) $(staprun_CFLAGS) $(CFLAGS) -MT staprun-symbols.obj -MD -MP -MF $(DEPDIR)/staprun-symbols.Tpo -c -o staprun-symbols.obj `if test -f 'runtime/staprun/symbols.c'; then $(CYGPATH_W) 'runtime/staprun/symbols.c'; else $(CYGPATH_W) '$(srcdir)/runtime/staprun/symbols.c'; fi`
-@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/staprun-symbols.Tpo $(DEPDIR)/staprun-symbols.Po
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='runtime/staprun/symbols.c' object='staprun-symbols.obj' libtool=no @AMDEPBACKSLASH@
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
-@am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(staprun_CPPFLAGS) $(CPPFLAGS) $(staprun_CFLAGS) $(CFLAGS) -c -o staprun-symbols.obj `if test -f 'runtime/staprun/symbols.c'; then $(CYGPATH_W) 'runtime/staprun/symbols.c'; else $(CYGPATH_W) '$(srcdir)/runtime/staprun/symbols.c'; fi`
-
 .cxx.o:
 @am__fastdepCXX_TRUE@  $(CXXCOMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $<
 @am__fastdepCXX_TRUE@  mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po
@@ -1498,8 +1498,9 @@ dist-hook: dist-add-samples
        find $(distdir) -name 'stap' -o -name '*.log' -o -name '*.sum' -o -name 'site.exp' | xargs rm -rf
 
 install-data-local:
-#      mkdir -p $(DESTDIR)$(pkgdatadir)/runtime/transport $(DESTDIR)$(pkgdatadir)/tapset
        (cd $(srcdir)/runtime; for f in *.[ch]; do $(INSTALL_DATA) -D $$f $(DESTDIR)$(pkgdatadir)/runtime/$$f; done)
+       (cd $(srcdir)/runtime/unwind; find . \( -name '*.[ch]' \) -print \
+               | while read f; do $(INSTALL_DATA) -D $$f $(DESTDIR)$(pkgdatadir)/runtime/unwind/$$f; done)
        (cd $(srcdir)/runtime/transport; for f in *.[ch]; \
                do $(INSTALL_DATA) -D $$f $(DESTDIR)$(pkgdatadir)/runtime/transport/$$f; done)
        (cd $(srcdir)/runtime/uprobes; for f in Makefile *.[ch]; \
index e652078dfb55c67ed10512719a5ae3843fc5a840..902e1d1e0017ee1a7167d2eac77b9091e4d97ebe 100644 (file)
@@ -1,7 +1,3 @@
-2008-03-25  Frank Ch. Eigler  <fche@elastic.org>
-
-       * langref.tex: Clarify utility of epilogue-type probe aliases.
-
 2008-03-04  David Smith  <dsmith@redhat.com>
 
        * tutorial.tex: Made minor changes to remove warnings.
index 973769d46bdb7164a4958bd1d3436d921ff1b84f..5b91d01d0acd25df0333a3342fa213dc462f83d9 100644 (file)
@@ -230,7 +230,7 @@ This prints:
 \end{verbatim}
 \end{vindent}
 Any larger number input to the function may exceed the MAXACTION or MAXNESTING
-limits, which will be caught at run time and result in an error. For more
+limits, which will be caught by the parser and result in an error. For more
 about limits see Section~\ref{sub:SystemTap-safety}.
 \newpage{}
 \subsection{The stap command}
@@ -436,10 +436,8 @@ probe syscall.read = kernel.function("sys_read") {
 \index{epilogue-style aliases}
 \index{+=}
 The statement block that follows an alias definition is implicitly added
-as an epilogue to any probe that refers to the alias.  It is not useful
-to define new variable there (since no subsequent code will see it), but
-rather the code can take action based upon variables left set by the
-prologue or by the user code.  The following is an example:
+as an epilogue to any probe that refers to the alias. The following is an
+example:
 
 \begin{vindent}
 \begin{verbatim}
@@ -447,15 +445,15 @@ prologue or by the user code.  The following is an example:
 # epilogue.
 #
 probe syscall.read += kernel.function("sys_read") {
-    if (traceme) println ("tracing me")
+    fildes = $fd
 }
 \end{verbatim}
 \end{vindent}
 
 \subsubsection{Probe alias usage}
 
-A probe alias is used the same way as any built-in probe type, by
-naming it:
+Another probe definition may use a previously defined alias. The following
+is an example.
 
 \begin{vindent}
 \begin{verbatim}
@@ -1029,6 +1027,12 @@ type conversions between strings and numbers. Inconsistent type-related use
 of identifiers signals an error.
 
 
+\subsubsection{Numbers}
+\index{numbers}
+Numbers are 64-bit signed integers. The parser will also accept (and wrap
+around) values above positive $2^{63}$.
+
+
 \subsubsection{Literals}
 \index{literals}
 Literals are either strings or integers. Literals can be expressed as decimal,
@@ -1037,10 +1041,10 @@ octal, or hexadecimal, using C notation. Type suffixes (e.g., \emph{L} or
 
 
 \subsubsection{Integers\label{sub:Integers}}
-\index{integers} \index{numbers}
+\index{integers}
 Integers are decimal, hexadecimal, or octal, and use the same notation as
 in C. Integers are 64-bit signed quantities, although the parser also accepts
-(and wraps around) values above positive $2^{63}$ but below $2^{64}$.
+(and wraps around) values above positive $2^{63}$.
 
 
 \subsubsection{Strings\label{sub:Strings}}
diff --git a/runtime/.gitignore b/runtime/.gitignore
new file mode 100644 (file)
index 0000000..ceddd64
--- /dev/null
@@ -0,0 +1 @@
+!staprun
diff --git a/runtime/Makefile b/runtime/Makefile
deleted file mode 100644 (file)
index 22d25ff..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#
-# Makefile for SystemTap runtime and example probes
-#
-
-all:
-       make -w -C stpd
-       cd probes; ./build
-
-relayfs:
-       make -w -C relayfs
-
-clean:
-       make -w -C relayfs clean
-       make -w -C stpd clean
-       cd probes; ./build clean
diff --git a/runtime/bench2/Makefile b/runtime/bench2/Makefile
deleted file mode 100644 (file)
index ffb2991..0000000
+++ /dev/null
@@ -1,7 +0,0 @@
-all: itest
-
-itest: itest.c
-       gcc -D_GNU_SOURCE -Wall -Wextra -Wstrict-prototypes -Werror -O3 -o itest itest.c -lpthread
-
-clean:
-       /bin/rm -f itest
index 8f877edec5ff744153b3d6c585b4965f4501d804..9b2fe5c5c7b2540d8cd2582243c5bfff339fff53 100644 (file)
@@ -14,6 +14,8 @@
  * _dbug() writes to systemtap stderr.
  * errk() writes to the system log.
  */
+int _stp_transport_state = 0;
+
 #define _dbug(args...) _stp_dbug(__FUNCTION__, __LINE__, args)
 
 #define errk(args...) do {                                             \
                printk(args);                                           \
        } while (0)
 
-#ifdef DEBUG_TRANSPORT
-#undef DEBUG_TRANSPORT
-#define DEBUG_TRANSPORT 1
-#else
-#define DEBUG_TRANSPORT 0
-#endif
+/*
+ * To use these, enable them from the command line when compiling. 
+ * For example, "stap -DDEBUG_UNWIND=3"
+ * will activate dbug_unwind() and print messages with level <= 3.
+ */
 
-#ifdef DEBUG_UNWIND
-#undef DEBUG_UNWIND
-#define DEBUG_UNWIND 2
-#else
-#define DEBUG_UNWIND 0
-#endif
+/* Note: DEBUG_MEM is implemented in alloc.c */
 
-#ifdef DEBUG_SYMBOLS
-#undef DEBUG_SYMBOLS
-#define DEBUG_SYMBOLS 4
+#ifdef DEBUG_TRANS /* transport */
+/* Note: transport is debugged using printk() */
+#define dbug_trans(level, args...) do {                                        \
+               if ((level) <= DEBUG_TRANS) {                           \
+                       printk("%s:%d ",__FUNCTION__, __LINE__);        \
+                       printk(args);                                   \
+               }                                                       \
+       } while (0)
 #else
-#define DEBUG_SYMBOLS 0
+#define dbug_trans(level, args...) ;
 #endif
 
-#define DEBUG_TYPE (DEBUG_TRANSPORT|DEBUG_UNWIND|DEBUG_SYMBOLS)
-
-#if DEBUG_TYPE > 0
-
-#define dbug(type, args...) do {                                       \
-               if ((type) & DEBUG_TYPE)                                \
+#ifdef DEBUG_UNWIND /* stack unwinder */
+#define dbug_unwind(level, args...) do {                                       \
+               if ((level) <= DEBUG_UNWIND)                            \
                        _stp_dbug(__FUNCTION__, __LINE__, args);        \
        } while (0)
+#else
+#define dbug_unwind(level, args...) ;
+#endif
 
-#define kbug(type, args...) do {                                       \
-               if ((type) & DEBUG_TYPE) {                              \
-                       printk("%s:%d ",__FUNCTION__, __LINE__);        \
-                       printk(args);                                   \
-               }                                                       \
+#ifdef DEBUG_SYMBOLS
+#define dbug_sym(level, args...) do {                                  \
+               if ((level) <= DEBUG_SYMBOLS)                           \
+                       _stp_dbug(__FUNCTION__, __LINE__, args);        \
        } while (0)
-
 #else
-#define dbug(type, args...) ;
-#define kbug(type, args...) ;
-#endif /* DEBUG_TYPE > 0 */
+#define dbug_sym(level, args...) ;
+#endif
 
 #endif /* _STP_DEBUG_H_ */
diff --git a/runtime/lket/b2a/.cvsignore b/runtime/lket/b2a/.cvsignore
deleted file mode 100644 (file)
index e289e6f..0000000
+++ /dev/null
@@ -1 +0,0 @@
-Makefile lket-b2a .deps
diff --git a/runtime/lket/b2a/Makefile.am b/runtime/lket/b2a/Makefile.am
deleted file mode 100644 (file)
index 01472f6..0000000
+++ /dev/null
@@ -1,18 +0,0 @@
-bin_PROGRAMS = lket-b2a
-lket_b2a_SOURCES = lket_b2a.c
-lket_b2a_DEPENDENCIES = lket_b2a.h
-lket_b2a_LDFLAGS = `pkg-config --libs glib-2.0`
-lket_b2a_CFLAGS = -O2 -D_GNU_SOURCE -Wall `pkg-config --cflags glib-2.0`
-
-if HAS_MYSQL
-lket_b2a_CFLAGS += -DHAS_MYSQL
-if HAS_MYSQL_CONFIG
-lket_b2a_LDFLAGS += `mysql_config --libs`
-lket_b2a_CFLAGS += `mysql_config --cflags`
-else
-lket_b2a_CFLAGS += -I/usr/include/mysql -g -pipe -fsigned-char -D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -fno-strict-aliasing
-lket_b2a_LDFLAGS += -L/usr/lib/mysql -lmysqlclient -lz -lcrypt -lnsl -lm -L/usr/lib -lssl -lcrypto
-endif
-endif
-
-
diff --git a/runtime/lket/b2a/Makefile.in b/runtime/lket/b2a/Makefile.in
deleted file mode 100644 (file)
index e262682..0000000
+++ /dev/null
@@ -1,449 +0,0 @@
-# Makefile.in generated by automake 1.10 from Makefile.am.
-# @configure_input@
-
-# Copyright (C) 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002,
-# 2003, 2004, 2005, 2006  Free Software Foundation, Inc.
-# This Makefile.in is free software; the Free Software Foundation
-# gives unlimited permission to copy and/or distribute it,
-# with or without modifications, as long as this notice is preserved.
-
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY, to the extent permitted by law; without
-# even the implied warranty of MERCHANTABILITY or FITNESS FOR A
-# PARTICULAR PURPOSE.
-
-@SET_MAKE@
-
-VPATH = @srcdir@
-pkgdatadir = $(datadir)/@PACKAGE@
-pkglibdir = $(libdir)/@PACKAGE@
-pkgincludedir = $(includedir)/@PACKAGE@
-am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd
-install_sh_DATA = $(install_sh) -c -m 644
-install_sh_PROGRAM = $(install_sh) -c
-install_sh_SCRIPT = $(install_sh) -c
-INSTALL_HEADER = $(INSTALL_DATA)
-transform = $(program_transform_name)
-NORMAL_INSTALL = :
-PRE_INSTALL = :
-POST_INSTALL = :
-NORMAL_UNINSTALL = :
-PRE_UNINSTALL = :
-POST_UNINSTALL = :
-bin_PROGRAMS = lket-b2a$(EXEEXT)
-@HAS_MYSQL_TRUE@am__append_1 = -DHAS_MYSQL
-@HAS_MYSQL_CONFIG_TRUE@@HAS_MYSQL_TRUE@am__append_2 = `mysql_config --libs`
-@HAS_MYSQL_CONFIG_TRUE@@HAS_MYSQL_TRUE@am__append_3 = `mysql_config --cflags`
-@HAS_MYSQL_CONFIG_FALSE@@HAS_MYSQL_TRUE@am__append_4 = -I/usr/include/mysql -g -pipe -fsigned-char -D_GNU_SOURCE -D_FILE_OFFSET_BITS=64 -D_LARGEFILE_SOURCE -fno-strict-aliasing
-@HAS_MYSQL_CONFIG_FALSE@@HAS_MYSQL_TRUE@am__append_5 = -L/usr/lib/mysql -lmysqlclient -lz -lcrypt -lnsl -lm -L/usr/lib -lssl -lcrypto
-subdir = runtime/lket/b2a
-DIST_COMMON = $(srcdir)/Makefile.am $(srcdir)/Makefile.in
-ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
-am__aclocal_m4_deps = $(top_srcdir)/configure.ac
-am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \
-       $(ACLOCAL_M4)
-mkinstalldirs = $(install_sh) -d
-CONFIG_HEADER = $(top_builddir)/config.h
-CONFIG_CLEAN_FILES =
-am__installdirs = "$(DESTDIR)$(bindir)"
-binPROGRAMS_INSTALL = $(INSTALL_PROGRAM)
-PROGRAMS = $(bin_PROGRAMS)
-am_lket_b2a_OBJECTS = lket_b2a-lket_b2a.$(OBJEXT)
-lket_b2a_OBJECTS = $(am_lket_b2a_OBJECTS)
-lket_b2a_LDADD = $(LDADD)
-lket_b2a_LINK = $(CCLD) $(lket_b2a_CFLAGS) $(CFLAGS) \
-       $(lket_b2a_LDFLAGS) $(LDFLAGS) -o $@
-DEFAULT_INCLUDES = -I. -I$(top_builddir)@am__isrc@
-depcomp = $(SHELL) $(top_srcdir)/depcomp
-am__depfiles_maybe = depfiles
-COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \
-       $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)
-CCLD = $(CC)
-LINK = $(CCLD) $(AM_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@
-SOURCES = $(lket_b2a_SOURCES)
-DIST_SOURCES = $(lket_b2a_SOURCES)
-ETAGS = etags
-CTAGS = ctags
-DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)
-ACLOCAL = @ACLOCAL@
-AMTAR = @AMTAR@
-AUTOCONF = @AUTOCONF@
-AUTOHEADER = @AUTOHEADER@
-AUTOMAKE = @AUTOMAKE@
-AWK = @AWK@
-CC = @CC@
-CCDEPMODE = @CCDEPMODE@
-CFLAGS = @CFLAGS@
-CPP = @CPP@
-CPPFLAGS = @CPPFLAGS@
-CXX = @CXX@
-CXXDEPMODE = @CXXDEPMODE@
-CXXFLAGS = @CXXFLAGS@
-CYGPATH_W = @CYGPATH_W@
-DATE = @DATE@
-DEFS = @DEFS@
-DEPDIR = @DEPDIR@
-ECHO_C = @ECHO_C@
-ECHO_N = @ECHO_N@
-ECHO_T = @ECHO_T@
-EGREP = @EGREP@
-EXEEXT = @EXEEXT@
-GREP = @GREP@
-INSTALL = @INSTALL@
-INSTALL_DATA = @INSTALL_DATA@
-INSTALL_PROGRAM = @INSTALL_PROGRAM@
-INSTALL_SCRIPT = @INSTALL_SCRIPT@
-INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@
-LDFLAGS = @LDFLAGS@
-LIBOBJS = @LIBOBJS@
-LIBS = @LIBS@
-LN_S = @LN_S@
-LTLIBOBJS = @LTLIBOBJS@
-MAINT = @MAINT@
-MAKEINFO = @MAKEINFO@
-MKDIR_P = @MKDIR_P@
-MYSQL_CONFIG = @MYSQL_CONFIG@
-OBJEXT = @OBJEXT@
-PACKAGE = @PACKAGE@
-PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@
-PACKAGE_NAME = @PACKAGE_NAME@
-PACKAGE_STRING = @PACKAGE_STRING@
-PACKAGE_TARNAME = @PACKAGE_TARNAME@
-PACKAGE_VERSION = @PACKAGE_VERSION@
-PATH_SEPARATOR = @PATH_SEPARATOR@
-PROCFLAGS = @PROCFLAGS@
-RANLIB = @RANLIB@
-SET_MAKE = @SET_MAKE@
-SHELL = @SHELL@
-STRIP = @STRIP@
-U = @U@
-VERSION = @VERSION@
-abs_builddir = @abs_builddir@
-abs_srcdir = @abs_srcdir@
-abs_top_builddir = @abs_top_builddir@
-abs_top_srcdir = @abs_top_srcdir@
-ac_ct_CC = @ac_ct_CC@
-ac_ct_CXX = @ac_ct_CXX@
-am__include = @am__include@
-am__leading_dot = @am__leading_dot@
-am__quote = @am__quote@
-am__tar = @am__tar@
-am__untar = @am__untar@
-bindir = @bindir@
-build_alias = @build_alias@
-builddir = @builddir@
-cap_LIBS = @cap_LIBS@
-datadir = @datadir@
-datarootdir = @datarootdir@
-docdir = @docdir@
-dvidir = @dvidir@
-elfutils_abs_srcdir = @elfutils_abs_srcdir@
-exec_prefix = @exec_prefix@
-host_alias = @host_alias@
-htmldir = @htmldir@
-includedir = @includedir@
-infodir = @infodir@
-install_sh = @install_sh@
-libdir = @libdir@
-libexecdir = @libexecdir@
-localedir = @localedir@
-localstatedir = @localstatedir@
-mandir = @mandir@
-mkdir_p = @mkdir_p@
-oldincludedir = @oldincludedir@
-pdfdir = @pdfdir@
-prefix = @prefix@
-program_transform_name = @program_transform_name@
-psdir = @psdir@
-sbindir = @sbindir@
-sharedstatedir = @sharedstatedir@
-sqlite3_LIBS = @sqlite3_LIBS@
-srcdir = @srcdir@
-stap_LIBS = @stap_LIBS@
-subdirs = @subdirs@
-sysconfdir = @sysconfdir@
-target_alias = @target_alias@
-top_builddir = @top_builddir@
-top_srcdir = @top_srcdir@
-lket_b2a_SOURCES = lket_b2a.c
-lket_b2a_DEPENDENCIES = lket_b2a.h
-lket_b2a_LDFLAGS = `pkg-config --libs glib-2.0` $(am__append_2) \
-       $(am__append_5)
-lket_b2a_CFLAGS = -O2 -D_GNU_SOURCE -Wall `pkg-config --cflags \
-       glib-2.0` $(am__append_1) $(am__append_3) $(am__append_4)
-all: all-am
-
-.SUFFIXES:
-.SUFFIXES: .c .o .obj
-$(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am  $(am__configure_deps)
-       @for dep in $?; do \
-         case '$(am__configure_deps)' in \
-           *$$dep*) \
-             cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh \
-               && exit 0; \
-             exit 1;; \
-         esac; \
-       done; \
-       echo ' cd $(top_srcdir) && $(AUTOMAKE) --gnu  runtime/lket/b2a/Makefile'; \
-       cd $(top_srcdir) && \
-         $(AUTOMAKE) --gnu  runtime/lket/b2a/Makefile
-.PRECIOUS: Makefile
-Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status
-       @case '$?' in \
-         *config.status*) \
-           cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh;; \
-         *) \
-           echo ' cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe)'; \
-           cd $(top_builddir) && $(SHELL) ./config.status $(subdir)/$@ $(am__depfiles_maybe);; \
-       esac;
-
-$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)
-       cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
-
-$(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps)
-       cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
-$(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps)
-       cd $(top_builddir) && $(MAKE) $(AM_MAKEFLAGS) am--refresh
-install-binPROGRAMS: $(bin_PROGRAMS)
-       @$(NORMAL_INSTALL)
-       test -z "$(bindir)" || $(MKDIR_P) "$(DESTDIR)$(bindir)"
-       @list='$(bin_PROGRAMS)'; for p in $$list; do \
-         p1=`echo $$p|sed 's/$(EXEEXT)$$//'`; \
-         if test -f $$p \
-         ; then \
-           f=`echo "$$p1" | sed 's,^.*/,,;$(transform);s/$$/$(EXEEXT)/'`; \
-          echo " $(INSTALL_PROGRAM_ENV) $(binPROGRAMS_INSTALL) '$$p' '$(DESTDIR)$(bindir)/$$f'"; \
-          $(INSTALL_PROGRAM_ENV) $(binPROGRAMS_INSTALL) "$$p" "$(DESTDIR)$(bindir)/$$f" || exit 1; \
-         else :; fi; \
-       done
-
-uninstall-binPROGRAMS:
-       @$(NORMAL_UNINSTALL)
-       @list='$(bin_PROGRAMS)'; for p in $$list; do \
-         f=`echo "$$p" | sed 's,^.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/'`; \
-         echo " rm -f '$(DESTDIR)$(bindir)/$$f'"; \
-         rm -f "$(DESTDIR)$(bindir)/$$f"; \
-       done
-
-clean-binPROGRAMS:
-       -test -z "$(bin_PROGRAMS)" || rm -f $(bin_PROGRAMS)
-lket-b2a$(EXEEXT): $(lket_b2a_OBJECTS) $(lket_b2a_DEPENDENCIES) 
-       @rm -f lket-b2a$(EXEEXT)
-       $(lket_b2a_LINK) $(lket_b2a_OBJECTS) $(lket_b2a_LDADD) $(LIBS)
-
-mostlyclean-compile:
-       -rm -f *.$(OBJEXT)
-
-distclean-compile:
-       -rm -f *.tab.c
-
-@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/lket_b2a-lket_b2a.Po@am__quote@
-
-.c.o:
-@am__fastdepCC_TRUE@   $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ $<
-@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
-@am__fastdepCC_FALSE@  $(COMPILE) -c $<
-
-.c.obj:
-@am__fastdepCC_TRUE@   $(COMPILE) -MT $@ -MD -MP -MF $(DEPDIR)/$*.Tpo -c -o $@ `$(CYGPATH_W) '$<'`
-@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/$*.Tpo $(DEPDIR)/$*.Po
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='$<' object='$@' libtool=no @AMDEPBACKSLASH@
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
-@am__fastdepCC_FALSE@  $(COMPILE) -c `$(CYGPATH_W) '$<'`
-
-lket_b2a-lket_b2a.o: lket_b2a.c
-@am__fastdepCC_TRUE@   $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lket_b2a_CFLAGS) $(CFLAGS) -MT lket_b2a-lket_b2a.o -MD -MP -MF $(DEPDIR)/lket_b2a-lket_b2a.Tpo -c -o lket_b2a-lket_b2a.o `test -f 'lket_b2a.c' || echo '$(srcdir)/'`lket_b2a.c
-@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/lket_b2a-lket_b2a.Tpo $(DEPDIR)/lket_b2a-lket_b2a.Po
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='lket_b2a.c' object='lket_b2a-lket_b2a.o' libtool=no @AMDEPBACKSLASH@
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
-@am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lket_b2a_CFLAGS) $(CFLAGS) -c -o lket_b2a-lket_b2a.o `test -f 'lket_b2a.c' || echo '$(srcdir)/'`lket_b2a.c
-
-lket_b2a-lket_b2a.obj: lket_b2a.c
-@am__fastdepCC_TRUE@   $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lket_b2a_CFLAGS) $(CFLAGS) -MT lket_b2a-lket_b2a.obj -MD -MP -MF $(DEPDIR)/lket_b2a-lket_b2a.Tpo -c -o lket_b2a-lket_b2a.obj `if test -f 'lket_b2a.c'; then $(CYGPATH_W) 'lket_b2a.c'; else $(CYGPATH_W) '$(srcdir)/lket_b2a.c'; fi`
-@am__fastdepCC_TRUE@   mv -f $(DEPDIR)/lket_b2a-lket_b2a.Tpo $(DEPDIR)/lket_b2a-lket_b2a.Po
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      source='lket_b2a.c' object='lket_b2a-lket_b2a.obj' libtool=no @AMDEPBACKSLASH@
-@AMDEP_TRUE@@am__fastdepCC_FALSE@      DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@
-@am__fastdepCC_FALSE@  $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lket_b2a_CFLAGS) $(CFLAGS) -c -o lket_b2a-lket_b2a.obj `if test -f 'lket_b2a.c'; then $(CYGPATH_W) 'lket_b2a.c'; else $(CYGPATH_W) '$(srcdir)/lket_b2a.c'; fi`
-
-ID: $(HEADERS) $(SOURCES) $(LISP) $(TAGS_FILES)
-       list='$(SOURCES) $(HEADERS) $(LISP) $(TAGS_FILES)'; \
-       unique=`for i in $$list; do \
-           if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
-         done | \
-         $(AWK) '    { files[$$0] = 1; } \
-              END { for (i in files) print i; }'`; \
-       mkid -fID $$unique
-tags: TAGS
-
-TAGS:  $(HEADERS) $(SOURCES)  $(TAGS_DEPENDENCIES) \
-               $(TAGS_FILES) $(LISP)
-       tags=; \
-       here=`pwd`; \
-       list='$(SOURCES) $(HEADERS)  $(LISP) $(TAGS_FILES)'; \
-       unique=`for i in $$list; do \
-           if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
-         done | \
-         $(AWK) '    { files[$$0] = 1; } \
-              END { for (i in files) print i; }'`; \
-       if test -z "$(ETAGS_ARGS)$$tags$$unique"; then :; else \
-         test -n "$$unique" || unique=$$empty_fix; \
-         $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \
-           $$tags $$unique; \
-       fi
-ctags: CTAGS
-CTAGS:  $(HEADERS) $(SOURCES)  $(TAGS_DEPENDENCIES) \
-               $(TAGS_FILES) $(LISP)
-       tags=; \
-       here=`pwd`; \
-       list='$(SOURCES) $(HEADERS)  $(LISP) $(TAGS_FILES)'; \
-       unique=`for i in $$list; do \
-           if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \
-         done | \
-         $(AWK) '    { files[$$0] = 1; } \
-              END { for (i in files) print i; }'`; \
-       test -z "$(CTAGS_ARGS)$$tags$$unique" \
-         || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \
-            $$tags $$unique
-
-GTAGS:
-       here=`$(am__cd) $(top_builddir) && pwd` \
-         && cd $(top_srcdir) \
-         && gtags -i $(GTAGS_ARGS) $$here
-
-distclean-tags:
-       -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags
-
-distdir: $(DISTFILES)
-       @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
-       topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \
-       list='$(DISTFILES)'; \
-         dist_files=`for file in $$list; do echo $$file; done | \
-         sed -e "s|^$$srcdirstrip/||;t" \
-             -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \
-       case $$dist_files in \
-         */*) $(MKDIR_P) `echo "$$dist_files" | \
-                          sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \
-                          sort -u` ;; \
-       esac; \
-       for file in $$dist_files; do \
-         if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \
-         if test -d $$d/$$file; then \
-           dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \
-           if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \
-             cp -pR $(srcdir)/$$file $(distdir)$$dir || exit 1; \
-           fi; \
-           cp -pR $$d/$$file $(distdir)$$dir || exit 1; \
-         else \
-           test -f $(distdir)/$$file \
-           || cp -p $$d/$$file $(distdir)/$$file \
-           || exit 1; \
-         fi; \
-       done
-check-am: all-am
-check: check-am
-all-am: Makefile $(PROGRAMS)
-installdirs:
-       for dir in "$(DESTDIR)$(bindir)"; do \
-         test -z "$$dir" || $(MKDIR_P) "$$dir"; \
-       done
-install: install-am
-install-exec: install-exec-am
-install-data: install-data-am
-uninstall: uninstall-am
-
-install-am: all-am
-       @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am
-
-installcheck: installcheck-am
-install-strip:
-       $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \
-         install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \
-         `test -z '$(STRIP)' || \
-           echo "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'"` install
-mostlyclean-generic:
-
-clean-generic:
-
-distclean-generic:
-       -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES)
-
-maintainer-clean-generic:
-       @echo "This command is intended for maintainers to use"
-       @echo "it deletes files that may require special tools to rebuild."
-clean: clean-am
-
-clean-am: clean-binPROGRAMS clean-generic mostlyclean-am
-
-distclean: distclean-am
-       -rm -rf ./$(DEPDIR)
-       -rm -f Makefile
-distclean-am: clean-am distclean-compile distclean-generic \
-       distclean-tags
-
-dvi: dvi-am
-
-dvi-am:
-
-html: html-am
-
-info: info-am
-
-info-am:
-
-install-data-am:
-
-install-dvi: install-dvi-am
-
-install-exec-am: install-binPROGRAMS
-
-install-html: install-html-am
-
-install-info: install-info-am
-
-install-man:
-
-install-pdf: install-pdf-am
-
-install-ps: install-ps-am
-
-installcheck-am:
-
-maintainer-clean: maintainer-clean-am
-       -rm -rf ./$(DEPDIR)
-       -rm -f Makefile
-maintainer-clean-am: distclean-am maintainer-clean-generic
-
-mostlyclean: mostlyclean-am
-
-mostlyclean-am: mostlyclean-compile mostlyclean-generic
-
-pdf: pdf-am
-
-pdf-am:
-
-ps: ps-am
-
-ps-am:
-
-uninstall-am: uninstall-binPROGRAMS
-
-.MAKE: install-am install-strip
-
-.PHONY: CTAGS GTAGS all all-am check check-am clean clean-binPROGRAMS \
-       clean-generic ctags distclean distclean-compile \
-       distclean-generic distclean-tags distdir dvi dvi-am html \
-       html-am info info-am install install-am install-binPROGRAMS \
-       install-data install-data-am install-dvi install-dvi-am \
-       install-exec install-exec-am install-html install-html-am \
-       install-info install-info-am install-man install-pdf \
-       install-pdf-am install-ps install-ps-am install-strip \
-       installcheck installcheck-am installdirs maintainer-clean \
-       maintainer-clean-generic mostlyclean mostlyclean-compile \
-       mostlyclean-generic pdf pdf-am ps ps-am tags uninstall \
-       uninstall-am uninstall-binPROGRAMS
-
-# Tell versions [3.59,3.63) of GNU make to not export all variables.
-# Otherwise a system limit (for SysV at least) may be exceeded.
-.NOEXPORT:
diff --git a/runtime/lket/b2a/lket_b2a.c b/runtime/lket/b2a/lket_b2a.c
deleted file mode 100644 (file)
index ab1bb29..0000000
+++ /dev/null
@@ -1,1030 +0,0 @@
-// Copyright (C) 2005, 2006 IBM Corp.
-// Copyright (C) 2006 Red Hat Inc.
-// Copyright (C) 2007 Bull S.A.S
-//
-// This file is part of systemtap, and is free software.  You can
-// redistribute it and/or modify it under the terms of the GNU General
-// Public License (GPL); either version 2, or (at your option) any
-// later version.
-
-#include <sys/types.h>
-#include <sys/time.h>
-#include <sys/stat.h>
-#include <ctype.h>
-#include <assert.h>
-#include <errno.h>
-#include <unistd.h>
-#include <fcntl.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <time.h>
-#include "lket_b2a.h"
-
-/* A flag indicate whether to store the trace
-   data into local file/MySQL database */
-int into_file, into_db;
-int name_flag=1, id_flag=0, appname_flag=1;
-#ifdef HAS_MYSQL
-
-#define SQLSIZE 1024*1024
-int sql_count;
-#define INSERT_THRESHOLD 100
-char sql[4096];
-char sqlStatement[SQLSIZE];
-char sql_col[1024];
-char sql_val[2048];
-
-MYSQL mysql;
-#endif
-
-/* A FILE handle points to a local file used to
-   store the trace data */
-FILE *outfp;
-
-#define TIMING_GETCYCLES       0x01
-#define TIMING_GETTIMEOFDAY    0x02
-#define TIMING_SCHEDCLOCK      0x03
-
-typedef struct _cpufreq_info {
-       long            timebase;
-       long long       last_cycles;
-       long long       last_time;
-} cpufreq_info;
-
-#define MAX_CPUS               256
-cpufreq_info cpufreq[MAX_CPUS];
-
-static long timing_method = TIMING_GETTIMEOFDAY;
-
-static long long start_timestamp;
-
-GTree *appNameTree;
-
-/* event table */
-event_desc *events_des[MAX_EVT_TYPES][MAX_GRPID][MAX_HOOKID]; 
-
-#define b2a_error(fmt, args...) do { fprintf(stderr, "Error %d@%s: "fmt, __LINE__, __func__, ## args);\
-                exit(-1); } while(0)
-
-void usage()
-{
-printf("Usage:\n\
-  lket-b2a Options INFILE1 [INFILE2...]\n\
-    Options:\n\
-       -f     dump the trace data into a local file named \"lket.out\"\n\
-       -n     name_flag. name_flag set to 0 means not printing the event\n\
-              description string and 1 means printing. Only valid with -f\n\
-              option. name_flag is set to 1 by default.\n\
-       -i     id_flag. id_flag set to 0 means not printing event groupid and\n\
-              hookid and 1 means printing. Only valid with -f option. id_flag\n\
-              is set to 0 by default.\n\
-       -a     appname_flag. appname_flag set to 0 means not printing process\n\
-              name and 1 means printing. Only valid with -f option. appname_flag\n\
-              is set to 1 by default.\n\
-       -m     dump the trace data into MySQL\n\
-   Example:\n\
-       lket-b2a -f -a 1 -i 1 -n 0 stpd_cpu*\n\
-       lket-b2a -m stpd_cpu*\n");
-}
-
-int main(int argc, char *argv[])
-{
-       lket_pkt_header *hdrs = NULL;
-       FILE    **infps = NULL;
-       char    outfilename[MAX_STRINGLEN]={0};
-       int     i, j, total_infiles = 0;
-       long long min;
-       int retvalue = 0;
-
-       char database[18];
-       time_t timer;
-        struct tm *tm;
-
-        time(&timer);
-        tm = localtime(&timer);
-        strftime(database, 18,  "DB%Y%m%d%H%M%S", tm);
-
-        while (1) {
-                int c = getopt(argc, argv, "mfi:n:a:");
-                if (c < 0) // no more options
-                        break;
-                switch (c) {
-               case 'm':
-                       into_db = 1;
-                       break;
-               case 'f':
-                       into_file = 1;
-                       break;
-               case 'n':
-                       name_flag = atoi(optarg);
-                       if(name_flag!=0 && name_flag!=1) {
-                               fprintf(stderr, "you must specify 0 or 1 for -n option\n");
-                               usage();
-                               exit(-1);
-                       }
-                       break;
-               case 'i':
-                       id_flag = atoi(optarg);
-                       if(id_flag!=0 && id_flag!=1) {
-                               fprintf(stderr, "you must specify 0 or 1 for -i option\n");
-                               usage();
-                               exit(-1);
-                       }
-                       break;
-               case 'a':
-                       appname_flag = atoi(optarg);
-                       if(appname_flag!=0 && appname_flag!=1) {
-                               fprintf(stderr, "you must specify 0 or 1 for -a option\n");
-                               usage();
-                               exit(-1);
-                       }
-                       break;
-
-               default:
-                       printf("Error in options\n");
-                       usage();
-                       exit(-1);
-                       break;
-               }
-        }
-
-#ifndef HAS_MYSQL
-       if(into_db)  {
-               b2a_error("-m option is not supported since lket-b2a is not compiled with mysql support\n");
-       }
-#endif
-       if(into_file==0 && into_db==0)  {
-#ifdef HAS_MYSQL
-               fprintf(stderr, "At least one of -m/-f option should be specified\n");
-#else
-               fprintf(stderr, "-f option must be specified\n");
-#endif
-               usage();
-               exit(-1);
-       }
-
-       total_infiles = argc - optind;
-
-       // open the input files and the output file
-       infps = (FILE **)malloc(total_infiles * sizeof(FILE *));
-       if(!infps) {
-               b2a_error("Unable to malloc infps\n");
-       }
-
-       memset(infps, 0, total_infiles * sizeof(FILE *));
-       for(i=0; i < total_infiles; i++) {
-               infps[i] = fopen(argv[optind++], "r");
-               if(infps[i] == NULL) {
-                       printf("Unable to open %s\n", argv[optind-1]);
-                       retvalue = -1;
-                       goto failed;
-               }
-       }
-
-       if(into_file)  {
-               if(strnlen(outfilename, MAX_STRINGLEN) == 0)
-                       strncpy(outfilename, DEFAULT_OUTFILE_NAME, MAX_STRINGLEN);
-       
-               outfp = fopen(outfilename, "w");
-               if(outfp == NULL) {
-                       fprintf(stderr,"Unable to create %s\n", outfilename);
-                       retvalue = -1;
-                       goto failed;
-               }
-       }
-       /* create the search tree */
-        appNameTree = g_tree_new_full(compareFunc, NULL, NULL, destroyTreeData);
-
-#ifdef HAS_MYSQL
-       if(into_db)  {
-               if(!mysql_init(&mysql))  {
-                       b2a_error("Failed to Init MySQL: Error: %s\n",
-                               mysql_error(&mysql));
-               }
-
-               if(!mysql_real_connect(&mysql, NULL, NULL, NULL, NULL, 0, NULL, 
-                       CLIENT_MULTI_STATEMENTS))  {
-                       b2a_error("Failed to connect to database: Error: %s\n",
-                               mysql_error(&mysql));
-               }
-
-               snprintf(sql, 64,"create database %s", database);
-
-               if(mysql_query(&mysql, sql))  {
-                       b2a_error("Failed create database %s, Error: %s\n",
-                               database, mysql_error(&mysql));
-               }
-
-               if(!mysql_real_connect(&mysql, NULL, NULL, NULL, database, 0, NULL, 
-                       CLIENT_MULTI_STATEMENTS))  {
-                       b2a_error("Failed to connect to database %s: Error: %s\n",
-                               database, mysql_error(&mysql));
-               }
-       }
-#endif
-       
-       // find the lket header
-       find_init_header(infps, total_infiles);
-
-       // allocate packet headers array
-       hdrs = malloc(total_infiles * sizeof(lket_pkt_header));
-       if(!hdrs) {
-               printf("Unable to malloc hdrs \n");
-               retvalue = -1;
-               goto failed;
-       }
-       memset(hdrs, 0, total_infiles * sizeof(lket_pkt_header));
-
-       // initialize packet headers array
-       start_timestamp = 0;
-       j = 0;
-       for(i=0; i < total_infiles; i++) {
-               get_pkt_header(infps[i], &hdrs[i]);
-               if( (hdrs[i].microsecond < start_timestamp && hdrs[i].microsecond >0)
-                      || (start_timestamp == 0)) {
-                       start_timestamp = hdrs[i].microsecond;
-                       j = i;
-               }
-       }
-
-       // initialize the start cycles
-       if(timing_method == TIMING_GETCYCLES) {
-               for(i=0; i<MAX_CPUS; i++) {
-                       cpufreq[i].last_cycles = start_timestamp;
-                       cpufreq[i].last_time   = 0;
-               }
-       }
-
-       // main loop of parsing & merging
-       min = start_timestamp;
-       do {
-               // j is the next
-               if(min) {
-                       if(HDR_GroupID(&hdrs[j])==_GROUP_REGEVT)  {
-                               if(HDR_HookID(&hdrs[j]) == _HOOKID_REGEVTDESC)
-                                       register_evt_desc(infps[j],hdrs[j].sys_size);
-                               else
-                                       register_events(HDR_HookID(&hdrs[j]), infps[j], 
-                                               hdrs[j].sys_size);
-                       } else  {
-
-                               if(HDR_GroupID(&hdrs[j])==_GROUP_PROCESS &&
-                                       (HDR_HookID(&hdrs[j])==_HOOKID_PROCESS_SNAPSHOT 
-                                       || HDR_HookID(&hdrs[j])==_HOOKID_PROCESS_EXECVE
-                                       || HDR_HookID(&hdrs[j])==_HOOKID_PROCESS_FORK))
-                               {
-                                       register_appname(j, infps[j], &hdrs[j]);
-                               }
-
-                               if(HDR_GroupID(&hdrs[j])==_GROUP_CPUFREQ
-                                       && HDR_HookID(&hdrs[j])==_HOOKID_SWITCH_CPUFREQ
-                                       && timing_method == TIMING_GETCYCLES) 
-                               {
-                                       int64_t new_timebase;
-                                       fread(&new_timebase, sizeof(new_timebase), 1, infps[j]);
-
-                                       cpufreq[HDR_CpuID(&hdrs[j])].last_time += 
-                                               (hdrs[j].microsecond 
-                                               - cpufreq[HDR_CpuID(&hdrs[j])].last_cycles)
-                                               / cpufreq[HDR_CpuID(&hdrs[j])].timebase;
-                                       cpufreq[j].last_cycles = hdrs[j].microsecond;
-                                       cpufreq[HDR_CpuID(&hdrs[j])].timebase = new_timebase;
-
-                                       fseek(infps[j], -sizeof(new_timebase), SEEK_CUR);
-                               }
-
-                               dump_data(hdrs[j], infps[j]);
-                       }
-                       // update hdr[j]
-#ifdef DEBUG_OUTPUT
-                       fprintf(stderr, "File %d, Offset: %ld\n", j, ftell(infps[j]));
-#endif
-                       get_pkt_header(infps[j], &hdrs[j]);
-               }
-               // recalculate the smallest timestamp
-               min = hdrs[0].microsecond;
-               j = 0;
-               for(i=1; i < total_infiles ; i++) {
-                       if((min == 0) || 
-                               (hdrs[i].microsecond < min && hdrs[i].microsecond > 0)) {
-                               min = hdrs[i].microsecond;
-                               j = i;
-                       }
-               }
-       } while(min != 0);
-
-failed:
-       // close all opened files
-       for(i=0; i < total_infiles; i++)
-               if(infps[i])
-                       fclose(infps[i]);
-       if(outfp)
-               fclose(outfp);
-       
-       // free all allocated memory space
-       if(infps)
-               free(infps);
-       if(hdrs)
-               free(hdrs);
-
-       for(i=1; i<MAX_GRPID; i++)
-       for(j=1; j<MAX_HOOKID; j++) {
-               if(events_des[_HOOKID_REGSYSEVT][i][j] != NULL) {
-#ifdef HAS_MYSQL
-                       if(events_des[_HOOKID_REGSYSEVT][i][j]->flag == 0 && into_db)  {
-                               snprintf(sql, 256, "drop table %d_%d",i,j);
-                               if(mysql_query(&mysql,sql))  {
-                                       b2a_error("Failed to exec sql: %s, Error: %s\n",
-                                               sql, mysql_error(&mysql));
-                               }
-                               snprintf(sql, 256, "delete from table_desc where table_name='%d_%d'",i,j);
-                               if(mysql_query(&mysql,sql))  {
-                                       b2a_error("Failed to exec sql: %s, Error: %s\n",
-                                               sql, mysql_error(&mysql));
-                               }
-                       }
-                       /* destroy entrytime tree */
-                       if(events_des[_HOOKID_REGSYSEVT][i][j]->entrytime)
-                               g_tree_destroy(events_des[_HOOKID_REGSYSEVT][i][j]->entrytime);
-#endif
-               }
-       }
-
-#ifdef HAS_MYSQL
-       if(into_db)  {
-               mysql_close(&mysql);
-       }
-#endif
-       if (appNameTree)
-               g_tree_destroy(appNameTree);
-
-       return retvalue;
-}
-
-/* register newly found process name for addevent.process.snapshot
-  and addevent.process.execve */
-void register_appname(int i, FILE *fp, lket_pkt_header *phdr)
-{
-       int pid, tid, ppid;
-       char *appname=NULL;
-       int count;
-       int len;
-       int c;
-       int location;
-       len=0;
-       count=0;
-
-#ifdef HAS_MYSQL
-       static int flag = 0;
-
-       if(into_db)  {
-               if(flag==0)  {
-                       if(mysql_query(&mysql, "create table appNameMap ( pid INT, pname varchar(20))"))  {
-                               b2a_error("Failed to create appNameMap table, Error: %s\n",
-                                       mysql_error(&mysql));
-                       }
-               }
-               flag=1;
-       }
-#endif
-       appname = (char *)malloc(512);
-       location = ftell(fp);
-
-       if(HDR_HookID(phdr) == _HOOKID_PROCESS_SNAPSHOT )  {  /* process_snapshot */
-               fread(&tid, 1, 4, fp); /* read tid */
-               fread(&pid, 1, 4, fp); /* read pid */
-               fread(&ppid, 1, 4, fp); /* read ppid */
-               c = fgetc_unlocked(fp);
-               len+=13;
-               while (c && len < 1024) {
-                       appname[count++] = (char)c;     
-                       c = fgetc_unlocked(fp);
-                       ++len;
-               }
-               appname[count]='\0';
-       } else if (HDR_HookID(phdr) == _HOOKID_PROCESS_EXECVE)  { /* process.execve */
-               fread(&tid, 1, 4, fp); /* read tid */
-               fread(&pid, 1, 4, fp); /* read pid */
-               fread(&ppid, 1, 4, fp); /* read ppid */
-               c = fgetc_unlocked(fp);
-               len+=5;
-               while (c && len < 1024) {
-                       appname[count++] = (char)c;     
-                       c = fgetc_unlocked(fp);
-                       ++len;
-               }
-               appname[count]='\0';
-       } else  if (HDR_HookID(phdr) == _HOOKID_PROCESS_FORK) {
-               fread(&tid, 1, 4, fp); /* read tid */
-               fread(&pid, 1, 4, fp); /* read pid */
-               fread(&ppid, 1, 4, fp); /* read ppid */
-
-               char *appname_ptr;
-               appname_ptr = (char *)(g_tree_lookup(appNameTree,(gconstpointer)((long)ppid)));
-               if(appname_ptr == NULL)
-                       strncpy(appname, "N/A", 4);
-               else
-                       strncpy(appname, appname_ptr, 256);
-
-       } else {
-               free(appname);
-               return;
-       }
-       fseek(fp, location, SEEK_SET);
-#ifdef HAS_MYSQL
-               if(into_db)  {
-                       snprintf(sql, 256,"insert into appNameMap values ( %d, \"%s\")", pid, appname);
-                       if(mysql_query(&mysql,sql))  {
-                               b2a_error("Failed to exec SQL: %s, Error: %s\n",
-                                       sql, mysql_error(&mysql));
-                       }
-               }
-#endif
-       g_tree_insert(appNameTree, (gpointer)((long)pid), (gpointer)appname);
-}
-
-
-gint compareFunc(gconstpointer a, gconstpointer b, gpointer user_data)
-{
-        if((long)(a) > (long)(b)) return 1;
-        else if ((long)(a) < (long)(b)) return -1;
-        else return 0;
-}
-
-void destroyTreeData(gpointer data)
-{
-        free(data);
-}
-
-/* 
- * search the LKET init header in a set of input files, 
- * and the header structure is defined in tapsets/lket_trace.stp
- */
-void find_init_header(FILE **infps, const int total_infiles)
-{
-       int      i, j, k;
-       int32_t magic;
-        percpu_header pcpu;
-
-       /* information from lket_init_header */
-       int16_t inithdr_len;
-       int8_t ver_major;
-       int8_t ver_minor;
-       int8_t big_endian;
-       int8_t timing_field; 
-       int8_t bits_width;
-       int32_t init_timebase;
-       char  timing_methods_str[128];
-
-       if(total_infiles <= 0 )
-               b2a_error("total_infiles <= 0\n");
-       j = total_infiles;
-       for(i=0; i<total_infiles; i++) {
-               /* skip percpu header */
-               if(fread(&pcpu, 1, sizeof(pcpu), infps[i]) < sizeof(pcpu))
-                       continue;
-               if(fread(&magic, 1, sizeof(magic), infps[i]) < sizeof(magic))
-                       continue;
-               if(magic == (int32_t)LKET_MAGIC) {
-                       //found
-                       j = i;
-                       if(into_file)
-                               fprintf(outfp, "LKET Magic:\t0x%X\n", magic);
-                       //read other content of lket_int_header
-                       if(fread(&inithdr_len, 1, sizeof(inithdr_len), infps[i]) 
-                               < sizeof(inithdr_len))
-                               break;
-                       if(into_file)
-                               fprintf(outfp, "InitHdrLen:\t%d\n", inithdr_len);
-                       if(fread(&ver_major, 1, sizeof(ver_major), infps[i]) < sizeof(ver_major))
-                               break;
-                       if(into_file)
-                               fprintf(outfp, "Version Major:\t%d\n", ver_major);
-                       if(fread(&ver_minor, 1, sizeof(ver_minor), infps[i]) < sizeof(ver_minor))
-                               break;
-                       if(into_file)
-                               fprintf(outfp, "Version Minor:\t%d\n", ver_minor);
-                       if(fread(&big_endian, 1, sizeof(big_endian), infps[i]) < sizeof(big_endian))
-                               break;
-                       if(into_file)
-                               fprintf(outfp, "Big endian:\t%s\n", big_endian ? "YES":"NO");
-                       if(fread(&timing_field, 1, sizeof(timing_field), infps[i]) 
-                               < sizeof(timing_field))
-                               break;
-                       timing_method = timing_field;
-                       if(into_file)
-                               fprintf(outfp, "Timing method:\t");
-                       switch(timing_method) {
-                               case TIMING_GETCYCLES: 
-                                       snprintf(timing_methods_str, 128, "get_cycles");
-                                       if(into_file)
-                                               fprintf(outfp, "get_cycles()\n"); 
-                                       break;
-                               case TIMING_GETTIMEOFDAY:
-                                       snprintf(timing_methods_str, 128,"do_gettimeofday");
-                                       if(into_file)
-                                               fprintf(outfp, "do_gettimeofday()\n");  
-                                       break;
-                               case TIMING_SCHEDCLOCK:
-                                       snprintf(timing_methods_str, 128, "sched_clock");
-                                       if(into_file)
-                                               fprintf(outfp, "sched_clock()\n"); 
-                                       break;
-                               default:
-                                       snprintf(timing_methods_str,128,
-                                               "Unsupported timing method");
-                                       if(into_file)
-                                               fprintf(outfp, "Unsupported timging method\n");
-                       }
-                       if(fread(&bits_width, 1, sizeof(bits_width), infps[i]) < sizeof(bits_width))
-                               break;
-                       if(into_file)
-                               fprintf(outfp, "Bits width:\t%d\n", bits_width);
-                       if(fread(&init_timebase, 1, sizeof(init_timebase), infps[i]) 
-                               < sizeof(init_timebase))
-                               break;
-                       if(into_file)
-                               fprintf(outfp, 
-                                       "Initial CPU timebase:\t%d (cycles per microsecond)\n", 
-                                       init_timebase);
-                       if(timing_method == TIMING_GETCYCLES) {
-                               for(k = 0; k < MAX_CPUS; k++)
-                                       cpufreq[k].timebase = init_timebase;
-                       }
-                       break;
-               }
-       }
-
-#ifdef HAS_MYSQL
-       if(into_db)  {
-               if(mysql_query(&mysql, "create table trace_header ( Major_Ver TINYINT, Minor_Ver TINYINT, Big_Endian TINYINT, Timing_Method varchar(20), Bits_Width TINYINT)" )) {
-                       b2a_error("Failed to create trace_header table, Error: %s\n",
-                               mysql_error(&mysql));
-               }
-               snprintf(sql, 256, "insert into trace_header value ( %d, %d, %d, \"%s\", %d )",
-                       ver_major, ver_minor, big_endian, timing_methods_str, bits_width);      
-
-               if(mysql_query(&mysql, sql)) {
-                       b2a_error("Failed exec SQL %d: \n %s \n, Error: %s\n",
-                               __LINE__, sql, mysql_error(&mysql));
-               }
-       }
-#endif
-       for(i=0; i<total_infiles && i!=j; i++)
-               fseek(infps[i], 0LL, SEEK_SET);
-       return;
-}
-
-/* 
- * read the lket_pkt_header structure at the begining of the input file 
- */
-int get_pkt_header(FILE *fp, lket_pkt_header *phdr)
-{
-       percpu_header pcpu;
-       size_t size;
-       if(feof(fp)) return 0;
-
-        if((size = fread(&pcpu, 1, sizeof(pcpu), fp)) < sizeof(pcpu)) {
-               if (feof(fp)) {
-                       bzero(phdr, sizeof(lket_pkt_header));
-                        return 0;
-                } else
-                       b2a_error("fread read %u bytes than expected %u, feof:%d\n",
-                                  (unsigned) size, (unsigned) sizeof(pcpu),
-                                  feof(fp));
-        }
-
-       if((size = fread(phdr, 1, sizeof(lket_pkt_header), fp)) < sizeof(lket_pkt_header))  {
-               if(feof(fp))  {
-                       bzero(phdr, sizeof(lket_pkt_header));
-                       return 0;
-               } else 
-                       b2a_error("fread read %u bytes than expected %u, feof:%d\n", (unsigned) size, (unsigned) sizeof(lket_pkt_header), feof(fp));
-       }
-
-       phdr->sys_size -= sizeof(lket_pkt_header)-sizeof(phdr->total_size)-sizeof(phdr->sys_size);
-       phdr->total_size -= sizeof(lket_pkt_header)-sizeof(phdr->total_size)-sizeof(phdr->sys_size);
-       return 0;
-}      
-
-void print_pkt_header(lket_pkt_header *phdr)
-{
-       long long usecs;
-       int sec, usec;
-       int grpid, hookid, pid, tid, ppid;
-
-       if(!phdr)
-               b2a_error("phdr is NULL\n");
-
-       if(timing_method == TIMING_GETCYCLES)
-               usecs = (phdr->microsecond - cpufreq[HDR_CpuID(phdr)].last_cycles)
-                       / cpufreq[HDR_CpuID(phdr)].timebase + cpufreq[HDR_CpuID(phdr)].last_time;
-       else if(timing_method == TIMING_SCHEDCLOCK)
-               usecs = (phdr->microsecond - start_timestamp) / 1000;
-       else
-               usecs = phdr->microsecond - start_timestamp;
-       
-       sec = usecs/1000000;
-       usec = usecs%1000000;
-
-       grpid = HDR_GroupID(phdr);      
-       hookid = HDR_HookID(phdr);
-       pid = HDR_PID(phdr);
-       tid = HDR_TID(phdr);
-       ppid = HDR_PPID(phdr);
-
-       if(into_file) {
-               fprintf(outfp, "\n%d.%d CPU:%d TID:%d, PID:%d, PPID:%d, ", sec, usec, 
-                       HDR_CpuID(phdr), tid, pid, ppid);
-               if(appname_flag==1)  {
-                       char *appname_ptr;
-                       appname_ptr = (char *)(g_tree_lookup(appNameTree,(gconstpointer)((long)pid)));
-                       if(appname_ptr == NULL)  
-                               fprintf(outfp, "APPNAME:N/A ");
-                       else
-                               fprintf(outfp, "APPNAME:%s ", appname_ptr);
-               }
-               if(name_flag==1)
-                       fprintf(outfp, "EVT_NAME:%s ", events_des[_HOOKID_REGSYSEVT][grpid][hookid]->description);
-               if(id_flag==1)
-                       fprintf(outfp, "HOOKGRP:%d HOOKID:%d ", grpid, hookid);
-       }
-
-#ifdef HAS_MYSQL
-       if(into_db)  {
-               if(!(hookid%2)) { // return type event
-                       long long *entrytime;
-                       long long entryusecs;
-                       entrytime = g_tree_lookup(events_des[_HOOKID_REGSYSEVT][grpid][hookid-1]->entrytime,
-                                        (gconstpointer)((long)tid));
-                       if(entrytime==NULL)  // key not found
-                               entryusecs = 0;
-                       else
-                               entryusecs = *entrytime;
-                       snprintf(sql_col, 128, "groupid, hookid, usec, thread_id, process_id, parentprocess_id, \
-                               cpu_id, entry_usec,");
-                       snprintf(sql_val, 256, "%d, %d, %lld, %d, %d, %d, %d, %lld,", grpid,
-                               hookid, usecs, tid, pid, ppid, HDR_CpuID(phdr), 
-                               entryusecs);
-               }  else  {
-                       snprintf(sql_col, 128, "groupid, hookid, usec, thread_id, process_id, parentprocess_id, cpu_id,");
-                       snprintf(sql_val, 256, "%d, %d, %lld, %d, %d, %d, %d, ", grpid, 
-                               hookid, usecs, tid, pid, ppid, HDR_CpuID(phdr));
-               }
-               if(hookid%2) {
-                       char *entrytime = malloc(sizeof(long long));
-                       *((long long *)entrytime) = usecs;
-                       g_tree_insert(events_des[_HOOKID_REGSYSEVT][grpid][hookid]->entrytime, 
-                               (gpointer)((long)tid), (gpointer)entrytime);
-               }
-       }
-#endif
-
-}
-
-#ifdef HAS_MYSQL
-char *get_sqltype(char *fmt)
-{
-        if(strncmp(fmt, "INT8", 4) == 0)
-               return "TINYINT";
-        if(strncmp(fmt, "INT16", 5) == 0)
-               return "SMALLINT";
-        if(strncmp(fmt, "INT32", 5) == 0)
-               return "INT";
-        if(strncmp(fmt, "INT64", 5) == 0)
-               return "BIGINT";
-        if(strncmp(fmt, "STRING", 6) == 0)
-               return "VARCHAR(20)";
-       return "";
-}
-#endif
-
-void register_evt_desc(FILE *infp, size_t size)
-{
-#ifdef HAS_MYSQL
-       static int has_table = 0;
-#endif
-       int grpid, hookid;
-       int len = 0;
-       char *evt_body;
-       evt_body = malloc(size);
-       fread(evt_body, size, 1, infp);
-       grpid = *(int8_t *)evt_body;
-        hookid  = *(int8_t *)(evt_body+1);
-       len = strlen(evt_body+2)+2;
-       if(!events_des[_HOOKID_REGSYSEVT][grpid][hookid])
-               events_des[_HOOKID_REGSYSEVT][grpid][hookid] = malloc(sizeof(event_desc));
-       events_des[_HOOKID_REGSYSEVT][grpid][hookid]->description = malloc(len);
-
-       strncpy(events_des[_HOOKID_REGSYSEVT][grpid][hookid]->description, evt_body+2, len);
-#ifdef HAS_MYSQL
-       events_des[_HOOKID_REGSYSEVT][grpid][hookid]->entrytime = g_tree_new_full(
-               compareFunc, NULL, NULL, destroyTreeData);
-       if(into_db)  {
-               if(!has_table)  {
-                       snprintf(sql, 1024, "create table table_desc ( table_name varchar(6), table_desc varchar(32))");
-                       if(mysql_query(&mysql, sql))  {
-                               b2a_error("Failed exec SQL: \n %s \n, Error: %s\n",
-                                       sql, mysql_error(&mysql));
-                       }
-                       has_table = 1;
-               } 
-
-               snprintf(sql, 1024, "insert into table_desc ( table_name, table_desc) values ( \"%d_%d\", \"%s\")", grpid, hookid,
-                       evt_body+2);
-
-               if(mysql_query(&mysql, sql))  {
-                       b2a_error("Failed exec SQL:\n %s \n, Error: %s\n",
-                               sql, mysql_error(&mysql));
-               }
-       }
-#endif
-       free(evt_body);
-}
-
-void register_events(int evt_type, FILE *infp, size_t size)
-{
-       int cnt=0, len=0;
-
-       char *evt_body, *evt_fmt, *evt_names, *tmp, *fmt, *name;
-       int8_t grpid, hookid;
-
-       evt_body = malloc(size);
-
-       fread(evt_body, size, 1, infp);
-
-       grpid = *(int8_t *)evt_body;
-       hookid  = *(int8_t *)(evt_body+1);
-
-       if(!events_des[evt_type][grpid][hookid])
-               events_des[evt_type][grpid][hookid] = malloc(sizeof(event_desc));
-       if(!events_des[evt_type][grpid][hookid])  {
-               b2a_error("error when malloc for event_des[%d][%d][%d]\n",
-                       evt_type, grpid, hookid);
-       }
-
-#ifdef HAS_MYSQL
-       if(into_db)  {
-               if(evt_type==_HOOKID_REGSYSEVT)  {  /* if sys event, create a table */
-                       if(!(hookid%2))  {/* if this is a return type event, should record 
-                                            the entry time of this event */
-                               snprintf(sql, 1024, "create table %d_%d ( groupid TINYINT, hookid TINYINT, usec BIGINT, thread_id INT, process_id INT, parentprocess_id INT, cpu_id TINYINT, entry_usec BIGINT,", grpid, hookid);
-                       } else  {
-                               snprintf(sql, 1024, "create table %d_%d ( groupid TINYINT, hookid TINYINT, usec BIGINT, thread_id INT, process_id INT, parentprocess_id INT, cpu_id TINYINT,", grpid, hookid);
-                       }
-               }
-               if(evt_type==_HOOKID_REGUSREVT)  { /* if user event, alter an existing table */
-                       snprintf(sql, 1024, "alter table %d_%d ", grpid, hookid);
-               }
-       }
-
-       if(size == 2) // skip if no event format is provided
-               goto gen_sql;
-#endif
-
-       evt_fmt = evt_body+2;
-       
-       for(tmp=evt_fmt; *tmp!=0; tmp++);
-
-       evt_names = tmp+1;
-
-       fmt = strsep(&evt_fmt, ":");
-       name = strsep(&evt_names, ":");
-
-       if(fmt==NULL || name==NULL)  {
-               b2a_error("error in event format/names string\n");
-       }
-
-       while(fmt!=NULL && name!=NULL)  {
-#ifdef HAS_MYSQL
-               if(into_db)  {
-                       if(evt_type==_HOOKID_REGSYSEVT)  {
-                               strcat(sql, "`");
-                               strcat(sql, name);
-                               strcat(sql, "` ");
-                               strcat(sql, get_sqltype(fmt));
-                               strcat(sql, ",");
-                       }
-                       if(evt_type==_HOOKID_REGUSREVT)  {
-                               strcat(sql, "add ");
-                               strcat(sql, "`");
-                               strcat(sql, name);
-                               strcat(sql, "` ");
-                               strcat(sql, get_sqltype(fmt));
-                               strcat(sql, ",");
-                       }
-               }
-#endif
-               strncpy(events_des[evt_type][grpid][hookid]->evt_fmt[cnt], fmt, 7);
-               strncpy(events_des[evt_type][grpid][hookid]->evt_names[cnt], 
-                       name, MAX_FIELDNAME_LEN);
-               strncpy(events_des[evt_type][grpid][hookid]->fmt+len, get_fmtstr(fmt), 8);
-               len+=strlen(get_fmtstr(fmt));
-               fmt = strsep(&evt_fmt, ":");
-               name = strsep(&evt_names, ":");
-               cnt++;
-       }
-       events_des[evt_type][grpid][hookid]->count = cnt;
-       *(events_des[evt_type][grpid][hookid]->fmt+len)='\0';
-
-#ifdef HAS_MYSQL
-gen_sql:
-       if(into_db)  {
-               if(evt_type==_HOOKID_REGSYSEVT)
-                       sql[strlen(sql)-1]=')';
-               if(evt_type==_HOOKID_REGUSREVT)
-                       sql[strlen(sql)-1]='\0';
-
-               if(mysql_query(&mysql, sql))  {
-                       b2a_error("Failed exec SQL: \n %s \n, Error: %s\n",
-                               sql, mysql_error(&mysql));
-               }
-       }
-#endif
-       free(evt_body);
-}
-
-char *get_fmtstr(char *fmt)
-{
-        if(strncmp(fmt, "INT8", 4) == 0)
-               return "%1b";
-        if(strncmp(fmt, "INT16", 5) == 0)
-               return "%2b";
-        if(strncmp(fmt, "INT32", 5) == 0)
-               return "%4b";
-        if(strncmp(fmt, "INT64", 5) == 0)
-               return "%8b";
-        if(strncmp(fmt, "STRING", 6) == 0)
-               return "%0s";
-       return "";
-}
-
-int dump_data(lket_pkt_header header, FILE *infp)
-{
-       int i, c, j;
-       int16_t stemp;
-       int32_t ntemp;
-       long long lltemp;
-       int readbytes = 0;
-       int total_bytes = 0;
-       int size = 0;
-       int evt_num = 1;
-
-       char tmp_int[32];
-
-       char *fmt, *name, *buffer;
-       int grpid = HDR_GroupID(&header);
-       int hookid = HDR_HookID(&header);
-
-       print_pkt_header(&header);
-
-       /* if the data contains user appended extra data */
-       if(header.total_size != header.sys_size)
-               evt_num = 3;
-
-       /* iterate the sys and user event */
-       for(j=1; j<= evt_num; j+=2)  {
-               
-               readbytes = 0;
-
-               if(j == 1) /* if current one is a sys event */
-                       size = header.sys_size;
-               if(j == 2) /* if current one is a user event */
-                       size = header.total_size - header.sys_size;
-
-               if(into_file && (events_des[j][grpid][hookid] == NULL ||
-                       events_des[j][grpid][hookid]->count <= 0)) {
-                       //no format is provided, dump in hex
-                       buffer = malloc(size);
-                       fread(buffer, size, 1, infp);
-                       fwrite(buffer, size, 1, outfp);
-                       free(buffer);
-                       total_bytes += size;
-                       continue;
-               }
-
-               events_des[j][grpid][hookid]->flag = 1;
-
-               for(i=0; i<events_des[j][grpid][hookid]->count; i++)  {
-                       fmt = events_des[j][grpid][hookid]->evt_fmt[i];
-                       name = events_des[j][grpid][hookid]->evt_names[i];
-#ifdef HAS_MYSQL
-                       if(into_db) {
-                               strcat(sql_col, "`");
-                               strcat(sql_col, name);
-                               strcat(sql_col, "`,");
-                       }
-#endif
-
-                       if(into_file)  {
-                               fwrite(name, strlen(name), 1, outfp);
-                               fwrite(":", 1, 1, outfp);
-                       }
-                       if(strncmp(fmt, "INT8", 4)==0)  {
-                               c = fgetc_unlocked(infp);
-                               if(into_file)
-                                       fprintf(outfp, "%d,", (int8_t)c);
-                               sprintf(tmp_int, "%d,", (int8_t)c);
-#ifdef HAS_MYSQL
-                               if(into_db)
-                                       strcat(sql_val, tmp_int);
-#endif
-                               readbytes+=1;
-                       } else if(strncmp(fmt, "INT16", 5)==0)  {
-                               fread(&stemp, 2, 1, infp);
-                               if(into_file)
-                                       fprintf(outfp, "%d,", (int16_t)stemp);
-                               sprintf(tmp_int, "%d,", (int16_t)stemp);
-#ifdef HAS_MYSQL
-                               if(into_db)
-                                       strcat(sql_val, tmp_int);
-#endif
-                               readbytes+=2;
-                       } else if(strncmp(fmt, "INT32", 5)==0) {
-                               fread(&ntemp, 4, 1, infp);
-                               if(into_file)
-                                       fprintf(outfp, "%d,", (int32_t)ntemp);
-                               snprintf(tmp_int, 20, "%d,", (int32_t)ntemp);
-#ifdef HAS_MYSQL
-                               if(into_db)
-                                       strcat(sql_val, tmp_int);
-#endif
-                               readbytes+=4;
-                       } else if(strncmp(fmt, "INT64", 5)==0) {
-                               fread(&lltemp, 8, 1, infp);
-                               if(into_file)
-                                       fprintf(outfp, "%lld,",lltemp);
-                               snprintf(tmp_int, 30, "%lld,", lltemp);
-#ifdef HAS_MYSQL
-                               if(into_db)
-                                       strcat(sql_val, tmp_int);
-#endif
-                               readbytes+=8;
-                       } else if(strncmp(fmt, "STRING", 6)==0)  {
-
-#ifdef HAS_MYSQL
-                               int tmplen=0;
-                               if(into_db) {
-                                       tmplen=strlen(sql_val);
-                                       sql_val[tmplen++]='"';
-                               }
-#endif
-                               c = fgetc_unlocked(infp);
-                               ++readbytes;
-                               while (c && readbytes < size) {
-                                       if(into_file)
-                                               fputc_unlocked(c, outfp);
-#ifdef HAS_MYSQL
-                                       if(into_db)
-                                               sql_val[tmplen++]=c;
-#endif
-                                       c = fgetc_unlocked(infp);
-                                       ++readbytes;
-                               }
-                               if(!c) {
-                                       if(into_file)
-                                               fputc_unlocked(',', outfp);
-#ifdef HAS_MYSQL
-                                       if(into_db) {
-                                               sql_val[tmplen++]='"';
-                                               sql_val[tmplen++]=',';
-                                               sql_val[tmplen]='\0';
-                                       }
-#endif
-                                       continue;
-                               }
-                               else {
-                                       b2a_error("error processing STRING\n");
-                               }
-                       }
-               }
-               total_bytes += readbytes;
-       }
-
-#ifdef HAS_MYSQL
-       if(into_db) {
-               sql_col[strlen(sql_col)-1] = '\0';
-               sql_val[strlen(sql_val)-1] = '\0';
-               snprintf(sql, 1024, "insert into %d_%d (%s) values (%s)", 
-                       grpid, hookid, sql_col, sql_val);
-
-               if(sql_count >= INSERT_THRESHOLD)  {
-                       if(mysql_query(&mysql, sqlStatement))  {
-                               b2a_error("Failed exec SQL:\n%s\n, Error:\n%s\n",
-                                       sqlStatement, mysql_error(&mysql));
-                       }
-                       while(!mysql_next_result(&mysql));
-                       sql_count=0;
-                       sqlStatement[0]='\0';
-               }  else {
-                       //strncpy(sqlStatement, sql, 2048);
-                       strcat(sqlStatement, sql);
-                       strcat(sqlStatement, ";");
-                       sql_count++;
-               }
-       }
-#endif
-
-       return total_bytes;
-}
diff --git a/runtime/lket/b2a/lket_b2a.h b/runtime/lket/b2a/lket_b2a.h
deleted file mode 100644 (file)
index 46ca91f..0000000
+++ /dev/null
@@ -1,101 +0,0 @@
-#ifndef _LKET_B2A_H
-#define _LKET_B2A_H
-
-#include <glib.h>
-
-#ifdef HAS_MYSQL
-#include <mysql/mysql.h>
-#endif
-
-typedef struct _percpu_header {
-  int32_t seq;
-  int32_t len;
-} percpu_header;
-
-#define LKET_MAGIC     0xAEFCDB6B
-
-#define MAX_STRINGLEN  256
-
-#define MAX_GRPID  255
-#define MAX_HOOKID  255
-#define MAX_EVT_TYPES 3
-
-#define DEFAULT_OUTFILE_NAME "lket.out"
-
-/* Group ID Definitions */
-int _GROUP_REGEVT = 1;
-int _GROUP_PROCESS = 3;
-int _GROUP_CPUFREQ = 15;
-
-/* hookIDs defined inside each group */
-int _HOOKID_REGSYSEVT = 1;
-int _HOOKID_REGUSREVT = 3;
-int _HOOKID_REGEVTDESC = 5;
-
-int _HOOKID_PROCESS_SNAPSHOT = 1;
-int _HOOKID_PROCESS_EXECVE = 3;
-int _HOOKID_PROCESS_FORK = 5;
-
-//int _HOOKID_INIT_CPUFREQ = 1;
-int _HOOKID_SWITCH_CPUFREQ = 1;
-
-typedef struct _lket_pkt_header {
-       int16_t total_size;
-       int16_t sys_size;
-       int64_t microsecond;
-       /* tid_pid is (tid<<32|pid) */
-       int64_t tid_pid;
-       /* aggr is the bit-OP of:
-               (int64_t)current->parent->tgid << 32 |
-               (int32_t)GroupID << 24 | (int32_t)hookID << 16 |
-               (int16_t)current->thread_info->cpu << 8
-       */
-       int64_t aggr;
-} __attribute__((packed)) lket_pkt_header;
-
-#define HDR_TID(ptr)  (int32_t)(((ptr)->tid_pid)>>32)
-#define HDR_PID(ptr)  (int32_t)((ptr)->tid_pid)
-#define HDR_PPID(ptr)  (int32_t)(((ptr)->aggr)>>32)
-#define HDR_GroupID(ptr)  (int8_t)(((ptr)->aggr)>>24) 
-#define HDR_HookID(ptr)  (int8_t)(((ptr)->aggr)>>16) 
-#define HDR_CpuID(ptr)  (int8_t)(((ptr)->aggr)>>8) 
-
-#define MAX_FIELDS  32 /* max fields in a record */
-#define MAX_FIELDNAME_LEN 16 /* max len of a field */
-
-typedef struct {
-#ifdef HAS_MYSQL
-       GTree *entrytime;
-#endif
-       char evt_fmt[MAX_FIELDS][7]; /* e.g. INT8,STRING,INT16,... */
-       char evt_names[MAX_FIELDS][MAX_FIELDNAME_LEN]; /* e.g. protocal,dev_name,buff_len,... */
-       char fmt[256];  /* e.g. %1b,%0s,%2b,... */
-       char *description; /* a string description of this event, such as "iosyscall.read.entry" */
-       int count; /* # of fields */
-       int flag; /* a flag indicates whether exists trace data for this event */
-} event_desc;
-
-/* 
- * search the lket_init_header structure in a set of input files 
- */
-static void find_init_header(FILE **fp, const int total_infiles);
-
-/* 
- * read the lket_pkt_header structure at the begining of the input file 
- */
-static int get_pkt_header(FILE *fp, lket_pkt_header *phdr);
-
-/* 
- * print the lket_pkt_header structure into the output file
- */
-static void print_pkt_header(lket_pkt_header *phdr);
-
-void register_appname(int i, FILE *fp, lket_pkt_header *phdr);
-gint compareFunc(gconstpointer a, gconstpointer b, gpointer user_data);
-void destroyTreeData(gpointer data);
-void register_evt_desc(FILE *infp, size_t size);
-void register_events(int evt_type, FILE *infp, size_t size);
-int dump_data(lket_pkt_header header, FILE *infp);
-char *get_fmtstr(char *fmt);
-
-#endif
index 513e27df790bf8260e7ad3c9f8fe3ec50eede009..a436d7ed7c5170f94ccf56b70d63ab9084a73cb2 100644 (file)
@@ -15,7 +15,6 @@
  * @brief Implements maps (associative arrays) and lists
  */
 
-#include "alloc.c"
 #include "sym.c"
 #include "stat-common.c"
 #include "map-stat.c"
index 19539044d1fc379b4f8a8ae2429616512906df11..6fe844fbc4cbb3d1208fbc966392399cd5de5d92 100644 (file)
@@ -25,7 +25,7 @@ void _stp_unregister_jprobes (struct jprobe *probes, int num_probes)
        int i;
        for (i = 0; i < num_probes; i++)
                unregister_jprobe(&probes[i]);
-       dbug("All jprobes removed\n");
+       // dbug("All jprobes removed\n");
 }
 
 /** Register a group of jprobes.
@@ -46,7 +46,7 @@ int _stp_register_jprobes (struct jprobe *probes, int num_probes)
                        ret = -1; /* FIXME */
                        goto out;
                }
-               dbug("inserting jprobe at %s (%p)\n", probes[i].kp.addr, addr);
+               // dbug("inserting jprobe at %s (%p)\n", probes[i].kp.addr, addr);
                probes[i].kp.addr = (kprobe_opcode_t *)addr;
                ret = register_jprobe(&probes[i]);
                if (ret)
@@ -69,7 +69,7 @@ void _stp_unregister_kprobes (struct kprobe *probes, int num_probes)
        int i;
        for (i = 0; i < num_probes; i++)
                unregister_kprobe(&probes[i]);
-       dbug("All kprobes removed\n");
+       // dbug("All kprobes removed\n");
 }
 
 
@@ -83,7 +83,7 @@ void _stp_unregister_kretprobes (struct kretprobe *probes, int num_probes)
        int i;
        for (i = 0; i < num_probes; i++)
                unregister_kretprobe(&probes[i]);
-       dbug("All return probes removed\n");
+       // dbug("All return probes removed\n");
 }
 #endif
 
@@ -104,7 +104,7 @@ int _stp_register_kprobes (struct kprobe *probes, int num_probes)
                        ret = -1;
                        goto out;
                }
-               dbug("inserting kprobe at %s (%p)\n", probes[i].addr, addr);
+               // dbug("inserting kprobe at %s (%p)\n", probes[i].addr, addr);
                probes[i].addr = (kprobe_opcode_t *)addr;
                ret = register_kprobe(&probes[i]);
                if (ret)
@@ -136,7 +136,7 @@ int _stp_register_kretprobes (struct kretprobe *probes, int num_probes)
                        ret = -1; /* FIXME */
                        goto out;
                }
-               dbug("inserting kretprobe at %s (%p)\n", probes[i].kp.addr, addr);
+               // dbug("inserting kretprobe at %s (%p)\n", probes[i].kp.addr, addr);
                probes[i].kp.addr = (kprobe_opcode_t *)addr;
                ret = register_kretprobe(&probes[i]);
                if (ret)
diff --git a/runtime/probes/bench/Makefile b/runtime/probes/bench/Makefile
deleted file mode 100644 (file)
index 9154e3d..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-all: ttest itest
-
-ttest: ttest.c
-       gcc -Wall -O3 -o ttest ttest.c
-
-itest: itest.c
-       gcc -Wall -O3 -o itest itest.c
-
-clean:
-       /bin/rm -f itest ttest stpd_cpu* xxx* 
index 318d30380ac1442f6cc9ab8bcce95acf818e0d7a..b9a9c778375d8680cf8433a8e273497c54f743a4 100644 (file)
@@ -76,7 +76,6 @@ static struct
 #include "io.c"
 #include "arith.c"
 #include "copy.c"
-#include "sym.h"
 #include "sym.c"
 #ifdef STP_PERFMON
 #include "perf.c"
index 186b2ad440b695785d09b943e2ec034cd9956358..3ba992014c5fc28c53cf6379fa5d3c752940f08c 100644 (file)
@@ -1,6 +1,6 @@
 /* -*- linux-c -*-
  * x86_64 stack tracing functions
- * Copyright (C) 2005, 2006, 2007 Red Hat Inc.
+ * Copyright (C) 2005-2008 Red Hat Inc.
  *
  * This file is part of systemtap, and is free software.  You can
  * redistribute it and/or modify it under the terms of the GNU General
@@ -8,13 +8,38 @@
  * later version.
  */
 
-static void __stp_stack_print (struct pt_regs *regs, int verbose, int levels)
+// todo: don't use unwinder  for kernel if CONFIG_FRAME
+
+/* DWARF unwinder failed.  Just dump intereting addresses on kernel stack. */
+static void _stp_stack_print_fallback(unsigned long stack, int verbose)
 {
-       unsigned long *stack = (unsigned long *)REG_SP(regs);
        unsigned long addr;
 
-       while ((long)stack & (THREAD_SIZE-1)) {
-               addr = *stack++;
-               _stp_func_print(addr, verbose, 1);
+       while (stack & (THREAD_SIZE - 1)) {
+               if (unlikely(__stp_get_user(addr, (unsigned long *)stack))) {
+                       /* cannot access stack.  give up. */
+                       return;
+               }
+               _stp_func_print(addr, verbose, 0);
+               stack++;
+       }
+}
+
+static void __stp_stack_print(struct pt_regs *regs, int verbose, int levels)
+{
+       struct unwind_frame_info info;
+       arch_unw_init_frame_info(&info, regs);
+
+       /* we haven't actually executed the instruction at the IP yet. */
+       UNW_PC(&info) -= 1;
+
+       while (!arch_unw_user_mode(&info)) {
+               int ret = unwind(&info);
+               dbug_unwind(1, "ret=%d PC=%lx\n", ret, UNW_PC(&info));
+               if (ret < 0) {
+                       _stp_stack_print_fallback(UNW_SP(&info), verbose);
+                       break;
+               }
+               _stp_func_print(UNW_PC(&info), verbose, 1);
        }
 }
index 9c01d65c25bb080be2e3b06248c368796dd173ac..e338f58762fc878e596d4a1868f4c95b56982819 100644 (file)
@@ -1,6 +1,6 @@
 /*  -*- linux-c -*-
  * Stack tracing functions
- * Copyright (C) 2005, 2006, 2007 Red Hat Inc.
+ * Copyright (C) 2005-2008 Red Hat Inc.
  * Copyright (C) 2005 Intel Corporation.
  *
  * This file is part of systemtap, and is free software.  You can
@@ -23,6 +23,7 @@
 
 #include "sym.c"
 #include "regs.h"
+#include "unwind.c"
 
 #define MAXBACKTRACE 20
 
index 2e0c3c5c50b3a13a7986e43ad3ce7f4401ca712d..1dcb6b00fa18bd48527740219263274810817005 100644 (file)
@@ -27,7 +27,7 @@ static void sigproc(int signum)
                        return;
                send_request(STP_EXIT, NULL, 0);
        } else if (signum == SIGQUIT)
-               cleanup_and_exit(2);    
+               cleanup_and_exit(2);
        else if (signum == SIGINT || signum == SIGHUP || signum == SIGTERM)
                send_request(STP_EXIT, NULL, 0);
 }
@@ -40,7 +40,7 @@ static void setup_main_signals(int cleanup)
        if (cleanup == 0) {
                a.sa_handler = sigproc;
                sigaction(SIGCHLD, &a, NULL);
-       } else 
+       } else
                a.sa_handler = SIG_IGN;
        sigaction(SIGINT, &a, NULL);
        sigaction(SIGTERM, &a, NULL);
@@ -48,7 +48,6 @@ static void setup_main_signals(int cleanup)
        sigaction(SIGQUIT, &a, NULL);
 }
 
-
 /* 
  * start_cmd forks the command given on the command line
  * with the "-c" option. It will not exec that command
@@ -75,7 +74,7 @@ void start_cmd(void)
        a.sa_handler = SIG_IGN;
        sigaction(SIGINT, &a, NULL);
 
-       dbug (1, "execing target_cmd %s\n", target_cmd);
+       dbug(1, "execing target_cmd %s\n", target_cmd);
        if ((pid = fork()) < 0) {
                _perr("fork");
                exit(1);
@@ -86,8 +85,8 @@ void start_cmd(void)
                sigaction(SIGINT, &a, NULL);
 
                /* commands we fork need to run at normal priority */
-               setpriority (PRIO_PROCESS, 0, 0);
-               
+               setpriority(PRIO_PROCESS, 0, 0);
+
                /* wait here until signaled */
                sigwait(&usrset, &signum);
 
@@ -107,11 +106,11 @@ void system_cmd(char *cmd)
 {
        pid_t pid;
 
-       dbug (2, "system %s\n", cmd);
+       dbug(2, "system %s\n", cmd);
        if ((pid = fork()) < 0) {
                _perr("fork");
        } else if (pid == 0) {
-               setpriority (PRIO_PROCESS, 0, 0);
+               setpriority(PRIO_PROCESS, 0, 0);
                if (execl("/bin/sh", "sh", "-c", cmd, NULL) < 0)
                        perr("%s", cmd);
                _exit(1);
@@ -128,7 +127,7 @@ static void read_buffer_info(void)
        if (!use_old_transport)
                return;
 
-       if (statfs("/sys/kernel/debug", &st) == 0 && (int) st.f_type == (int) DEBUGFS_MAGIC)
+       if (statfs("/sys/kernel/debug", &st) == 0 && (int)st.f_type == (int)DEBUGFS_MAGIC)
                return;
 
        if (sprintf_chk(buf, "/proc/systemtap/%s/bufsize", modname))
@@ -152,7 +151,6 @@ static void read_buffer_info(void)
        return;
 }
 
-
 /**
  *     init_stapio - initialize the app
  *     @print_summary: boolean, print summary or not at end of run
@@ -177,7 +175,7 @@ int init_stapio(void)
                        if (init_oldrelayfs() < 0) {
                                close_ctl_channel();
                                return -1;
-                       } 
+                       }
                } else {
                        if (init_relayfs() < 0) {
                                close_ctl_channel();
@@ -192,7 +190,6 @@ int init_stapio(void)
        if (target_cmd)
                start_cmd();
 
-
        return 0;
 }
 
@@ -202,7 +199,7 @@ int init_stapio(void)
  * 2 - disconnected
  * 3 - initialized
  */
-void cleanup_and_exit (int closed)
+void cleanup_and_exit(int closed)
 {
        pid_t err;
        static int exiting = 0;
@@ -219,7 +216,7 @@ void cleanup_and_exit (int closed)
        err = waitpid(-1, NULL, WNOHANG);
        if (err >= 0)
                err("\nWaiting for processes to exit\n");
-       while(wait(NULL) > 0) ;
+       while (wait(NULL) > 0) ;
 
        if (use_old_transport)
                close_oldrelayfs(closed == 2);
@@ -230,8 +227,7 @@ void cleanup_and_exit (int closed)
        close_ctl_channel();
 
        if (initialized == 2 && closed == 2) {
-               err("\nDisconnecting from systemtap module.\n"          \
-                   "To reconnect, type \"staprun -A %s\"\n", modname);
+               err("\nDisconnecting from systemtap module.\n" "To reconnect, type \"staprun -A %s\"\n", modname);
        } else if (initialized)
                closed = 3;
        else
@@ -247,7 +243,7 @@ int stp_main_loop(void)
 {
        ssize_t nb;
        void *data;
-       int type;
+       uint32_t type;
        FILE *ofp = stdout;
        char recvbuf[8196];
 
@@ -257,80 +253,93 @@ int stp_main_loop(void)
        dbug(2, "in main loop\n");
        send_request(STP_READY, NULL, 0);
 
-       while (1) { /* handle messages from control channel */
+       while (1) {             /* handle messages from control channel */
                nb = read(control_channel, recvbuf, sizeof(recvbuf));
                if (nb <= 0) {
                        if (errno != EINTR)
                                _perr("Unexpected EOF in read (nb=%ld)", (long)nb);
                        continue;
                }
-               
-               type = *(int *)recvbuf;
-               data = (void *)(recvbuf + sizeof(int));
 
-               switch (type) { 
+               type = *(uint32_t *)recvbuf;
+               data = (void *)(recvbuf + sizeof(uint32_t));
+               nb -= sizeof(uint32_t);
+
+               switch (type) {
 #ifdef STP_OLD_TRANSPORT
                case STP_REALTIME_DATA:
-               {
-                       ssize_t bw = write(out_fd[0], data, nb - sizeof(int));
-                       if (bw >= 0 && bw != (nb - (ssize_t)sizeof(int))) {
-                               nb = nb - bw; 
-                               bw = write(out_fd[0], data, nb - sizeof(int));
-                       }
-                       if (bw != (nb - (ssize_t)sizeof(int))) {
-                               _perr("write error (nb=%ld)", (long)nb);
-                               cleanup_and_exit(1);
+                       {
+                               ssize_t bw = write(out_fd[0], data, nb);
+                               if (bw >= 0 && bw != nb) {
+                                       nb = nb - bw;
+                                       bw = write(out_fd[0], data, nb);
+                               }
+                               if (bw != nb) {
+                                       _perr("write error (nb=%ld)", (long)nb);
+                                       cleanup_and_exit(1);
+                               }
+                               break;
                        }
-                        break;
-               }
 #endif
                case STP_OOB_DATA:
-                       fputs ((char *)data, stderr);
-                       break;
-               case STP_EXIT: 
-               {
-                       /* module asks us to unload it and exit */
-                       int *closed = (int *)data;
-                       dbug(2, "got STP_EXIT, closed=%d\n", *closed);
-                       cleanup_and_exit(*closed);
-                       break;
-               }
-               case STP_START: 
-               {
-                       struct _stp_msg_start *t = (struct _stp_msg_start *)data;
-                       dbug(2, "probe_start() returned %d\n", t->res);
-                       if (t->res < 0) {
-                               if (target_cmd)
-                                       kill (target_pid, SIGKILL);
-                               cleanup_and_exit(1);
-                       } else if (target_cmd)
-                               kill (target_pid, SIGUSR1);
+                       fputs((char *)data, stderr);
                        break;
-               }
+               case STP_EXIT:
+                       {
+                               /* module asks us to unload it and exit */
+                               int *closed = (int *)data;
+                               dbug(2, "got STP_EXIT, closed=%d\n", *closed);
+                               cleanup_and_exit(*closed);
+                               break;
+                       }
+               case STP_START:
+                       {
+                               struct _stp_msg_start *t = (struct _stp_msg_start *)data;
+                               dbug(2, "probe_start() returned %d\n", t->res);
+                               if (t->res < 0) {
+                                       if (target_cmd)
+                                               kill(target_pid, SIGKILL);
+                                       cleanup_and_exit(1);
+                               } else if (target_cmd)
+                                       kill(target_pid, SIGUSR1);
+                               break;
+                       }
                case STP_SYSTEM:
-               {
-                       struct _stp_msg_cmd *c = (struct _stp_msg_cmd *)data;
-                       dbug(2, "STP_SYSTEM: %s\n", c->cmd);
-                       system_cmd(c->cmd);
-                       break;
-               }
+                       {
+                               struct _stp_msg_cmd *c = (struct _stp_msg_cmd *)data;
+                               dbug(2, "STP_SYSTEM: %s\n", c->cmd);
+                               system_cmd(c->cmd);
+                               break;
+                       }
                case STP_TRANSPORT:
-               {
-                       struct _stp_msg_start ts;
-                       if (use_old_transport) {
-                               if (init_oldrelayfs() < 0)
-                                       cleanup_and_exit(1);
-                       } else {
-                               if (init_relayfs() < 0)
-                                       cleanup_and_exit(1);
+                       {
+                               struct _stp_msg_start ts;
+                               if (use_old_transport) {
+                                       if (init_oldrelayfs() < 0)
+                                               cleanup_and_exit(1);
+                               } else {
+                                       if (init_relayfs() < 0)
+                                               cleanup_and_exit(1);
+                               }
+                               ts.target = target_pid;
+                               initialized = 2;
+                               send_request(STP_START, &ts, sizeof(ts));
+                               if (load_only)
+                                       cleanup_and_exit(2);
+                               break;
+                       }
+               case STP_UNWIND:
+                       {
+                               int len;
+                               char *ptr = (char *)data;
+                               while (nb > 0) {
+                                       send_unwind_data(ptr);
+                                       len = strlen(ptr) + 1;
+                                       ptr += len;
+                                       nb -= len;
+                               }
+                               break;
                        }
-                       ts.target = target_pid;
-                       initialized = 2;
-                       send_request(STP_START, &ts, sizeof(ts));
-                       if (load_only)
-                               cleanup_and_exit(2);
-                       break;
-               }
                default:
                        err("WARNING: ignored message of type %d\n", (type));
                }
index f4e67fdbac1d3a891d1cfe99a9c488dd53e7f757..8db2ac5bba789cf1061f81e358b0c6b8fea76d86 100644 (file)
@@ -181,8 +181,6 @@ static void cleanup(int rc)
        if (setpriority (PRIO_PROCESS, 0, 0) < 0)
                _perr("setpriority");
        
-       stop_symbol_thread();
-
        /* rc == 2 means disconnected */
        if (rc == 2)
                return;
@@ -278,7 +276,6 @@ int main(int argc, char **argv)
                exit(1);
 
        setup_staprun_signals();
-       start_symbol_thread();
 
        rc = run_stapio(argv);
        cleanup(rc);
index 1128fb4c65856db01ecf15cffd988a44886a0d98..08797a3762349df9a3c0f950cd3b80c73ae60315 100644 (file)
@@ -118,8 +118,7 @@ int init_stapio(void);
 int stp_main_loop(void);
 int send_request(int type, void *data, int len);
 void cleanup_and_exit (int);
-int do_module(void *);
-int do_kernel_symbols(void);
+void send_unwind_data(const char *name);
 int init_ctl_channel(int);
 void close_ctl_channel(void);
 int init_relayfs(void);
index 34e12c25e1d6c04c959a1d3c35968aec8fe2a480..b95a9a5ac62e7bf6df902d6589122f6c7371be4c 100644 (file)
@@ -401,95 +401,3 @@ int check_permissions(void)
         * is in that directory. */
        return check_path();
 }
-
-pthread_t symbol_thread_id = (pthread_t)0;
-int kernel_ptr_size = 0;
-
-/* Symbol handling thread */
-void *handle_symbols(void __attribute__((unused)) *arg)
-{
-       ssize_t nb;
-       void *data;
-       int32_t type;
-       char recvbuf[8192];
-
-       dbug(2, "waiting for symbol requests\n");
-
-       /* handle messages from control channel */
-       while (1) {
-               nb = read(control_channel, recvbuf, sizeof(recvbuf));
-               if (nb <= 0) {
-                       if (errno != EINTR)
-                               _perr("Unexpected EOF in read (nb=%ld)", (long)nb);
-                       continue;
-               }
-               
-               type = *(int32_t *)recvbuf;
-               data = (void *)(recvbuf + sizeof(int32_t));
-               
-               switch (type) { 
-               case STP_MODULE:
-               {
-                       dbug(2, "STP_MODULES request received\n");
-                       if (do_module(data) < 0)
-                               goto done;
-                       break;
-               }               
-               case STP_SYMBOLS:
-               {
-                       struct _stp_msg_symbol *req = (struct _stp_msg_symbol *)data;
-                       dbug(2, "STP_SYMBOLS request received\n");
-                       if (req->endian != 0x1234) {
-                               err("ERROR: staprun is compiled with different endianess than the kernel!\n");
-                               goto done;
-                       }
-                       kernel_ptr_size = req->ptr_size;
-                       if (kernel_ptr_size != 4 && kernel_ptr_size != 8) {
-                               err("ERROR: invalid kernel pointer size %d\n", kernel_ptr_size);
-                               goto done;
-                       }
-                       if (do_kernel_symbols() < 0)
-                               goto done;
-                       break;
-               }
-               default:
-                       err("WARNING: ignored message of type %d\n", (type));
-               }
-       }
-
-done:
-       /* signal stapio we're done */
-       kill(0, SIGINT);
-
-       return NULL;
-}
-
-void start_symbol_thread(void)
-{
-       int status;
-
-       /* create symbol control channel */
-       status = do_cap(CAP_DAC_OVERRIDE, init_ctl_channel, 1);
-       drop_cap(CAP_DAC_OVERRIDE);
-       if (status < 0) {
-               err("Failed to initialize control channel.\n");
-               exit(1);
-       }
-       status = pthread_create(&symbol_thread_id, NULL, handle_symbols, NULL);
-       if (status) {
-               perr("Failed to create symbol thread.\n");
-               exit(1);
-       }
-}
-
-void stop_symbol_thread(void)
-{
-
-       if (symbol_thread_id) {
-               dbug(2, "Stopping symbol thread.\n");
-               pthread_cancel(symbol_thread_id);
-               pthread_join(symbol_thread_id, NULL);
-       }
-       close_ctl_channel();
-}
-
diff --git a/runtime/staprun/unwind_data.c b/runtime/staprun/unwind_data.c
new file mode 100644 (file)
index 0000000..ed27cc2
--- /dev/null
@@ -0,0 +1,97 @@
+/* -*- linux-c -*-
+ * Unwind data functions for staprun.
+ *
+ * Copyright (C) 2008 Red Hat Inc.
+ *
+ * This file is part of systemtap, and is free software.  You can
+ * redistribute it and/or modify it under the terms of the GNU General
+ * Public License (GPL); either version 2, or (at your option) any
+ * later version.
+ */
+
+#include "staprun.h"
+#include <elfutils/libdwfl.h>
+#include <dwarf.h>
+
+static char debuginfo_path_arr[] = "-:.debug:/usr/lib/debug";
+static char *debuginfo_path = debuginfo_path_arr;
+static const Dwfl_Callbacks kernel_callbacks = {
+       .find_debuginfo = dwfl_standard_find_debuginfo,
+       .debuginfo_path = &debuginfo_path,
+       .find_elf = dwfl_linux_kernel_find_elf,
+       .section_address = dwfl_linux_kernel_module_section_address,
+};
+
+void *get_module_unwind_data(Dwfl * dwfl, const char *name, int *len)
+{
+       Dwarf_Addr bias = 0;
+       Dwarf *dw;
+       GElf_Ehdr *ehdr, ehdr_mem;
+       GElf_Shdr *shdr, shdr_mem;
+       Elf_Scn *scn = NULL;
+       Elf_Data *data = NULL;
+
+       Dwfl_Module *mod = dwfl_report_module(dwfl, name, 0, 0);
+       dwfl_report_end(dwfl, NULL, NULL);
+       dw = dwfl_module_getdwarf(mod, &bias);
+       Elf *elf = dwarf_getelf(dw);
+       ehdr = gelf_getehdr(elf, &ehdr_mem);
+       while ((scn = elf_nextscn(elf, scn))) {
+               shdr = gelf_getshdr(scn, &shdr_mem);
+               if (strcmp(elf_strptr(elf, ehdr->e_shstrndx, shdr->sh_name), ".debug_frame") == 0) {
+                       data = elf_rawdata(scn, NULL);
+                       break;
+               }
+       }
+
+       if (data == NULL) {
+               *len = 0;
+               dbug(2, "module %s returns NULL\n", name);
+               return NULL;
+       }
+       dbug(2, "module %s returns %d\n", name, (int)data->d_size);
+       *len = data->d_size;
+       return data->d_buf;
+}
+
+void send_unwind_data(const char *name)
+{
+       struct _stp_msg_unwind *un;
+       int unwind_data_len = 0;
+       void *unwind_data = NULL;
+       char *buf;
+
+       dbug(2, "module %s\n", name);
+       if (strcmp(name, "*")) {
+               Dwfl *dwfl = dwfl_begin(&kernel_callbacks);
+
+               if (name[0] == 0)
+                       unwind_data = get_module_unwind_data(dwfl, "kernel", &unwind_data_len);
+               else
+                       unwind_data = get_module_unwind_data(dwfl, name, &unwind_data_len);
+
+               /* yuck */
+               buf = (char *)malloc(unwind_data_len + sizeof(*un) + sizeof(uint32_t));
+               if (!buf) {
+                       err("malloc failed\n");
+                       return;
+               }
+               memcpy(buf + sizeof(*un) + sizeof(uint32_t), unwind_data, unwind_data_len);
+               dwfl_end(dwfl);
+       } else {
+               buf = (char *)malloc(sizeof(*un) + sizeof(uint32_t));
+               if (!buf) {
+                       err("malloc failed\n");
+                       return;
+               }
+       }
+               
+       un = (struct _stp_msg_unwind *)(buf + sizeof(uint32_t));
+       strncpy(un->name, name, sizeof(un->name));
+       un->unwind_len = unwind_data_len;
+       *(uint32_t *) buf = STP_UNWIND;
+
+       /* send unwind data */
+       if (write(control_channel, buf, unwind_data_len + sizeof(*un) + sizeof(uint32_t)) <= 0)
+               err("write failed\n");
+}
index 3c2f859a85e00b6e19cdb8e360108322bdce6f89..3d5ff01df2f85f59f57733fdc5bf5f2d04e6a53a 100644 (file)
@@ -33,7 +33,7 @@ unsigned long _stp_module_relocate(const char *module, const char *section, unsi
                return 0;
        }
 
-       dbug(DEBUG_SYMBOLS, "%s, %s, %lx\n", module, section, offset);
+       dbug_sym(1, "%s, %s, %lx\n", module, section, offset);
 
        STP_RLOCK_MODULES;
        if (!module || !strcmp(section, "")     /* absolute, unrelocated address */
@@ -47,7 +47,7 @@ unsigned long _stp_module_relocate(const char *module, const char *section, unsi
                if (!strcmp(module, last->name) && !strcmp(section, last_sec->symbol)) {
                        offset += last_sec->addr;
                        STP_RUNLOCK_MODULES;
-                       dbug(DEBUG_SYMBOLS, "offset = %lx\n", offset);
+                       dbug_sym(1, "offset = %lx\n", offset);
                        return offset;
                }
        }
@@ -72,7 +72,7 @@ unsigned long _stp_module_relocate(const char *module, const char *section, unsi
                                if (!strcmp(section, last_sec->symbol)) {
                                        offset += last_sec->addr;
                                        STP_RUNLOCK_MODULES;
-                                       dbug(DEBUG_SYMBOLS, "offset = %lx\n", offset);
+                                       dbug_sym(1, "offset = %lx\n", offset);
                                        return offset;
                                }
                        }
index b124882a225cd1c3c9273ab5a8a33ead89703526..631a5bbf84e3037f5b155451c05ce08577778767 100644 (file)
@@ -7,8 +7,8 @@
  * later version.
  */
 
-#ifndef _STAP_SYMBOLS_H_
-#define _STAP_SYMBOLS_H_
+#ifndef _STP_SYM_H_
+#define _STP_SYM_H_
 
 #define STP_MODULE_NAME_LEN 64
 
@@ -16,11 +16,6 @@ struct _stp_symbol {
        unsigned long addr;
        const char *symbol;
 };
-struct stap_symbol {
-       unsigned long addr;
-       const char *symbol;
-       const char *module;
-};
 
 DEFINE_RWLOCK(_stp_module_lock);
 #define STP_RLOCK_MODULES  read_lock_irqsave(&_stp_module_lock, flags)
@@ -50,8 +45,14 @@ struct _stp_module {
        /* how many sections this module has */
        uint32_t num_sections;
        
-       /* how the symbol_data below was allocated */
-       int32_t allocated;  /* 0 = kmalloc, 1 = vmalloc */
+       /* how the data below was allocated */
+       /* 0 = kmalloc, 1 = vmalloc */
+       struct {
+               unsigned symbols :1;
+               unsigned symbol_data :1;
+               unsigned unwind_data :1;
+               unsigned unwind_hdr :1;
+       } allocated;
        
        struct _stp_symbol *sections;
        
@@ -63,7 +64,10 @@ struct _stp_module {
        
        /* the stack unwind data for this module */
        void *unwind_data;
+       void *unwind_hdr;       
        uint32_t unwind_data_len;
+       uint32_t unwind_hdr_len;
+       uint32_t unwind_is_ehframe; /* unwind data comes from .eh_frame */
        rwlock_t lock; /* lock while unwinding is happening */
        
 };
@@ -83,4 +87,4 @@ int _stp_num_modules = 0;
 
 unsigned long _stp_module_relocate (const char *module, const char *section, unsigned long offset);
 static struct _stp_module *_stp_get_unwind_info (unsigned long addr);
-#endif /* _STAP_SYMBOLS_H_ */
+#endif /* _STP_SYM_H_ */
diff --git a/runtime/tests/Makefile b/runtime/tests/Makefile
deleted file mode 100644 (file)
index 4e744d2..0000000
+++ /dev/null
@@ -1,3 +0,0 @@
-tests:
-       tclsh all.tcl
-
diff --git a/runtime/tests/agg/Makefile b/runtime/tests/agg/Makefile
deleted file mode 100644 (file)
index c396c13..0000000
+++ /dev/null
@@ -1,5 +0,0 @@
-default: tests
-
-tests:
-       tclsh all.tcl
-
diff --git a/runtime/tests/maps/Makefile b/runtime/tests/maps/Makefile
deleted file mode 100644 (file)
index c396c13..0000000
+++ /dev/null
@@ -1,5 +0,0 @@
-default: tests
-
-tests:
-       tclsh all.tcl
-
diff --git a/runtime/tests/math/Makefile b/runtime/tests/math/Makefile
deleted file mode 100644 (file)
index c396c13..0000000
+++ /dev/null
@@ -1,5 +0,0 @@
-default: tests
-
-tests:
-       tclsh all.tcl
-
diff --git a/runtime/tests/pmaps/Makefile b/runtime/tests/pmaps/Makefile
deleted file mode 100644 (file)
index c396c13..0000000
+++ /dev/null
@@ -1,5 +0,0 @@
-default: tests
-
-tests:
-       tclsh all.tcl
-
diff --git a/runtime/tests/string/Makefile b/runtime/tests/string/Makefile
deleted file mode 100644 (file)
index c396c13..0000000
+++ /dev/null
@@ -1,5 +0,0 @@
-default: tests
-
-tests:
-       tclsh all.tcl
-
index 6a5b272d7b399882ec62c723cd2a13ac0847b6d7..ed7725fa8ac94e6f3505e287176b4ec52a470035 100644 (file)
@@ -14,80 +14,31 @@ static int _stp_current_buffers = STP_DEFAULT_BUFFERS;
 
 static _stp_mempool_t *_stp_pool_q;
 static struct list_head _stp_ctl_ready_q;
-static struct list_head _stp_sym_ready_q;
 DEFINE_SPINLOCK(_stp_ctl_ready_lock);
-DEFINE_SPINLOCK(_stp_sym_ready_lock);
 
-static ssize_t _stp_sym_write_cmd(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
-{
-       static int saved_type = 0;
-       int type;
-
-       if (count < sizeof(int32_t))
-               return 0;
-
-       /* Allow sending of packet type followed by data in the next packet. */
-       if (count == sizeof(int32_t)) {
-               if (get_user(saved_type, (int __user *)buf))
-                       return -EFAULT;
-               return count;
-       } else if (saved_type) {
-               type = saved_type;
-               saved_type = 0;
-       } else {
-               if (get_user(type, (int __user *)buf))
-                       return -EFAULT;
-               count -= sizeof(int);
-               buf += sizeof(int);
-       }
-
-#if DEBUG_TRANSPORT > 0
-       if (type < STP_MAX_CMD)
-               _dbug("Got %s. len=%d\n", _stp_command_name[type], (int)count);
-#endif
-
-       switch (type) {
-       case STP_SYMBOLS:
-               count = _stp_do_symbols(buf, count);
-               break;
-       case STP_MODULE:
-               if (count > 1)
-                       count = _stp_do_module(buf, count);
-               else {
-                       /* count == 1 indicates end of initial modules list */
-                       _stp_ctl_send(STP_TRANSPORT, NULL, 0);
-               }
-               break;
-       case STP_EXIT:
-               _stp_exit_flag = 1;
-               break;
-       default:
-               errk("invalid symbol command type %d\n", type);
-               return -EINVAL;
-       }
-
-       return count;
-}
 static ssize_t _stp_ctl_write_cmd(struct file *file, const char __user *buf, size_t count, loff_t *ppos)
 {
-       int type;
+       u32 type;
        static int started = 0;
 
-       if (count < sizeof(int))
+       if (count < sizeof(u32))
                return 0;
 
-       if (get_user(type, (int __user *)buf))
+       if (get_user(type, (u32 __user *)buf))
                return -EFAULT;
 
-#if DEBUG_TRANSPORT > 0
+       count -= sizeof(u32);
+       buf += sizeof(u32);
+
+#ifdef DEBUG_TRANS
        if (type < STP_MAX_CMD)
                _dbug("Got %s. len=%d\n", _stp_command_name[type], (int)count);
 #endif
 
-       count -= sizeof(int);
-       buf += sizeof(int);
-
        switch (type) {
+       case STP_UNWIND:
+               _stp_do_unwind_data(buf, count);
+               break;
        case STP_START:
                if (started == 0) {
                        struct _stp_msg_start st;
@@ -110,7 +61,7 @@ static ssize_t _stp_ctl_write_cmd(struct file *file, const char __user *buf, siz
 #endif
        case STP_READY:
                /* request symbolic information */
-               _stp_ask_for_symbols();
+               /*  _stp_ask_for_symbols(); */
                break;
 
        default:
@@ -121,8 +72,6 @@ static ssize_t _stp_ctl_write_cmd(struct file *file, const char __user *buf, siz
        return count;
 }
 
-#define STP_CTL_BUFFER_SIZE 256
-
 struct _stp_buffer {
        struct list_head list;
        int len;
@@ -131,9 +80,8 @@ struct _stp_buffer {
 };
 
 static DECLARE_WAIT_QUEUE_HEAD(_stp_ctl_wq);
-static DECLARE_WAIT_QUEUE_HEAD(_stp_sym_wq);
 
-#if DEBUG_TRANSPORT > 0
+#ifdef DEBUG_TRANS
 static void _stp_ctl_write_dbug(int type, void *data, int len)
 {
        char buf[64];
@@ -155,20 +103,9 @@ static void _stp_ctl_write_dbug(int type, void *data, int len)
        case STP_TRANSPORT:
                _dbug("sending STP_TRANSPORT\n");
                break;
-       default:
-               _dbug("ERROR: unknown message type: %d\n", type);
-               break;
-       }
-}
-static void _stp_sym_write_dbug(int type, void *data, int len)
-{
-       switch (type) {
-       case STP_SYMBOLS:
-               _dbug("sending STP_SYMBOLS\n");
-               break;
-       case STP_MODULE:
-               _dbug("sending STP_MODULE\n");
-               break;
+       case STP_UNWIND:
+               snprintf(buf, sizeof(buf), "%s", (char *)data);
+               _dbug("sending STP_UNWIND %s [len=%d]\n", buf, len);
        default:
                _dbug("ERROR: unknown message type: %d\n", type);
                break;
@@ -181,7 +118,7 @@ static int _stp_ctl_write(int type, void *data, unsigned len)
        struct _stp_buffer *bptr;
        unsigned long flags;
 
-#if DEBUG_TRANSPORT > 0
+#ifdef DEBUG_TRANS
        _stp_ctl_write_dbug(type, data, len);
 #endif
 
@@ -206,96 +143,19 @@ static int _stp_ctl_write(int type, void *data, unsigned len)
        return len;
 }
 
-static int _stp_sym_write(int type, void *data, unsigned len)
-{
-       struct _stp_buffer *bptr;
-       unsigned long flags;
-
-#if DEBUG_TRANSPORT > 0
-       _stp_sym_write_dbug(type, data, len);
-#endif
-
-       /* make sure we won't overflow the buffer */
-       if (unlikely(len > STP_CTL_BUFFER_SIZE))
-               return 0;
-
-       /* get a buffer from the free pool */
-       bptr = _stp_mempool_alloc(_stp_pool_q);
-       if (unlikely(bptr == NULL))
-               return -1;
-
-       bptr->type = type;
-       memcpy(bptr->buf, data, len);
-       bptr->len = len;
-
-       /* put it on the pool of ready buffers */
-       spin_lock_irqsave(&_stp_sym_ready_lock, flags);
-       list_add_tail(&bptr->list, &_stp_sym_ready_q);
-       spin_unlock_irqrestore(&_stp_sym_ready_lock, flags);
-
-       /* OK, it's queued. Now signal any waiters. */
-       wake_up_interruptible(&_stp_sym_wq);
-
-       return len;
-}
-
 /* send commands with timeout and retry */
 static int _stp_ctl_send(int type, void *data, int len)
 {
        int err, trylimit = 50;
-       kbug(DEBUG_TRANSPORT, "ctl_send: type=%d len=%d\n", type, len);
-       if (unlikely(type == STP_SYMBOLS || type == STP_MODULE)) {
-               while ((err = _stp_sym_write(type, data, len)) < 0 && trylimit--)
-                       msleep(5);
-       } else {
-               while ((err = _stp_ctl_write(type, data, len)) < 0 && trylimit--)
-                       msleep(5);
-               if (err > 0)
-                       wake_up_interruptible(&_stp_ctl_wq);
-       }
-       kbug(DEBUG_TRANSPORT, "returning %d\n", err);
+       dbug_trans(1, "ctl_send: type=%d len=%d\n", type, len);
+       while ((err = _stp_ctl_write(type, data, len)) < 0 && trylimit--)
+               msleep(5);
+       if (err > 0)
+               wake_up_interruptible(&_stp_ctl_wq);
+       dbug_trans(1, "returning %d\n", err);
        return err;
 }
 
-static ssize_t _stp_sym_read_cmd(struct file *file, char __user *buf, size_t count, loff_t *ppos)
-{
-       struct _stp_buffer *bptr;
-       int len;
-       unsigned long flags;
-
-       /* wait for nonempty ready queue */
-       spin_lock_irqsave(&_stp_sym_ready_lock, flags);
-       while (list_empty(&_stp_sym_ready_q)) {
-               spin_unlock_irqrestore(&_stp_sym_ready_lock, flags);
-               if (file->f_flags & O_NONBLOCK)
-                       return -EAGAIN;
-               if (wait_event_interruptible(_stp_sym_wq, !list_empty(&_stp_sym_ready_q)))
-                       return -ERESTARTSYS;
-               spin_lock_irqsave(&_stp_sym_ready_lock, flags);
-       }
-
-       /* get the next buffer off the ready list */
-       bptr = (struct _stp_buffer *)_stp_sym_ready_q.next;
-       list_del_init(&bptr->list);
-       spin_unlock_irqrestore(&_stp_sym_ready_lock, flags);
-
-       /* write it out */
-       len = bptr->len + 4;
-       if (len > count || copy_to_user(buf, &bptr->type, len)) {
-               /* now what?  We took it off the queue then failed to send it */
-               /* we can't put it back on the queue because it will likely be out-of-order */
-               /* fortunately this should never happen */
-               /* FIXME need to mark this as a transport failure */
-               errk("Supplied buffer too small. count:%d len:%d\n", (int)count, len);
-               return -EFAULT;
-       }
-
-       /* put it on the pool of free buffers */
-       _stp_mempool_free(bptr);
-
-       return len;
-}
-
 static ssize_t _stp_ctl_read_cmd(struct file *file, char __user *buf, size_t count, loff_t *ppos)
 {
        struct _stp_buffer *bptr;
@@ -335,29 +195,10 @@ static ssize_t _stp_ctl_read_cmd(struct file *file, char __user *buf, size_t cou
        return len;
 }
 
-static int _stp_sym_opens = 0;
-static int _stp_sym_open_cmd(struct inode *inode, struct file *file)
-{
-       /* only allow one reader */
-       if (_stp_sym_opens)
-               return -1;
-
-       _stp_sym_opens++;
-       return 0;
-}
-
-static int _stp_sym_close_cmd(struct inode *inode, struct file *file)
-{
-       if (_stp_sym_opens)
-               _stp_sym_opens--;
-       return 0;
-}
-
 static int _stp_ctl_open_cmd(struct inode *inode, struct file *file)
 {
        if (_stp_attached)
                return -1;
-
        _stp_attach();
        return 0;
 }
@@ -377,16 +218,7 @@ static struct file_operations _stp_ctl_fops_cmd = {
        .release = _stp_ctl_close_cmd,
 };
 
-static struct file_operations _stp_sym_fops_cmd = {
-       .owner = THIS_MODULE,
-       .read = _stp_sym_read_cmd,
-       .write = _stp_sym_write_cmd,
-       .open = _stp_sym_open_cmd,
-       .release = _stp_sym_close_cmd,
-};
-
 static struct dentry *_stp_cmd_file = NULL;
-static struct dentry *_stp_sym_file = NULL;
 
 static int _stp_register_ctl_channel(void)
 {
@@ -400,7 +232,6 @@ static int _stp_register_ctl_channel(void)
        }
 
        INIT_LIST_HEAD(&_stp_ctl_ready_q);
-       INIT_LIST_HEAD(&_stp_sym_ready_q);
 
        /* allocate buffers */
        _stp_pool_q = _stp_mempool_init(sizeof(struct _stp_buffer), STP_DEFAULT_BUFFERS);
@@ -415,15 +246,9 @@ static int _stp_register_ctl_channel(void)
        _stp_cmd_file->d_inode->i_uid = _stp_uid;
        _stp_cmd_file->d_inode->i_gid = _stp_gid;
 
-       /* create [debugfs]/systemtap/module_name/.symbols  */
-       _stp_sym_file = debugfs_create_file(".symbols", 0600, _stp_utt->dir, NULL, &_stp_sym_fops_cmd);
-       if (_stp_sym_file == NULL)
-               goto err0;
        return 0;
 
 err0:
-       if (_stp_cmd_file)
-               debugfs_remove(_stp_cmd_file);
        _stp_mempool_destroy(_stp_pool_q);
        errk("Error creating systemtap debugfs entries.\n");
        return -1;
@@ -432,16 +257,10 @@ err0:
 static void _stp_unregister_ctl_channel(void)
 {
        struct list_head *p, *tmp;
-       if (_stp_sym_file)
-               debugfs_remove(_stp_sym_file);
        if (_stp_cmd_file)
                debugfs_remove(_stp_cmd_file);
 
        /* Return memory to pool and free it. */
-       list_for_each_safe(p, tmp, &_stp_sym_ready_q) {
-               list_del(p);
-               _stp_mempool_free(p);
-       }
        list_for_each_safe(p, tmp, &_stp_ctl_ready_q) {
                list_del(p);
                _stp_mempool_free(p);
index 2afea1c90fdf6a959c856635b4137d4157dece49..750e1994a73456128e6f8459a811621edc003a89 100644 (file)
@@ -161,7 +161,7 @@ struct _stp_buffer {
        struct list_head list;
        int len;
        int type;
-       char buf[STP_BUFFER_SIZE];
+       char buf[STP_CTL_BUFFER_SIZE];
 };
 
 static DECLARE_WAIT_QUEUE_HEAD(_stp_ctl_wq);
index 8c453a553bba5be2a1682c953ed989e02a21cc1b..6406d6ad1380121a67a12644ce68f74dd210ccaf 100644 (file)
@@ -12,8 +12,8 @@
  * lib/sort.c of kernel 2.6.22-rc5. It was written by Matt Mackall.
  */
 
-#ifndef _SYMBOLS_C_
-#define _SYMBOLS_C_
+#ifndef _STP_SYMBOLS_C_
+#define _STP_SYMBOLS_C_
 #include "../sym.h"
 
 static char *_stp_symbol_data = NULL;
@@ -21,17 +21,12 @@ static int _stp_symbol_state = 0;
 static char *_stp_module_data = NULL;
 static int _stp_module_state = 0;
 
-
 /* these are all the symbol types we are interested in */
 static int _stp_sym_type_ok(int type)
 {
-       switch (type) {
-       case 'T':
-       case 't':
+       /* we only care about function symbols, which are in the text section */
+       if (type == 'T' || type == 't')
                return 1;
-       default:
-               return 0;
-       }
        return 0;
 }
 
@@ -41,10 +36,10 @@ static unsigned _stp_get_sym_sizes(struct module *m, unsigned *dsize)
 {
        unsigned int i;
        unsigned num = 0, datasize = 0;
-       for (i=0; i < m->num_symtab; i++) {
+       for (i = 0; i < m->num_symtab; i++) {
                char *str = (char *)(m->strtab + m->symtab[i].st_name);
                if (*str != '\0' && _stp_sym_type_ok(m->symtab[i].st_info)) {
-                       datasize += strlen(str)+1;
+                       datasize += strlen(str) + 1;
                        num++;
                }
        }
@@ -52,19 +47,23 @@ static unsigned _stp_get_sym_sizes(struct module *m, unsigned *dsize)
        return num;
 }
 
-/* allocate space for a module and symbols */
-static struct _stp_module * _stp_alloc_module(unsigned num, unsigned datasize, unsigned unwindsize)
+/* allocate space for a module, sections, and symbols */
+static struct _stp_module *_stp_alloc_module(unsigned sectsize, unsigned num, unsigned datasize)
 {
        struct _stp_module *mod = (struct _stp_module *)_stp_kzalloc(sizeof(struct _stp_module));
        if (mod == NULL)
                goto bad;
 
+       mod->sections = (struct _stp_symbol *)_stp_kmalloc(sectsize);
+       if (mod->sections == NULL)
+               goto bad;
+
        mod->symbols = (struct _stp_symbol *)_stp_kmalloc(num * sizeof(struct _stp_symbol));
        if (mod->symbols == NULL) {
                mod->symbols = (struct _stp_symbol *)_stp_vmalloc(num * sizeof(struct _stp_symbol));
                if (mod->symbols == NULL)
                        goto bad;
-               mod->allocated = 1;
+               mod->allocated.symbols = 1;
        }
 
        mod->symbol_data = _stp_kmalloc(datasize);
@@ -72,91 +71,63 @@ static struct _stp_module * _stp_alloc_module(unsigned num, unsigned datasize, u
                mod->symbol_data = _stp_vmalloc(datasize);
                if (mod->symbol_data == NULL)
                        goto bad;
-               mod->allocated |= 2;
+               mod->allocated.symbol_data = 1;
        }
 
-       mod->unwind_data = _stp_kmalloc(unwindsize);
-       if (mod->unwind_data == NULL) {
-               mod->unwind_data = _stp_vmalloc(unwindsize);
-               if (mod->unwind_data == NULL)
-                       goto bad;
-               mod->allocated |= 4;
-       }
-       
        mod->num_symbols = num;
        return mod;
 
 bad:
        if (mod) {
+               if (mod->sections)
+                       _stp_kfree(mod->sections);
                if (mod->symbols) {
-                       if (mod->allocated & 1)
+                       if (mod->allocated.symbols)
                                _stp_vfree(mod->symbols);
                        else
                                _stp_kfree(mod->symbols);
-                       mod->symbols = NULL;
                }
-               if (mod->symbol_data) {
-                       if (mod->allocated & 2)
-                               _stp_vfree(mod->symbol_data);
-                       else
-                               _stp_kfree(mod->symbol_data);
-                       mod->symbol_data = NULL;
-               }
-               _stp_kfree(mod); 
-               if (mod->symbols) {
-                       if (mod->allocated & 1)
-                               _stp_vfree(mod->symbols);
-                       else
-                               _stp_kfree(mod->symbols);
-                       mod->symbols = NULL;
-               }
-               _stp_kfree(mod); 
+               _stp_kfree(mod);
        }
        return NULL;
 }
 
-static struct _stp_module * _stp_alloc_module_from_module (struct module *m, uint32_t unwind_len)
-{
-       unsigned datasize, num = _stp_get_sym_sizes(m, &datasize);
-       return _stp_alloc_module(num, datasize, unwind_len);
-}
-
 static void _stp_free_module(struct _stp_module *mod)
 {
        /* The module write lock is held. Any prior readers of this */
        /* module's data will have read locks and need to finish before */
        /* the memory is freed. */
        write_lock(&mod->lock);
-       write_unlock(&mod->lock); /* there will be no more readers */
+       write_unlock(&mod->lock);       /* there will be no more readers */
 
-       /* free symbol memory */
-       if (mod->symbols) {
-               if (mod->allocated & 1)
-                       _stp_vfree(mod->symbols);
-               else
-                       _stp_kfree(mod->symbols);
-               mod->symbols = NULL;
-       }
+       /* Free symbol memory */
+       /* If symbol_data wasn't allocated, then symbols weren't either. */
        if (mod->symbol_data) {
-               if (mod->allocated & 2)
+               if (mod->symbols) {
+                       if (mod->allocated.symbols)
+                               _stp_vfree(mod->symbols);
+                       else
+                               _stp_kfree(mod->symbols);
+               }
+               if (mod->allocated.symbol_data)
                        _stp_vfree(mod->symbol_data);
                else
                        _stp_kfree(mod->symbol_data);
-               mod->symbol_data = NULL;
-
        }
        if (mod->unwind_data) {
-               if (mod->allocated & 4)
+               if (mod->allocated.unwind_data)
                        _stp_vfree(mod->unwind_data);
                else
                        _stp_kfree(mod->unwind_data);
-               mod->unwind_data = NULL;
-
        }
-       if (mod->sections) {
-               _stp_kfree(mod->sections);
-               mod->sections = NULL;
+       if (mod->unwind_hdr) {
+               if (mod->allocated.unwind_hdr)
+                       _stp_vfree(mod->unwind_hdr);
+               else
+                       _stp_kfree(mod->unwind_hdr);
        }
+       if (mod->sections)
+               _stp_kfree(mod->sections);
 
        /* free module memory */
        _stp_kfree(mod);
@@ -168,7 +139,7 @@ static void _stp_del_module(struct _stp_module *mod)
 {
        int i, num;
 
-       // kbug(DEBUG_SYMBOLS, "deleting %s\n", mod->name);
+       dbug_sym(1, "deleting module %s\n", mod->name);
 
        /* signal relocation code to clear its cache */
        _stp_module_relocate((char *)-1, NULL, 0);
@@ -181,15 +152,15 @@ static void _stp_del_module(struct _stp_module *mod)
        if (num >= _stp_num_modules)
                return;
 
-       for (i = num; i < _stp_num_modules-1; i++)
-               _stp_modules[i] = _stp_modules[i+1];
+       for (i = num; i < _stp_num_modules - 1; i++)
+               _stp_modules[i] = _stp_modules[i + 1];
 
        for (num = 0; num < _stp_num_modules; num++) {
                if (_stp_modules_by_addr[num] == mod)
                        break;
        }
-       for (i = num; i < _stp_num_modules-1; i++)
-               _stp_modules_by_addr[i] = _stp_modules_by_addr[i+1];
+       for (i = num; i < _stp_num_modules - 1; i++)
+               _stp_modules_by_addr[i] = _stp_modules_by_addr[i + 1];
 
        _stp_num_modules--;
 
@@ -197,10 +168,8 @@ static void _stp_del_module(struct _stp_module *mod)
 }
 
 static void _stp_free_modules(void)
-{      
+{
        int i;
-       unsigned long flags;
-
        /* This only happens when the systemtap module unloads */
        /* so there is no need for locks. */
        for (i = _stp_num_modules - 1; i >= 0; i--)
@@ -208,82 +177,120 @@ static void _stp_free_modules(void)
 }
 
 static unsigned long _stp_kallsyms_lookup_name(const char *name);
+static void _stp_create_unwind_hdr(struct _stp_module *m);
+
+extern unsigned _stp_num_kernel_symbols;
+extern struct _stp_symbol _stp_kernel_symbols[];
 
-/* process the KERNEL symbols */
-static int _stp_do_symbols(const char __user *buf, int count)
+/* initialize the kernel symbols */
+static int _stp_init_kernel_symbols(void)
 {
-       struct _stp_symbol *s;
-       unsigned datasize, num, unwindsize;     
+       _stp_modules[0] = (struct _stp_module *)_stp_kzalloc(sizeof(struct _stp_module));
+       if (_stp_modules[0] == NULL) {
+               errk("cannot allocate memory\n");
+               return -EFAULT;
+       }
+       _stp_modules[0]->symbols = _stp_kernel_symbols;
+       _stp_modules[0]->num_symbols = _stp_num_kernel_symbols;
+       rwlock_init(&_stp_modules[0]->lock);
+       _stp_num_modules = 1;
+
+       /* Note: this mapping is used by kernel/_stext pseudo-relocations. */
+       _stp_modules[0]->text = _stp_kallsyms_lookup_name("_stext");
+       _stp_modules[0]->data = _stp_kallsyms_lookup_name("_etext");
+       _stp_modules[0]->text_size = _stp_modules[0]->data - _stp_modules[0]->text;
+       _stp_modules_by_addr[0] = _stp_modules[0];
+       return 0;
+}
+
+static void _stp_do_unwind_data(const char __user *buf, size_t count)
+{
+       u64 unwind_len;
+       unsigned long flags;
+       char name[STP_MODULE_NAME_LEN];
        int i;
+       struct _stp_module *m;
 
-       switch (_stp_symbol_state) {
-       case 0:
-               if (count != sizeof(struct _stp_msg_symbol_hdr)) {
-                       errk("count=%d\n", count);
-                       return -EFAULT;
-               }               
-               if (get_user(num, (unsigned __user *)buf))
-                       return -EFAULT;
-               if (get_user(datasize, (unsigned __user *)(buf+4)))
-                       return -EFAULT;
-               if (get_user(unwindsize, (unsigned __user *)(buf+8)))
-                       return -EFAULT;
-               dbug(DEBUG_UNWIND, "num=%d datasize=%d unwindsize=%d\n", num, datasize, unwindsize);
-
-               _stp_modules[0] = _stp_alloc_module(num, datasize, unwindsize);
-               if (_stp_modules[0] == NULL) {
-                       errk("cannot allocate memory\n");
-                       return -EFAULT;
+       dbug_unwind(1, "got unwind data, count=%d\n", count);
+
+       if (count < STP_MODULE_NAME_LEN + sizeof(u64)) {
+               dbug_unwind(1, "unwind message too short\n");
+               return;
+       }
+       if (strncpy_from_user(name, buf, STP_MODULE_NAME_LEN) < 0) {
+               errk("userspace copy failed\n");
+               return;
+       }
+       dbug_unwind(1, "name=%s\n", name);
+       if (!strcmp(name,"*")) {
+               /* OK, all initial unwind data received. Ready to go. */
+               _stp_ctl_send(STP_TRANSPORT, NULL, 0);
+               return;
+       }
+       count -= STP_MODULE_NAME_LEN;
+       buf += STP_MODULE_NAME_LEN;
+
+       if (get_user(unwind_len, (u64 __user *)buf)) {
+               errk("userspace copy failed\n");
+               return;
+       }
+       count -= sizeof(u64);
+       buf += sizeof(u64);
+       if (count != unwind_len) {
+               dbug_unwind(1, "count=%d unwind_len=%d\n", (int)count, (int)unwind_len);
+               return;
+       }
+
+       STP_RLOCK_MODULES;
+       for (i = 0; i < _stp_num_modules; i++) {
+               if (strcmp(name, _stp_modules[i]->name) == 0)
+                       break;
+       }
+       if (unlikely(i == _stp_num_modules)) {
+               dbug_unwind(1, "module %s not found!\n", name);
+               STP_RUNLOCK_MODULES;
+               return;
+       }
+       m = _stp_modules[i];
+       write_lock(&m->lock);
+       STP_RUNLOCK_MODULES;
+
+       /* allocate space for unwind data */
+       m->unwind_data = _stp_kmalloc(count);
+       if (unlikely(m->unwind_data == NULL)) {
+               m->unwind_data = _stp_vmalloc(count);
+               if (m->unwind_data == NULL) {
+                       errk("kmalloc failed\n");
+                       goto done;
                }
-               rwlock_init(&_stp_modules[0]->lock);
-               _stp_symbol_state = 1;
-               break;
-       case 1:
-               dbug(DEBUG_SYMBOLS, "got stap_symbols, count=%d\n", count);
-               if (copy_from_user ((char *)_stp_modules[0]->symbols, buf, count))
-                       return -EFAULT;
-               _stp_symbol_state = 2;
-               break;
-       case 2:
-               dbug(DEBUG_SYMBOLS, "got symbol data, count=%d buf=%p\n", count, buf);
-               if (copy_from_user (_stp_modules[0]->symbol_data, buf, count))
-                       return -EFAULT;
-               _stp_num_modules = 1;
-               
-               s = _stp_modules[0]->symbols;
-               for (i = 0; i < _stp_modules[0]->num_symbols; i++) 
-                       s[i].symbol += (long)_stp_modules[0]->symbol_data;
-
-               _stp_symbol_state = 3;
-                /* NB: this mapping is used by kernel/_stext pseudo-relocations. */
-               _stp_modules[0]->text = _stp_kallsyms_lookup_name("_stext");
-               _stp_modules[0]->data = _stp_kallsyms_lookup_name("_etext");
-               _stp_modules[0]->text_size = _stp_modules[0]->data - _stp_modules[0]->text;             
-               _stp_modules_by_addr[0] = _stp_modules[0];
-               dbug(DEBUG_SYMBOLS, "Got kernel symbols. text=%p len=%u\n", 
-                    (int64_t)_stp_modules[0]->text, _stp_modules[0]->text_size);
-               break;
-       case 3:
-               dbug(DEBUG_UNWIND, "got unwind data, count=%d\n", count);
-               _stp_symbol_state = 4;
-               if (copy_from_user (_stp_modules[0]->unwind_data, buf, count)) {
-                       _dbug("cfu failed\n");
-                       return -EFAULT;
+               m->allocated.unwind_data = 1;
+       }
+
+       if (unlikely(copy_from_user(m->unwind_data, buf, count))) {
+               errk("userspace copy failed\n");
+               if (m->unwind_data) {
+                       if (m->allocated.unwind_data)
+                               _stp_vfree(m->unwind_data);
+                       else
+                               _stp_kfree(m->unwind_data);
+                       m->unwind_data = NULL;
                }
-               _stp_modules[0]->unwind_data_len = count;
-               break;
-       default:
-               errk("unexpected symbol data of size %d.\n", count);
+               goto done;
        }
-       return count;
+       m->unwind_data_len = count;
+       _stp_create_unwind_hdr(m);
+done:
+       write_unlock(&m->lock);
 }
 
 static int _stp_compare_addr(const void *p1, const void *p2)
 {
        struct _stp_symbol *s1 = (struct _stp_symbol *)p1;
        struct _stp_symbol *s2 = (struct _stp_symbol *)p2;
-       if (s1->addr == s2->addr) return 0;
-       if (s1->addr < s2->addr) return -1;
+       if (s1->addr == s2->addr)
+               return 0;
+       if (s1->addr < s2->addr)
+               return -1;
        return 1;
 }
 
@@ -332,18 +339,17 @@ static void generic_swap(void *a, void *b, int size)
  * it less suitable for kernel use.
 */
 void _stp_sort(void *base, size_t num, size_t size,
-       int (*cmp)(const void *, const void *),
-       void (*swap)(void *, void *, int size))
+              int (*cmp) (const void *, const void *), void (*swap) (void *, void *, int size))
 {
        /* pre-scale counters for performance */
-       int i = (num/2 - 1) * size, n = num * size, c, r;
+       int i = (num / 2 - 1) * size, n = num * size, c, r;
 
        if (!swap)
                swap = (size == 4 ? u32_swap : generic_swap);
 
        /* heapify */
-       for ( ; i >= 0; i -= size) {
-               for (r = i; r * 2 + size < n; r  = c) {
+       for (; i >= 0; i -= size) {
+               for (r = i; r * 2 + size < n; r = c) {
                        c = r * 2 + size;
                        if (c < n - size && cmp(base + c, base + c + size) < 0)
                                c += size;
@@ -367,65 +373,114 @@ void _stp_sort(void *base, size_t num, size_t size,
        }
 }
 
+/* filter out section names we don't care about */
+static int _stp_section_is_interesting(const char *name)
+{
+       int ret = 1;
+       if (!strncmp("__", name, 2)
+           || !strncmp(".note", name, 5)
+           || !strncmp(".gnu", name, 4)
+           || !strncmp(".mod", name, 4))
+               ret = 0;
+       return ret;
+}
+
 /* Create a new _stp_module and load the symbols */
-static struct _stp_module *_stp_load_module_symbols (struct _stp_module *imod, uint32_t unwind_len)
+static struct _stp_module *_stp_load_module_symbols(struct module *mod)
 {
-       unsigned i, num=0;
-       struct module *m = (struct module *)imod->module;
-       struct _stp_module *mod = NULL;
-       char *dataptr;
+       int i, num, overflow = 0;
+       struct module_sect_attrs *sa;
+       unsigned sect_size = 0, sect_num = 0, sym_size, sym_num;
+       struct _stp_module *sm;
+       char *dataptr, *endptr;
+
+       sa = mod->sect_attrs;
+       /* calculate how much space to allocate for section strings */
+       for (i = 0; i < sa->nsections; i++) {
+               if (_stp_section_is_interesting(sa->attrs[i].name)) {
+                       sect_num++;
+                       sect_size += strlen(sa->attrs[i].name) + 1;
+                       dbug_sym(2, "\t%s\t%lx\n", sa->attrs[i].name, sa->attrs[i].address);
+               }
+       }
+       sect_size += sect_num * sizeof(struct _stp_symbol);
+
+       /* and how much space for symbols */
+       sym_num = _stp_get_sym_sizes(mod, &sym_size);
 
-       if (m == NULL) {
-               kbug(DEBUG_SYMBOLS, "imod->module is NULL\n");
+       sm = _stp_alloc_module(sect_size, sym_num, sym_size);
+       if (!sm) {
+               errk("failed to allocate memory for module.\n");
                return NULL;
        }
-       if (try_module_get(m)) {
 
-               mod = _stp_alloc_module_from_module(m, unwind_len);
-               if (mod == NULL) {
-                       module_put(m);
-                       errk("failed to allocate memory for module.\n");
-                       return NULL;
-               }
+       strlcpy(sm->name, mod->name, STP_MODULE_NAME_LEN);
+       sm->module = (unsigned long)mod;
+       sm->text = (unsigned long)mod->module_core;
+       sm->text_size = mod->core_text_size;
+       sm->data = 0;           /* fixme */
+       sm->num_sections = sect_num;
+       rwlock_init(&sm->lock);
 
-               strlcpy(mod->name, imod->name, STP_MODULE_NAME_LEN);
-               mod->module = imod->module;
-               mod->text = imod->text;
-               mod->data = imod->data;
-               mod->num_sections = imod->num_sections;
-               mod->sections = imod->sections;
-               mod->text_size = m->core_text_size;
-               rwlock_init(&mod->lock);
-
-               /* now copy all the symbols we are interested in */
-               dataptr = mod->symbol_data;
-               for (i=0; i < m->num_symtab; i++) {
-                       char *str = (char *)(m->strtab + m->symtab[i].st_name);
-                       if (*str != '\0' && _stp_sym_type_ok(m->symtab[i].st_info)) {
-                               mod->symbols[num].symbol = dataptr;
-                               mod->symbols[num].addr = m->symtab[i].st_value;
-                               while (*str) *dataptr++ = *str++;
-                               *dataptr++ = 0;
-                               num++;
+       /* copy in section data */
+       dataptr = (char *)((long)sm->sections + sect_num * sizeof(struct _stp_symbol));
+       endptr = (char *)((long)sm->sections + sect_size);
+       num = 0;
+       for (i = 0; i < sa->nsections; i++) {
+               size_t len, maxlen;
+               if (_stp_section_is_interesting(sa->attrs[i].name)) {
+                       sm->sections[num].addr = sa->attrs[i].address;
+                       sm->sections[num].symbol = dataptr;
+                       maxlen = (size_t) (endptr - dataptr);
+                       len = strlcpy(dataptr, sa->attrs[i].name, maxlen);
+                       if (unlikely(len >= maxlen)) {
+                               _dbug("dataptr=%lx endptr=%lx len=%d maxlen=%d\n", dataptr, endptr, len, maxlen);
+                               overflow = 1;
                        }
+                       dataptr += len + 1;
+                       num++;
                }
-               module_put(m);
+       }
+       if (unlikely(overflow)) {
+               errk("Section names truncated!!! Should never happen!!\n");
+               *endptr = 0;
+               overflow = 0;
+       }
 
-               /* sort symbols by address */
-               _stp_sort (mod->symbols, num, sizeof(struct _stp_symbol), _stp_compare_addr, _stp_swap_symbol);
+       /* now copy all the symbols we are interested in */
+       dataptr = sm->symbol_data;
+       endptr = dataptr + sym_size - 1;
+       num = 0;
+       for (i = 0; i < mod->num_symtab; i++) {
+               char *str = (char *)(mod->strtab + mod->symtab[i].st_name);
+               if (*str != '\0' && _stp_sym_type_ok(mod->symtab[i].st_info)) {
+                       sm->symbols[num].symbol = dataptr;
+                       sm->symbols[num].addr = mod->symtab[i].st_value;
+                       while (*str && (dataptr < endptr))
+                               *dataptr++ = *str++;
+                       if (unlikely(*str))
+                               overflow = 1;
+                       *dataptr++ = 0;
+                       num++;
+               }
        }
-       return mod;
+       if (unlikely(overflow))
+               errk("Symbol names truncated!!! Should never happen!!\n");
+
+       /* sort symbols by address */
+       _stp_sort(sm->symbols, num, sizeof(struct _stp_symbol), _stp_compare_addr, _stp_swap_symbol);
+
+       return sm;
 }
 
-/* Remove any old module info from our database */
-static void _stp_module_exists_delete (struct _stp_module *mod)
+/* Remove any old module info from our database. */
+static void _stp_module_exists_delete(struct _stp_module *mod)
 {
        int i, num;
-
        /* remove any old modules with the same name */
        for (num = 1; num < _stp_num_modules; num++) {
                if (strcmp(_stp_modules[num]->name, mod->name) == 0) {
-                       dbug(DEBUG_SYMBOLS, "found existing module with name %s. Deleting.\n", mod->name);
+                       dbug_sym(1, "found existing module with name %s. Deleting.\n", mod->name);
                        _stp_del_module(_stp_modules[num]);
                        break;
                }
@@ -435,143 +490,61 @@ static void _stp_module_exists_delete (struct _stp_module *mod)
        for (num = 1; num < _stp_num_modules; num++) {
                if (mod->text + mod->text_size < _stp_modules_by_addr[num]->text)
                        continue;
-               if (mod->text < _stp_modules_by_addr[num]->text 
-                   + _stp_modules_by_addr[num]->text_size) {
-                       dbug(DEBUG_SYMBOLS, "New module %s overlaps with old module %s. Deleting old.\n", 
-                            mod->name, _stp_modules_by_addr[num]->name);
+               if (mod->text < _stp_modules_by_addr[num]->text + _stp_modules_by_addr[num]->text_size) {
+                       dbug_sym(1, "New module %s overlaps with old module %s. Deleting old.\n",
+                                mod->name, _stp_modules_by_addr[num]->name);
                        _stp_del_module(_stp_modules_by_addr[num]);
                }
        }
 
 }
 
-static int _stp_ins_module(struct _stp_module *mod)
+static void _stp_ins_module(struct module *mod)
 {
-       int i, num, res, ret = 0;
+       int i, num, res;
        unsigned long flags;
-
-       // kbug(DEBUG_SYMBOLS, "insert %s\n", mod->name);
+       struct _stp_module *m;
+       dbug_sym(1, "insert %s\n", mod->name);
+       m = _stp_load_module_symbols(mod);
+       if (m == NULL)
+               return;
 
        STP_WLOCK_MODULES;
-
-       _stp_module_exists_delete(mod);
-
+       _stp_module_exists_delete(m);
        /* check for overflow */
        if (_stp_num_modules == STP_MAX_MODULES) {
                errk("Exceeded the limit of %d modules\n", STP_MAX_MODULES);
-               ret = -ENOMEM;
                goto done;
        }
-       
+
        /* insert alphabetically in _stp_modules[] */
        for (num = 1; num < _stp_num_modules; num++)
-               if (strcmp(_stp_modules[num]->name, mod->name) > 0)
+               if (strcmp(_stp_modules[num]->name, m->name) > 0)
                        break;
        for (i = _stp_num_modules; i > num; i--)
-               _stp_modules[i] = _stp_modules[i-1];
-       _stp_modules[num] = mod;
-
+               _stp_modules[i] = _stp_modules[i - 1];
+       _stp_modules[num] = m;
        /* insert by text address in _stp_modules_by_addr[] */
        for (num = 1; num < _stp_num_modules; num++)
-               if (mod->text < _stp_modules_by_addr[num]->text)
+               if (m->text < _stp_modules_by_addr[num]->text)
                        break;
        for (i = _stp_num_modules; i > num; i--)
-               _stp_modules_by_addr[i] = _stp_modules_by_addr[i-1];
-       _stp_modules_by_addr[num] = mod;
-       
+               _stp_modules_by_addr[i] = _stp_modules_by_addr[i - 1];
+       _stp_modules_by_addr[num] = m;
        _stp_num_modules++;
-
 done:
        STP_WUNLOCK_MODULES;
-       return ret;
+       return;
 }
 
-
-/* Called from procfs.c when a STP_MODULE msg is received */
-static int _stp_do_module(const char __user *buf, int count)
-{
-       struct _stp_msg_module tmpmod;
-       struct _stp_module mod, *m;
-       unsigned i, section_len;
-
-       if (count < (int)sizeof(tmpmod)) {
-               errk("expected %d and got %d\n", (int)sizeof(tmpmod), count);
-               return -EFAULT;
-       }
-       if (copy_from_user ((char *)&tmpmod, buf, sizeof(tmpmod)))
-               return -EFAULT;
-
-       section_len = count - sizeof(tmpmod) - tmpmod.unwind_len;
-       if (section_len <= 0) {
-               errk("section_len = %d\n", section_len);
-               return -EFAULT;
-       }
-       dbug(DEBUG_SYMBOLS, "Got module %s, count=%d section_len=%d unwind_len=%d\n", 
-            tmpmod.name, count, section_len, tmpmod.unwind_len);
-
-       strcpy(mod.name, tmpmod.name);
-       mod.module = tmpmod.module;
-       mod.text = tmpmod.text;
-       mod.data = tmpmod.data;
-       mod.num_sections = tmpmod.num_sections;
-       
-       /* copy in section data */
-       mod.sections = _stp_kmalloc(section_len);
-       if (mod.sections == NULL) {
-               errk("unable to allocate memory.\n");
-               return -EFAULT;
-       }
-       if (copy_from_user ((char *)mod.sections, buf+sizeof(tmpmod), section_len)) {
-               _stp_kfree(mod.sections);
-               return -EFAULT;
-       }
-       for (i = 0; i < mod.num_sections; i++) {
-               mod.sections[i].symbol =  
-                       (char *)((long)mod.sections[i].symbol 
-                                + (long)((long)mod.sections + mod.num_sections * sizeof(struct _stp_symbol)));
-       }
-
-       #if 0
-       for (i = 0; i < mod.num_sections; i++)
-               _dbug("section %d (stored at %p): %s %lx\n", i, &mod.sections[i], mod.sections[i].symbol, mod.sections[i].addr);
-       #endif
-
-       /* load symbols from tmpmod.module to mod */
-       m = _stp_load_module_symbols(&mod, tmpmod.unwind_len); 
-       if (m == NULL) {
-               _stp_kfree(mod.sections);
-               return 0;
-       }
-
-       dbug(DEBUG_SYMBOLS, "module %s loaded.  Text=%p text_size=%u\n", m->name, (int64_t)m->text, m->text_size);
-       /* finally copy unwind info */
-       if (copy_from_user (m->unwind_data, buf+sizeof(tmpmod)+section_len, tmpmod.unwind_len)) {
-               _stp_free_module(m);
-               _stp_kfree(mod.sections);
-               return -EFAULT;
-       }
-       m->unwind_data_len = tmpmod.unwind_len;
-
-       if (_stp_ins_module(m) < 0) {
-               _stp_free_module(m);
-               return -ENOMEM;
-       }
-       
-       return count;
-}
-
-static int _stp_ctl_send (int type, void *data, int len);
-
-static int _stp_module_load_notify(struct notifier_block * self, unsigned long val, void * data)
+static int _stp_module_load_notify(struct notifier_block *self, unsigned long val, void *data)
 {
        struct module *mod = (struct module *)data;
        struct _stp_module rmod;
-
        switch (val) {
        case MODULE_STATE_COMING:
-               dbug(DEBUG_SYMBOLS, "module %s load notify\n", mod->name);
-               strlcpy(rmod.name, mod->name, STP_MODULE_NAME_LEN);
-               _stp_ctl_send(STP_MODULE, &rmod, sizeof(struct _stp_module));
+               dbug_sym(1, "module %s load notify\n", mod->name);
+               _stp_ins_module(mod);
                break;
        default:
                errk("module loaded? val=%ld\n", val);
@@ -583,4 +556,63 @@ static struct notifier_block _stp_module_load_nb = {
        .notifier_call = _stp_module_load_notify,
 };
 
-#endif /* _SYMBOLS_C_ */
+#include <linux/seq_file.h>
+extern unsigned long _stp_modules_op;  /* from stap */
+static int _stp_init_modules(void)
+{
+       loff_t pos = 0;
+       void *res;
+       struct module *mod;
+
+       const struct seq_operations *modules_op = (const struct seq_operations *)_stp_modules_op;
+       /* Use the seq_file interface to safely get a list of installed modules */
+       res = modules_op->start(NULL, &pos);
+       while (res) {
+               mod = list_entry(res, struct module, list);
+               _stp_ins_module(mod);
+               res = modules_op->next(NULL, res, &pos);
+       }
+
+       if (register_module_notifier(&_stp_module_load_nb))
+               errk("failed to load module notifier\n");
+
+       /* unlocks the list */
+       modules_op->stop(NULL, NULL);
+
+#ifndef CONFIG_FRAME_POINTER
+       /* now that we have all the modules, ask for their unwind info */
+       {
+               unsigned long flags;
+               int i, left = STP_CTL_BUFFER_SIZE;
+               char buf[STP_CTL_BUFFER_SIZE];
+               char *ptr = buf;
+               *ptr = 0;
+
+               STP_RLOCK_MODULES;
+               /* Loop through modules, sending module names packed into */
+               /* messages of size STP_CTL_BUFFER. */
+               for (i = 0; i < _stp_num_modules; i++) {
+                       char *name = _stp_modules[i]->name;
+                       int len = strlen(name);
+                       if (len >= left) {
+                               _stp_ctl_send(STP_UNWIND, buf, sizeof(buf) - left);
+                               ptr = buf;
+                               left = STP_CTL_BUFFER_SIZE;
+                       }
+                       strlcpy(ptr, name, left);
+                       ptr += len + 1;
+                       left -= len + 1;
+               }
+               STP_RUNLOCK_MODULES;
+
+               /* Send terminator.  When we get this back from stapio */
+               /* that means all the unwind info has been sent. */
+               strlcpy(ptr, "*", left);
+               left -= 2;
+               _stp_ctl_send(STP_UNWIND, buf, sizeof(buf) - left);
+       }
+#endif
+       return 0;
+}
+
+#endif /* _STP_SYMBOLS_C_ */
index 8335e44b3dd88866cb0e98406ecf55aa3429a7ff..aa96a50e6a01d6768ed3033c4925f137b160830e 100644 (file)
 #include "../procfs.c"
 
 static struct utt_trace *_stp_utt = NULL;
-
+static unsigned int utt_seq = 1;
+static int _stp_probes_started = 0;
+pid_t _stp_target = 0;
+static int _stp_exit_called = 0;
+int _stp_exit_flag = 0;
 #ifdef STP_OLD_TRANSPORT
 #include "relayfs.c"
+#include "procfs.c"
 #else
 #include "utt.c"
+#include "control.c"
 #endif
 
-static unsigned int utt_seq = 1;
-
-static int _stp_probes_started = 0;
-
 /* module parameters */
 static int _stp_bufsize;
 module_param(_stp_bufsize, int, 0);
 MODULE_PARM_DESC(_stp_bufsize, "buffer size");
 
-pid_t _stp_target = 0;
-static int _stp_exit_called = 0;
-int _stp_exit_flag = 0;
-
 /* forward declarations */
 void probe_exit(void);
 int probe_start(void);
 void _stp_exit(void);
-void _stp_handle_start (struct _stp_msg_start *st);
-static void _stp_detach(void);
-static void _stp_attach(void);
 
 /* check for new workqueue API */
-#ifdef DECLARE_DELAYED_WORK 
-static void _stp_work_queue (struct work_struct *data);
+#ifdef DECLARE_DELAYED_WORK
+static void _stp_work_queue(struct work_struct *data);
 static DECLARE_DELAYED_WORK(_stp_work, _stp_work_queue);
 #else
-static void _stp_work_queue (void *data);
+static void _stp_work_queue(void *data);
 static DECLARE_WORK(_stp_work, _stp_work_queue, NULL);
 #endif
 
 static struct workqueue_struct *_stp_wq;
-static void _stp_ask_for_symbols(void);
-
-#ifdef STP_OLD_TRANSPORT
-#include "procfs.c"
-#else
-#include "control.c"
-#endif
-
-static void _stp_ask_for_symbols(void)
-{
-       struct _stp_msg_symbol req;
-       struct _stp_module mod;
-       static int sent_symbols = 0;
-
-       if (sent_symbols == 0) {
-               /* ask for symbols and modules */
-               kbug(DEBUG_SYMBOLS|DEBUG_TRANSPORT, "AFS\n");
-               
-               req.endian = 0x1234;
-               req.ptr_size = sizeof(char *);
-               _stp_ctl_send(STP_SYMBOLS, &req, sizeof(req));
-               
-               strcpy(mod.name, "");
-               _stp_ctl_send(STP_MODULE, &mod, sizeof(mod));
-               sent_symbols = 1;
-       }
-}
 
 /*
  *     _stp_handle_start - handle STP_START
  */
 
-void _stp_handle_start (struct _stp_msg_start *st)
+void _stp_handle_start(struct _stp_msg_start *st)
 {
-       kbug (DEBUG_TRANSPORT, "stp_handle_start\n");
-
-       if (register_module_notifier(&_stp_module_load_nb))
-               errk("failed to load module notifier\n");
-
+       dbug_trans(1, "stp_handle_start\n");
        _stp_target = st->target;
        st->res = probe_start();
        if (st->res >= 0)
@@ -108,16 +72,15 @@ void _stp_handle_start (struct _stp_msg_start *st)
        _stp_ctl_send(STP_START, st, sizeof(*st));
 }
 
-
 /* common cleanup code. */
 /* This is called from the kernel thread when an exit was requested */
 /* by staprun or the exit() function. It is also called by transport_close() */
 /* when the module  is removed. In that case "dont_rmmod" is set to 1. */
 /* We need to call it both times because we want to clean up properly */
 /* when someone does /sbin/rmmod on a loaded systemtap module. */
-static void _stp_cleanup_and_exit (int dont_rmmod)
+static void _stp_cleanup_and_exit(int dont_rmmod)
 {
-       kbug(DEBUG_TRANSPORT, "cleanup_and_exit (%d)\n", dont_rmmod);
+       dbug_trans(1, "cleanup_and_exit (%d)\n", dont_rmmod);
        if (!_stp_exit_called) {
                int failures;
 
@@ -128,23 +91,24 @@ static void _stp_cleanup_and_exit (int dont_rmmod)
                _stp_exit_called = 1;
 
                if (_stp_probes_started) {
-                       kbug(DEBUG_TRANSPORT, "calling probe_exit\n");
+                       dbug_trans(1, "calling probe_exit\n");
                        /* tell the stap-generated code to unload its probes, etc */
                        probe_exit();
-                       kbug(DEBUG_TRANSPORT, "done with probe_exit\n");
+                       dbug_trans(1, "done with probe_exit\n");
                }
 
                failures = atomic_read(&_stp_transport_failures);
                if (failures)
-                       _stp_warn ("There were %d transport failures.\n", failures);
+                       _stp_warn("There were %d transport failures.\n", failures);
 
-               kbug(DEBUG_TRANSPORT, "************** calling startstop 0 *************\n");
-               if (_stp_utt) utt_trace_startstop(_stp_utt, 0, &utt_seq);
+               dbug_trans(1, "************** calling startstop 0 *************\n");
+               if (_stp_utt)
+                       utt_trace_startstop(_stp_utt, 0, &utt_seq);
 
-               kbug(DEBUG_TRANSPORT, "ctl_send STP_EXIT\n");
+               dbug_trans(1, "ctl_send STP_EXIT\n");
                /* tell staprun to exit (if it is still there) */
                _stp_ctl_send(STP_EXIT, &dont_rmmod, sizeof(int));
-               kbug(DEBUG_TRANSPORT, "done with ctl_send STP_EXIT\n");
+               dbug_trans(1, "done with ctl_send STP_EXIT\n");
        }
 }
 
@@ -153,7 +117,7 @@ static void _stp_cleanup_and_exit (int dont_rmmod)
  */
 static void _stp_detach(void)
 {
-       kbug(DEBUG_TRANSPORT, "detach\n");
+       dbug_trans(1, "detach\n");
        _stp_attached = 0;
        _stp_pid = 0;
 
@@ -169,10 +133,10 @@ static void _stp_detach(void)
  */
 static void _stp_attach(void)
 {
-       kbug(DEBUG_TRANSPORT, "attach\n");
+       dbug_trans(1, "attach\n");
        _stp_attached = 1;
        _stp_pid = current->pid;
-               utt_set_overwrite(0);
+       utt_set_overwrite(0);
        queue_delayed_work(_stp_wq, &_stp_work, STP_WORK_TIMER);
 }
 
@@ -180,10 +144,10 @@ static void _stp_attach(void)
  *     _stp_work_queue - periodically check for IO or exit
  *     This is run by a kernel thread and may sleep.
  */
-#ifdef DECLARE_DELAYED_WORK 
-static void _stp_work_queue (struct work_struct *data)
+#ifdef DECLARE_DELAYED_WORK
+static void _stp_work_queue(struct work_struct *data)
 #else
-static void _stp_work_queue (void *data)
+static void _stp_work_queue(void *data)
 #endif
 {
        int do_io = 0;
@@ -211,19 +175,19 @@ static void _stp_work_queue (void *data)
  */
 void _stp_transport_close()
 {
-       kbug(DEBUG_TRANSPORT, "%d: ************** transport_close *************\n", current->pid);
+       dbug_trans(1, "%d: ************** transport_close *************\n", current->pid);
        _stp_cleanup_and_exit(1);
        destroy_workqueue(_stp_wq);
        _stp_unregister_ctl_channel();
-       if (_stp_utt) utt_trace_remove(_stp_utt);
+       if (_stp_utt)
+               utt_trace_remove(_stp_utt);
        _stp_free_modules();
        _stp_kill_time();
-       _stp_print_cleanup();   /* free print buffers */
+       _stp_print_cleanup();   /* free print buffers */
        _stp_mem_debug_done();
-       kbug(DEBUG_TRANSPORT, "---- CLOSED ----\n");
+       dbug_trans(1, "---- CLOSED ----\n");
 }
 
-
 static struct utt_trace *_stp_utt_open(void)
 {
        struct utt_trace_setup utts;
@@ -249,22 +213,22 @@ int _stp_transport_init(void)
 {
        int ret;
 
-       kbug(DEBUG_TRANSPORT, "transport_init\n");
+       dbug_trans(1, "transport_init\n");
        _stp_init_pid = current->pid;
        _stp_uid = current->uid;
        _stp_gid = current->gid;
 
 #ifdef RELAY_GUEST
-        /* Guest scripts use relay only for reporting warnings and errors */
-        _stp_subbuf_size = 65536;
-        _stp_nsubbufs = 2;
+       /* Guest scripts use relay only for reporting warnings and errors */
+       _stp_subbuf_size = 65536;
+       _stp_nsubbufs = 2;
 #endif
 
        if (_stp_bufsize) {
                unsigned size = _stp_bufsize * 1024 * 1024;
                _stp_subbuf_size = ((size >> 2) + 1) * 65536;
                _stp_nsubbufs = size / _stp_subbuf_size;
-               kbug(DEBUG_TRANSPORT, "Using %d subbufs of size %d\n", _stp_nsubbufs, _stp_subbuf_size);
+               dbug_trans(1, "Using %d subbufs of size %d\n", _stp_nsubbufs, _stp_subbuf_size);
        }
 
        /* initialize timer code */
@@ -286,41 +250,57 @@ int _stp_transport_init(void)
        if (_stp_print_init() < 0)
                goto err2;
 
+       /* start transport */
        utt_trace_startstop(_stp_utt, 1, &utt_seq);
 
        /* create workqueue of kernel threads */
        _stp_wq = create_workqueue("systemtap");
        if (!_stp_wq)
                goto err3;
+       
+       _stp_transport_state = 1;
+       
+       dbug_trans(1, "calling init_kernel_symbols\n");
+       if (_stp_init_kernel_symbols() < 0)
+               goto err4;
+       
+       dbug_trans(1, "calling init_modules\n");
+       if (_stp_init_modules() < 0)
+               goto err4;
+
        return 0;
 
+err4:
+       errk("failed to initialize modules\n");
+       _stp_free_modules();
+       destroy_workqueue(_stp_wq);
 err3:
        _stp_print_cleanup();
 err2:
        _stp_unregister_ctl_channel();
 err1:
-       if (_stp_utt) utt_trace_remove(_stp_utt);       
+       if (_stp_utt)
+               utt_trace_remove(_stp_utt);
 err0:
        _stp_kill_time();
        return -1;
 }
 
-
 static inline void _stp_lock_inode(struct inode *inode)
 {
 #ifdef DEFINE_MUTEX
-        mutex_lock(&inode->i_mutex);
+       mutex_lock(&inode->i_mutex);
 #else
-        down(&inode->i_sem);
+       down(&inode->i_sem);
 #endif
 }
 
 static inline void _stp_unlock_inode(struct inode *inode)
 {
 #ifdef DEFINE_MUTEX
-        mutex_unlock(&inode->i_mutex);
+       mutex_unlock(&inode->i_mutex);
 #else
-        up(&inode->i_sem);
+       up(&inode->i_sem);
 #endif
 }
 
@@ -358,7 +338,8 @@ static void _stp_unlock_debugfs(void)
 /* utt.c and relayfs.c. Will not be necessary if utt is included */
 /* in the kernel. */
 
-static struct dentry *_stp_get_root_dir(const char *name) {
+static struct dentry *_stp_get_root_dir(const char *name)
+{
        struct file_system_type *fs;
        struct dentry *root;
        struct super_block *sb;
@@ -377,7 +358,6 @@ static struct dentry *_stp_get_root_dir(const char *name) {
                errk("Couldn't lock transport directory.\n");
                return NULL;
        }
-
 #ifdef STP_OLD_TRANSPORT
        root = relayfs_create_dir(name, NULL);
 #else
@@ -389,12 +369,12 @@ static struct dentry *_stp_get_root_dir(const char *name) {
                _stp_lock_inode(sb->s_root->d_inode);
                root = lookup_one_len(name, sb->s_root, strlen(name));
                _stp_unlock_inode(sb->s_root->d_inode);
-               kbug(DEBUG_TRANSPORT, "root=%p\n", root);
+               errk("ERROR: root=%p\n", root);
                if (!IS_ERR(root))
                        dput(root);
                else {
                        root = NULL;
-                       kbug(DEBUG_TRANSPORT, "Could not create or find transport directory.\n");
+                       errk("Could not create or find transport directory.\n");
                }
        }
        _stp_unlock_debugfs();
index 6dc00d2b4d858e9411ee0e08a8c166678cd19745..dc4999612cc95fa73950ac73d7ab13bb340b1ffa 100644 (file)
@@ -7,21 +7,37 @@
 
 #include "transport_msgs.h"
 
-void _stp_warn (const char *fmt, ...);
-
+/* The size of print buffers. This limits the maximum */
+/* amount of data a print can send. */
 #define STP_BUFFER_SIZE 8192
 
+/* STP_CTL_BUFFER_SIZE is the maximum size of a message */
+/* exchanged on the control channel. */
+#ifdef STP_OLD_TRANSPORT
+/* Old transport sends print output on control channel */
+#define STP_CTL_BUFFER_SIZE STP_BUFFER_SIZE
+#else
+#define STP_CTL_BUFFER_SIZE 256
+#endif
+
 /* how often the work queue wakes up and checks buffers */
 #define STP_WORK_TIMER (HZ/100)
 
 static unsigned _stp_nsubbufs = 8;
 static unsigned _stp_subbuf_size = 65536*4;
+
+void _stp_warn (const char *fmt, ...);
 extern void _stp_transport_close(void);
 extern int _stp_print_init(void);
 extern void _stp_print_cleanup(void);
 static struct dentry *_stp_get_root_dir(const char *name);
 static int _stp_lock_debugfs(void);
 static void _stp_unlock_debugfs(void);
+static int _stp_ctl_send(int type, void *data, int len);
+static void _stp_attach(void);
+static void _stp_detach(void);
+void _stp_handle_start(struct _stp_msg_start *st);
+
 int _stp_pid = 0;
 uid_t _stp_uid = 0;
 gid_t _stp_gid = 0;
index 55de2d4ac58ef1300b21f993b44797dea2f149cf..0e65b63acb347284f8c1172a49c84f5bd1c27259 100644 (file)
@@ -23,8 +23,7 @@ enum
         STP_EXIT,
        STP_OOB_DATA,
        STP_SYSTEM,
-       STP_SYMBOLS,
-       STP_MODULE,
+       STP_UNWIND,
        STP_TRANSPORT,
        STP_CONNECT,
        STP_DISCONNECT,
@@ -36,18 +35,16 @@ enum
        STP_SUBBUFS_CONSUMED,
        STP_REALTIME_DATA,
 #endif
-
        STP_MAX_CMD
 };
 
-#ifdef DEBUG_TRANSPORT
+#ifdef DEBUG_TRANS
 static const char *_stp_command_name[] = {
        "STP_START",
        "STP_EXIT",
        "STP_OOB_DATA",
        "STP_SYSTEM",
-       "STP_SYMBOLS",
-       "STP_MODULE",
+       "STP_UNWIND",
        "STP_TRANSPORT",
        "STP_CONNECT",
        "STP_DISCONNECT",
@@ -59,68 +56,34 @@ static const char *_stp_command_name[] = {
        "STP_REALTIME_DATA",
 #endif
 };
-#endif /* DEBUG_TRANSPORT */
+#endif /* DEBUG_TRANS */
 
 /* control channel messages */
 
-/* command to execute: sent to staprun */
+/* command to execute: module->stapio */
 struct _stp_msg_cmd
 {
        char cmd[128];
 };
 
-/* request for symbol data. sent to staprun */
-struct _stp_msg_symbol
+/* Unwind data. stapio->module */
+struct _stp_msg_unwind
 {
-       int32_t endian;
-       int32_t ptr_size;
+       /* the module name, or "*" for all */
+       char name[STP_MODULE_NAME_LEN];
+       /* length of unwind data */
+       uint64_t unwind_len;
+       /* data ...*/
 };
 
 /* Request to start probes. */
-/* Sent from staprun. Then returned from module. */
+/* stapio->module->stapio */
 struct _stp_msg_start
 {
        pid_t target;
         int32_t res;    // for reply: result of probe_start()
 };
 
-struct _stp_symbol32
-{
-       uint32_t addr;
-       uint32_t symbol;
-};
-
-struct _stp_symbol64
-{
-       uint64_t addr;
-       uint64_t symbol;
-};
-
-struct _stp_msg_symbol_hdr
-{
-       uint32_t num_syms;
-       uint32_t sym_size;
-       uint32_t unwind_size;
-};
-
-struct _stp_msg_module {
-       /* the module name, or "" for kernel */
-       char name[STP_MODULE_NAME_LEN];
-       
-       /* A pointer to the struct module */
-       uint64_t module;
-
-       /* the start of the module's text and data sections */
-       uint64_t text;
-       uint64_t data;
-       
-       /* how many sections this module has */
-       uint32_t num_sections;
-
-       /* length of unwind data */
-       uint32_t unwind_len;
-};
-
 #ifdef STP_OLD_TRANSPORT
 /**** for compatibility with old relayfs ****/
 struct _stp_buf_info
diff --git a/runtime/unwind.c b/runtime/unwind.c
new file mode 100644 (file)
index 0000000..9a5d61e
--- /dev/null
@@ -0,0 +1,895 @@
+/*
+ * Copyright (C) 2002-2006 Novell, Inc.
+ *     Jan Beulich <jbeulich@novell.com>
+ * This code is released under version 2 of the GNU GPL.
+ *
+ * A simple API for unwinding kernel stacks.  This is used for
+ * debugging and error reporting purposes.  The kernel doesn't need
+ * full-blown stack unwinding with all the bells and whistles, so there
+ * is not much point in implementing the full Dwarf2 unwind API.
+ */
+
+#include "unwind/unwind.h"
+
+struct eh_frame_hdr_table_entry {
+       unsigned long start, fde;
+};
+
+static int cmp_eh_frame_hdr_table_entries(const void *p1, const void *p2)
+{
+       const struct eh_frame_hdr_table_entry *e1 = p1;
+       const struct eh_frame_hdr_table_entry *e2 = p2;
+       return (e1->start > e2->start) - (e1->start < e2->start);
+}
+
+static void swap_eh_frame_hdr_table_entries(void *p1, void *p2, int size)
+{
+       struct eh_frame_hdr_table_entry *e1 = p1;
+       struct eh_frame_hdr_table_entry *e2 = p2;
+       unsigned long v;
+
+       v = e1->start;
+       e1->start = e2->start;
+       e2->start = v;
+       v = e1->fde;
+       e1->fde = e2->fde;
+       e2->fde = v;
+}
+
+/* Build a binary-searchable unwind header.  Also do some
+ * validity checks. In the future we might use */
+/* .eh_frame_hdr if it is already present. */
+static void _stp_create_unwind_hdr(struct _stp_module *m)
+{
+       const u8 *ptr;
+       unsigned long tableSize, hdrSize, last;
+       unsigned n = 0;
+       const u32 *fde;
+       int bad_order = 0;
+       struct {
+               u8 version;
+               u8 eh_frame_ptr_enc;
+               u8 fde_count_enc;
+               u8 table_enc;
+               unsigned long eh_frame_ptr;
+               unsigned int fde_count;
+               struct eh_frame_hdr_table_entry table[];
+       } __attribute__ ((__packed__)) * header = NULL;
+
+       /* already did this or no data? */
+       if (m->unwind_hdr || m->unwind_data_len == 0)
+               return;
+
+       tableSize = m->unwind_data_len;
+       if (tableSize & (sizeof(*fde) - 1)) {
+               dbug_unwind(1, "tableSize=0x%x not a multiple of 0x%x\n", (int)tableSize, (int)sizeof(*fde));
+               goto bad;
+       }
+
+       /* count the FDEs */
+       for (fde = m->unwind_data;
+            tableSize > sizeof(*fde) && tableSize - sizeof(*fde) >= *fde;
+            tableSize -= sizeof(*fde) + *fde, fde += 1 + *fde / sizeof(*fde)) {
+               signed ptrType;
+               const u32 *cie;
+
+               /* check for extended length */
+               if ((*fde & 0xfffffff0) == 0xfffffff0) {
+                       dbug_unwind(1, "Module %s has extended-length CIE or FDE.");
+                       dbug_unwind(1, "This is not supported at this time.");
+                       goto bad;
+               }
+               cie = cie_for_fde(fde, m);
+               if (cie == &not_fde)
+                       continue;       /* fde was a CIE. That's OK, just skip it. */
+               if (cie == NULL || cie == &bad_cie || (ptrType = fde_pointer_type(cie)) < 0)
+                       goto bad;
+               /* we have a real FDE */
+               ptr = (const u8 *)(fde + 2);
+               if (!read_pointer(&ptr, (const u8 *)(fde + 1) + *fde, ptrType))
+                       goto bad;
+               ++n;
+       }
+
+       if (tableSize || !n) {
+               dbug_unwind(1, "%s: tableSize=%ld, n=%d\n", m->name, tableSize, n);
+               goto bad;
+       }
+
+       hdrSize = 4 + sizeof(unsigned long) + sizeof(unsigned int) + 2 * n * sizeof(unsigned long);
+       header = _stp_kmalloc(hdrSize);
+       if (header == NULL) {
+               header = _stp_vmalloc(hdrSize);
+               if (header == NULL)
+                       return;
+               m->allocated.unwind_hdr = 1;
+       }
+
+       header->version = 1;
+       header->eh_frame_ptr_enc = DW_EH_PE_absptr;
+       header->fde_count_enc = DW_EH_PE_data4;
+       header->table_enc = DW_EH_PE_absptr;
+       _stp_put_unaligned((unsigned long)m->unwind_data, &header->eh_frame_ptr);
+
+       BUILD_BUG_ON(offsetof(typeof(*header), fde_count)
+                    % __alignof(typeof(header->fde_count)));
+       header->fde_count = n;
+
+       BUILD_BUG_ON(offsetof(typeof(*header), table) % __alignof(typeof(*header->table)));
+
+       n = 0;
+       last = 0;
+       tableSize = m->unwind_data_len;
+       for (fde = m->unwind_data; tableSize; tableSize -= sizeof(*fde) + *fde, fde += 1 + *fde / sizeof(*fde)) {
+               const u32 *cie = cie_for_fde(fde, m);
+               if (cie == &not_fde)
+                       continue;
+               if (cie == NULL || cie == &bad_cie)
+                       goto bad;
+               /* we have a real FDE */
+               ptr = (const u8 *)(fde + 2);
+               header->table[n].start = read_pointer(&ptr, (const u8 *)(fde + 1) + *fde, fde_pointer_type(cie));
+               header->table[n].fde = (unsigned long)fde;
+               if (header->table[n].start < last)
+                       bad_order++;
+               last = header->table[n].start;
+               ++n;
+       }
+       WARN_ON(n != header->fde_count);
+
+       /* Is sort ever necessary? */
+       if (bad_order)
+               _stp_sort(header->table, n, sizeof(*header->table), cmp_eh_frame_hdr_table_entries,
+                         swap_eh_frame_hdr_table_entries);
+
+       m->unwind_hdr_len = hdrSize;
+       m->unwind_hdr = header;
+       return;
+
+       /* unwind data is not acceptable. free it and return */
+bad:
+       dbug_unwind(1, "unwind data for %s is unacceptable. Freeing.", m->name);
+       if (header) {
+               if (m->allocated.unwind_hdr) {
+                       m->allocated.unwind_hdr = 0;
+                       _stp_vfree(header);
+               } else
+                       _stp_kfree(header);
+       }
+       if (m->unwind_data) {
+               if (m->allocated.unwind_data)
+                       _stp_vfree(m->unwind_data);
+               else
+                       _stp_kfree(m->unwind_data);
+               m->unwind_data = NULL;
+               m->unwind_data_len = 0;
+       }
+       return;
+}
+
+static uleb128_t get_uleb128(const u8 **pcur, const u8 *end)
+{
+       const u8 *cur = *pcur;
+       uleb128_t value = 0;
+       unsigned shift;
+
+       for (shift = 0; cur < end; shift += 7) {
+               if (shift + 7 > 8 * sizeof(value)
+                   && (*cur & 0x7fU) >= (1U << (8 * sizeof(value) - shift))) {
+                       cur = end + 1;
+                       break;
+               }
+               value |= (uleb128_t)(*cur & 0x7f) << shift;
+               if (!(*cur++ & 0x80))
+                       break;
+       }
+       *pcur = cur;
+
+       return value;
+}
+
+static sleb128_t get_sleb128(const u8 **pcur, const u8 *end)
+{
+       const u8 *cur = *pcur;
+       sleb128_t value = 0;
+       unsigned shift;
+
+       for (shift = 0; cur < end; shift += 7) {
+               if (shift + 7 > 8 * sizeof(value)
+                   && (*cur & 0x7fU) >= (1U << (8 * sizeof(value) - shift))) {
+                       cur = end + 1;
+                       break;
+               }
+               value |= (sleb128_t)(*cur & 0x7f) << shift;
+               if (!(*cur & 0x80)) {
+                       value |= -(*cur++ & 0x40) << shift;
+                       break;
+               }
+       }
+       *pcur = cur;
+
+       return value;
+}
+
+/* given an FDE, find its CIE */
+static const u32 *cie_for_fde(const u32 *fde, const struct _stp_module *m)
+{
+       const u32 *cie;
+
+       /* check that length is proper */
+       if (!*fde || (*fde & (sizeof(*fde) - 1)))
+               return &bad_cie;
+
+       /* CIE id for eh_frame is 0, otherwise 0xffffffff */
+       if (m->unwind_is_ehframe && fde[1] == 0)
+               return &not_fde;
+       else if (fde[1] == 0xffffffff)
+               return &not_fde;
+
+       /* OK, must be an FDE.  Now find its CIE. */
+
+       /* CIE_pointer must be a proper offset */
+       if ((fde[1] & (sizeof(*fde) - 1)) || fde[1] > (unsigned long)(fde + 1) - (unsigned long)m->unwind_data) {
+               dbug_unwind(1, "fde[1]=%lx fde+1=%lx, unwind_data=%lx  %lx\n",
+                    (unsigned long)fde[1], (unsigned long)(fde + 1),
+                    (unsigned long)m->unwind_data, (unsigned long)(fde + 1) - (unsigned long)m->unwind_data);
+               return NULL;    /* this is not a valid FDE */
+       }
+
+       /* cie pointer field is different in eh_frame vs debug_frame */
+       if (m->unwind_is_ehframe)
+               cie = fde + 1 - fde[1] / sizeof(*fde);
+       else
+               cie = m->unwind_data + fde[1];
+
+       if (*cie <= sizeof(*cie) + 4 || *cie >= fde[1] - sizeof(*fde)
+           || (*cie & (sizeof(*cie) - 1))
+           || (cie[1] != 0xffffffff && cie[1] != 0)) {
+               dbug_unwind(1, "cie is not valid %lx %x %x %x\n", cie, *cie, fde[1], cie[1]);
+               return NULL;    /* this is not a (valid) CIE */
+       }
+
+       return cie;
+}
+
+/* read an encoded pointer */
+static unsigned long read_pointer(const u8 **pLoc, const void *end, signed ptrType)
+{
+       unsigned long value = 0;
+       union {
+               const u8 *p8;
+               const u16 *p16u;
+               const s16 *p16s;
+               const u32 *p32u;
+               const s32 *p32s;
+               const unsigned long *pul;
+       } ptr;
+
+       if (ptrType < 0 || ptrType == DW_EH_PE_omit)
+               return 0;
+
+       ptr.p8 = *pLoc;
+       switch (ptrType & DW_EH_PE_FORM) {
+       case DW_EH_PE_data2:
+               if (end < (const void *)(ptr.p16u + 1))
+                       return 0;
+               if (ptrType & DW_EH_PE_signed)
+                       value = _stp_get_unaligned(ptr.p16s++);
+               else
+                       value = _stp_get_unaligned(ptr.p16u++);
+               break;
+       case DW_EH_PE_data4:
+#ifdef CONFIG_64BIT
+               if (end < (const void *)(ptr.p32u + 1))
+                       return 0;
+               if (ptrType & DW_EH_PE_signed)
+                       value = _stp_get_unaligned(ptr.p32s++);
+               else
+                       value = _stp_get_unaligned(ptr.p32u++);
+               break;
+       case DW_EH_PE_data8:
+               BUILD_BUG_ON(sizeof(u64) != sizeof(value));
+#else
+               BUILD_BUG_ON(sizeof(u32) != sizeof(value));
+#endif
+       case DW_EH_PE_absptr:
+               if (end < (const void *)(ptr.pul + 1))
+                       return 0;
+               value = _stp_get_unaligned(ptr.pul++);
+               break;
+       case DW_EH_PE_leb128:
+               BUILD_BUG_ON(sizeof(uleb128_t) > sizeof(value));
+               value = ptrType & DW_EH_PE_signed ? get_sleb128(&ptr.p8, end)
+                   : get_uleb128(&ptr.p8, end);
+               if ((const void *)ptr.p8 > end)
+                       return 0;
+               break;
+       default:
+               return 0;
+       }
+       switch (ptrType & DW_EH_PE_ADJUST) {
+       case DW_EH_PE_absptr:
+               break;
+       case DW_EH_PE_pcrel:
+               value += (unsigned long)*pLoc;
+               break;
+       default:
+               return 0;
+       }
+       if ((ptrType & DW_EH_PE_indirect)
+           && __stp_get_user(value, (unsigned long *)value))
+               return 0;
+       *pLoc = ptr.p8;
+
+       return value;
+}
+
+static signed fde_pointer_type(const u32 *cie)
+{
+       const u8 *ptr = (const u8 *)(cie + 2);
+       unsigned version = *ptr;
+
+       if (version != 1)
+               return -1;      /* unsupported */
+       if (*++ptr) {
+               const char *aug;
+               const u8 *end = (const u8 *)(cie + 1) + *cie;
+               uleb128_t len;
+
+               /* check if augmentation size is first (and thus present) */
+               if (*ptr != 'z')
+                       return -1;
+               /* check if augmentation string is nul-terminated */
+               if ((ptr = memchr(aug = (const void *)ptr, 0, end - ptr)) == NULL)
+                       return -1;
+               ++ptr;          /* skip terminator */
+               get_uleb128(&ptr, end); /* skip code alignment */
+               get_sleb128(&ptr, end); /* skip data alignment */
+               /* skip return address column */
+               version <= 1 ? (void)++ptr : (void)get_uleb128(&ptr, end);
+               len = get_uleb128(&ptr, end);   /* augmentation length */
+               if (ptr + len < ptr || ptr + len > end)
+                       return -1;
+               end = ptr + len;
+               while (*++aug) {
+                       if (ptr >= end)
+                               return -1;
+                       switch (*aug) {
+                       case 'L':
+                               ++ptr;
+                               break;
+                       case 'P':{
+                                       signed ptrType = *ptr++;
+
+                                       if (!read_pointer(&ptr, end, ptrType) || ptr > end)
+                                               return -1;
+                               }
+                               break;
+                       case 'R':
+                               return *ptr;
+                       default:
+                               return -1;
+                       }
+               }
+       }
+       return DW_EH_PE_absptr;
+}
+
+static int advance_loc(unsigned long delta, struct unwind_state *state)
+{
+       state->loc += delta * state->codeAlign;
+       dbug_unwind(1, "state->loc=%lx\n", state->loc);
+       return delta > 0;
+}
+
+static void set_rule(uleb128_t reg, enum item_location where, uleb128_t value, struct unwind_state *state)
+{
+       dbug_unwind(1, "reg=%d, where=%d, value=%lx\n", reg, where, value);
+       if (reg < ARRAY_SIZE(state->regs)) {
+               state->regs[reg].where = where;
+               state->regs[reg].value = value;
+       }
+}
+
+static int processCFI(const u8 *start, const u8 *end, unsigned long targetLoc, signed ptrType, struct unwind_state *state)
+{
+       union {
+               const u8 *p8;
+               const u16 *p16;
+               const u32 *p32;
+       } ptr;
+       int result = 1;
+
+       if (start != state->cieStart) {
+               state->loc = state->org;
+               result = processCFI(state->cieStart, state->cieEnd, 0, ptrType, state);
+               if (targetLoc == 0 && state->label == NULL)
+                       return result;
+       }
+
+       for (ptr.p8 = start; result && ptr.p8 < end;) {
+               switch (*ptr.p8 >> 6) {
+                       uleb128_t value;
+               case 0:
+                       switch (*ptr.p8++) {
+                       case DW_CFA_nop:
+                               dbug_unwind(1, "DW_CFA_nop\n");
+                               break;
+                       case DW_CFA_set_loc:
+                               if ((state->loc = read_pointer(&ptr.p8, end, ptrType)) == 0)
+                                       result = 0;
+                               dbug_unwind(1, "DW_CFA_set_loc %lx (result=%d)\n", state->loc, result);
+                               break;
+                       case DW_CFA_advance_loc1:
+                               result = ptr.p8 < end && advance_loc(*ptr.p8++, state);
+                               dbug_unwind(1, "DW_CFA_advance_loc1 %d\n", result);
+                               break;
+                       case DW_CFA_advance_loc2:
+                               result = ptr.p8 <= end + 2 && advance_loc(*ptr.p16++, state);
+                               dbug_unwind(1, "DW_CFA_advance_loc2 %d\n", result);
+                               break;
+                       case DW_CFA_advance_loc4:
+                               result = ptr.p8 <= end + 4 && advance_loc(*ptr.p32++, state);
+                               dbug_unwind(1, "DW_CFA_advance_loc4 %d\n", result);
+                               break;
+                       case DW_CFA_offset_extended:
+                               value = get_uleb128(&ptr.p8, end);
+                               set_rule(value, Memory, get_uleb128(&ptr.p8, end), state);
+                               dbug_unwind(1, "DW_CFA_offset_extended\n");
+                               break;
+                       case DW_CFA_val_offset:
+                               value = get_uleb128(&ptr.p8, end);
+                               set_rule(value, Value, get_uleb128(&ptr.p8, end), state);
+                               dbug_unwind(1, "DW_CFA_val_offset\n");
+                               break;
+                       case DW_CFA_offset_extended_sf:
+                               value = get_uleb128(&ptr.p8, end);
+                               set_rule(value, Memory, get_sleb128(&ptr.p8, end), state);
+                               dbug_unwind(1, "DW_CFA_offset_extended_sf\n");
+                               break;
+                       case DW_CFA_val_offset_sf:
+                               value = get_uleb128(&ptr.p8, end);
+                               set_rule(value, Value, get_sleb128(&ptr.p8, end), state);
+                               dbug_unwind(1, "DW_CFA_val_offset_sf\n");
+                               break;
+                       case DW_CFA_restore_extended:
+                       case DW_CFA_undefined:
+                       case DW_CFA_same_value:
+                               set_rule(get_uleb128(&ptr.p8, end), Nowhere, 0, state);
+                               dbug_unwind(1, "DW_CFA_undefined\n");
+                               break;
+                       case DW_CFA_register:
+                               value = get_uleb128(&ptr.p8, end);
+                               set_rule(value, Register, get_uleb128(&ptr.p8, end), state);
+                               dbug_unwind(1, "DW_CFA_register\n");
+                               break;
+                       case DW_CFA_remember_state:
+                               dbug_unwind(1, "DW_CFA_remember_state\n");
+                               if (ptr.p8 == state->label) {
+                                       state->label = NULL;
+                                       return 1;
+                               }
+                               if (state->stackDepth >= MAX_STACK_DEPTH)
+                                       return 0;
+                               state->stack[state->stackDepth++] = ptr.p8;
+                               break;
+                       case DW_CFA_restore_state:
+                               dbug_unwind(1, "DW_CFA_restore_state\n");
+                               if (state->stackDepth) {
+                                       const uleb128_t loc = state->loc;
+                                       const u8 *label = state->label;
+
+                                       state->label = state->stack[state->stackDepth - 1];
+                                       memcpy(&state->cfa, &badCFA, sizeof(state->cfa));
+                                       memset(state->regs, 0, sizeof(state->regs));
+                                       state->stackDepth = 0;
+                                       result = processCFI(start, end, 0, ptrType, state);
+                                       state->loc = loc;
+                                       state->label = label;
+                               } else
+                                       return 0;
+                               break;
+                       case DW_CFA_def_cfa:
+                               state->cfa.reg = get_uleb128(&ptr.p8, end);
+                               dbug_unwind(1, "DW_CFA_def_cfa reg=%ld\n", state->cfa.reg);
+                               /*nobreak */
+                       case DW_CFA_def_cfa_offset:
+                               state->cfa.offs = get_uleb128(&ptr.p8, end);
+                               dbug_unwind(1, "DW_CFA_def_cfa_offset offs=%lx\n", state->cfa.offs);
+                               break;
+                       case DW_CFA_def_cfa_sf:
+                               state->cfa.reg = get_uleb128(&ptr.p8, end);
+                               dbug_unwind(1, "DW_CFA_def_cfa_sf reg=%ld\n", state->cfa.reg);
+                               /*nobreak */
+                       case DW_CFA_def_cfa_offset_sf:
+                               state->cfa.offs = get_sleb128(&ptr.p8, end) * state->dataAlign;
+                               dbug_unwind(1, "DW_CFA_def_cfa_offset_sf offs=%lx\n", state->cfa.offs);
+                               break;
+                       case DW_CFA_def_cfa_register:
+                               state->cfa.reg = get_uleb128(&ptr.p8, end);
+                               dbug_unwind(1, "DW_CFA_def_cfa_register reg=%ld\n", state->cfa.reg);
+                               break;
+                               /*todo case DW_CFA_def_cfa_expression: */
+                               /*todo case DW_CFA_expression: */
+                               /*todo case DW_CFA_val_expression: */
+                       case DW_CFA_GNU_args_size:
+                               get_uleb128(&ptr.p8, end);
+                               dbug_unwind(1, "DW_CFA_GNU_args_size\n");
+                               break;
+                       case DW_CFA_GNU_negative_offset_extended:
+                               value = get_uleb128(&ptr.p8, end);
+                               set_rule(value, Memory, (uleb128_t)0 - get_uleb128(&ptr.p8, end), state);
+                               dbug_unwind(1, "DW_CFA_GNU_negative_offset_extended\n");
+                               break;
+                       case DW_CFA_GNU_window_save:
+                       default:
+                               dbug_unwind(1, "unimplemented call frame instruction: 0x%x\n", *(ptr.p8 - 1));
+                               result = 0;
+                               break;
+                       }
+                       break;
+               case 1:
+                       result = advance_loc(*ptr.p8++ & 0x3f, state);
+                       dbug_unwind(1, "case 1\n");
+                       break;
+               case 2:
+                       value = *ptr.p8++ & 0x3f;
+                       set_rule(value, Memory, get_uleb128(&ptr.p8, end), state);
+                       dbug_unwind(1, "case 2\n");
+                       break;
+               case 3:
+                       set_rule(*ptr.p8++ & 0x3f, Nowhere, 0, state);
+                       dbug_unwind(1, "case 3\n");
+                       break;
+               }
+               if (ptr.p8 > end)
+                       result = 0;
+               if (result && targetLoc != 0 && targetLoc < state->loc)
+                       return 1;
+       }
+       return result && ptr.p8 == end && (targetLoc == 0 || state->label == NULL);
+}
+
+/* If we previously created an unwind header, then use it now to binary search */
+/* for the FDE corresponding to pc. */
+
+static u32 *_stp_search_unwind_hdr(unsigned long pc, struct _stp_module *m)
+{
+       const u8 *ptr, *end, *hdr = m->unwind_hdr;
+       unsigned long startLoc;
+       u32 *fde = NULL;
+       unsigned num, tableSize, t2;
+
+       /* TOTO: only really need to test hdr == NULL */
+       /* The rest should be validated at load time */
+
+       if (hdr == NULL || hdr[0] != 1)
+               return NULL;
+
+       dbug_unwind(1, "search for %lx", pc);
+
+       /* table_enc */
+       switch (hdr[3] & DW_EH_PE_FORM) {
+       case DW_EH_PE_absptr:
+               tableSize = sizeof(unsigned long);
+               break;
+       case DW_EH_PE_data2:
+               tableSize = 2;
+               break;
+       case DW_EH_PE_data4:
+               tableSize = 4;
+               break;
+       case DW_EH_PE_data8:
+               tableSize = 8;
+               break;
+       default:
+               dbug_unwind(1, "bad table encoding");
+               return NULL;
+       }
+       ptr = hdr + 4;
+       end = hdr + m->unwind_hdr_len;
+
+       if (read_pointer(&ptr, end, hdr[1]) != (unsigned long)m->unwind_data) {
+               dbug_unwind(1, "eh_frame_ptr not valid");
+               return NULL;
+       }
+
+       num = read_pointer(&ptr, end, hdr[2]);
+       if (num == 0 || num != (end - ptr) / (2 * tableSize) || (end - ptr) % (2 * tableSize)) {
+               dbug_unwind(1, "Bad num=%d end-ptr=%ld 2*tableSize=%d", num, end - ptr, 2 * tableSize);
+               return NULL;
+       }
+
+       do {
+               const u8 *cur = ptr + (num / 2) * (2 * tableSize);
+               startLoc = read_pointer(&cur, cur + tableSize, hdr[3]);
+               if (pc < startLoc)
+                       num /= 2;
+               else {
+                       ptr = cur - tableSize;
+                       num = (num + 1) / 2;
+               }
+       } while (startLoc && num > 1);
+
+       if (num == 1 && (startLoc = read_pointer(&ptr, ptr + tableSize, hdr[3])) != 0 && pc >= startLoc)
+               fde = (void *)read_pointer(&ptr, ptr + tableSize, hdr[3]);
+
+       dbug_unwind(1, "returning %lx", fde);
+       return fde;
+}
+
+/* Unwind to previous to frame.  Returns 0 if successful, negative
+ * number in case of an error. */
+int unwind(struct unwind_frame_info *frame)
+{
+#define FRAME_REG(r, t) (((t *)frame)[reg_info[r].offs])
+       const u32 *fde, *cie = NULL;
+       const u8 *ptr = NULL, *end = NULL;
+       unsigned long pc = UNW_PC(frame) - frame->call_frame;
+       unsigned long tableSize, startLoc = 0, endLoc = 0, cfa;
+       unsigned i;
+       signed ptrType = -1;
+       uleb128_t retAddrReg = 0;
+       struct _stp_module *m;
+       struct unwind_state state;
+
+       dbug_unwind(1, "pc=%lx, %lx", pc, UNW_PC(frame));
+
+       if (UNW_PC(frame) == 0)
+               return -EINVAL;
+
+       m = _stp_get_unwind_info(pc);
+       if (unlikely(m == NULL)) {
+               dbug_unwind(1, "No module found for pc=%lx", pc);
+               return -EINVAL;
+       }
+
+       if (unlikely(m->unwind_data_len == 0 || m->unwind_data_len & (sizeof(*fde) - 1))) {
+               dbug_unwind(1, "Module %s: unwind_data_len=%d", m->name, m->unwind_data_len);
+               goto done;
+       }
+
+       fde = _stp_search_unwind_hdr(pc, m);
+       dbug_unwind(1, "%s: fde=%lx\n", m->name, fde);
+
+       if (fde != NULL) {
+               cie = cie_for_fde(fde, m);
+               ptr = (const u8 *)(fde + 2);
+               if (cie != NULL
+                   && cie != &bad_cie
+                   && cie != &not_fde
+                   && (ptrType = fde_pointer_type(cie)) >= 0
+                   && read_pointer(&ptr, (const u8 *)(fde + 1) + *fde, ptrType) == startLoc) {
+                       if (!(ptrType & DW_EH_PE_indirect))
+                               ptrType &= DW_EH_PE_FORM | DW_EH_PE_signed;
+                       endLoc = startLoc + read_pointer(&ptr, (const u8 *)(fde + 1) + *fde, ptrType);
+                       if (pc >= endLoc)
+                               fde = NULL;
+               } else
+                       fde = NULL;
+       }
+       if (fde == NULL) {
+               for (fde = m->unwind_data, tableSize = m->unwind_data_len; cie = NULL, tableSize > sizeof(*fde)
+                    && tableSize - sizeof(*fde) >= *fde; tableSize -= sizeof(*fde) + *fde, fde += 1 + *fde / sizeof(*fde)) {
+                       // dbug_unwind(1,"fde=%lx tableSize=%d\n", (long)*fde, (int)tableSize);
+                       cie = cie_for_fde(fde, m);
+                       if (cie == &bad_cie) {
+                               cie = NULL;
+                               break;
+                       }
+                       if (cie == NULL || cie == &not_fde || (ptrType = fde_pointer_type(cie)) < 0)
+                               continue;
+
+                       ptr = (const u8 *)(fde + 2);
+                       startLoc = read_pointer(&ptr, (const u8 *)(fde + 1) + *fde, ptrType);
+                       // dbug_unwind(1,"startLoc=%p\n",(u64)startLoc);                                
+                       if (!startLoc)
+                               continue;
+                       if (!(ptrType & DW_EH_PE_indirect))
+                               ptrType &= DW_EH_PE_FORM | DW_EH_PE_signed;
+                       endLoc = startLoc + read_pointer(&ptr, (const u8 *)(fde + 1) + *fde, ptrType);
+                       // dbug_unwind(1,"endLoc=%p\n",(u64)endLoc);                                                            
+                       if (pc >= startLoc && pc < endLoc)
+                               break;
+               }
+       }
+
+       dbug_unwind(1, "cie=%lx fde=%lx startLoc=%lx endLoc=%lx\n", cie, fde, startLoc, endLoc);
+       if (cie == NULL || fde == NULL)
+               goto done;
+
+       /* found the CIE and FDE */
+
+       memset(&state, 0, sizeof(state));
+       state.cieEnd = ptr;     /* keep here temporarily */
+       ptr = (const u8 *)(cie + 2);
+       end = (const u8 *)(cie + 1) + *cie;
+       frame->call_frame = 1;
+       if ((state.version = *ptr) != 1) {
+               dbug_unwind(1, "CIE version number is %d.  1 is supported.\n", state.version);
+               goto done;      /* unsupported version */
+       }
+       if (*++ptr) {
+               /* check if augmentation size is first (and thus present) */
+               if (*ptr == 'z') {
+                       while (++ptr < end && *ptr) {
+                               switch (*ptr) {
+                                       /* check for ignorable (or already handled)
+                                        * nul-terminated augmentation string */
+                               case 'L':
+                               case 'P':
+                               case 'R':
+                                       continue;
+                               case 'S':
+                                       frame->call_frame = 0;
+                                       continue;
+                               default:
+                                       break;
+                               }
+                               break;
+                       }
+               }
+               if (ptr >= end || *ptr) {
+                       dbug_unwind(1, "Problem parsing the augmentation string.\n");
+                       goto done;
+               }
+       }
+       ++ptr;
+
+       /* get code aligment factor */
+       state.codeAlign = get_uleb128(&ptr, end);
+       /* get data aligment factor */
+       state.dataAlign = get_sleb128(&ptr, end);
+       if (state.codeAlign == 0 || state.dataAlign == 0 || ptr >= end)
+               goto done;;
+
+       retAddrReg = state.version <= 1 ? *ptr++ : get_uleb128(&ptr, end);
+
+       /* skip augmentation */
+       if (((const char *)(cie + 2))[1] == 'z') {
+               uleb128_t augSize = get_uleb128(&ptr, end);
+               ptr += augSize;
+       }
+       if (ptr > end || retAddrReg >= ARRAY_SIZE(reg_info)
+           || REG_INVALID(retAddrReg)
+           || reg_info[retAddrReg].width != sizeof(unsigned long))
+               goto done;
+
+       state.cieStart = ptr;
+       ptr = state.cieEnd;
+       state.cieEnd = end;
+       end = (const u8 *)(fde + 1) + *fde;
+
+       /* skip augmentation */
+       if (((const char *)(cie + 2))[1] == 'z') {
+               uleb128_t augSize = get_uleb128(&ptr, end);
+               if ((ptr += augSize) > end)
+                       goto done;
+       }
+
+       state.org = startLoc;
+       memcpy(&state.cfa, &badCFA, sizeof(state.cfa));
+       /* process instructions */
+       if (!processCFI(ptr, end, pc, ptrType, &state)
+           || state.loc > endLoc || state.regs[retAddrReg].where == Nowhere || state.cfa.reg >= ARRAY_SIZE(reg_info)
+           || reg_info[state.cfa.reg].width != sizeof(unsigned long)
+           || state.cfa.offs % sizeof(unsigned long))
+               goto done;
+
+       /* update frame */
+       dbug_unwind(1, "cie=%lx fde=%lx\n", cie, fde);
+#ifndef CONFIG_AS_CFI_SIGNAL_FRAME
+       if (frame->call_frame && !UNW_DEFAULT_RA(state.regs[retAddrReg], state.dataAlign))
+               frame->call_frame = 0;
+#endif
+       cfa = FRAME_REG(state.cfa.reg, unsigned long) + state.cfa.offs;
+       startLoc = min((unsigned long)UNW_SP(frame), cfa);
+       endLoc = max((unsigned long)UNW_SP(frame), cfa);
+       dbug_unwind(1, "cfa=%lx SP startLoc=%lx, endLoc=%lx\n", cfa, startLoc, endLoc);
+       if (STACK_LIMIT(startLoc) != STACK_LIMIT(endLoc)) {
+               startLoc = min(STACK_LIMIT(cfa), cfa);
+               endLoc = max(STACK_LIMIT(cfa), cfa);
+               dbug_unwind(1, "SP startLoc=%p, endLoc=%p\n", (u64)startLoc, (u64)endLoc);
+       }
+#ifndef CONFIG_64BIT
+# define CASES CASE(8); CASE(16); CASE(32)
+#else
+# define CASES CASE(8); CASE(16); CASE(32); CASE(64)
+#endif
+       dbug_unwind(1, "cie=%p fde=%p\n", (u64)cie, (u64)fde);
+       for (i = 0; i < ARRAY_SIZE(state.regs); ++i) {
+               if (REG_INVALID(i)) {
+                       if (state.regs[i].where == Nowhere)
+                               continue;
+                       dbug_unwind(1, "REG_INVALID %d\n", i);
+                       goto done;
+               }
+               dbug_unwind(1, "register %d. where=%d\n", i, state.regs[i].where);
+               switch (state.regs[i].where) {
+               default:
+                       break;
+               case Register:
+                       if (state.regs[i].value >= ARRAY_SIZE(reg_info)
+                           || REG_INVALID(state.regs[i].value)
+                           || reg_info[i].width > reg_info[state.regs[i].value].width) {
+                               dbug_unwind(1, "case Register bad\n");
+                               goto done;
+                       }
+                       switch (reg_info[state.regs[i].value].width) {
+#define CASE(n) \
+                       case sizeof(u##n): \
+                               state.regs[i].value = FRAME_REG(state.regs[i].value, \
+                                                               const u##n); \
+                               break
+                               CASES;
+#undef CASE
+                       default:
+                               dbug_unwind(1, "default\n");
+                               goto done;
+                       }
+                       break;
+               }
+       }
+       for (i = 0; i < ARRAY_SIZE(state.regs); ++i) {
+               dbug_unwind(1, "register %d. invalid=%d\n", i, REG_INVALID(i));
+               if (REG_INVALID(i))
+                       continue;
+               dbug_unwind(1, "register %d. where=%d\n", i, state.regs[i].where);
+               switch (state.regs[i].where) {
+               case Nowhere:
+                       if (reg_info[i].width != sizeof(UNW_SP(frame))
+                           || &FRAME_REG(i, __typeof__(UNW_SP(frame)))
+                           != &UNW_SP(frame))
+                               continue;
+                       UNW_SP(frame) = cfa;
+                       break;
+               case Register:
+                       switch (reg_info[i].width) {
+#define CASE(n) case sizeof(u##n): \
+                               FRAME_REG(i, u##n) = state.regs[i].value; \
+                               break
+                               CASES;
+#undef CASE
+                       default:
+                               dbug_unwind(1, "default\n");
+                               goto done;
+                       }
+                       break;
+               case Value:
+                       if (reg_info[i].width != sizeof(unsigned long)) {
+                               dbug_unwind(1, "Value\n");
+                               goto done;
+                       }
+                       FRAME_REG(i, unsigned long) = cfa + state.regs[i].value * state.dataAlign;
+                       break;
+               case Memory:{
+                               unsigned long addr = cfa + state.regs[i].value * state.dataAlign;
+                               dbug_unwind(1, "addr=%lx width=%d\n", addr, reg_info[i].width);
+                               switch (reg_info[i].width) {
+#define CASE(n)     case sizeof(u##n): \
+                                       if (unlikely(__stp_get_user(FRAME_REG(i, u##n), (u##n *)addr))) \
+                                               goto copy_failed;\
+                                       dbug_unwind(1, "set register %d to %lx\n", i, (long)FRAME_REG(i,u##n));\
+                                       break
+                                       CASES;
+#undef CASE
+                               default:
+                                       dbug_unwind(1, "default\n");
+                                       goto done;
+                               }
+                       }
+                       break;
+               }
+       }
+       read_unlock(&m->lock);
+       dbug_unwind(1, "returning 0 (%lx)\n", UNW_PC(frame));
+       return 0;
+
+copy_failed:
+       dbug_unwind(1, "_stp_get_user failed to access memory\n");
+done:
+       read_unlock(&m->lock);
+       return -EIO;
+#undef CASES
+#undef FRAME_REG
+}
diff --git a/runtime/uprobes/Makefile b/runtime/uprobes/Makefile
deleted file mode 100644 (file)
index 40af7aa..0000000
+++ /dev/null
@@ -1,16 +0,0 @@
-obj-m := uprobes.o
-KDIR := /lib/modules/$(shell uname -r)/build
-PWD := $(shell pwd)
-DEPENDENCIES := $(shell echo uprobes_arch.[ch] uprobes.[ch] uprobes_*.[ch])
-DEPENDENCIES += Makefile $(KDIR)/Module.symvers
-
-default:
-       $(MAKE) -C $(KDIR) SUBDIRS=$(PWD) modules
-
-# This target is used with "make -q" to see whether a "real" build is needed.
-uprobes.ko: $(DEPENDENCIES)
-       @echo uprobes.ko is not a valid target.  See Makefile.
-
-clean:
-       rm -f *.mod.c *.ko *.o .*.cmd *~
-       rm -rf .tmp_versions
diff --git a/safety/README b/safety/README
deleted file mode 100644 (file)
index 61eda4a..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-This is a static safety-checker for SystemTap modules.  It attempts to
-validate modules by checking the opcodes used and the external references
-against a whitelist.
-
-The script relies on external data files to provide the whitelists, which by
-default are in the <script-dir>/data directory.  The 'references' file
-provides a plain list of allowed references.  The 'opcodes' file provides a
-list of regular expressions that match allowed opcodes.  Either data file may
-have an optional kernel and/or architecture suffix, as in 'opcodes-i686' or
-'references-2.6.9-32.ELsmp-x86_64'.
diff --git a/safety/data/opcodes-i686 b/safety/data/opcodes-i686
deleted file mode 100644 (file)
index 123fa2b..0000000
+++ /dev/null
@@ -1,107 +0,0 @@
-aaa
-aad
-aam
-aas
-adc[bwl]?
-add[bwl]?
-and[bwl]?
-bound[wl]?
-bsf[wl]?
-bsr[wl]?
-bswapl?
-btc[wl]?
-btr[wl]?
-bts[wl]?
-bt[wl]?
-call
-cbtw
-cbw
-cdq
-clc
-cld
-cli
-cltd
-cmc
-cmovn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)[wl]?
-cmp[bwl]?
-cmps[bwl]?
-cmpxchg8b
-cmpxchg[bwl]?
-cpuid
-cwd
-cwde
-cwtd
-cwtl
-daa
-das
-dec[bwl]?
-div[bwl]?
-enter
-idiv[bwl]?
-imul[bwl]?
-inc[bwl]?
-je?cxz
-jmp
-jn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-lcall
-lds[wl]?
-leave
-lea[wl]?
-les[wl]?
-lfence
-lfs[wl]?
-lgs[wl]?
-lods[bwl]?
-loopn?[ze]?
-lret
-lss[wl]?
-mfence
-movaps
-mov[bwl]?
-movs[bwl]?
-movsb[wl]?
-movswl?
-movzb[wl]?
-movzwl?
-mul[bwl]?
-neg[bwl]?
-nop
-not[bwl]?
-or[bwl]?
-pause
-popa[wl]?
-popf[wl]?
-pop[wl]?
-prefetch(?:t[012]|nta)
-pusha[wl]?
-pushf[wl]?
-push[wl]?
-rcl[bwl]?
-rcr[bwl]?
-rdmsr
-rdtsc
-ret
-rol[bwl]?
-ror[bwl]?
-sahf
-sal[bwl]?
-sar[bwl]?
-sbb[bwl]?
-scas[bwl]?
-setn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-shl[bwl]?
-shld[bwl]?
-shr[bwl]?
-shrd[bwl]?
-smov[lw]?
-stc
-std
-sti
-stos[bwl]?
-sub[bwl]?
-test[bwl]?
-xadd[bwl]?
-xchg[bwl]?
-xlat
-xlatb
-xor[bwl]?
diff --git a/safety/data/opcodes-ia64 b/safety/data/opcodes-ia64
deleted file mode 100644 (file)
index edb1792..0000000
+++ /dev/null
@@ -1,89 +0,0 @@
-add[sl]?
-addp4
-alloc
-and
-andcm
-br(?:\.cond)?(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.cond(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.call(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.ret(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.cloop(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.ctop(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.cexit(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.wtop(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-br\.wexit(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-brl(?:\.cond)?(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-brl\.call(?:\.(?:spnt|sptk|dpnt|dptk))?(?:\.(?:few|many))?(?:\.clr)?
-brp(?:\.(?:sptk|loop|exit|dptk))(?:\.imp)?
-brp\.ret(?:\.(?:sptk|loop|exit|dptk))(?:\.imp)?
-chk\.s(?:\.[im])?
-chk\.a\.(?:clr|nc)
-clrrrb
-cmp\.(?:eq|ne|l[te]u?|g[te]u?)(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-cmp4\.(?:eq|ne|l[te]u?|g[te]u?)(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-cmpxchg[1248]\.(?:acq|rel)(?:\.nt[1a])?
-cmp8xchg16\.(?:acq|rel)(?:\.nt[1a])?
-cover
-czx[12]\.[lr]
-dep(?:\.z)?
-extr(?:\.u)?
-fetchadd[48]\.(?:acq|rel)(?:\.nt[1a])?
-getf\.(?:s|d|exp|sig)
-hint(?:\.[ibmfx])?
-ld[1248](?:\.(?:s|a|sa|c\.nc|c\.clr|c\.clr\.acq|acq|bias))?(?:\.nt[1a])?
-ld8\.fill(?:\.nt[1a])?
-ld16(?:\.acq)?(?:\.nt[1a])?
-ldf8(?:\.(?:s|a|sa|c\.nc|c\.clr))?(?:\.nt[1a])?
-lfetch(?:.fault)?(?:\.excl)?(?:\.nt[12a])?
-mf
-mix[124]\.[lr]
-mov(?:\.[im])?
-mov(?:\.ret)?(?:\.sptk|\.dptk)?(?:\.imp)?
-movl
-mux[12]
-nop(?:\.[ibmfx])?
-or
-pack2\.[us]ss
-pack4.sss
-padd[124]
-padd[12]\.(?:sss|uus|uuu)
-pavg[12](?:\.raz)
-pavgsub[12]
-pcmp[124]\.(?:eq|gt)
-pmax1\.u
-pmax2
-pmin1\.u
-pmin2
-pmpy2\.[rl]
-pmpyshr2(?:\.u)?
-popcnt
-psad1
-pshl[24]
-pshladd2
-pshr[24](?:\.u)?
-pshradd2
-psub[124]
-psub[12]\.(?:sss|uus|uuu)
-rsm
-setf\.(?:s|d|exp|sig)
-shl
-shladd
-shladdp4
-shr(?:\.u)?
-shrp
-srlz\.[id]
-ssm
-st[1248](?:\.rel)?(?:\.nta)?
-st16(?:\.rel)?(?:\.nta)?
-st8\.spill(?:\.nta)?
-stf8(?:\.nta)?
-sub
-sxt[124]
-tbit\.n?z(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-tnat\.n?z(?:\.(?:unc|or|and|or.andcm|orcm|andcm|and.orcm))?
-unpack[124]\.[hl]
-xchg[1248](?:\.nt[1a])?
-xma\.[lh]u?
-xmpy\.[lh]u?
-xor
-zxt[124]
diff --git a/safety/data/opcodes-x86_64 b/safety/data/opcodes-x86_64
deleted file mode 100644 (file)
index b89df87..0000000
+++ /dev/null
@@ -1,104 +0,0 @@
-adc[bwlq]?
-add[bwlq]?
-and[bwlq]?
-boundl?
-bsf[wlq]?
-bsr[wlq]?
-bswap[lq]?
-btc[wlq]?
-btr[wlq]?
-bts[wlq]?
-bt[wlq]?
-callq?
-cbtw
-cbw
-cdq
-cdqe
-clc
-cld
-cli
-cltd
-cltq
-cmc
-cmovn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)[wlq]?
-cmp[bwlq]?
-cmps[bwlq]?
-cmpxchg16b
-cmpxchg8b
-cmpxchg[bwlq]?
-cpuid
-cqo
-cqtd
-cqto
-cwd
-cwde
-cwtd
-cwtl
-dec[bwlq]?
-div[bwlq]?
-enterq?
-idiv[bwlq]?
-imul[bwlq]?
-inc[bwlq]?
-jcxz
-jmpq?
-jn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-lcallq?
-leaveq?
-lea[wlq]?
-lfence
-lfs[wl]?
-lgs[wl]?
-lods[bwlq]?
-loopn?[ze]?
-lretq?
-lss[wl]?
-mfence
-movaps
-mov[bwlq]?
-movs[bwlq]?
-movsb[wlq]?
-movslq?
-movsw[lq]?
-movzb[wlq]?
-movzw[lq]?
-mul[bwlq]?
-neg[bwlq]?
-nop
-not[bwlq]?
-or[bwlq]?
-pause
-popf[wlq]?
-pop[wlq]?
-prefetch(?:t[012]|nta)
-pushf[wlq]?
-push[wlq]?
-rcl[bwlq]?
-rcr[bwlq]?
-rdmsr
-rdtsc
-retq?
-rol[bwlq]?
-ror[bwlq]?
-sahf
-sal[bwlq]?
-sar[bwlq]?
-sbb[bwlq]?
-scas[bwlq]?
-setn?(?:a|ae|b|be|c|e|g|ge|l|le|o|p|pe|po|s|z)
-shl[bwlq]?
-shld[bwlq]?
-shr[bwlq]?
-shrd[bwlq]?
-smov[lw]?
-stc
-std
-sti
-stos[bwlq]?
-sub[bwlq]?
-test[bwlq]?
-xadd[bwlq]?
-xchg[bwlq]?
-xlat
-xlatb
-xor[bwlq]?
diff --git a/safety/data/references b/safety/data/references
deleted file mode 100644 (file)
index bfea8e8..0000000
+++ /dev/null
@@ -1,94 +0,0 @@
-__alloc_percpu
-autoremove_wake_function
-__bitmap_weight
-cond_resched
-__const_udelay
-copy_from_user
-__copy_from_user_ll
-copy_to_user
-__copy_user
-copy_user_generic
-cpu_callout_map
-cpu_online_map
-cpu_possible_map
-cpu_to_node
-create_proc_entry
-del_timer_sync
-__divdi3
-do_gettimeofday
-__down_failed
-__find_next_bit
-find_next_bit
-finish_wait
-free_percpu
-__get_user_4
-init_timer
-__init_timer_base
-jiffies
-kallsyms_lookup_name
-kfree
-__kmalloc
-kmalloc_node
-kmem_cache_alloc
-malloc_sizes
-memcmp
-memcpy
-memset
-__might_sleep
-__moddi3
-__mod_timer
-mod_timer
-msleep
-node_online_map
-param_get_int
-param_get_long
-param_get_string
-param_set_copystring
-param_set_int
-param_set_long
-per_cpu__cpu_info
-prepare_to_wait
-printk
-proc_mkdir
-proc_root
-_read_lock
-_read_trylock
-_read_unlock
-register_kprobe
-register_kretprobe
-register_profile_notifier
-register_timer_hook
-remove_proc_entry
-schedule
-schedule_delayed_work
-scnprintf
-simple_strtol
-snprintf
-_spin_lock
-_spin_lock_irqsave
-_spin_trylock
-_spin_unlock
-_spin_unlock_irqrestore
-sprintf
-strcmp
-strlcat
-strlcpy
-strlen
-strncmp
-strncpy
-__strncpy_from_user
-strsep
-__udivdi3
-__umoddi3
-unregister_kprobe
-unregister_kretprobe
-unregister_profile_notifier
-unregister_timer_hook
-unw_init_running
-unw_unwind
-__up_wakeup
-vscnprintf
-vsnprintf
-__wake_up
-_write_trylock
-_write_unlock
diff --git a/safety/safety.py b/safety/safety.py
deleted file mode 100755 (executable)
index 8607ce7..0000000
+++ /dev/null
@@ -1,245 +0,0 @@
-#!/usr/bin/env python
-# -*- coding: utf-8 -*-
-# vim: noet sw=4 ts=4 enc=utf-8
-"A static safety-checker for SystemTap modules."
-
-# Copyright (C) 2006 Intel Corporation.
-#
-# This file is part of systemtap, and is free software.  You can
-# redistribute it and/or modify it under the terms of the GNU General
-# Public License (GPL); either version 2, or (at your option) any
-# later version.
-
-
-# in python 2.4, set & frozenset are builtins
-# in python 2.3, the equivalents live in the 'sets' module
-from sys import hexversion as __hexversion
-if __hexversion < 0x020400f0:
-       from sets import Set as set, ImmutableSet as frozenset
-
-
-def main(argv):
-       """
-               CLI to the SystemTap static safety-checker.
-
-               Provides a command-line interface for running the SystemTap module
-               safety checker.  Use '-h' or '--help' for a description of the
-               command-line options.
-
-               Returns the number of modules that failed the check.
-       """
-       bad = 0
-       (options, args) = __parse_args(argv[1:])
-       safe = StaticSafety(options.arch, options.release, options.datapath)
-       for m in args:
-               if not safe.check_module(m):
-                       bad += 1
-       return bad
-
-
-def __parse_args(argv):
-       from optparse import OptionParser
-       parser = OptionParser(usage="usage: %prog [options] [module]...",
-                       description=__doc__)
-       parser.add_option('--data-path', dest='datapath', metavar='PATH',
-                       help='specify the whitelist data files [default: <script-dir>/data]')
-       parser.add_option('-m', '--machine', '--architecture', dest='arch',
-                       help='specify the machine architecture of the target')
-       parser.add_option('-r', '--kernel-release', dest='release',
-                       help='specify the kernel release running on the target')
-       return parser.parse_args(argv)
-
-
-class StaticSafety:
-       "Manage a safety-checking session."
-
-       def __init__(self, arch=None, release=None, datapath=None):
-               from os import uname
-               self.__arch = arch or uname()[4]
-               self.__release = release or uname()[2]
-               self.__build_data_path(datapath)
-               self.__build_search_suffixes()
-               self.__load_allowed_references()
-               self.__load_allowed_opcodes()
-
-       def __build_data_path(self, datapath):
-               "Determine where the data directory resides."
-               from sys import argv
-               from os.path import dirname, isdir, realpath
-               if datapath is None:
-                       local = dirname(realpath(argv[0]))
-                       self.__data_path = local + '/data'
-               else:
-                       self.__data_path = datapath
-
-               if not isdir(self.__data_path):
-                       raise StandardError(
-                                       "Can't find the data directory! (looking in %s)"
-                                       % self.__data_path)
-
-       def __build_search_suffixes(self):
-               "Construct arch & kernel-versioning search suffixes."
-               ss = set()
-
-               # add empty string
-               ss.add('')
-
-               # add architecture search path
-               archsfx = '-%s' % self.__arch
-               ss.add(archsfx)
-
-               # add full kernel-version-release (2.6.NN-FOOBAR) + arch
-               relsfx = '-%s' % self.__release
-               ss.add(relsfx)
-               ss.add(relsfx + archsfx)
-
-               # add kernel version (2.6.NN) + arch
-               dash_i = relsfx.find('-')
-               if dash_i > 0:
-                       ss.add(relsfx[:dash_i])
-                       ss.add(relsfx[:dash_i] + archsfx)
-
-               # start dropping decimals
-               dot_i = relsfx.rfind('.', 0, dash_i)
-               while dot_i > 0:
-                       ss.add(relsfx[:dot_i])
-                       ss.add(relsfx[:dot_i] + archsfx)
-                       dot_i = relsfx.rfind('.', 0, dot_i)
-
-               self.__search_suffixes = frozenset(ss)
-       
-       def __load_allowed_references(self):
-               "Build the list of allowed external references from the data files."
-               wr = set()
-               for sfx in self.__search_suffixes:
-                       try:
-                               refs = open(self.__data_path + '/references' + sfx)
-                               for line in refs:
-                                       wr.add(line.rstrip())
-                               refs.close()
-                       except IOError:
-                               pass
-               if not len(wr):
-                       raise StandardError("No whitelisted references found!")
-               self.__white_references = frozenset(wr)
-
-       def __load_allowed_opcodes(self):
-               "Build the regular expression matcher for allowed opcodes from the data files."
-               from re import compile
-               wo = []
-               for sfx in self.__search_suffixes:
-                       try:
-                               opcs = open(self.__data_path + '/opcodes' + sfx)
-                               for line in opcs:
-                                       wo.append(line.rstrip())
-                               opcs.close()
-                       except IOError:
-                               pass
-               if not len(wo):
-                       raise StandardError("No whitelisted opcodes found!")
-               self.__white_opcodes_re = compile(r'^(?:' + r'|'.join(wo) + r')$')
-
-       def __check_references(self, module):
-               "Check that all unresolved references in the module are allowed."
-               from os import popen
-               from re import compile
-
-               sym_re = compile(r'^([\w@.]+) [Uw]\s+$')
-               def check(line):
-                       m = sym_re.match(line)
-                       if m:
-                               ref = m.group(1)
-                               if ref not in self.__white_references:
-                                       print 'ERROR: Invalid reference to %s' % ref
-                                       return False
-                               return True
-                       print 'WARNING: Unmatched line:\n  %s' % `line`
-                       return True
-
-               command = 'nm --format=posix --no-sort --undefined-only ' + `module`
-               ok = True
-               nm = popen(command)
-               for line in nm:
-                       ok &= check(line)
-               if nm.close():
-                       ok = False
-               return ok
-
-       def __check_opcodes(self, module):
-               "Check that all disassembled opcodes in the module are allowed."
-               from os import popen
-               from re import compile
-
-               skip_ud2a = [0]
-
-               ignore_re = compile(r'^$|^\s+\.{3}$|^.*Disassembly of section|^.*file format')
-               if self.__arch == 'ia64':
-                       opc = r'(?:\[[IBFLMX]{3}\]\s+)?(?:\(p\d\d\)\s+)?([\w.]+)\b'
-               elif self.__arch == 'x86_64' or self.__arch == 'i686':
-                       opc = r'(?:lock\s+)?|(?:repn?[ze]?\s+)?|(?:rex\w+\s+)?(\w+)\b'
-               else:
-                       opc = r'(\w+)\b'
-               opc_re = compile(r'^[A-Fa-f\d]+\s+<([^>]+)>\s+%s' % opc)
-               def check(line):
-                       m = ignore_re.match(line)
-                       if m:
-                               return True
-                       m = opc_re.match(line)
-                       if m:
-                               loc, opc = m.groups()
-                               if opc == 'ud2a':
-                                       # The kernel abuses ud2a for BUG checks by following it
-                                       # directly with __LINE__ and __FILE__.  Objdump doesn't
-                                       # know this though, so it tries to interpret the data as
-                                       # real instructions.  Because x86(-64) instructions are
-                                       # variable-length, it's hard to tell when objdump is synced
-                                       # up again.  We'll fast-forward to the next function
-                                       # boundary and hope things are better there.
-                                       for skip in objdump:
-                                               mskip = opc_re.match(skip)
-                                               if mskip:
-                                                       locskip = mskip.group(1)
-                                                       # a loc without an offset marks a new function
-                                                       if '+' not in locskip:
-                                                               return check(skip)
-                                                       skip_ud2a[0] += 1
-                                       return True
-                               elif not self.__white_opcodes_re.match(opc):
-                                       print "ERROR: Invalid opcode '%s' at <%s>" % (opc, loc)
-                                       return False
-                               return True
-                       print 'WARNING: Unmatched line:\n  %s' % `line`
-                       return True
-
-               command = 'objdump --disassemble --prefix-addresses ' + `module`
-               ok = True
-               objdump = popen(command)
-               for line in objdump:
-                       ok &= check(line)
-               if objdump.close():
-                       ok = False
-
-               if skip_ud2a[0]:
-                       #print 'WARNING: Skipped %d lines due to ud2a corruption' % skip_ud2a[0]
-                       pass
-
-               return ok
-
-       def check_module(self, module):
-               "Check a module for exclusively safe opcodes and external references."
-               from os.path import isfile
-               if not isfile(module):
-                       print 'ERROR: %s is not a file!' % `module`
-                       return False
-               res = self.__check_references(module) and self.__check_opcodes(module)
-               if res:
-                       print 'PASS: %s' % module
-               else:
-                       print 'FAIL: %s' % module
-               return res
-
-
-if __name__ == '__main__':
-       from sys import exit, argv
-       exit(main(argv))
-
index acfc64c334b0e5a6265430bf34b6ef5048381c5f..c557350a61640c076932b3a5c330e5510d005cd2 100644 (file)
--- a/stap.1.in
+++ b/stap.1.in
@@ -467,12 +467,11 @@ For prologue style alias, the statement block that follows an alias
 definition is implicitly added as a prologue to any probe that refers
 to the alias. While for the epilogue style alias, the statement block
 that follows an alias definition is implicitly added as an epilogue to
-any probe that refers to the alias.  For example:
+any probe that refers to the alias. For example:
 
 .SAMPLE
 probe syscall.read = kernel.function("sys_read") {
   fildes = $fd
-  if (execname == "init") next  # skip rest of probe
 }
 .ESAMPLE
 defines a new probe point
@@ -483,23 +482,19 @@ which expands to
 .nh
 .IR kernel.function("sys_read") ,
 .hy
-with the given statement as a prologue, which is useful to predefine
-some variables for the alias user and/or to skip probe processing
-entirely based on some conditions.  And
+with the given statement as a prologue. And 
 .SAMPLE
 probe syscall.read += kernel.function("sys_read") {
-  if (tracethis) println ($fd)
+  fildes = $fd
 }
 .ESAMPLE
-defines a new probe point with the given statement as an epilogue, which
-is useful to take actions based upon variables set or left over by the
-the alias user.
+defines a new probe point with the given statement as an epilogue. 
 
-An alias is used just like a built-in probe type.
+Another probe definition
+may use the alias like this:
 .SAMPLE
 probe syscall.read {
   printf("reading fd=%d\n", fildes)
-  if (fildes > 10) tracethis = 1
 }
 .ESAMPLE
 
index 9bca845d32e696a3370362216290e015ee4fa194..85a00b3774b8c9482cac07ae2fd1e138b05f1957 100644 (file)
@@ -92,60 +92,6 @@ fault, return instead the err_msg value.
 user_string_warn:string (addr:long)
 Copy a string from user space at given address.  If the access would
 fault, signal a warning and return "<unknown>".
-.TP
-user_string_quoted:string (addr:long)
-Copy a string from user space at given address. Any ASCII characters
-that are not printable are replaced by the corresponding escape
-sequence in the returned string.
-.TP
-user_string_n:string (addr:long, n:long)
-Copy a string of n bytes from user space at given address. If the access
-would fault, return "<unknown>".
-.TP
-user_string_n2:string (addr:long, n:long, err_msg:string)
-Copy a string of n bytes from user space at given address. If the access
-would fault, return the err_msg value.
-.TP
-user_string_n_warn:string (addr:long, n:long)
-Copy a string of n bytes from user space at given address. If the access
-would fault, signal a warning and return "<unknown>".
-.TP
-user_string_n_quoted:string (addr:long, n:long)
-Copy a string of n bytes from user space at given address. Any ASCII
-characters that are not printable are replaced by the corresponding escape
-sequence in the returned string. If the access would fault, return "<unknown>".
-.TP
-user_short:long (addr:long)
-Copy a short from user space at given address. If the access would fault,
-return 0.
-.TP
-user_short_warn:long (addr:long)
-Copy a short from user space at given address. If the access would fault,
-signal a warning and return 0.
-.TP
-user_int:long (addr:long)
-Copy an int from user space at given address. If the access would fault,
-return 0.
-.TP
-user_int_warn:long (addr:long)
-Copy an int from user space at given address. If the access would fault,
-signal a warning and return 0.
-.TP
-user_long:long (addr:long)
-Copy a long from user space at given address. If the access would fault,
-return 0.
-.TP
-user_long_warn:long (addr:long)
-Copy a long from user space at given address. If the access would fault,
-signal a warning and return 0.
-.TP
-user_char:long (addr:long)
-Copy a char from user space at given address. If the access would fault,
-return 0.
-.TP
-user_char_warn:long (addr:long)
-Copy a char from user space at given address. If the access would fault,
-signal a warning and return 0.
 .SS STRING
 .TP
 strlen:long (str:string)
index dae8b452287b0a43b0f0679625a56d65a2ed5aa0..da21a5ff7fa2b12351af31c2f8c364ccd10a77c4 100644 (file)
@@ -1,11 +1,3 @@
-2008-03-21  Eugene Teo  <eugeneteo@kernel.sg>
-
-       PR 5528
-       * conversions.stp (user_string_n, user_string_n2, user_string_n_warn,
-       user_string_n_quoted, user_short, user_short_warn, user_int,
-       user_int_warn, user_long, user_long_warn, user_char, user_char_warn):
-       New user_* functions.
-
 2008-03-20  Frank Ch. Eigler  <fche@elastic.org>
 
        PR 5956.
index 70725e9d327e244313354fecd6d8f410288f7f4a..af993992aee3b01bc0a064c6ad5a0e1ff57242b7 100644 (file)
@@ -1,5 +1,5 @@
 // conversions tapset
-// Copyright (C) 2005-2008 Red Hat Inc.
+// Copyright (C) 2005-2007 Red Hat Inc.
 // Copyright (C) 2007 Intel Corporation.
 //
 // This file is part of systemtap, and is free software.  You can
@@ -108,131 +108,3 @@ function user_string_quoted:string (addr:long) %{ /* pure */
     _stp_text_str(THIS->__retvalue, (char *)(uintptr_t)THIS->addr,
         MAXSTRINGLEN, 1, 1);
 %}
-
-function user_string_n:string (addr:long, n:long) {
-       return user_string_n2(addr, n, "<unknown>")
-}
-       
-function user_string_n2:string (addr:long, n:long, err_msg:string) %{ /* pure */
-       long len = THIS->n + 1;
-       len = (len > MAXSTRINGLEN) ? MAXSTRINGLEN : len;
-       if (_stp_strncpy_from_user(THIS->__retvalue,
-                               (char __user *) (uintptr_t) THIS->addr,
-                               len) < 0)
-               strlcpy(THIS->__retvalue, THIS->err_msg, MAXSTRINGLEN);
-%}
-
-function user_string_n_warn:string (addr:long, n:long) %{ /* pure */
-       long len = THIS->n + 1;
-       long rc;
-
-       len = (len > MAXSTRINGLEN) ? MAXSTRINGLEN : len;
-       rc = _stp_strncpy_from_user(THIS->__retvalue,
-                       (char __user *) (uintptr_t) THIS->addr, len);
-       if (rc < 0) {
-               // NB: using error_buffer to get local space for the warning, but we're
-               // not aborting, so leave last_error alone.
-               snprintf (CONTEXT->error_buffer, sizeof(CONTEXT->error_buffer),
-                               "user string copy fault %ld at %p", rc,
-                               (void *) (uintptr_t) THIS->addr);
-               _stp_warn(CONTEXT->error_buffer);
-               strlcpy (THIS->__retvalue, "<unknown>", MAXSTRINGLEN);
-       }
-%}
-
-function user_string_n_quoted:string (addr:long, n:long) %{ /* pure */
-       long len = THIS->n + 1;
-       if (THIS->addr == 0)
-               strlcpy(THIS->__retvalue, "NULL", MAXSTRINGLEN);
-       else
-               /* XXX: stp_text_str uses sleepy __get_user() => unsafe ?!  */
-               _stp_text_str(THIS->__retvalue, (char *)(uintptr_t)THIS->addr,
-                               len, 1, 1);
-%}
-
-// When userspace data is not accessible, the following functions return 0
-
-function user_short:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (short *) (intptr_t) THIS->addr, sizeof(short)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (short *) (intptr_t) THIS->addr)) {
-fault:
-               THIS->__retvalue = 0;
-       }
-%}
-
-function user_short_warn:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (short *) (intptr_t) THIS->addr, sizeof(short)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (short *) (intptr_t) THIS->addr)) {
-fault:
-               snprintf (CONTEXT->error_buffer, sizeof(CONTEXT->error_buffer),
-                               "user short copy fault %p", (void *) (uintptr_t) THIS->addr);
-               _stp_warn(CONTEXT->error_buffer);
-               THIS->__retvalue = 0;
-       }
-%}
-
-function user_int:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (int *) (intptr_t) THIS->addr, sizeof(int)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (int *) (intptr_t) THIS->addr)) {
-fault:
-               THIS->__retvalue = 0;
-       }
-%}
-
-function user_int_warn:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (int *) (intptr_t) THIS->addr, sizeof(int)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (int *) (intptr_t) THIS->addr)) {
-fault:
-               snprintf (CONTEXT->error_buffer, sizeof(CONTEXT->error_buffer),
-                               "user int copy fault %p", (void *) (uintptr_t) THIS->addr);
-               _stp_warn(CONTEXT->error_buffer);
-               THIS->__retvalue = 0;
-       }
-%}
-
-function user_long:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (long *) (intptr_t) THIS->addr, sizeof(long)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (long *) (intptr_t) THIS->addr)) {
-fault:
-               THIS->__retvalue = 0;
-       }
-%}
-
-function user_long_warn:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (long *) (intptr_t) THIS->addr, sizeof(long)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (long *) (intptr_t) THIS->addr)) {
-fault:
-               snprintf (CONTEXT->error_buffer, sizeof(CONTEXT->error_buffer),
-                               "user long copy fault %p", (void *) (uintptr_t) THIS->addr);
-               _stp_warn(CONTEXT->error_buffer);
-               THIS->__retvalue = 0;
-       }
-%}
-
-function user_char:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (char *) (intptr_t) THIS->addr, sizeof(char)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (char *) (intptr_t) THIS->addr)) {
-fault:
-               THIS->__retvalue = 0;
-       }
-%}
-
-function user_char_warn:long (addr:long) %{ /* pure */
-       if (!access_ok(VERIFY_READ, (char *) (intptr_t) THIS->addr, sizeof(char)))
-               goto fault;
-       if (__stp_get_user(THIS->__retvalue, (char *) (intptr_t) THIS->addr)) {
-fault:
-               snprintf (CONTEXT->error_buffer, sizeof(CONTEXT->error_buffer),
-                               "user char copy fault %p", (void *) (uintptr_t) THIS->addr);
-               _stp_warn(CONTEXT->error_buffer);
-               THIS->__retvalue = 0;
-       }
-%}
-
index a54e80bd5b4a45856f995e61e15aece391a7e4df..16f7af5767254d68fb375ebdd78fd57c16d3252c 100644 (file)
@@ -1,21 +1,3 @@
-2008-03-23  Frank Ch. Eigler  <fche@elastic.org>
-
-       * lib/stap_run.exp (stap_run): Ignore missing debuginfo warnings.
-       Try harder to kill stap child in case of timeouts and errors.
-
-2008-03-23  Frank Ch. Eigler  <fche@elastic.org>
-
-       PR 5980.
-       * lib/systemtap.exp: Set default Snapshot: value from "stap -V"
-       output.
-
-2008-03-21  Eugene Teo  <eugeneteo@kernel.sg>
-
-       PR 5528
-       * systemtap.stress/conversions.stp: Test new user_* functions.
-       * buildok/conversions.stp: Test new user_* functions.
-       * buildok/conversions-embedded.stp: Test new user_* functions.
-
 2008-03-20  Frank Ch. Eigler  <fche@elastic.org>
 
        PR 5956.
index 55f6cdb780b782b26cb6a7cca2e81947ae23e17c..7aa5a0b47b0216d32a5da1cbdc0eef2e631641dd 100755 (executable)
@@ -9,18 +9,5 @@ probe begin {
        print (user_string2 (0, ""))
        print (user_string_warn (0))
        print (user_string_quoted (0))
-
-       print (user_string_n(0, 5))
-       print (user_string_n2(0, 5, "foobar"))
-       print (user_string_n_warn(0, 0))
-       print (user_string_n_quoted(0, 0))
-       print (user_short(0))
-       print (user_short_warn(0))
-       print (user_int(0))
-       print (user_int_warn(0))
-       print (user_long(0))
-       print (user_long_warn(0))
-       print (user_char(0))
-       print (user_char_warn(0))
 }
 
index 5f151f1d5ab1834e6d7e94e783a0cf62ae49fb9c..e83bd968b44e0244312d6f266db1210786039aca 100755 (executable)
@@ -12,17 +12,4 @@ probe begin {
   print (user_string(2342))
   print (user_string2(2342,"foobar"))
   print (user_string_warn(2342))
-
-  print (user_string_n(2342, 5))
-  print (user_string_n2(2342, 5, "foobar"))
-  print (user_string_n_warn(2342, 5))
-  print (user_string_n_quoted(2342, 5))
-  print (user_short(2342))
-  print (user_short_warn(2342))
-  print (user_int(2342))
-  print (user_int_warn(2342))
-  print (user_long(2342))
-  print (user_long_warn(2342))
-  print (user_char(2342))
-  print (user_char_warn(2342))
 }
index 42efa4f8e7b2017a45187a937315a9747ab9154e..c2b4e74d4e512c2bc88b66c4c3dfe0409dea4e4b 100644 (file)
@@ -34,7 +34,6 @@ proc stap_run { TEST_NAME {LOAD_GEN_FUNCTION ""} {OUTPUT_CHECK_STRING ""} args }
     expect {
        -timeout 180
        -re {^Warning: using '-m' disables cache support.\r\n} {exp_continue}
-       -re {^WARNING: cannot find module [^\r]*DWARF[^\r]*\r\n} {exp_continue}
        -re {^Pass\ ([1234]):[^\r]*\ in\ ([0-9]+)usr/([0-9]+)sys/([0-9]+)real\ ms\.\r\n}
        {set pass$expect_out(1,string) "\t$expect_out(2,string)\t$expect_out(3,string)\t$expect_out(4,string)"; exp_continue}
        -re {^Pass\ ([34]): using cached [^\r]+\r\n}
@@ -74,22 +73,15 @@ proc stap_run { TEST_NAME {LOAD_GEN_FUNCTION ""} {OUTPUT_CHECK_STRING ""} args }
                            set skipped_probes $expect_out(2,string)}
                    }
                }
-               timeout { 
-                    fail "$TEST_NAME shutdown (timeout)"
-                    exec kill -INT -[exp_pid] 
-                }
+               timeout { fail "$TEST_NAME shutdown (timeout)" }
                eof { fail "$TEST_NAME shutdown (eof)" }
            }
        }
        -re "semantic error:" { fail "$TEST_NAME compilation" }
-       timeout { 
-            fail "$TEST_NAME startup (timeout)"
-            exec kill -INT -[exp_pid]
-        }
+       timeout { fail "$TEST_NAME startup (timeout)"
+                 exec kill -INT [exp_pid] }
        eof { fail "$TEST_NAME startup (eof)" }
     }
-  # again for good measure
-  exec kill -INT -[exp_pid]
   catch close
   wait
 }
index d458e98f1e62c6d5967523fd063dcd1221b43f8b..baed0e412008a7e63d26f5bc805499d9b5a3aaf3 100644 (file)
@@ -58,9 +58,8 @@ proc get_system_info {} {
     } elseif [file exists $env(SRCDIR)/../SNAPSHOT] {
        set Snapshot [exec /bin/cat $env(SRCDIR)/../SNAPSHOT]
     } else {
-        regexp {version [^)]*} [exec stap -V 2>@ stdout] version
-       set Snapshot $version
-    }
+       set Snapshot "unknown"
+       }
     set Distro "Linux"
     if [file exists /etc/fedora-release] {set Distro [exec /bin/cat /etc/fedora-release]}
     if [file exists /etc/redhat-release] {set Distro [exec /bin/cat /etc/redhat-release]}
index 34bd0c28a825e2ecf88b5f4c0d19b7d7b28cd691..07795a6ddf20f26278453e0f1c8795295d00443e 100644 (file)
@@ -13,16 +13,4 @@ probe begin { print (user_string ($1)) }
 probe begin { print (user_string2 ($1,"<only suspected, not known>")) }
 probe begin { print (user_string_warn ($1)) }
 probe begin { print (user_string_quoted ($1)) }
-probe begin { print (user_string_n ($1, 5)) }
-probe begin { print (user_string_n2 ($1, 5, "<only suspected, not known>")) }
-probe begin { print (user_string_n_warn ($1, 5)) }
-probe begin { print (user_string_n_quoted ($1, 5)) }
-probe begin { print (user_short ($1)) }
-probe begin { print (user_short_warn ($1)) }
-probe begin { print (user_int ($1)) }
-probe begin { print (user_int_warn ($1)) }
-probe begin { print (user_long ($1)) }
-probe begin { print (user_long_warn ($1)) }
-probe begin { print (user_char ($1)) }
-probe begin { print (user_char_warn ($1)) }
 probe begin(1) { print ("\n") exit () }
index 2bfacefc8205cba792845d31989b360e7d46f373..8b9dee5456a060e776d0708e1ff1b4f6b06f9848 100644 (file)
@@ -4356,80 +4356,43 @@ c_unparser::visit_hist_op (hist_op*)
 int
 emit_symbol_data (systemtap_session& s)
 {
-  int rc = 0;
-
   // Instead of processing elf symbol tables, for now we just snatch
-  // /proc/kallsyms and convert it to our use.  We need it sorted by
-  // address (so we can binary search) , and filtered (to show text
-  // symbols only), a task that we defer to grep(1) and sort(1).  It
-  // may be useful to cache the symbols.sorted file, perhaps indexed
-  // by md5sum(/proc/modules), but let's not until this simple method
-  // proves too costly.  LC_ALL=C is already set to avoid the
-  // excessive penalty of i18n code in some glibc/coreutils versions.
-
-  string sorted_kallsyms = s.tmpdir + "/symbols.sorted";
-  string sortcmd = "grep \" [AtT] \" /proc/kallsyms | ";
-  if (s.symtab == false)
-    {
-      s.op->newline() << "/* filled in by runtime */";
-      s.op->newline() << "struct stap_symbol *stap_symbols;";
-      s.op->newline() << "unsigned stap_num_symbols;\n";
-      return 0;
-    }
+  // /proc/kallsyms and convert it to our use.  
 
-  sortcmd += "sort ";
-#if __LP64__
-  sortcmd += "-k 1,16 ";
-#else
-  sortcmd += "-k 1,8 ";
-#endif
-  sortcmd += "-s -o " + sorted_kallsyms;
+  unsigned i=0;
+  ifstream kallsyms("/proc/kallsyms");
+  char kallsyms_outbuf [4096];
+  ofstream kallsyms_out ((s.tmpdir + "/stap-symbols.h").c_str());
+  kallsyms_out.rdbuf()->pubsetbuf (kallsyms_outbuf,
+                                       sizeof(kallsyms_outbuf));
 
-  if (s.verbose>1) clog << "Running " << sortcmd << endl;
-  rc = system(sortcmd.c_str());
-  if (rc == 0)
+  s.op->newline() << "\n\n#include \"stap-symbols.h\"";
+  kallsyms_out << "struct _stp_symbol _stp_kernel_symbols [] = {";
+  string lastaddr, modules_op_addr;
+
+  while (! kallsyms.eof())
     {
-      ifstream kallsyms (sorted_kallsyms.c_str());
-      char kallsyms_outbuf [4096];
-      ofstream kallsyms_out ((s.tmpdir + "/stap-symbols.h").c_str());
-      kallsyms_out.rdbuf()->pubsetbuf (kallsyms_outbuf,
-                                       sizeof(kallsyms_outbuf));
-      
-      s.op->newline() << "\n\n#include \"stap-symbols.h\"";
+      string addr, type, sym;
+      kallsyms >> addr >> type >> sym >> ws;
 
-      unsigned i=0;
-      kallsyms_out << "struct stap_symbol _stp_stap_symbols [] = {";
-      string lastaddr;
-      while (! kallsyms.eof())
+      if (kallsyms.peek() == '[')
+       break;
+      
+      // NB: kallsyms includes some duplicate addresses
+      if ((type == "t" || type == "T" || type == "A") && lastaddr != addr)
        {
-         string addr, type, sym, module;
-         kallsyms >> addr >> type >> sym;
-         kallsyms >> ws;
-         if (kallsyms.peek() == '[')
-           {
-             string bracketed;
-             kallsyms >> bracketed;
-             module = bracketed.substr (1, bracketed.length()-2);
-           }
-         
-         // NB: kallsyms includes some duplicate addresses
-         if ((type == "t" || type == "T" || type == "A") && lastaddr != addr)
-           {
-             kallsyms_out << "  { 0x" << addr << ", "
-                           << "\"" << sym << "\", "
-                           << "\"" << module << "\" },"
-                           << "\n";
-             lastaddr = addr;
-             i ++;
-           }
+         kallsyms_out << "  { 0x" << addr << ", " << "\"" << sym << "\" },\n";
+         lastaddr = addr;
+         i ++;
        }
-      kallsyms_out << "};\n";
-      kallsyms_out << "struct stap_symbol *stap_symbols = _stp_stap_symbols;";
-      kallsyms_out << "unsigned stap_num_symbols = " << i << ";\n";
+      else if (sym == "modules_op")
+       modules_op_addr = addr;
     }
+  kallsyms_out << "};\n";
+  kallsyms_out << "unsigned _stp_num_kernel_symbols = " << i << ";\n";
+  kallsyms_out << "unsigned long _stp_modules_op = 0x" << modules_op_addr << ";\n";
 
-  return rc;
+  return (i == 0);
 }
 
 
@@ -4515,7 +4478,7 @@ translate_pass (systemtap_session& s)
       s.op->newline() << "#include <linux/random.h>";
       s.op->newline() << "#include <linux/utsname.h>";
       s.op->newline() << "#include \"loc2c-runtime.h\" ";
-      
+
       // XXX: old 2.6 kernel hack
       s.op->newline() << "#ifndef read_trylock";
       s.op->newline() << "#define read_trylock(x) ({ read_lock(x); 1; })";
diff --git a/vim/filetype.vim b/vim/filetype.vim
deleted file mode 100644 (file)
index 8c1fdfb..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-" Vim support file to detect file types
-" Language:    SystemTap
-" Maintainer:  Josh Stone <joshua.i.stone@intel.com>
-" Last Change: 2005 Dec 16
-" Note: this overrides the default *.stp mapping to "Stored Procedures"
-"   It would be nice to find a way to intelligently detect this.
-
-" SystemTap scripts
-au BufNewFile,BufRead *.stp                    setf stap
-
diff --git a/vim/ftplugin/stap.vim b/vim/ftplugin/stap.vim
deleted file mode 100644 (file)
index de49a4f..0000000
+++ /dev/null
@@ -1,25 +0,0 @@
-" Vim filetype plugin file
-" Language:    SystemTap
-" Maintainer:  Josh Stone <joshua.i.stone@intel.com>
-" Last Change: 2005 Dec 15
-
-" Only do this when not done yet for this buffer
-if exists("b:did_ftplugin")
-  finish
-endif
-
-" Don't load another plugin for this buffer
-let b:did_ftplugin = 1
-
-set cpo-=C
-
-let b:undo_ftplugin = "setl cin< fo< com<"
-
-setlocal cindent
-
-" Set 'formatoptions' to break comment lines but not other lines,
-" and insert the comment leader when hitting <CR> or using "o".
-setlocal fo-=t fo+=croql
-
-" Set 'comments' to format dashed lists in comments.
-setlocal comments=sO:*\ -,mO:*\ \ ,exO:*/,s1:/*,mb:*,ex:*/,://,:#
diff --git a/vim/indent/stap.vim b/vim/indent/stap.vim
deleted file mode 100644 (file)
index 16658d6..0000000
+++ /dev/null
@@ -1,35 +0,0 @@
-" Vim indent file
-" Language:    SystemTap
-" Maintainer:  Josh Stone <joshua.i.stone@intel.com>
-" Last Change: 2005 Dec 15
-
-" Only load this indent file when no other was loaded.
-if exists("b:did_indent")
-   finish
-endif
-let b:did_indent = 1
-
-" SystemTap indenting works *mostly* the same as C, so this gets things pretty
-" close.  For 'real' SystemTap indenting, we would have to write a custom
-" indentexpr function.
-
-" indenting is similar to C, so start there...
-setlocal cindent
-
-" Statements don't require a ';', so don't indent following lines
-setlocal cino=+0
-
-" Known issues:
-" - need to detect when following lines are a continuation of the previous
-"   statement, and indent appropriately.
-" - one-liners with control flow try to indent the next line if there's no
-"   ';'.  For example:
-"       if (my_condition) break
-"           do_work()
-"   The second line should not be indented.
-" - The embedded-C braces do not line up correctly
-" - Preprocessor braces don't line up correctly, and internals of the
-"   preprocessor aren't getting any special handling.
-" - Embedded-C statements across multiple lines don't indent
-" - '#' comments don't maintain indenting (they get treated like C
-"   preprocessor statements)
diff --git a/vim/syntax/stap.vim b/vim/syntax/stap.vim
deleted file mode 100644 (file)
index 86c7d26..0000000
+++ /dev/null
@@ -1,97 +0,0 @@
-" Vim syntax file
-" Language:    SystemTap
-" Maintainer:  Josh Stone <joshua.i.stone@intel.com>
-" Last Change: 2005 Dec 20
-
-" For version 5.x: Clear all syntax items
-" For version 6.x: Quit when a syntax file was already loaded
-if version < 600
-  syn clear
-elseif exists("b:current_syntax")
-  finish
-endif
-
-syn keyword stapStatement   contained break continue return next delete containedin=stapBlock
-syn keyword stapRepeat      contained while for foreach in containedin=stapBlock
-syn keyword stapConditional contained if else containedin=stapBlock
-syn keyword stapDeclaration global probe function
-syn keyword stapType        string long
-
-syn region stapProbeDec start="\<probe\>"lc=5 end="{"me=s-1 contains=stapString,stapNumber
-syn match stapProbe contained "\<\w\+\>" containedin=stapProbeDec
-
-syn region stapFuncDec start="\<function\>"lc=8 end=":\|("me=s-1 contains=stapString,stapNumber
-syn match stapFuncCall contained "\<\w\+\ze\(\s\|\n\)*(" containedin=stapBlock
-syn match stapFunc contained "\<\w\+\>" containedin=stapFuncDec,stapFuncCall
-
-syn match stapStat contained "@\<\w\+\ze\(\s\|\n\)*(" containedin=stapBlock
-
-" decimal number
-syn match      stapNumber              "\<\d\+\>" containedin=stapBlock
-" octal number
-syn match      stapNumber      "\<0\o\+\>" contains=stapOctalZero containedin=stapBlock
-" Flag the first zero of an octal number as something special
-syn match      stapOctalZero   contained "\<0"
-" flag an octal number with wrong digits
-syn match      stapOctalError  "\<0\o*[89]\d*" containedin=stapBlock
-" hex number
-syn match      stapNumber              "0x\x\+\>" containedin=stapBlock
-
-syn region  stapString  oneline start=+"+ skip=+\\"+ end=+"+ containedin=stapBlock
-
-syn region stapPreProc fold start="%(" end="%)" contains=stapNumber,stapString containedin=ALL
-syn keyword stapPreProcCond contained kernel_v kernel_vr arch containedin=stapPreProc
-
-syn include @C syntax/c.vim
-syn keyword stapCMacro  contained THIS CONTEXT containedin=@C,stapCBlock
-syn region  stapCBlock fold matchgroup=stapCBlockDelims start="%{"rs=e end="%}"re=s contains=@C
-
-syn region stapBlock fold matchgroup=stapBlockEnds start="{"rs=e end="}"re=s containedin=stapBlock
-
-syn keyword stapTodo    contained TODO FIXME XXX
-
-syn match   stapComment "#.*" contains=stapTodo containedin=stapBlock
-syn match   stapComment "//.*" contains=stapTodo containedin=stapBlock
-syn region  stapComment matchgroup=stapComment start="/\*" end="\*/" contains=stapTodo,stapCommentBad containedin=stapBlock
-syn match   stapCommentBad contained "/\*"
-
-" treat ^#! as special
-syn match   stapSharpBang   "^#!.*"
-
-
-" define the default highlighting
-" For version 5.7 and earlier: only when not done already
-" For version 5.8 and later: only when an item doesn't have highlightling yet
-if version >= 508 || !exists("did_stap_syn_inits")
-  if version < 508
-    let did_stap_syn_inits = 1
-    command -nargs=+ HiLink hi link <args>
-  else
-    command -nargs=+ HiLink hi def link <args>
-  endif
-
-  HiLink stapNumber            Number
-  HiLink stapOctalZero         PreProc " c.vim does it this way...
-  HiLink stapOctalError                Error
-  HiLink stapString            String
-  HiLink stapTodo       Todo
-  HiLink stapComment    Comment
-  HiLink stapCommentBad Error
-  HiLink stapSharpBang  PreProc
-  HiLink stapCBlockDelims  Special
-  HiLink stapCMacro Macro
-  HiLink stapStatement  Statement
-  HiLink stapConditional  Conditional
-  HiLink stapRepeat  Repeat
-  HiLink stapType  Type
-  HiLink stapProbe  Function
-  HiLink stapFunc  Function
-  HiLink stapStat  Function
-  HiLink stapPreProc  PreProc
-  HiLink stapPreProcCond  Special
-  HiLink stapDeclaration  Typedef
-
-  delcommand HiLink
-endif
-
-let b:current_syntax = "stap"
This page took 0.226944 seconds and 5 git commands to generate.