Browse Source

Add mpers support

Add a subsystem for semi-automatical definition of how parsers should
work with personality-dependent (mpers) types of tracee's data.  Create
auxiliary libraries containing mpers syscall parsers and printer
functions, one library for each possible nonnative target personality.

Currently some parsers do not handle differences in definitions of data
types between personalities, namely LP64 and ILP32.  When
this is the case, long integers, pointers, and all compound
types containing long and pointer members may be printed incorrectly,
because of differences in sizes, offsets and alignments.

Since in most cases these are the only differences in desired behaviour
of parsers and printers for different personalities, a correct way
would be to compile one source code into multiple parsers, differing
only in definitions of mpers types.

To get a definition of a given type for nonnative personality
a very basic .c file containing a declaration of a variable of this type
is being compiled for this personality (using -m32 or -mx32 compiler
flag).  Information about the type is then being extracted from
this binary's DWARF debug info with an awk script and put
into a corresponding header file.  Resulting headers are being used to
compile mpers variations of syscall parsers and printer functions.

In addition to syscall parsers, there can occur a need to create mpers
printing functions, which then can be called from many places
in the code (for example, printsiginfo_at).  Such functions (printers)
are marked in a special manner.

For each possible nonnative target personality a library is being
created, containing mpers variations of syscall parsers and printers.
Only syscall parsers from files marked in a special manner and specially
marked functions from such files are being recompiled and included
in these libraries.

generate_mpers_am.sh is called by bootstrap to find the files
from strace_SOURCES which include MPERS_DEFS.  During compilation,
these files are being inspected for inclusions of DEF_MPERS_TYPE,
and nonnative variations of each included type are being generated
by an awk script.

Mpers parser names are being modified during inclusions of syscallent
headers for nonnative personalities.  Pointers to printers are
being stored in structs struct_printers, and a master
pointer printers is being updated on every set_personality.

* README-mpers: New README explaining how to use mpers support.
* empty.h: New empty file.
* generate_mpers_am.sh: New file.
* mpers.awk: Likewise.
* mpers.sh: Likewise.
* mpers_test.sh: Likewise.
* mpers_type.h: Likewise.
* Makefile.am (strace_SOURCES): Add empty.h and mpers_type.h.
(strace_CPPFLAGS, strace_LDFLAGS, strace_LDADD): Move to the beginning
of the file.
(strace_LDADD, noinst_LIBRARIES): Add libmpers-%.a.
(EXTRA_DIST): Add mpers.awk, mpers.sh, mpers_test.sh.
(BUILT_SOURCES, CLEANFILES): Add new generated files:
native_printer_decls.h, native_printer_defs.h, printers.h,
[HAVE_M32_MPERS] $(mpers_m32_targets), and [HAVE_MX32_MPERS]
$(mpers_mx32_targets).
(mpers_NAME, mpers_PREFIX, mpers_DEFS, mpers_INCLUDES, mpers_CPPFLAGS,
mpers_sh_opts, libmpers_CPPFLAGS, libmpers_m[x]32_a_SOURCES,
libmpers_m[x]32_a_CPPFLAGS, mpers_m[x]32_targets): New variables.
(mpers-m[x]32.stamp, m[x]32_defs.h, m[x]32_funcs.h, printers.h,
%_printer_decls.h, %_printer_defs.h, clean-local,
native_printer_decls.h, native_printer_defs.h, $mpers_m[x]32_targets):
New targets.
* bootstrap: Add generate_mpers_am.sh.
* configure.ac: Add AC_PROG_RANLIB.
* m4/mpers.m4: Add HAVE_MPERS variable.  Add $st_cv_mpers checks.
* defs.h: Include mpers_type.h.
Include printers.h, native_printer_decls.h, define MPERS_PRINTER_NAME.
Redefine SYS_FUNC_NAME.  Define MPERS_PRINTER_DECL.
[HAVE_M32_MPERS]: define PERSONALITY1_INCLUDE_FUNCS,
PERSONALITY1_INCLUDE_PRINTERS_DECLS, PERSONALITY1_INCLUDE_PRINTERS_DEFS
for X86_64, X32.
[HAVE_MX32_MPERS]: define PERSONALITY2_INCLUDE_FUNCS,
PERSONALITY2_INCLUDE_PRINTERS_DECLS, PERSONALITY2_INCLUDE_PRINTERS_DEFS
for X86_64.
Add fallback definitions of
PERSONALITY1_INCLUDE_FUNCS, PERSONALITY2_INCLUDE_FUNCS,
PERSONALITY0_INCLUDE_PRINTERS_DECLS, PERSONALITY0_INCLUDE_PRINTERS_DEFS,
PERSONALITY1_INCLUDE_PRINTERS_DECLS, PERSONALITY1_INCLUDE_PRINTERS_DEFS,
PERSONALITY2_INCLUDE_PRINTERS_DECLS, PERSONALITY2_INCLUDE_PRINTERS_DEFS.
* syscall.c: Include PERSONALITY1_INCLUDE_FUNCS,
PERSONALITY2_INCLUDE_FUNCS,
PERSONALITY0_INCLUDE_PRINTERS_DECLS, PERSONALITY0_INCLUDE_PRINTERS_DEFS,
PERSONALITY1_INCLUDE_PRINTERS_DECLS, PERSONALITY1_INCLUDE_PRINTERS_DEFS,
PERSONALITY2_INCLUDE_PRINTERS_DECLS, PERSONALITY2_INCLUDE_PRINTERS_DEFS.
(printers): New struct.  Update it when needed.
* .gitignore: Add libmpers-m32.a, libmpers-mx32.a, m32_defs.h,
m32_funcs.h, m32_printer_decls.h, m32_printer_defs.h, mpers-m32,
mpers-m32.stamp, mpers-mx32, mpers-mx32.stamp, mpers.am, mx32_defs.h,
mx32_funcs.h, mx32_printer_decls.h, mx32_printer_defs.h,
native_printer_decls.h, native_printer_defs.h, and printers.h.
Elvira Khabirova 4 years ago
parent
commit
092942206c
14 changed files with 483 additions and 13 deletions
  1. 19
    0
      .gitignore
  2. 113
    10
      Makefile.am
  3. 12
    0
      README-mpers
  4. 1
    0
      bootstrap
  5. 1
    0
      configure.ac
  6. 63
    3
      defs.h
  7. 0
    0
      empty.h
  8. 11
    0
      generate_mpers_am.sh
  9. 17
    0
      m4/mpers.m4
  10. 135
    0
      mpers.awk
  11. 49
    0
      mpers.sh
  12. 28
    0
      mpers_test.sh
  13. 15
    0
      mpers_type.h
  14. 19
    0
      syscall.c

+ 19
- 0
.gitignore View File

@@ -45,3 +45,22 @@ Makefile.in
45 45
 
46 46
 /tests-m32
47 47
 /tests-mx32
48
+
49
+/libmpers-m32.a
50
+/libmpers-mx32.a
51
+/m32_defs.h
52
+/m32_funcs.h
53
+/m32_printer_decls.h
54
+/m32_printer_defs.h
55
+/mpers-m32
56
+/mpers-m32.stamp
57
+/mpers-mx32
58
+/mpers-mx32.stamp
59
+/mpers.am
60
+/mx32_defs.h
61
+/mx32_funcs.h
62
+/mx32_printer_decls.h
63
+/mx32_printer_defs.h
64
+/native_printer_decls.h
65
+/native_printer_defs.h
66
+/printers.h

+ 113
- 10
Makefile.am View File

@@ -27,6 +27,11 @@ AM_CPPFLAGS = -I$(builddir)/$(OS)/$(ARCH) \
27 27
 
28 28
 include xlat/Makemodule.am
29 29
 
30
+strace_CPPFLAGS = $(AM_CPPFLAGS)
31
+strace_LDFLAGS =
32
+strace_LDADD =
33
+noinst_LIBRARIES =
34
+
30 35
 strace_SOURCES =	\
31 36
 	access.c	\
32 37
 	affinity.c	\
@@ -44,6 +49,7 @@ strace_SOURCES =	\
44 49
 	count.c		\
45 50
 	desc.c		\
46 51
 	dirent.c	\
52
+	empty.h		\
47 53
 	epoll.c		\
48 54
 	evdev.c		\
49 55
 	eventfd.c	\
@@ -80,6 +86,7 @@ strace_SOURCES =	\
80 86
 	memfd_create.c	\
81 87
 	mknod.c		\
82 88
 	mount.c		\
89
+	mpers_type.h	\
83 90
 	mq.c	\
84 91
 	mtd.c		\
85 92
 	net.c		\
@@ -146,15 +153,14 @@ strace_SOURCES =	\
146 153
 	vsprintf.c	\
147 154
 	wait.c		\
148 155
 	xattr.c		\
149
-	xmalloc.c
156
+	xmalloc.c	\
157
+	# end of strace_SOURCES
150 158
 
151 159
 if USE_LIBUNWIND
152 160
 strace_SOURCES += unwind.c
153
-strace_CPPFLAGS = $(AM_CPPFLAGS) $(libunwind_CPPFLAGS)
154
-strace_LDFLAGS = $(libunwind_LDFLAGS)
155
-strace_LDADD = $(libunwind_LIBS)
156
-else
157
-strace_CPPFLAGS = $(AM_CPPFLAGS)
161
+strace_CPPFLAGS += $(libunwind_CPPFLAGS)
162
+strace_LDFLAGS += $(libunwind_LDFLAGS)
163
+strace_LDADD += $(libunwind_LIBS)
158 164
 endif
159 165
 
160 166
 noinst_HEADERS = defs.h
@@ -575,6 +581,9 @@ EXTRA_DIST =				\
575 581
 	maint/ioctls_hex.sh		\
576 582
 	maint/ioctls_sym.sh		\
577 583
 	maint/print_ioctlent.c		\
584
+	mpers.awk			\
585
+	mpers.sh			\
586
+	mpers_test.sh			\
578 587
 	signalent.sh			\
579 588
 	strace-graph			\
580 589
 	strace-log-merge		\
@@ -589,8 +598,6 @@ EXTRA_DIST =				\
589 598
 srpm: dist-xz
590 599
 	rpmbuild --define '%_srcrpmdir .' -ts $(distdir).tar.xz
591 600
 
592
-BUILT_SOURCES = .version sys_func.h sen.h
593
-
594 601
 $(srcdir)/.version:
595 602
 	$(AM_V_GEN)echo $(VERSION) > $@-t && mv $@-t $@
596 603
 
@@ -635,8 +642,6 @@ ioctlsort_LDFLAGS = $(AM_LDFLAGS) $(LDFLAGS_FOR_BUILD)
635 642
 
636 643
 ioctls_inc_h = $(wildcard $(srcdir)/$(OS)/$(ARCH)/ioctls_inc*.h)
637 644
 ioctlent_h = $(patsubst $(srcdir)/$(OS)/$(ARCH)/ioctls_inc%,ioctlent%,$(ioctls_inc_h))
638
-BUILT_SOURCES += $(ioctlent_h)
639
-CLEANFILES = sys_func.h sen.h $(ioctlent_h)
640 645
 
641 646
 ioctlent%.h: ioctlsort%
642 647
 	./$< > $@
@@ -650,6 +655,104 @@ ioctlsort%.o: ioctls_all%.h $(srcdir)/ioctlsort.c
650 655
 ioctls_all%.h: $(srcdir)/$(OS)/$(ARCH)/ioctls_inc%.h $(srcdir)/$(OS)/$(ARCH)/ioctls_arch%.h
651 656
 	cat $^ > $@
652 657
 
658
+BUILT_SOURCES = $(ioctlent_h) native_printer_decls.h native_printer_defs.h printers.h sen.h sys_func.h .version
659
+CLEANFILES    = $(ioctlent_h) native_printer_decls.h native_printer_defs.h printers.h sen.h sys_func.h
660
+
661
+# defines mpers_source_files
662
+include mpers.am
663
+srcdir_mpers_source_files = $(patsubst %,$(srcdir)/%,$(mpers_source_files))
664
+
665
+mpers_NAME =
666
+mpers_PREFIX = $(mpers_NAME)_
667
+mpers_DEFS = $(DEFS)
668
+mpers_INCLUDES = $(DEFAULT_INCLUDES) $(INCLUDES)
669
+mpers_CPPFLAGS = $(strace_CPPFLAGS) $(CPPFLAGS)
670
+mpers_sh_opts = $(mpers_DEFS) $(mpers_INCLUDES) $(mpers_CPPFLAGS)
671
+libmpers_CPPFLAGS = $(AM_CPPFLAGS) -DIN_MPERS
672
+
673
+# mpers targets
674
+
675
+mpers-m%.stamp: $(srcdir_mpers_source_files)
676
+	for f in $^; do \
677
+		CC="$(CC)" CFLAGS="$(mpers_sh_opts)" \
678
+		CPP="$(CPP)" CPPFLAGS="$(mpers_CPPFLAGS) $(mpers_INCLUDES) -DIN_MPERS -DMPERS_IS_$(mpers_NAME)" \
679
+		$(srcdir)/mpers.sh -$(mpers_NAME) $$f || exit; \
680
+	done
681
+	> $@
682
+
683
+m%_defs.h: $(srcdir_mpers_source_files)
684
+	for f in $^; do \
685
+		sed -n 's/^#include DEF_MPERS_TYPE(\([^)]\+\))/#ifdef MPERS_$(mpers_PREFIX)\1\n# define \1 MPERS_$(mpers_PREFIX)\1\n#endif/p' $$f || exit; \
686
+	done > $@-t
687
+	mv $@-t $@
688
+
689
+m%_funcs.h: $(srcdir_mpers_source_files)
690
+	for f in $^; do \
691
+		sed -n 's/^SYS_FUNC(\([^)]\+\))/#undef sys_\1\n#define sys_\1 $(mpers_PREFIX)sys_\1/p' $$f || exit; \
692
+	done > $@-t && \
693
+	echo '#include "sys_func.h"' >> $@-t
694
+	mv $@-t $@
695
+
696
+# printers
697
+
698
+printers.h: $(srcdir_mpers_source_files)
699
+	echo '/* Generated by Makefile from $^; do not edit. */' > $@-t
700
+	echo 'typedef struct {' >> $@-t
701
+	for f in $^; do \
702
+		sed -n 's/^MPERS_PRINTER_DECL(\([^,]\+\),[[:space:]]*\([^)]\+\))\(.*\)/	\1 (*\2) \3;/p' $$f || exit; \
703
+	done >> $@-t
704
+	echo '} struct_printers;' >> $@-t
705
+	mv $@-t $@
706
+
707
+%_printer_decls.h: $(srcdir_mpers_source_files)
708
+	echo '/* Generated by Makefile from $^; do not edit. */' > $@-t
709
+	for f in $^; do \
710
+		sed -n 's/^MPERS_PRINTER_DECL(\([^,]\+\),[[:space:]]*\([^)]\+\))\(.*\)/extern \1 $(mpers_PREFIX)\2\3;/p' $$f || exit; \
711
+	done >> $@-t
712
+	mv $@-t $@
713
+
714
+%_printer_defs.h: $(srcdir_mpers_source_files)
715
+	echo '/* Generated by Makefile from $^; do not edit. */' > $@-t
716
+	for f in $^; do \
717
+		sed -n 's/^MPERS_PRINTER_DECL(\([^,]\+\),[[:space:]]*\([^)]\+\))\(.*\)/\.\2 = $(mpers_PREFIX)\2,/p' $$f || exit; \
718
+	done >> $@-t
719
+	mv $@-t $@
720
+
721
+native_printer_decls.h native_printer_defs.h: mpers_PREFIX =
722
+
723
+if HAVE_M32_MPERS
724
+
725
+strace_LDADD += libmpers-m32.a
726
+noinst_LIBRARIES += libmpers-m32.a
727
+libmpers_m32_a_SOURCES = $(mpers_source_files)
728
+libmpers_m32_a_CPPFLAGS = $(libmpers_CPPFLAGS) -DMPERS_IS_m32 -I$(builddir)/mpers-m32
729
+mpers_m32_targets = mpers-m32.stamp m32_defs.h m32_funcs.h m32_printer_decls.h m32_printer_defs.h
730
+
731
+BUILT_SOURCES += $(mpers_m32_targets)
732
+CLEANFILES    += $(mpers_m32_targets)
733
+
734
+$(mpers_m32_targets): mpers_NAME = m32
735
+
736
+endif # HAVE_M32_MPERS
737
+
738
+if HAVE_MX32_MPERS
739
+
740
+strace_LDADD += libmpers-mx32.a
741
+noinst_LIBRARIES += libmpers-mx32.a
742
+libmpers_mx32_a_SOURCES = $(mpers_source_files)
743
+libmpers_mx32_a_CPPFLAGS = $(libmpers_CPPFLAGS) -DMPERS_IS_mx32 -I$(builddir)/mpers-mx32
744
+mpers_mx32_targets = mpers-mx32.stamp mx32_defs.h mx32_funcs.h mx32_printer_decls.h mx32_printer_defs.h
745
+
746
+BUILT_SOURCES += $(mpers_mx32_targets)
747
+CLEANFILES    += $(mpers_mx32_targets)
748
+
749
+$(mpers_mx32_targets): mpers_NAME = mx32
750
+
751
+endif # HAVE_MX32_MPERS
752
+
753
+clean-local:
754
+	-rm -rf mpers-m32 mpers-mx32
755
+
653 756
 if MAINTAINER_MODE
654 757
 
655 758
 gen_changelog_start_date = 2009-07-08 20:00

+ 12
- 0
README-mpers View File

@@ -0,0 +1,12 @@
1
+To use mpers functionality, one should:
2
+* typedef all of the target types which are compound and not typedefed
3
+already;
4
+* for each target type, include DEF_MPERS_TYPE(target_type_t), these can
5
+be included conditionally;
6
+* include MPERS_DEFS once;
7
+* before inclusion of MPERS_DEFS include all important headers
8
+(containing definitions of these types or other behaviour-affecting
9
+defines);
10
+* printers should be defined
11
+as MPERS_PRINTER_DECL(return type, function name)(args) and called
12
+as MPERS_PRINTER_NAME(function name)(args).

+ 1
- 0
bootstrap View File

@@ -15,5 +15,6 @@ for m in -m32 -mx32; do
15 15
 done
16 16
 
17 17
 ./xlat/gen.sh
18
+./generate_mpers_am.sh
18 19
 
19 20
 exec autoreconf -f -i "$@"

+ 1
- 0
configure.ac View File

@@ -13,6 +13,7 @@ AC_CANONICAL_HOST
13 13
 AC_PROG_CC
14 14
 AX_PROG_CC_FOR_BUILD
15 15
 AC_USE_SYSTEM_EXTENSIONS
16
+AC_PROG_RANLIB
16 17
 
17 18
 AC_MSG_CHECKING([for supported architecture])
18 19
 case "$host_cpu" in

+ 63
- 3
defs.h View File

@@ -54,6 +54,8 @@
54 54
 #include <sys/time.h>
55 55
 #include <sys/syscall.h>
56 56
 
57
+#include "mpers_type.h"
58
+
57 59
 #ifndef HAVE_STRERROR
58 60
 const char *strerror(int);
59 61
 #endif
@@ -200,12 +202,27 @@ extern char *stpcpy(char *dst, const char *src);
200 202
 # define PERSONALITY0_WORDSIZE 8
201 203
 # define PERSONALITY1_WORDSIZE 4
202 204
 # define PERSONALITY2_WORDSIZE 4
205
+# ifdef HAVE_M32_MPERS
206
+#  define PERSONALITY1_INCLUDE_FUNCS "m32_funcs.h"
207
+#  define PERSONALITY1_INCLUDE_PRINTERS_DECLS "m32_printer_decls.h"
208
+#  define PERSONALITY1_INCLUDE_PRINTERS_DEFS "m32_printer_defs.h"
209
+# endif
210
+# ifdef HAVE_MX32_MPERS
211
+#  define PERSONALITY2_INCLUDE_FUNCS "mx32_funcs.h"
212
+#  define PERSONALITY2_INCLUDE_PRINTERS_DECLS "mx32_printer_decls.h"
213
+#  define PERSONALITY2_INCLUDE_PRINTERS_DEFS "mx32_printer_defs.h"
214
+# endif
203 215
 #endif
204 216
 
205 217
 #ifdef X32
206 218
 # define SUPPORTED_PERSONALITIES 2
207 219
 # define PERSONALITY0_WORDSIZE 4
208 220
 # define PERSONALITY1_WORDSIZE 4
221
+# ifdef HAVE_M32_MPERS
222
+#  define PERSONALITY1_INCLUDE_FUNCS "m32_funcs.h"
223
+#  define PERSONALITY1_INCLUDE_PRINTERS_DECLS "m32_printer_decls.h"
224
+#  define PERSONALITY1_INCLUDE_PRINTERS_DEFS "m32_printer_defs.h"
225
+# endif
209 226
 #endif
210 227
 
211 228
 #ifdef ARM
@@ -245,6 +262,34 @@ extern char *stpcpy(char *dst, const char *src);
245 262
 # define PERSONALITY0_WORDSIZE SIZEOF_LONG
246 263
 #endif
247 264
 
265
+#ifndef PERSONALITY0_INCLUDE_PRINTERS_DECLS
266
+# define PERSONALITY0_INCLUDE_PRINTERS_DECLS "native_printer_decls.h"
267
+#endif
268
+#ifndef PERSONALITY0_INCLUDE_PRINTERS_DEFS
269
+# define PERSONALITY0_INCLUDE_PRINTERS_DEFS "native_printer_defs.h"
270
+#endif
271
+
272
+#ifndef PERSONALITY1_INCLUDE_PRINTERS_DECLS
273
+# define PERSONALITY1_INCLUDE_PRINTERS_DECLS "native_printer_decls.h"
274
+#endif
275
+#ifndef PERSONALITY1_INCLUDE_PRINTERS_DEFS
276
+# define PERSONALITY1_INCLUDE_PRINTERS_DEFS "native_printer_defs.h"
277
+#endif
278
+
279
+#ifndef PERSONALITY2_INCLUDE_PRINTERS_DECLS
280
+# define PERSONALITY2_INCLUDE_PRINTERS_DECLS "native_printer_decls.h"
281
+#endif
282
+#ifndef PERSONALITY2_INCLUDE_PRINTERS_DEFS
283
+# define PERSONALITY2_INCLUDE_PRINTERS_DEFS "native_printer_defs.h"
284
+#endif
285
+
286
+#ifndef PERSONALITY1_INCLUDE_FUNCS
287
+# define PERSONALITY1_INCLUDE_FUNCS "empty.h"
288
+#endif
289
+#ifndef PERSONALITY2_INCLUDE_FUNCS
290
+# define PERSONALITY2_INCLUDE_FUNCS "empty.h"
291
+#endif
292
+
248 293
 typedef struct sysent {
249 294
 	unsigned nargs;
250 295
 	int	sys_flags;
@@ -694,6 +739,7 @@ extern const char *const signalent0[];
694 739
 extern const struct_ioctlent ioctlent0[];
695 740
 extern qualbits_t *qual_vec[SUPPORTED_PERSONALITIES];
696 741
 #define qual_flags (qual_vec[current_personality])
742
+
697 743
 #if SUPPORTED_PERSONALITIES > 1
698 744
 extern const struct_sysent *sysent;
699 745
 extern const char *const *errnoent;
@@ -705,12 +751,22 @@ extern const struct_ioctlent *ioctlent;
705 751
 # define signalent  signalent0
706 752
 # define ioctlent   ioctlent0
707 753
 #endif
754
+
708 755
 extern unsigned nsyscalls;
709 756
 extern unsigned nerrnos;
710 757
 extern unsigned nsignals;
711 758
 extern unsigned nioctlents;
712 759
 extern unsigned num_quals;
713 760
 
761
+#if SUPPORTED_PERSONALITIES > 1
762
+# include "printers.h"
763
+extern const struct_printers *printers;
764
+# define MPERS_PRINTER_NAME(printer_name) printers->printer_name
765
+#else
766
+# include "native_printer_decls.h"
767
+# define MPERS_PRINTER_NAME(printer_name) printer_name
768
+#endif
769
+
714 770
 /*
715 771
  * If you need non-NULL sysent[scno].sys_func and sysent[scno].sys_name
716 772
  */
@@ -721,8 +777,12 @@ extern unsigned num_quals;
721 777
 #define SCNO_IN_RANGE(scno) \
722 778
 	((unsigned long)(scno) < nsyscalls)
723 779
 
724
-#ifndef SYS_FUNC_NAME
725
-# define SYS_FUNC_NAME(syscall_name) sys_ ## syscall_name
726
-#endif
780
+#define MPERS_FUNC_NAME__(prefix, name) prefix ## name
781
+#define MPERS_FUNC_NAME_(prefix, name) MPERS_FUNC_NAME__(prefix, name)
782
+#define MPERS_FUNC_NAME(name) MPERS_FUNC_NAME_(MPERS_PREFIX, name)
783
+
784
+#define SYS_FUNC_NAME(syscall_name) MPERS_FUNC_NAME(sys_ ## syscall_name)
727 785
 
728 786
 #define SYS_FUNC(syscall_name) int SYS_FUNC_NAME(syscall_name)(struct tcb *tcp)
787
+
788
+#define MPERS_PRINTER_DECL(type, name) type MPERS_FUNC_NAME(name)

+ 0
- 0
empty.h View File


+ 11
- 0
generate_mpers_am.sh View File

@@ -0,0 +1,11 @@
1
+#!/bin/sh -e
2
+
3
+exec > mpers.am
4
+
5
+echo "# Generated by $0; do not edit."
6
+echo -n 'mpers_source_files = '
7
+
8
+sed -n '/^strace_SOURCES[[:space:]]*=/,/^[[:space:]]*# end of strace_SOURCES/ s/^[[:space:]]*\([[:alnum:]][^.]*\.c\)[[:space:]]*\\$/\1/p' Makefile.am |
9
+	xargs -r grep -lx '#[[:space:]]*include[[:space:]]\+MPERS_DEFS' |
10
+	tr '\n' ' '
11
+echo

+ 17
- 0
m4/mpers.m4 View File

@@ -1,10 +1,12 @@
1 1
 AC_DEFUN([st_MPERS],[
2 2
 
3 3
 pushdef([MPERS_NAME], translit([$1], [a-z], [A-Z]))
4
+pushdef([HAVE_MPERS], [HAVE_]MPERS_NAME[_MPERS])
4 5
 pushdef([HAVE_RUNTIME], [HAVE_]MPERS_NAME[_RUNTIME])
5 6
 pushdef([CFLAG], [-$1])
6 7
 pushdef([st_cv_cc], [st_cv_$1_cc])
7 8
 pushdef([st_cv_runtime], [st_cv_$1_runtime])
9
+pushdef([st_cv_mpers], [st_cv_$1_mpers])
8 10
 
9 11
 case "$arch" in
10 12
 	[$2])
@@ -22,21 +24,36 @@ case "$arch" in
22 24
 				       [st_cv_runtime=yes],
23 25
 				       [st_cv_runtime=no],
24 26
 				       [st_cv_runtime=no])])
27
+		AC_CACHE_CHECK([whether mpers.sh CFLAG works], [st_cv_mpers],
28
+			[if CC="$CC" CPP="$CPP" CPPFLAGS="$CPPFLAGS" \
29
+			    $srcdir/mpers_test.sh [$1]; then
30
+				st_cv_mpers=yes
31
+			 else
32
+				st_cv_mpers=no
33
+			 fi])
34
+		if test $st_cv_mpers = yes; then
35
+			AC_DEFINE(HAVE_MPERS, [1],
36
+				  [Define to 1 if you have CFLAG mpers support])
37
+		fi
25 38
 	fi
26 39
 	CFLAGS="$saved_CFLAGS"
27 40
 	;;
28 41
 
29 42
 	*)
30 43
 	st_cv_runtime=no
44
+	st_cv_mpers=no
31 45
 	;;
32 46
 esac
33 47
 
34 48
 AM_CONDITIONAL(HAVE_RUNTIME, [test "$st_cv_runtime" = yes])
49
+AM_CONDITIONAL(HAVE_MPERS, [test "$st_cv_mpers" = yes])
35 50
 
51
+popdef([st_cv_mpers])
36 52
 popdef([st_cv_runtime])
37 53
 popdef([st_cv_cc])
38 54
 popdef([CFLAG])
39 55
 popdef([HAVE_RUNTIME])
56
+popdef([HAVE_MPERS])
40 57
 popdef([MPERS_NAME])
41 58
 
42 59
 ])

+ 135
- 0
mpers.awk View File

@@ -0,0 +1,135 @@
1
+function compare_indices(i1, v1, i2, v2) {
2
+	c1 = strtonum(sprintf("%s", i1))
3
+	c2 = strtonum(sprintf("%s", i2))
4
+	if (c1 < c2)
5
+		return -1
6
+	return (c1 != c2)
7
+}
8
+function what_is(what_idx, type_idx, special, item)
9
+{
10
+	type_idx = array[what_idx]["type"]
11
+	special = array[what_idx]["special"]
12
+	switch (special) {
13
+	case "base_type":
14
+		switch (array[what_idx]["encoding"]) {
15
+		case 5: # signed
16
+			printf("%s ", "int" \
17
+			8*array[what_idx]["byte_size"] "_t")
18
+			break
19
+		case 7: # unsigned
20
+			printf("%s ", "uint" \
21
+			8*array[what_idx]["byte_size"] "_t")
22
+			break
23
+		default: # float, signed/unsigned char
24
+			printf("%s ", array[what_idx]["name"])
25
+			break
26
+		}
27
+		break
28
+	case "enumeration_type":
29
+		printf("%s ", "uint" 8*array[type_idx]["byte_size"] "_t")
30
+		break
31
+	case "pointer_type":
32
+		printf("%s", "mpers_ptr_t ")
33
+		break
34
+	case "array_type":
35
+		what_is(type_idx)
36
+		to_return = array[what_idx]["upper_bound"]
37
+		return to_return
38
+		break
39
+	case "structure_type":
40
+	case "union_type":
41
+		if (special == "structure_type") {
42
+			print "struct {"
43
+		} else {
44
+			print "union {"
45
+		}
46
+		for (item in array) {
47
+			if ("parent" in array[item] && array[item]["parent"] \
48
+				== what_idx) {
49
+				returned = what_is(item)
50
+				printf("%s", array[item]["name"])
51
+				if (returned) {
52
+					printf("%s", "[" returned "]")
53
+				}
54
+				print ";"
55
+			}
56
+		}
57
+		printf("%s", "} ")
58
+		break
59
+	case "typedef":
60
+		return what_is(type_idx)
61
+		break
62
+	case "member":
63
+		return what_is(type_idx)
64
+		break
65
+	default:
66
+		what_is(type_idx)
67
+		break
68
+	}
69
+	return 0
70
+}
71
+BEGIN {
72
+	print "#include <inttypes.h>"
73
+}
74
+/^<[[:xdigit:]]+>/ {
75
+	match($0, /([[:alnum:]]+)><([[:alnum:]]+)/, matches)
76
+	level = matches[1]
77
+	idx = "0x" matches[2]
78
+	array[idx]["idx"] = idx
79
+	parent[level] = idx
80
+	if (level > 1) {
81
+		array[idx]["parent"] = parent[level-1]
82
+	}
83
+}
84
+/^DW_AT_data_member_location/ {
85
+	match($0, /[[:digit:]]+/, temparray)
86
+	array[idx]["location"] = temparray[1]
87
+}
88
+/^DW_AT_name/ {
89
+	match($0, /:[[:space:]]+([[:alpha:]_][[:alnum:]_[:space:]]*)/, temparray)
90
+	array[idx]["name"] = temparray[1]
91
+}
92
+/^DW_AT_byte_size/ {
93
+	match($0, /[[:digit:]]+/, temparray)
94
+	array[idx]["byte_size"] = temparray[0]
95
+}
96
+/^DW_AT_encoding/ {
97
+	match($0, /[[:digit:]]+/, temparray)
98
+	array[idx]["encoding"] = temparray[0]
99
+}
100
+/^DW_AT_type/ {
101
+	match($0, /:[[:space:]]+<(0x[[:xdigit:]]*)>$/, temparray)
102
+	array[idx]["type"] = temparray[1]
103
+}
104
+/^DW_AT_upper_bound/ {
105
+	match($0, /[[:digit:]]+/, temparray)
106
+	array[parent[level-1]]["upper_bound"] = temparray[0] + 1
107
+}
108
+/^Abbrev Number:[^(]+\(DW_TAG_/ {
109
+	if (match($0, /typedef|union_type|structure_type|pointer_type\
110
+|enumeration_type|array_type|base_type|member/, temparray)) {
111
+		array[idx]["special"] = temparray[0]
112
+	}
113
+}
114
+END {
115
+	PROCINFO["sorted_in"] = "compare_indices"
116
+	for (item in array) {
117
+		if (array[item]["special"] == "pointer_type") {
118
+			print "typedef uint" \
119
+				8*array[item]["byte_size"] "_t mpers_ptr_t;"
120
+			break
121
+		}
122
+	}
123
+	for (item in array) {
124
+		if (array[item]["name"] == VAR_NAME) {
125
+			type=array[item]["type"]
126
+			print "typedef"
127
+			what_is(array[item]["type"])
128
+			print ARCH_FLAG "_" array[type]["name"] ";"
129
+			print "#define MPERS_" \
130
+				ARCH_FLAG "_" array[type]["name"] " " \
131
+				ARCH_FLAG "_" array[type]["name"]
132
+			break
133
+		}
134
+	}
135
+}

+ 49
- 0
mpers.sh View File

@@ -0,0 +1,49 @@
1
+#!/bin/sh -e
2
+
3
+export LC_ALL=C
4
+
5
+MPERS_AWK="${0%/*}/mpers.awk"
6
+ARCH_FLAG=$1
7
+PARSER_FILE=$2
8
+
9
+CC="${CC-gcc}"
10
+CFLAGS="$CFLAGS -gdwarf-4 -c"
11
+CPP="${CPP-$CC -E}"
12
+CPPFLAGS="$CPPFLAGS -MM -MG"
13
+
14
+VAR_NAME='mpers_target_var'
15
+BITS_DIR="mpers${ARCH_FLAG}"
16
+
17
+mkdir -p ${BITS_DIR}
18
+set -- $(sed -n \
19
+	's/^#[[:space:]]*include[[:space:]]\+DEF_MPERS_TYPE(\([^)[:space:]]*\))$/\1/p' \
20
+		"${PARSER_FILE}")
21
+for m_type; do
22
+	f_h="${BITS_DIR}/${m_type}.h"
23
+	f_c="${BITS_DIR}/${m_type}.c"
24
+	f_i="${BITS_DIR}/${m_type}.i"
25
+	f_o="${BITS_DIR}/${m_type}.o"
26
+	f_d1="${BITS_DIR}/${m_type}.d1"
27
+	f_d2="${BITS_DIR}/${m_type}.d2"
28
+	sed -e '
29
+		/DEF_MPERS_TYPE('"${m_type}"')$/n
30
+		/DEF_MPERS_TYPE/d
31
+		/^[[:space:]]*#[[:space:]]*include[[:space:]]\+\"xlat\//d
32
+		/^#[[:space:]]*include[[:space:]]\+MPERS_DEFS$/ {s//'"${m_type} ${VAR_NAME}"';/;q}
33
+		' "${PARSER_FILE}" > "${f_c}"
34
+	$CPP $CPPFLAGS "${f_c}" > "${f_i}"
35
+	grep -F -q "${m_type}.h" "${f_i}" ||
36
+		continue
37
+	sed -i -e '/DEF_MPERS_TYPE/d' "${f_c}"
38
+	$CC $CFLAGS $ARCH_FLAG "${f_c}" -o "${f_o}"
39
+	readelf --debug-dump=info "${f_o}" > "${f_d1}"
40
+	sed -n '
41
+		/^[[:space:]]*<1>/,/^[[:space:]]*<1><[^>]\+>: Abbrev Number: 0/!d
42
+		/^[[:space:]]*<[^>]\+><[^>]\+>: Abbrev Number: 0/d
43
+		s/^[[:space:]]*<[[:xdigit:]]\+>[[:space:]]\+//
44
+		s/^[[:space:]]*\(\(<[[:xdigit:]]\+>\)\{2\}\):[[:space:]]\+/\1\n/
45
+		s/[[:space:]]\+$//
46
+		p' "${f_d1}" > "${f_d2}"
47
+	gawk -v VAR_NAME="$VAR_NAME" -v ARCH_FLAG="${ARCH_FLAG#-}" \
48
+		-f "$MPERS_AWK" "${f_d2}" > "${f_h}"
49
+done

+ 28
- 0
mpers_test.sh View File

@@ -0,0 +1,28 @@
1
+#!/bin/sh -efu
2
+
3
+mpers_name="$1"; shift
4
+srcdir=${0%/*}
5
+mpers_sh="${srcdir}/mpers.sh"
6
+
7
+mpers_dir="mpers-$mpers_name"
8
+mkdir -p "$mpers_dir"
9
+
10
+sample="$mpers_dir/sample.c"
11
+cat > "$sample" <<EOF
12
+#include "mpers_type.h"
13
+#include DEF_MPERS_TYPE(int)
14
+#include MPERS_DEFS
15
+EOF
16
+
17
+expected="$mpers_dir/sample.expected"
18
+cat > "$expected" <<EOF
19
+#include <inttypes.h>
20
+typedef
21
+int32_t ${mpers_name}_int;
22
+#define MPERS_${mpers_name}_int ${mpers_name}_int
23
+EOF
24
+
25
+CFLAGS="$CPPFLAGS -I${srcdir}" \
26
+CPPFLAGS="$CPPFLAGS -I${srcdir} -DIN_MPERS -DMPERS_IS_${mpers_name}" \
27
+"$mpers_sh" "-$mpers_name" "$sample"
28
+cmp "$expected" "$mpers_dir"/int.h > /dev/null

+ 15
- 0
mpers_type.h View File

@@ -0,0 +1,15 @@
1
+#ifdef IN_MPERS
2
+# define STRINGIFY(a) #a
3
+# define DEF_MPERS_TYPE(args) STRINGIFY(args.h)
4
+# ifdef MPERS_IS_m32
5
+#  define MPERS_PREFIX m32_
6
+#  define MPERS_DEFS "m32_defs.h"
7
+# elif defined MPERS_IS_mx32
8
+#  define MPERS_PREFIX mx32_
9
+#  define MPERS_DEFS "mx32_defs.h"
10
+# endif
11
+#else
12
+# define MPERS_PREFIX
13
+# define DEF_MPERS_TYPE(args) "empty.h"
14
+# define MPERS_DEFS "empty.h"
15
+#endif

+ 19
- 0
syscall.c View File

@@ -89,12 +89,14 @@ const struct_sysent sysent0[] = {
89 89
 };
90 90
 
91 91
 #if SUPPORTED_PERSONALITIES > 1
92
+# include PERSONALITY1_INCLUDE_FUNCS
92 93
 static const struct_sysent sysent1[] = {
93 94
 # include "syscallent1.h"
94 95
 };
95 96
 #endif
96 97
 
97 98
 #if SUPPORTED_PERSONALITIES > 2
99
+# include PERSONALITY2_INCLUDE_FUNCS
98 100
 static const struct_sysent sysent2[] = {
99 101
 # include "syscallent2.h"
100 102
 };
@@ -143,6 +145,14 @@ static const char *const signalent1[] = {
143 145
 static const struct_ioctlent ioctlent1[] = {
144 146
 # include "ioctlent1.h"
145 147
 };
148
+# include PERSONALITY0_INCLUDE_PRINTERS_DECLS
149
+static const struct_printers printers0 = {
150
+# include PERSONALITY0_INCLUDE_PRINTERS_DEFS
151
+};
152
+# include PERSONALITY1_INCLUDE_PRINTERS_DECLS
153
+static const struct_printers printers1 = {
154
+# include PERSONALITY1_INCLUDE_PRINTERS_DEFS
155
+};
146 156
 #endif
147 157
 
148 158
 #if SUPPORTED_PERSONALITIES > 2
@@ -155,6 +165,10 @@ static const char *const signalent2[] = {
155 165
 static const struct_ioctlent ioctlent2[] = {
156 166
 # include "ioctlent2.h"
157 167
 };
168
+# include PERSONALITY2_INCLUDE_PRINTERS_DECLS
169
+static const struct_printers printers2 = {
170
+# include PERSONALITY2_INCLUDE_PRINTERS_DEFS
171
+};
158 172
 #endif
159 173
 
160 174
 enum {
@@ -202,7 +216,9 @@ const struct_sysent *sysent = sysent0;
202 216
 const char *const *errnoent = errnoent0;
203 217
 const char *const *signalent = signalent0;
204 218
 const struct_ioctlent *ioctlent = ioctlent0;
219
+const struct_printers *printers = &printers0;
205 220
 #endif
221
+
206 222
 unsigned nsyscalls = nsyscalls0;
207 223
 unsigned nerrnos = nerrnos0;
208 224
 unsigned nsignals = nsignals0;
@@ -278,6 +294,7 @@ set_personality(int personality)
278 294
 		nioctlents = nioctlents0;
279 295
 		signalent = signalent0;
280 296
 		nsignals = nsignals0;
297
+		printers = &printers0;
281 298
 		break;
282 299
 
283 300
 	case 1:
@@ -287,6 +304,7 @@ set_personality(int personality)
287 304
 		nioctlents = nioctlents1;
288 305
 		signalent = signalent1;
289 306
 		nsignals = nsignals1;
307
+		printers = &printers1;
290 308
 		break;
291 309
 
292 310
 # if SUPPORTED_PERSONALITIES > 2
@@ -297,6 +315,7 @@ set_personality(int personality)
297 315
 		nioctlents = nioctlents2;
298 316
 		signalent = signalent2;
299 317
 		nsignals = nsignals2;
318
+		printers = &printers2;
300 319
 		break;
301 320
 # endif
302 321
 	}

Loading…
Cancel
Save