~vcs-imports/qemu/git

« back to all changes in this revision

Viewing changes to bsd-user/strace.c

  • Committer: ths
  • Date: 2007-06-17 15:32:30 UTC
  • Revision ID: git-v1:ffb04fcf089865952592f1f8855c2848d4514a89
Allow relative paths for the interpreter prefix in linux-user emulation.


git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@2984 c046a42c-6fe2-441c-8c8c-71466251a162

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
#include <stdio.h>
2
 
#include <errno.h>
3
 
#include <sys/select.h>
4
 
#include <sys/types.h>
5
 
#include <unistd.h>
6
 
#include <sys/syscall.h>
7
 
#include "qemu.h"
8
 
 
9
 
int do_strace=0;
10
 
 
11
 
struct syscallname {
12
 
    int nr;
13
 
    const char *name;
14
 
    const char *format;
15
 
    void (*call)(const struct syscallname *,
16
 
                 abi_long, abi_long, abi_long,
17
 
                 abi_long, abi_long, abi_long);
18
 
    void (*result)(const struct syscallname *, abi_long);
19
 
};
20
 
 
21
 
/*
22
 
 * Utility functions
23
 
 */
24
 
 
25
 
static void
26
 
print_execve(const struct syscallname *name,
27
 
             abi_long arg1, abi_long arg2, abi_long arg3,
28
 
             abi_long arg4, abi_long arg5, abi_long arg6)
29
 
{
30
 
    abi_ulong arg_ptr_addr;
31
 
    char *s;
32
 
 
33
 
    if (!(s = lock_user_string(arg1)))
34
 
        return;
35
 
    gemu_log("%s(\"%s\",{", name->name, s);
36
 
    unlock_user(s, arg1, 0);
37
 
 
38
 
    for (arg_ptr_addr = arg2; ; arg_ptr_addr += sizeof(abi_ulong)) {
39
 
        abi_ulong *arg_ptr, arg_addr, s_addr;
40
 
 
41
 
        arg_ptr = lock_user(VERIFY_READ, arg_ptr_addr, sizeof(abi_ulong), 1);
42
 
        if (!arg_ptr)
43
 
            return;
44
 
        arg_addr = tswapl(*arg_ptr);
45
 
        unlock_user(arg_ptr, arg_ptr_addr, 0);
46
 
        if (!arg_addr)
47
 
            break;
48
 
        if ((s = lock_user_string(arg_addr))) {
49
 
            gemu_log("\"%s\",", s);
50
 
            unlock_user(s, s_addr, 0);
51
 
        }
52
 
    }
53
 
 
54
 
    gemu_log("NULL})");
55
 
}
56
 
 
57
 
/*
58
 
 * Variants for the return value output function
59
 
 */
60
 
 
61
 
static void
62
 
print_syscall_ret_addr(const struct syscallname *name, abi_long ret)
63
 
{
64
 
if( ret == -1 ) {
65
 
        gemu_log(" = -1 errno=%d (%s)\n", errno, strerror(errno));
66
 
    } else {
67
 
        gemu_log(" = 0x" TARGET_ABI_FMT_lx "\n", ret);
68
 
    }
69
 
}
70
 
 
71
 
#if 0 /* currently unused */
72
 
static void
73
 
print_syscall_ret_raw(struct syscallname *name, abi_long ret)
74
 
{
75
 
        gemu_log(" = 0x" TARGET_ABI_FMT_lx "\n", ret);
76
 
}
77
 
#endif
78
 
 
79
 
/*
80
 
 * An array of all of the syscalls we know about
81
 
 */
82
 
 
83
 
static const struct syscallname freebsd_scnames[] = {
84
 
#include "freebsd/strace.list"
85
 
};
86
 
static const struct syscallname netbsd_scnames[] = {
87
 
#include "netbsd/strace.list"
88
 
};
89
 
static const struct syscallname openbsd_scnames[] = {
90
 
#include "openbsd/strace.list"
91
 
};
92
 
 
93
 
static void
94
 
print_syscall(int num, const struct syscallname *scnames, unsigned int nscnames,
95
 
              abi_long arg1, abi_long arg2, abi_long arg3,
96
 
              abi_long arg4, abi_long arg5, abi_long arg6)
97
 
{
98
 
    unsigned int i;
99
 
    const char *format="%s(" TARGET_ABI_FMT_ld "," TARGET_ABI_FMT_ld ","
100
 
        TARGET_ABI_FMT_ld "," TARGET_ABI_FMT_ld "," TARGET_ABI_FMT_ld ","
101
 
        TARGET_ABI_FMT_ld ")";
102
 
 
103
 
    gemu_log("%d ", getpid() );
104
 
 
105
 
    for (i = 0; i < nscnames; i++)
106
 
        if (scnames[i].nr == num) {
107
 
            if (scnames[i].call != NULL) {
108
 
                scnames[i].call(&scnames[i], arg1, arg2, arg3, arg4, arg5,
109
 
                                arg6);
110
 
            } else {
111
 
                /* XXX: this format system is broken because it uses
112
 
                   host types and host pointers for strings */
113
 
                if (scnames[i].format != NULL)
114
 
                    format = scnames[i].format;
115
 
                gemu_log(format, scnames[i].name, arg1, arg2, arg3, arg4,
116
 
                         arg5, arg6);
117
 
            }
118
 
            return;
119
 
        }
120
 
    gemu_log("Unknown syscall %d\n", num);
121
 
}
122
 
 
123
 
static void
124
 
print_syscall_ret(int num, abi_long ret, const struct syscallname *scnames,
125
 
                  unsigned int nscnames)
126
 
{
127
 
    unsigned int i;
128
 
 
129
 
    for (i = 0; i < nscnames; i++)
130
 
        if (scnames[i].nr == num) {
131
 
            if (scnames[i].result != NULL) {
132
 
                scnames[i].result(&scnames[i], ret);
133
 
            } else {
134
 
                if( ret < 0 ) {
135
 
                    gemu_log(" = -1 errno=" TARGET_ABI_FMT_ld " (%s)\n", -ret,
136
 
                             strerror(-ret));
137
 
                } else {
138
 
                    gemu_log(" = " TARGET_ABI_FMT_ld "\n", ret);
139
 
                }
140
 
            }
141
 
            break;
142
 
        }
143
 
}
144
 
 
145
 
/*
146
 
 * The public interface to this module.
147
 
 */
148
 
void
149
 
print_freebsd_syscall(int num,
150
 
                      abi_long arg1, abi_long arg2, abi_long arg3,
151
 
                      abi_long arg4, abi_long arg5, abi_long arg6)
152
 
{
153
 
    print_syscall(num, freebsd_scnames, ARRAY_SIZE(freebsd_scnames),
154
 
                  arg1, arg2, arg3, arg4, arg5, arg6);
155
 
}
156
 
 
157
 
void
158
 
print_freebsd_syscall_ret(int num, abi_long ret)
159
 
{
160
 
    print_syscall_ret(num, ret, freebsd_scnames, ARRAY_SIZE(freebsd_scnames));
161
 
}
162
 
 
163
 
void
164
 
print_netbsd_syscall(int num,
165
 
                      abi_long arg1, abi_long arg2, abi_long arg3,
166
 
                      abi_long arg4, abi_long arg5, abi_long arg6)
167
 
{
168
 
    print_syscall(num, netbsd_scnames, ARRAY_SIZE(netbsd_scnames),
169
 
                  arg1, arg2, arg3, arg4, arg5, arg6);
170
 
}
171
 
 
172
 
void
173
 
print_netbsd_syscall_ret(int num, abi_long ret)
174
 
{
175
 
    print_syscall_ret(num, ret, netbsd_scnames, ARRAY_SIZE(netbsd_scnames));
176
 
}
177
 
 
178
 
void
179
 
print_openbsd_syscall(int num,
180
 
                      abi_long arg1, abi_long arg2, abi_long arg3,
181
 
                      abi_long arg4, abi_long arg5, abi_long arg6)
182
 
{
183
 
    print_syscall(num, openbsd_scnames, ARRAY_SIZE(openbsd_scnames),
184
 
                  arg1, arg2, arg3, arg4, arg5, arg6);
185
 
}
186
 
 
187
 
void
188
 
print_openbsd_syscall_ret(int num, abi_long ret)
189
 
{
190
 
    print_syscall_ret(num, ret, openbsd_scnames, ARRAY_SIZE(openbsd_scnames));
191
 
}