This jumbo-checkin is the Full Virtualization checkin.  This eliminates
Valgrind's dependency on the dynamic linker for getting started, and
instead takes things into its own hands.

This checkin doesn't add much in the way of new functionality, but it
is the basis for all future work on Valgrind.  It allows us much more
flexibility in implementation, and well as increasing the reliability
of Valgrind by protecting it more from its clients.

This patch requires some changes to tools to update them to the changes
in the tool API, but they are straightforward.  See the posting "Heads
up: Full Virtualization" on valgrind-developers for a more complete
description of this change and its effects on you.


git-svn-id: svn://svn.valgrind.org/valgrind/trunk@2118 a5019735-40e9-0310-863c-91ae7b9d1cf9
diff --git a/coregrind/Makefile.am b/coregrind/Makefile.am
index 4f5a6fc..4105775 100644
--- a/coregrind/Makefile.am
+++ b/coregrind/Makefile.am
@@ -1,40 +1,49 @@
 
-SUBDIRS = demangle . docs
+SUBDIRS = demangle . docs x86
 
-add_includes = -I$(srcdir)/demangle -I$(top_srcdir)/include
-
-AM_CPPFLAGS = $(add_includes) -DVG_LIBDIR="\"$(libdir)"\"
-AM_CFLAGS = $(WERROR) -Winline -Wall -Wshadow -O -fno-omit-frame-pointer \
-		@PREFERRED_STACK_BOUNDARY@ -g -fpic
-AM_CCASFLAGS = $(add_includes) -I..
+add_includes = -I$(srcdir)/demangle -I$(top_srcdir)/include -I$(srcdir)/x86
 
 valdir = $(libdir)/valgrind
+inplacedir = $(top_srcdir)/.in_place
 
-bin_SCRIPTS = valgrind
+AM_CPPFLAGS = $(add_includes) -DVG_LIBDIR="\"$(valdir)"\"
+AM_CFLAGS = $(WERROR) -Winline -Wall -Wshadow -O -fno-omit-frame-pointer \
+		@PREFERRED_STACK_BOUNDARY@ -g -DELFSZ=32
+AM_CCASFLAGS = $(add_includes) -I..
 
 default.supp: $(SUPP_FILES)
 
+bin_PROGRAMS = \
+	valgrind
+
 val_PROGRAMS = \
-	valgrind.so \
-	valgrinq.so \
-	libpthread.so
+	valgrind stage2 \
+	libpthread.so \
+	vg_inject.so
 
-EXTRA_DIST = vg_libpthread.vs valgrind.vs
+EXTRA_DIST = \
+	vg_libpthread.vs valgrind.vs \
+	gen_toolint.pl toolfuncs.def \
+	vg_replace_malloc.c
 
-libpthread_so_SOURCES = \
-	vg_libpthread.c \
-	vg_libpthread_unimp.c
-libpthread_so_DEPENDENCIES = $(srcdir)/vg_libpthread.vs
-libpthread_so_LDFLAGS	   = -Werror -fno-omit-frame-pointer -UVG_LIBDIR \
-	-shared -fpic \
-	-Wl,-version-script $(srcdir)/vg_libpthread.vs \
-	-Wl,-z,nodelete,-z,initfirst \
-	-Wl,--soname=libpthread.so.0
+BUILT_SOURCES = vg_toolint.c vg_toolint.h
+CLEANFILES = vg_toolint.c vg_toolint.h
 
-valgrinq_so_SOURCES = vg_valgrinq_dummy.c
-valgrinq_so_LDFLAGS = -shared
+valgrind_SOURCES = \
+	stage1.c \
+	ume.c \
+	x86/ume_entry.S \
+	x86/ume_go.c 
+valgrind_DEPENDENCIES =
+valgrind_LDFLAGS=-static -g -Wl,-e,_ume_entry
+valgrind_LDADD=
 
-valgrind_so_SOURCES = \
+stage2_SOURCES = \
+	stage2.c \
+	ume.c \
+	x86/ume_entry.S \
+	x86/ume_go.c \
+	\
 	vg_scheduler.c \
 	vg_default.c \
 	vg_demangle.c \
@@ -45,7 +54,6 @@
 	vg_hashtable.c \
 	vg_helpers.S \
 	vg_instrument.c \
-	vg_intercept.c \
 	vg_main.c \
 	vg_malloc2.c \
 	vg_memory.c \
@@ -60,47 +68,83 @@
 	vg_symtab2.c \
 	vg_dwarf.c \
 	vg_stabs.c \
+	vg_skiplist.c \
 	vg_symtypes.c \
 	vg_syscalls.c \
 	vg_syscall.S \
 	vg_to_ucode.c \
+	vg_toolint.c \
 	vg_translate.c \
 	vg_transtab.c \
 	vg_ldt.c
-valgrind_so_DEPENDENCIES = $(srcdir)/valgrind.vs
-valgrind_so_LDFLAGS = \
-	-Wl,-z,initfirst -shared \
+stage2_DEPENDENCIES = $(srcdir)/valgrind.vs $(srcdir)/x86/stage2.lds
+stage2_LDFLAGS=-Wl,--export-dynamic -Wl,-e,_ume_entry  -g \
+	-Wl,-defsym,kickstart_base=0xb8000000 \
+	-Wl,-T,$(srcdir)/x86/stage2.lds \
 	-Wl,-version-script $(srcdir)/valgrind.vs 
-
-valgrind_so_LDADD = \
+stage2_LDADD= \
 	demangle/cp-demangle.o \
 	demangle/cplus-dem.o \
 	demangle/dyn-string.o \
-	demangle/safe-ctype.o
+	demangle/safe-ctype.o \
+	-ldl
 
-## Build a .a library, but we don't actually use it;  just a ploy to ensure
-## vg_replace_malloc.o is built.
-noinst_LIBRARIES = lib_replace_malloc.a
+vg_toolint.c: $(srcdir)/gen_toolint.pl $(srcdir)/toolfuncs.def $(srcdir)/Makefile
+	rm -f $@
+	$(PERL) $(srcdir)/gen_toolint.pl callwrap     < $(srcdir)/toolfuncs.def >  $@ || rm -f $@
+	$(PERL) $(srcdir)/gen_toolint.pl missingfuncs < $(srcdir)/toolfuncs.def >> $@ || rm -f $@
+	$(PERL) $(srcdir)/gen_toolint.pl initfunc     < $(srcdir)/toolfuncs.def >> $@ || rm -f $@
+	$(PERL) $(srcdir)/gen_toolint.pl initdlsym    < $(srcdir)/toolfuncs.def >> $@ || rm -f $@
+	$(PERL) $(srcdir)/gen_toolint.pl structdef    < $(srcdir)/toolfuncs.def >> $@ || rm -f $@
 
-lib_replace_malloc_a_SOURCES = vg_replace_malloc.c
+vg_toolint.h:  $(srcdir)/gen_toolint.pl $(srcdir)/toolfuncs.def $(srcdir)/Makefile
+	rm -f $@
+	$(PERL) $(srcdir)/gen_toolint.pl proto  < $(srcdir)/toolfuncs.def >  $@ || rm -f $@
+	$(PERL) $(srcdir)/gen_toolint.pl struct < $(srcdir)/toolfuncs.def >> $@ || rm -f $@
+
+libpthread_so_SOURCES = \
+	vg_libpthread.c \
+	vg_libpthread_unimp.c \
+	vg_syscall.S
+libpthread_so_DEPENDENCIES = $(srcdir)/vg_libpthread.vs
+libpthread_so_LDFLAGS	   = -Werror -fno-omit-frame-pointer -UVG_LIBDIR \
+	-shared -fpic \
+	-Wl,-version-script $(srcdir)/vg_libpthread.vs \
+	-Wl,-z,nodelete \
+	-Wl,--soname=libpthread.so.0
+
+vg_inject_so_SOURCES = \
+	vg_intercept.c 
+
+# Not really true, but we need to build vg_replace_malloc.o somehow
+vg_inject_so_DEPENDENCIES = \
+	vg_replace_malloc.o
+
+vg_inject_so_LDFLAGS = \
+	-shared \
+	-Wl,--soname,vg_inject.so \
+	-Wl,-z,initfirst
 
 noinst_HEADERS = \
+	ume.h			\
+	ume_arch.h		\
         vg_include.h            \
         vg_constants.h          \
 	vg_symtab2.h		\
         vg_unistd.h             \
 	vg_symtypes.h		\
+	vg_toolint.h		\
 	vg_unsafe.h
 
-MANUAL_DEPS = $(noinst_HEADERS) $(include_HEADERS) .in_place/libpthread.so.0
+MANUAL_DEPS = $(noinst_HEADERS) $(include_HEADERS) $(inplacedir)/libpthread.so.0
 
-vg_intercept.o vg_libpthread.o vg_replace_malloc.o: CFLAGS += -fno-omit-frame-pointer
+vg_replace_malloc.o vg_intercept.o vg_libpthread.o: CFLAGS += -fno-omit-frame-pointer -g -fpic
 
 all-local:
-	mkdir -p .in_place
-	-rm -f .in_place/libpthread.so.0
-	-rm -f .in_place/valgrind.so
-	-rm -f .in_place/valgrinq.so
-	ln -f -s ../libpthread.so .in_place/libpthread.so.0
-	ln -f -s ../valgrind.so .in_place/valgrind.so
-	ln -f -s ../valgrinq.so .in_place/valgrinq.so
+	mkdir -p $(inplacedir)
+	for i in $(val_PROGRAMS); do \
+		to=$(inplacedir)/$$(echo $$i | sed 's,libpthread.so,libpthread.so.0,'); \
+		rm -f $$$to; \
+		ln -sf $(top_srcdir)/$(subdir)/$$i $$to; \
+	done
+