ruby-usdt 0.1.1 → 0.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/ext/libusdt/Makefile +77 -47
- data/ext/libusdt/test.pl +1 -1
- data/ext/libusdt/test_mem_usage.c +77 -0
- data/ext/libusdt/test_usdt.c +10 -3
- data/ext/libusdt/usdt.c +118 -3
- data/ext/libusdt/usdt.h +11 -2
- data/ext/libusdt/usdt_dof.c +8 -2
- data/ext/libusdt/usdt_dof_file.c +32 -2
- data/ext/libusdt/usdt_dof_sections.c +5 -2
- data/ext/libusdt/usdt_internal.h +1 -0
- data/ext/libusdt/usdt_probe.c +13 -9
- data/ext/libusdt/usdt_tracepoints_x86_64.s +1 -0
- data/lib/usdt/version.rb +1 -1
- metadata +2 -1
data/ext/libusdt/Makefile
CHANGED
@@ -1,25 +1,54 @@
|
|
1
|
-
|
2
|
-
|
1
|
+
CC = gcc
|
2
|
+
CFLAGS = -O2
|
3
3
|
|
4
|
-
MAC_BUILD
|
5
|
-
|
6
|
-
|
4
|
+
# MAC_BUILD - set this to "universal" to build a 2-way fat library
|
5
|
+
MAC_BUILD = universal
|
6
|
+
|
7
|
+
# if ARCH set, disable universal build on the mac
|
8
|
+
ifdef ARCH
|
9
|
+
MAC_BUILD =
|
10
|
+
else
|
11
|
+
ARCH = $(shell uname -m)
|
12
|
+
endif
|
13
|
+
|
14
|
+
UNAME = $(shell uname -s)
|
7
15
|
|
8
16
|
ifeq ($(UNAME), SunOS)
|
9
|
-
|
10
|
-
|
17
|
+
RANLIB=/bin/true
|
18
|
+
PATH +=:/usr/perl5/5.10.0/bin:/usr/perl5/5.12/bin
|
19
|
+
CFLAGS += -fPIC
|
20
|
+
|
21
|
+
ifeq ($(ARCH), i86pc)
|
22
|
+
ARCH = $(shell isainfo -k)
|
23
|
+
ifeq ($(ARCH), amd64)
|
24
|
+
ARCH = x86_64
|
25
|
+
else
|
26
|
+
ARCH = i386
|
27
|
+
endif
|
28
|
+
endif
|
11
29
|
ifeq ($(ARCH), x86_64)
|
12
30
|
CFLAGS += -m64
|
13
31
|
endif
|
14
32
|
endif
|
15
33
|
|
16
34
|
ifeq ($(UNAME), FreeBSD)
|
17
|
-
|
35
|
+
RANLIB=ranlib
|
36
|
+
CFLAGS += -Wno-error=unknown-pragmas -I/usr/src/sys/cddl/compat/opensolaris -I/usr/src/sys/cddl/contrib/opensolaris/uts/common
|
18
37
|
ifeq ($(ARCH), i386)
|
19
38
|
CFLAGS += -m32
|
20
39
|
endif
|
21
40
|
endif
|
22
41
|
|
42
|
+
ifeq ($(UNAME), Darwin)
|
43
|
+
RANLIB=ranlib
|
44
|
+
ifeq ($(MAC_BUILD), universal)
|
45
|
+
CFLAGS += -arch i386 -arch x86_64
|
46
|
+
else
|
47
|
+
CFLAGS += -arch $(ARCH)
|
48
|
+
endif
|
49
|
+
endif
|
50
|
+
|
51
|
+
# main library build
|
23
52
|
objects = usdt.o usdt_dof_file.o usdt_tracepoints.o usdt_probe.o usdt_dof.o usdt_dof_sections.o
|
24
53
|
headers = usdt.h usdt_internal.h
|
25
54
|
|
@@ -27,55 +56,66 @@ headers = usdt.h usdt_internal.h
|
|
27
56
|
|
28
57
|
all: libusdt.a
|
29
58
|
|
59
|
+
libusdt.a: $(objects) $(headers)
|
60
|
+
rm -f libusdt.a
|
61
|
+
$(AR) cru libusdt.a $(objects)
|
62
|
+
$(RANLIB) libusdt.a
|
63
|
+
|
64
|
+
# Tracepoints build.
|
65
|
+
#
|
66
|
+
# If on Darwin and building a universal library, manually assemble a
|
67
|
+
# two-way fat object file from both the 32 and 64 bit tracepoint asm
|
68
|
+
# files.
|
69
|
+
#
|
70
|
+
# Otherwise, just choose the appropriate asm file based on the build
|
71
|
+
# architecture.
|
72
|
+
|
30
73
|
ifeq ($(UNAME), Darwin)
|
31
74
|
ifeq ($(MAC_BUILD), universal)
|
32
|
-
CFLAGS+= -arch i386 -arch x86_64
|
33
75
|
|
34
76
|
usdt_tracepoints_i386.o: usdt_tracepoints_i386.s
|
35
|
-
|
77
|
+
$(CC) -arch i386 -o usdt_tracepoints_i386.o -c usdt_tracepoints_i386.s
|
36
78
|
|
37
79
|
usdt_tracepoints_x86_64.o: usdt_tracepoints_x86_64.s
|
38
|
-
|
80
|
+
$(CC) -arch x86_64 -o usdt_tracepoints_x86_64.o -c usdt_tracepoints_x86_64.s
|
39
81
|
|
40
82
|
usdt_tracepoints.o: usdt_tracepoints_i386.o usdt_tracepoints_x86_64.o
|
41
83
|
lipo -create -output usdt_tracepoints.o usdt_tracepoints_i386.o \
|
42
84
|
usdt_tracepoints_x86_64.o
|
43
|
-
else
|
44
|
-
|
45
|
-
ifeq ($(ARCH), x86_64)
|
46
|
-
usdt_tracepoints.o: usdt_tracepoints_x86_64.s
|
47
|
-
as -o usdt_tracepoints.o usdt_tracepoints_x86_64.s
|
48
|
-
else
|
49
|
-
usdt_tracepoints.o: usdt_tracepoints_i386.s
|
50
|
-
as -o usdt_tracepoints.o usdt_tracepoints_i386.s
|
51
|
-
endif
|
52
85
|
|
53
|
-
|
86
|
+
else # Darwin, not universal
|
87
|
+
usdt_tracepoints.o: usdt_tracepoints_$(ARCH).s
|
88
|
+
$(CC) -arch $(ARCH) -o usdt_tracepoints.o -c usdt_tracepoints_$(ARCH).s
|
54
89
|
endif
|
55
90
|
|
56
|
-
|
57
|
-
ifeq ($(ARCH), amd64)
|
58
|
-
usdt_tracepoints.o: usdt_tracepoints_x86_64.s
|
59
|
-
as --64 -o usdt_tracepoints.o usdt_tracepoints_x86_64.s
|
60
|
-
else
|
61
|
-
usdt_tracepoints.o: usdt_tracepoints_i386.s
|
62
|
-
as --32 -o usdt_tracepoints.o usdt_tracepoints_i386.s
|
63
|
-
endif
|
64
|
-
endif
|
91
|
+
else # not Darwin; FreeBSD and Illumos
|
65
92
|
|
66
|
-
ifeq ($(UNAME), SunOS)
|
67
93
|
ifeq ($(ARCH), x86_64)
|
68
94
|
usdt_tracepoints.o: usdt_tracepoints_x86_64.s
|
69
|
-
|
70
|
-
|
95
|
+
$(CC) $(CFLAGS) -o usdt_tracepoints.o -c usdt_tracepoints_x86_64.s
|
96
|
+
endif
|
97
|
+
ifeq ($(ARCH), i386)
|
71
98
|
usdt_tracepoints.o: usdt_tracepoints_i386.s
|
72
|
-
|
99
|
+
$(CC) $(CFLAGS) -o usdt_tracepoints.o -c usdt_tracepoints_i386.s
|
73
100
|
endif
|
101
|
+
|
74
102
|
endif
|
75
103
|
|
76
|
-
|
77
|
-
|
78
|
-
|
104
|
+
clean:
|
105
|
+
rm -f *.gch
|
106
|
+
rm -f *.o
|
107
|
+
rm -f libusdt.a
|
108
|
+
rm -f test_usdt
|
109
|
+
rm -f test_usdt32
|
110
|
+
rm -f test_usdt64
|
111
|
+
rm -f test_mem_usage
|
112
|
+
|
113
|
+
.PHONY: clean test
|
114
|
+
|
115
|
+
# testing
|
116
|
+
|
117
|
+
test_mem_usage: libusdt.a test_mem_usage.o
|
118
|
+
$(CC) $(CFLAGS) -o test_mem_usage test_mem_usage.o libusdt.a
|
79
119
|
|
80
120
|
ifeq ($(UNAME), Darwin)
|
81
121
|
ifeq ($(MAC_BUILD), universal)
|
@@ -92,15 +132,6 @@ test_usdt: libusdt.a test_usdt.o
|
|
92
132
|
$(CC) $(CFLAGS) -o test_usdt test_usdt.o libusdt.a
|
93
133
|
endif
|
94
134
|
|
95
|
-
clean:
|
96
|
-
rm -f *.gch
|
97
|
-
rm -f *.o
|
98
|
-
rm -f libusdt.a
|
99
|
-
rm -f fat_libusdt.a
|
100
|
-
rm -f test_usdt
|
101
|
-
rm -f test_usdt32
|
102
|
-
rm -f test_usdt64
|
103
|
-
|
104
135
|
ifeq ($(UNAME), Darwin)
|
105
136
|
ifeq ($(MAC_BUILD), universal)
|
106
137
|
test: test_usdt32 test_usdt64
|
@@ -115,4 +146,3 @@ test: test_usdt
|
|
115
146
|
sudo prove test.pl
|
116
147
|
endif
|
117
148
|
|
118
|
-
.PHONY: clean test
|
data/ext/libusdt/test.pl
CHANGED
@@ -83,7 +83,7 @@ sub run_dtrace {
|
|
83
83
|
my $t_pid = open3($t_wtr, $t_rdr, $t_err, @t_cmd);
|
84
84
|
my $enabled = $t_rdr->getline;
|
85
85
|
|
86
|
-
my @d_cmd = ('dtrace', '-p', $t_pid, '-n', $d);
|
86
|
+
my @d_cmd = ('/usr/sbin/dtrace', '-p', $t_pid, '-n', $d);
|
87
87
|
|
88
88
|
#diag(join(' ', @d_cmd));
|
89
89
|
my $d_pid = open3($d_wtr, $d_rdr, $d_err, @d_cmd);
|
@@ -0,0 +1,77 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright (c) 2012, Chris Andrews. All rights reserved.
|
3
|
+
*/
|
4
|
+
|
5
|
+
#include "usdt.h"
|
6
|
+
|
7
|
+
#include <stdio.h>
|
8
|
+
#include <stdlib.h>
|
9
|
+
#include <string.h>
|
10
|
+
|
11
|
+
static void
|
12
|
+
create_and_free_provider(int argc, char **argv)
|
13
|
+
{
|
14
|
+
usdt_provider_t *provider;
|
15
|
+
usdt_probedef_t *probedef;
|
16
|
+
|
17
|
+
if ((provider = usdt_create_provider("testlibusdt", "modname")) == NULL) {
|
18
|
+
fprintf(stderr, "unable to create provider\n");
|
19
|
+
exit (1);
|
20
|
+
}
|
21
|
+
if ((probedef = usdt_create_probe((const char *)argv[1],
|
22
|
+
(const char *)argv[2],
|
23
|
+
(argc-3), (const char **)&argv[3])) == NULL)
|
24
|
+
{
|
25
|
+
fprintf(stderr, "unable to create probe\n");
|
26
|
+
exit (1);
|
27
|
+
}
|
28
|
+
usdt_provider_add_probe(provider, probedef);
|
29
|
+
|
30
|
+
if ((usdt_provider_enable(provider)) < 0) {
|
31
|
+
fprintf(stderr, "unable to enable provider: %s\n", usdt_errstr(provider));
|
32
|
+
exit (1);
|
33
|
+
}
|
34
|
+
|
35
|
+
if ((usdt_provider_disable(provider)) < 0) {
|
36
|
+
fprintf(stderr, "unable to disable provider: %s\n", usdt_errstr(provider));
|
37
|
+
exit (1);
|
38
|
+
}
|
39
|
+
|
40
|
+
usdt_probe_release(probedef);
|
41
|
+
usdt_provider_free(provider);
|
42
|
+
}
|
43
|
+
|
44
|
+
int
|
45
|
+
main(int argc, char **argv)
|
46
|
+
{
|
47
|
+
char char_argv[USDT_ARG_MAX];
|
48
|
+
int int_argv[USDT_ARG_MAX * 2];
|
49
|
+
int i;
|
50
|
+
char buf[255];
|
51
|
+
|
52
|
+
for (i = 0; i < USDT_ARG_MAX; i++)
|
53
|
+
int_argv[i] = i + 1;
|
54
|
+
for (i = 0; i < USDT_ARG_MAX; i++)
|
55
|
+
char_argv[i] = (char) i + 65;
|
56
|
+
|
57
|
+
if (argc < 3) {
|
58
|
+
fprintf(stderr, "usage: %s func name [types ...]\n", argv[0]);
|
59
|
+
return(1);
|
60
|
+
}
|
61
|
+
|
62
|
+
for (i = 0; i < USDT_ARG_MAX; i++) {
|
63
|
+
if (argv[i+3] != NULL && i+3 < argc) {
|
64
|
+
if (strncmp("c", argv[i+3], 1) == 0) {
|
65
|
+
argv[i+3] = strdup("char *");
|
66
|
+
}
|
67
|
+
if (strncmp("i", argv[i+3], 1) == 0) {
|
68
|
+
argv[i+3] = strdup("int");
|
69
|
+
}
|
70
|
+
}
|
71
|
+
}
|
72
|
+
|
73
|
+
for (i = 0; i < 100000; i++)
|
74
|
+
create_and_free_provider(argc, argv);
|
75
|
+
|
76
|
+
return 0;
|
77
|
+
}
|
data/ext/libusdt/test_usdt.c
CHANGED
@@ -11,9 +11,8 @@
|
|
11
11
|
static void
|
12
12
|
fire_probe(usdt_probedef_t *probedef, int argc, void **argv)
|
13
13
|
{
|
14
|
-
if (usdt_is_enabled(probedef->probe))
|
14
|
+
if (usdt_is_enabled(probedef->probe))
|
15
15
|
usdt_fire_probe(probedef->probe, argc, argv);
|
16
|
-
}
|
17
16
|
}
|
18
17
|
|
19
18
|
int main(int argc, char **argv) {
|
@@ -21,7 +20,7 @@ int main(int argc, char **argv) {
|
|
21
20
|
usdt_probedef_t *probedef;
|
22
21
|
char char_argv[USDT_ARG_MAX];
|
23
22
|
int int_argv[USDT_ARG_MAX * 2];
|
24
|
-
void **args;
|
23
|
+
void **args = NULL;
|
25
24
|
int i;
|
26
25
|
char buf[255];
|
27
26
|
|
@@ -75,6 +74,14 @@ int main(int argc, char **argv) {
|
|
75
74
|
fgets(buf, 255, stdin);
|
76
75
|
|
77
76
|
fire_probe(probedef, (argc-3), (void **)args);
|
77
|
+
usdt_probe_release(probedef);
|
78
|
+
|
79
|
+
if ((usdt_provider_disable(provider)) < 0) {
|
80
|
+
fprintf(stderr, "unable to disable provider: %s\n", usdt_errstr(provider));
|
81
|
+
exit (1);
|
82
|
+
}
|
83
|
+
|
84
|
+
usdt_provider_free(provider);
|
78
85
|
|
79
86
|
return 0;
|
80
87
|
}
|
data/ext/libusdt/usdt.c
CHANGED
@@ -15,9 +15,33 @@ char *usdt_errors[] = {
|
|
15
15
|
"failed to allocate page-aligned memory",
|
16
16
|
"no probes defined",
|
17
17
|
"failed to load DOF: %s",
|
18
|
-
"provider is already enabled"
|
18
|
+
"provider is already enabled",
|
19
|
+
"failed to unload DOF: %s",
|
20
|
+
"probe named %s:%s:%s:%s already exists",
|
21
|
+
"failed to remove probe %s:%s:%s:%s"
|
19
22
|
};
|
20
23
|
|
24
|
+
static void
|
25
|
+
free_probedef(usdt_probedef_t *pd)
|
26
|
+
{
|
27
|
+
switch (pd->refcnt) {
|
28
|
+
case 1:
|
29
|
+
free((char *)pd->function);
|
30
|
+
free((char *)pd->name);
|
31
|
+
if (pd->probe) {
|
32
|
+
free(pd->probe->isenabled_addr);
|
33
|
+
free(pd->probe);
|
34
|
+
}
|
35
|
+
free(pd);
|
36
|
+
break;
|
37
|
+
case 2:
|
38
|
+
pd->refcnt = 1;
|
39
|
+
break;
|
40
|
+
default:
|
41
|
+
break;
|
42
|
+
}
|
43
|
+
}
|
44
|
+
|
21
45
|
usdt_provider_t *
|
22
46
|
usdt_create_provider(const char *name, const char *module)
|
23
47
|
{
|
@@ -46,6 +70,7 @@ usdt_create_probe(const char *func, const char *name, size_t argc, const char **
|
|
46
70
|
if ((p = malloc(sizeof *p)) == NULL)
|
47
71
|
return (NULL);
|
48
72
|
|
73
|
+
p->refcnt = 2;
|
49
74
|
p->function = strdup(func);
|
50
75
|
p->name = strdup(name);
|
51
76
|
p->argc = argc;
|
@@ -62,10 +87,28 @@ usdt_create_probe(const char *func, const char *name, size_t argc, const char **
|
|
62
87
|
}
|
63
88
|
|
64
89
|
void
|
90
|
+
usdt_probe_release(usdt_probedef_t *probedef)
|
91
|
+
{
|
92
|
+
free_probedef(probedef);
|
93
|
+
}
|
94
|
+
|
95
|
+
int
|
65
96
|
usdt_provider_add_probe(usdt_provider_t *provider, usdt_probedef_t *probedef)
|
66
97
|
{
|
67
98
|
usdt_probedef_t *pd;
|
68
99
|
|
100
|
+
if (provider->probedefs != NULL) {
|
101
|
+
for (pd = provider->probedefs; (pd != NULL); pd = pd->next) {
|
102
|
+
if ((strcmp(pd->name, probedef->name) == 0) &&
|
103
|
+
(strcmp(pd->function, probedef->function) == 0)) {
|
104
|
+
usdt_error(provider, USDT_ERROR_DUP_PROBE,
|
105
|
+
provider->name, provider->module,
|
106
|
+
probedef->function, probedef->name);
|
107
|
+
return (-1);
|
108
|
+
}
|
109
|
+
}
|
110
|
+
}
|
111
|
+
|
69
112
|
probedef->next = NULL;
|
70
113
|
if (provider->probedefs == NULL)
|
71
114
|
provider->probedefs = probedef;
|
@@ -73,6 +116,39 @@ usdt_provider_add_probe(usdt_provider_t *provider, usdt_probedef_t *probedef)
|
|
73
116
|
for (pd = provider->probedefs; (pd->next != NULL); pd = pd->next) ;
|
74
117
|
pd->next = probedef;
|
75
118
|
}
|
119
|
+
|
120
|
+
return (0);
|
121
|
+
}
|
122
|
+
|
123
|
+
int
|
124
|
+
usdt_provider_remove_probe(usdt_provider_t *provider, usdt_probedef_t *probedef)
|
125
|
+
{
|
126
|
+
usdt_probedef_t *pd, *prev_pd = NULL;
|
127
|
+
|
128
|
+
if (provider->probedefs == NULL) {
|
129
|
+
usdt_error(provider, USDT_ERROR_NOPROBES);
|
130
|
+
return (-1);
|
131
|
+
}
|
132
|
+
|
133
|
+
for (pd = provider->probedefs; (pd != NULL);
|
134
|
+
prev_pd = pd, pd = pd->next) {
|
135
|
+
|
136
|
+
if ((strcmp(pd->name, probedef->name) == 0) &&
|
137
|
+
(strcmp(pd->function, probedef->function) == 0)) {
|
138
|
+
|
139
|
+
if (prev_pd == NULL)
|
140
|
+
provider->probedefs = pd->next;
|
141
|
+
else
|
142
|
+
prev_pd->next = pd->next;
|
143
|
+
|
144
|
+
return (0);
|
145
|
+
}
|
146
|
+
}
|
147
|
+
|
148
|
+
usdt_error(provider, USDT_ERROR_REMOVE_PROBE,
|
149
|
+
provider->name, provider->module,
|
150
|
+
probedef->function, probedef->name);
|
151
|
+
return (-1);
|
76
152
|
}
|
77
153
|
|
78
154
|
int
|
@@ -87,7 +163,7 @@ usdt_provider_enable(usdt_provider_t *provider)
|
|
87
163
|
|
88
164
|
if (provider->enabled == 1) {
|
89
165
|
usdt_error(provider, USDT_ERROR_ALREADYENABLED);
|
90
|
-
return (0);
|
166
|
+
return (0); /* not fatal */
|
91
167
|
}
|
92
168
|
|
93
169
|
if (provider->probedefs == NULL) {
|
@@ -107,7 +183,7 @@ usdt_provider_enable(usdt_provider_t *provider)
|
|
107
183
|
return (-1);
|
108
184
|
}
|
109
185
|
|
110
|
-
if ((usdt_strtab_add(&strtab, provider->name))
|
186
|
+
if ((usdt_strtab_add(&strtab, provider->name)) == 0) {
|
111
187
|
usdt_error(provider, USDT_ERROR_MALLOC);
|
112
188
|
return (-1);
|
113
189
|
}
|
@@ -133,15 +209,54 @@ usdt_provider_enable(usdt_provider_t *provider)
|
|
133
209
|
|
134
210
|
usdt_dof_file_generate(file, &strtab);
|
135
211
|
|
212
|
+
usdt_dof_section_free(&strtab);
|
213
|
+
for (i = 0; i < 5; i++)
|
214
|
+
usdt_dof_section_free(§s[i]);
|
215
|
+
|
136
216
|
if ((usdt_dof_file_load(file, provider->module)) < 0) {
|
137
217
|
usdt_error(provider, USDT_ERROR_LOADDOF, strerror(errno));
|
138
218
|
return (-1);
|
139
219
|
}
|
140
220
|
|
141
221
|
provider->enabled = 1;
|
222
|
+
provider->file = file;
|
223
|
+
|
224
|
+
return (0);
|
225
|
+
}
|
226
|
+
|
227
|
+
int
|
228
|
+
usdt_provider_disable(usdt_provider_t *provider)
|
229
|
+
{
|
230
|
+
if (provider->enabled == 0)
|
231
|
+
return (0);
|
232
|
+
|
233
|
+
if ((usdt_dof_file_unload((usdt_dof_file_t *)provider->file)) < 0) {
|
234
|
+
usdt_error(provider, USDT_ERROR_UNLOADDOF, strerror(errno));
|
235
|
+
return (-1);
|
236
|
+
}
|
237
|
+
|
238
|
+
usdt_dof_file_free(provider->file);
|
239
|
+
provider->file = NULL;
|
240
|
+
provider->enabled = 0;
|
241
|
+
|
142
242
|
return (0);
|
143
243
|
}
|
144
244
|
|
245
|
+
void
|
246
|
+
usdt_provider_free(usdt_provider_t *provider)
|
247
|
+
{
|
248
|
+
usdt_probedef_t *pd, *next;
|
249
|
+
|
250
|
+
for (pd = provider->probedefs; pd != NULL; pd = next) {
|
251
|
+
next = pd->next;
|
252
|
+
free_probedef(pd);
|
253
|
+
}
|
254
|
+
|
255
|
+
free((char *)provider->name);
|
256
|
+
free((char *)provider->module);
|
257
|
+
free(provider);
|
258
|
+
}
|
259
|
+
|
145
260
|
int
|
146
261
|
usdt_is_enabled(usdt_probe_t *probe)
|
147
262
|
{
|
data/ext/libusdt/usdt.h
CHANGED
@@ -17,7 +17,10 @@ typedef enum usdt_error {
|
|
17
17
|
USDT_ERROR_VALLOC,
|
18
18
|
USDT_ERROR_NOPROBES,
|
19
19
|
USDT_ERROR_LOADDOF,
|
20
|
-
USDT_ERROR_ALREADYENABLED
|
20
|
+
USDT_ERROR_ALREADYENABLED,
|
21
|
+
USDT_ERROR_UNLOADDOF,
|
22
|
+
USDT_ERROR_DUP_PROBE,
|
23
|
+
USDT_ERROR_REMOVE_PROBE
|
21
24
|
} usdt_error_t;
|
22
25
|
|
23
26
|
typedef struct usdt_probe {
|
@@ -35,10 +38,12 @@ typedef struct usdt_probedef {
|
|
35
38
|
usdt_argtype_t types[USDT_ARG_MAX];
|
36
39
|
struct usdt_probe *probe;
|
37
40
|
struct usdt_probedef *next;
|
41
|
+
int refcnt;
|
38
42
|
} usdt_probedef_t;
|
39
43
|
|
40
44
|
usdt_probedef_t *usdt_create_probe(const char *func, const char *name,
|
41
45
|
size_t argc, const char **types);
|
46
|
+
void usdt_probe_release(usdt_probedef_t *probedef);
|
42
47
|
|
43
48
|
typedef struct usdt_provider {
|
44
49
|
const char *name;
|
@@ -46,11 +51,15 @@ typedef struct usdt_provider {
|
|
46
51
|
usdt_probedef_t *probedefs;
|
47
52
|
char *error;
|
48
53
|
int enabled;
|
54
|
+
void *file;
|
49
55
|
} usdt_provider_t;
|
50
56
|
|
51
57
|
usdt_provider_t *usdt_create_provider(const char *name, const char *module);
|
52
|
-
|
58
|
+
int usdt_provider_add_probe(usdt_provider_t *provider, usdt_probedef_t *probedef);
|
59
|
+
int usdt_provider_remove_probe(usdt_provider_t *provider, usdt_probedef_t *probedef);
|
53
60
|
int usdt_provider_enable(usdt_provider_t *provider);
|
61
|
+
int usdt_provider_disable(usdt_provider_t *provider);
|
62
|
+
void usdt_provider_free(usdt_provider_t *provider);
|
54
63
|
|
55
64
|
void usdt_error(usdt_provider_t *provider, usdt_error_t error, ...);
|
56
65
|
char *usdt_errstr(usdt_provider_t *provider);
|
data/ext/libusdt/usdt_dof.c
CHANGED
@@ -79,6 +79,12 @@ usdt_dof_section_init(usdt_dof_section_t *section, uint32_t type, dof_secidx_t i
|
|
79
79
|
return (0);
|
80
80
|
}
|
81
81
|
|
82
|
+
void
|
83
|
+
usdt_dof_section_free(usdt_dof_section_t *section)
|
84
|
+
{
|
85
|
+
free(section->data);
|
86
|
+
}
|
87
|
+
|
82
88
|
int
|
83
89
|
usdt_strtab_init(usdt_strtab_t *strtab, dof_secidx_t index)
|
84
90
|
{
|
@@ -112,11 +118,11 @@ usdt_strtab_add(usdt_strtab_t *strtab, const char *string)
|
|
112
118
|
strtab->strindex += (length + 1);
|
113
119
|
|
114
120
|
if ((strtab->data = realloc(strtab->data, strtab->strindex)) == NULL)
|
115
|
-
return (
|
121
|
+
return (0);
|
116
122
|
|
117
123
|
memcpy((char *) (strtab->data + index), (char *)string, length + 1);
|
118
124
|
strtab->size = index + length + 1;
|
119
125
|
|
120
|
-
return index;
|
126
|
+
return (index);
|
121
127
|
}
|
122
128
|
|
data/ext/libusdt/usdt_dof_file.c
CHANGED
@@ -47,7 +47,10 @@ load_dof(int fd, dof_helper_t *dh)
|
|
47
47
|
val = (user_addr_t)(unsigned long)ioctlData;
|
48
48
|
ret = ioctl(fd, DTRACEHIOC_ADDDOF, &val);
|
49
49
|
|
50
|
-
|
50
|
+
if (ret < 0)
|
51
|
+
return ret;
|
52
|
+
|
53
|
+
return (int)(ioctlData->dofiod_helpers[0].dofhp_dof);
|
51
54
|
}
|
52
55
|
|
53
56
|
#else /* Solaris */
|
@@ -129,7 +132,8 @@ static size_t
|
|
129
132
|
add_section(usdt_dof_file_t *file, size_t offset, usdt_dof_section_t *section)
|
130
133
|
{
|
131
134
|
if (section->pad > 0) {
|
132
|
-
|
135
|
+
/* maximum padding required is 7 */
|
136
|
+
memcpy((file->dof + offset), "\0\0\0\0\0\0\0", section->pad);
|
133
137
|
offset += section->pad;
|
134
138
|
}
|
135
139
|
|
@@ -137,6 +141,25 @@ add_section(usdt_dof_file_t *file, size_t offset, usdt_dof_section_t *section)
|
|
137
141
|
return (offset + section->size);
|
138
142
|
}
|
139
143
|
|
144
|
+
int
|
145
|
+
usdt_dof_file_unload(usdt_dof_file_t *file)
|
146
|
+
{
|
147
|
+
int fd, ret;
|
148
|
+
|
149
|
+
if ((fd = open(helper, O_RDWR)) < 0)
|
150
|
+
return (-1);
|
151
|
+
|
152
|
+
ret = ioctl(fd, DTRACEHIOC_REMOVE, file->gen);
|
153
|
+
|
154
|
+
if (ret < 0)
|
155
|
+
return (-1);
|
156
|
+
|
157
|
+
if ((close(fd)) < 0)
|
158
|
+
return (-1);
|
159
|
+
|
160
|
+
return (0);
|
161
|
+
}
|
162
|
+
|
140
163
|
int
|
141
164
|
usdt_dof_file_load(usdt_dof_file_t *file, const char *module)
|
142
165
|
{
|
@@ -245,3 +268,10 @@ usdt_dof_file_init(usdt_provider_t *provider, size_t size)
|
|
245
268
|
|
246
269
|
return (file);
|
247
270
|
}
|
271
|
+
|
272
|
+
void
|
273
|
+
usdt_dof_file_free(usdt_dof_file_t *file)
|
274
|
+
{
|
275
|
+
free(file->dof);
|
276
|
+
free(file);
|
277
|
+
}
|
@@ -20,6 +20,7 @@ usdt_dof_probes_sect(usdt_dof_section_t *probes,
|
|
20
20
|
for (pd = provider->probedefs; pd != NULL; pd = pd->next) {
|
21
21
|
argc = 0;
|
22
22
|
argv = 0;
|
23
|
+
type = 0;
|
23
24
|
|
24
25
|
for (i = 0; i < pd->argc; i++) {
|
25
26
|
switch(pd->types[i]) {
|
@@ -45,7 +46,7 @@ usdt_dof_probes_sect(usdt_dof_section_t *probes,
|
|
45
46
|
|
46
47
|
#ifdef __x86_64__
|
47
48
|
p.dofpr_addr = (uint64_t) pd->probe->isenabled_addr;
|
48
|
-
#elif __i386__
|
49
|
+
#elif __i386__ || __i386
|
49
50
|
p.dofpr_addr = (uint32_t) pd->probe->isenabled_addr;
|
50
51
|
#else
|
51
52
|
#error "only x86_64 and i386 supported"
|
@@ -61,6 +62,8 @@ usdt_dof_probes_sect(usdt_dof_section_t *probes,
|
|
61
62
|
p.dofpr_noffs = 1;
|
62
63
|
p.dofpr_enoffidx = offidx;
|
63
64
|
p.dofpr_nenoffs = 1;
|
65
|
+
p.dofpr_pad1 = 0;
|
66
|
+
p.dofpr_pad2 = 0;
|
64
67
|
|
65
68
|
usdt_dof_section_add_data(probes, &p, sizeof(dof_probe_t));
|
66
69
|
probes->entsize = sizeof(dof_probe_t);
|
@@ -150,7 +153,7 @@ usdt_dof_provider_sect(usdt_dof_section_t *provider_s, usdt_provider_t *provider
|
|
150
153
|
p.dofpv_prargs = 2;
|
151
154
|
p.dofpv_proffs = 3;
|
152
155
|
p.dofpv_prenoffs = 4;
|
153
|
-
p.dofpv_name = 1;
|
156
|
+
p.dofpv_name = 1; /* provider name always first strtab entry. */
|
154
157
|
|
155
158
|
/*
|
156
159
|
* Stability is something of a hack. Everything is marked *
|
data/ext/libusdt/usdt_internal.h
CHANGED
@@ -80,6 +80,7 @@ usdt_dof_file_t *usdt_dof_file_init(usdt_provider_t *provider, size_t size);
|
|
80
80
|
void usdt_dof_file_append_section(usdt_dof_file_t *file, usdt_dof_section_t *section);
|
81
81
|
void usdt_dof_file_generate(usdt_dof_file_t *file, usdt_strtab_t *strtab);
|
82
82
|
int usdt_dof_file_load(usdt_dof_file_t *file, const char *module);
|
83
|
+
int usdt_dof_file_unload(usdt_dof_file_t *file);
|
83
84
|
|
84
85
|
int usdt_dof_probes_sect(usdt_dof_section_t *probes,
|
85
86
|
usdt_provider_t *provider, usdt_strtab_t *strtab);
|
data/ext/libusdt/usdt_probe.c
CHANGED
@@ -25,7 +25,7 @@ usdt_is_enabled_offset(usdt_probe_t *probe, char *dof)
|
|
25
25
|
{
|
26
26
|
uint32_t offset;
|
27
27
|
#ifdef __x86_64__
|
28
|
-
offset = ((uint64_t) probe->isenabled_addr - (uint64_t) dof +
|
28
|
+
offset = ((uint64_t) probe->isenabled_addr - (uint64_t) dof + 6);
|
29
29
|
#elif __i386__
|
30
30
|
offset = ((uint32_t) probe->isenabled_addr - (uint32_t) dof + 6);
|
31
31
|
#else
|
@@ -39,13 +39,13 @@ usdt_is_enabled_offset(usdt_probe_t *probe, char *dof)
|
|
39
39
|
uint32_t
|
40
40
|
usdt_probe_offset(usdt_probe_t *probe, char *dof, uint8_t argc)
|
41
41
|
{
|
42
|
-
return (
|
42
|
+
return (16);
|
43
43
|
}
|
44
44
|
|
45
45
|
uint32_t
|
46
46
|
usdt_is_enabled_offset(usdt_probe_t *probe, char *dof)
|
47
47
|
{
|
48
|
-
return (
|
48
|
+
return (8);
|
49
49
|
}
|
50
50
|
|
51
51
|
#endif
|
@@ -53,16 +53,20 @@ usdt_is_enabled_offset(usdt_probe_t *probe, char *dof)
|
|
53
53
|
int
|
54
54
|
usdt_create_tracepoints(usdt_probe_t *probe)
|
55
55
|
{
|
56
|
+
size_t size;
|
57
|
+
|
56
58
|
/* ensure that the tracepoints will fit the heap we're allocating */
|
57
|
-
|
59
|
+
size = ((char *)usdt_tracepoint_end - (char *)usdt_tracepoint_isenabled);
|
60
|
+
assert(size < FUNC_SIZE);
|
58
61
|
|
59
|
-
if ((probe->isenabled_addr = valloc(FUNC_SIZE)) == NULL)
|
62
|
+
if ((probe->isenabled_addr = (int (*)())valloc(FUNC_SIZE)) == NULL)
|
60
63
|
return (-1);
|
61
|
-
}
|
62
|
-
probe->probe_addr = probe->isenabled_addr +
|
63
|
-
(usdt_tracepoint_probe - usdt_tracepoint_isenabled);
|
64
64
|
|
65
|
-
|
65
|
+
size = ((char *)usdt_tracepoint_probe - (char *)usdt_tracepoint_isenabled);
|
66
|
+
probe->probe_addr = (char *)probe->isenabled_addr + size;
|
67
|
+
|
68
|
+
memcpy((void *)probe->isenabled_addr,
|
69
|
+
(const void *)usdt_tracepoint_isenabled, FUNC_SIZE);
|
66
70
|
mprotect((void *)probe->isenabled_addr, FUNC_SIZE,
|
67
71
|
PROT_READ | PROT_WRITE | PROT_EXEC);
|
68
72
|
|
data/lib/usdt/version.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ruby-usdt
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.2
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -25,6 +25,7 @@ files:
|
|
25
25
|
- ext/libusdt/Makefile
|
26
26
|
- ext/libusdt/README.md
|
27
27
|
- ext/libusdt/test.pl
|
28
|
+
- ext/libusdt/test_mem_usage.c
|
28
29
|
- ext/libusdt/test_usdt.c
|
29
30
|
- ext/libusdt/usdt.c
|
30
31
|
- ext/libusdt/usdt.h
|