Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
B
bcc
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
bcc
Commits
a6200fbe
Commit
a6200fbe
authored
Mar 30, 2016
by
Brenden Blanco
Browse files
Options
Browse Files
Download
Plain Diff
Merge pull request #454 from brendangregg/master
IPv6 strings with an inet6_ntoa
parents
41f6a1eb
917cb853
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
34 additions
and
22 deletions
+34
-22
man/man8/tcpconnect.8
man/man8/tcpconnect.8
+2
-4
tools/tcpconnect.py
tools/tcpconnect.py
+30
-14
tools/tcpconnect_example.txt
tools/tcpconnect_example.txt
+2
-4
No files found.
man/man8/tcpconnect.8
View file @
a6200fbe
...
@@ -55,12 +55,10 @@ IP
...
@@ -55,12 +55,10 @@ IP
IP address family (4 or 6)
IP address family (4 or 6)
.TP
.TP
SADDR
SADDR
Source IP address. IPv4 as a dotted quad, IPv6 shows "..." then the last 4
Source IP address.
bytes (check for newer versions of this tool for the full address).
.TP
.TP
DADDR
DADDR
Destination IP address. IPv4 as a dotted quad, IPv6 shows "..." then the last 4
Destination IP address.
bytes (check for newer versions of this tool for the full address).
.TP
.TP
DPORT
DPORT
Destination port
Destination port
...
...
tools/tcpconnect.py
View file @
a6200fbe
...
@@ -24,6 +24,8 @@
...
@@ -24,6 +24,8 @@
from
__future__
import
print_function
from
__future__
import
print_function
from
bcc
import
BPF
from
bcc
import
BPF
import
argparse
import
argparse
import
re
from
struct
import
pack
,
unpack_from
import
ctypes
as
ct
import
ctypes
as
ct
# arguments
# arguments
...
@@ -65,12 +67,11 @@ struct ipv4_data_t {
...
@@ -65,12 +67,11 @@ struct ipv4_data_t {
BPF_PERF_OUTPUT(ipv4_events);
BPF_PERF_OUTPUT(ipv4_events);
struct ipv6_data_t {
struct ipv6_data_t {
// XXX: update to transfer full ipv6 addrs
u64 ts_us;
u64 ts_us;
u64 pid;
u64 pid;
u64 ip;
u64 ip;
u64 saddr;
u64 saddr
[2]
;
u64 daddr;
u64 daddr
[2]
;
u64 dport;
u64 dport;
char task[TASK_COMM_LEN];
char task[TASK_COMM_LEN];
};
};
...
@@ -125,13 +126,14 @@ static int trace_connect_return(struct pt_regs *ctx, short ipver)
...
@@ -125,13 +126,14 @@ static int trace_connect_return(struct pt_regs *ctx, short ipver)
struct ipv6_data_t data6 = {.pid = pid, .ip = ipver};
struct ipv6_data_t data6 = {.pid = pid, .ip = ipver};
data6.ts_us = bpf_ktime_get_ns() / 1000;
data6.ts_us = bpf_ktime_get_ns() / 1000;
// just grab the last 4 bytes for now
// just grab the last 4 bytes for now
u32 saddr = 0, daddr = 0;
bpf_probe_read(&data6.saddr[0], sizeof(data6.saddr[0]),
bpf_probe_read(&saddr, sizeof(saddr),
&skp->__sk_common.skc_v6_rcv_saddr.in6_u.u6_addr32[0]);
&skp->__sk_common.skc_v6_rcv_saddr.in6_u.u6_addr32[3]);
bpf_probe_read(&data6.saddr[1], sizeof(data6.saddr[1]),
bpf_probe_read(&daddr, sizeof(daddr),
&skp->__sk_common.skc_v6_rcv_saddr.in6_u.u6_addr32[2]);
&skp->__sk_common.skc_v6_daddr.in6_u.u6_addr32[3]);
bpf_probe_read(&data6.daddr[0], sizeof(data6.daddr[0]),
data6.saddr = bpf_ntohl(saddr);
&skp->__sk_common.skc_v6_daddr.in6_u.u6_addr32[0]);
data6.daddr = bpf_ntohl(daddr);
bpf_probe_read(&data6.daddr[1], sizeof(data6.daddr[1]),
&skp->__sk_common.skc_v6_daddr.in6_u.u6_addr32[2]);
data6.dport = ntohs(dport);
data6.dport = ntohs(dport);
bpf_get_current_comm(&data6.task, sizeof(data6.task));
bpf_get_current_comm(&data6.task, sizeof(data6.task));
ipv6_events.perf_submit(ctx, &data6, sizeof(data6));
ipv6_events.perf_submit(ctx, &data6, sizeof(data6));
...
@@ -179,8 +181,8 @@ class Data_ipv6(ct.Structure):
...
@@ -179,8 +181,8 @@ class Data_ipv6(ct.Structure):
(
"ts_us"
,
ct
.
c_ulonglong
),
(
"ts_us"
,
ct
.
c_ulonglong
),
(
"pid"
,
ct
.
c_ulonglong
),
(
"pid"
,
ct
.
c_ulonglong
),
(
"ip"
,
ct
.
c_ulonglong
),
(
"ip"
,
ct
.
c_ulonglong
),
(
"saddr"
,
ct
.
c_ulonglong
),
(
"saddr"
,
ct
.
c_ulonglong
*
2
),
(
"daddr"
,
ct
.
c_ulonglong
),
(
"daddr"
,
ct
.
c_ulonglong
*
2
),
(
"dport"
,
ct
.
c_ulonglong
),
(
"dport"
,
ct
.
c_ulonglong
),
(
"task"
,
ct
.
c_char
*
TASK_COMM_LEN
)
(
"task"
,
ct
.
c_char
*
TASK_COMM_LEN
)
]
]
...
@@ -195,14 +197,18 @@ def print_ipv4_event(cpu, data, size):
...
@@ -195,14 +197,18 @@ def print_ipv4_event(cpu, data, size):
print
(
"%-6d %-12.12s %-2d %-16s %-16s %-4d"
%
(
event
.
pid
,
event
.
task
,
print
(
"%-6d %-12.12s %-2d %-16s %-16s %-4d"
%
(
event
.
pid
,
event
.
task
,
event
.
ip
,
inet_ntoa
(
event
.
saddr
),
inet_ntoa
(
event
.
daddr
),
event
.
ip
,
inet_ntoa
(
event
.
saddr
),
inet_ntoa
(
event
.
daddr
),
event
.
dport
))
event
.
dport
))
def
print_ipv6_event
(
cpu
,
data
,
size
):
def
print_ipv6_event
(
cpu
,
data
,
size
):
event
=
ct
.
cast
(
data
,
ct
.
POINTER
(
Data_ipv6
)).
contents
event
=
ct
.
cast
(
data
,
ct
.
POINTER
(
Data_ipv6
)).
contents
if
args
.
timestamp
:
if
args
.
timestamp
:
if
start_ts
==
0
:
if
start_ts
==
0
:
start_ts
=
event
.
ts_us
start_ts
=
event
.
ts_us
print
(
"%-9.3f"
%
((
event
.
ts_us
-
start_ts
)
/
100000
),
end
=
""
)
print
(
"%-9.3f"
%
((
event
.
ts_us
-
start_ts
)
/
100000
),
end
=
""
)
print
(
"%-6d %-12.12s %-2d ...%-13x ...%-13x %-4d"
%
(
event
.
pid
,
print
(
"%-6d %-12.12s %-2d %-16s %-16s %-4d"
%
(
event
.
pid
,
event
.
task
,
event
.
ip
,
event
.
saddr
,
event
.
daddr
,
event
.
dport
))
event
.
task
,
event
.
ip
,
inet6_ntoa
(
event
.
saddr
[
1
]
<<
64
|
event
.
saddr
[
0
]),
inet6_ntoa
(
event
.
daddr
[
1
]
<<
64
|
event
.
daddr
[
0
]),
event
.
dport
))
# initialize BPF
# initialize BPF
b
=
BPF
(
text
=
bpf_text
)
b
=
BPF
(
text
=
bpf_text
)
...
@@ -220,6 +226,7 @@ print("%-6s %-12s %-2s %-16s %-16s %-4s" % ("PID", "COMM", "IP", "SADDR",
...
@@ -220,6 +226,7 @@ print("%-6s %-12s %-2s %-16s %-16s %-4s" % ("PID", "COMM", "IP", "SADDR",
start_ts
=
0
start_ts
=
0
def
inet_ntoa
(
addr
):
def
inet_ntoa
(
addr
):
# u32 to dotted quad string
dq
=
''
dq
=
''
for
i
in
range
(
0
,
4
):
for
i
in
range
(
0
,
4
):
dq
=
dq
+
str
(
addr
&
0xff
)
dq
=
dq
+
str
(
addr
&
0xff
)
...
@@ -228,6 +235,15 @@ def inet_ntoa(addr):
...
@@ -228,6 +235,15 @@ def inet_ntoa(addr):
addr
=
addr
>>
8
addr
=
addr
>>
8
return
dq
return
dq
def
inet6_ntoa
(
addr
):
# see RFC4291 summary in RFC5952 section 2
s
=
":"
.
join
([
"%x"
%
x
for
x
in
unpack_from
(
">HHHHHHHH"
,
pack
(
"QQ"
,
addr
&
0xffffffff
,
addr
>>
64
))])
# compress left-most zero run only (change to most for RFC5952):
s
=
re
.
sub
(
r'(^|:)0:(0:)+'
,
r'::'
,
s
,
1
)
return
s
# read events
# read events
b
[
"ipv4_events"
].
open_perf_buffer
(
print_ipv4_event
)
b
[
"ipv4_events"
].
open_perf_buffer
(
print_ipv4_event
)
b
[
"ipv6_events"
].
open_perf_buffer
(
print_ipv6_event
)
b
[
"ipv6_events"
].
open_perf_buffer
(
print_ipv6_event
)
...
...
tools/tcpconnect_example.txt
View file @
a6200fbe
...
@@ -10,16 +10,14 @@ PID COMM IP SADDR DADDR DPORT
...
@@ -10,16 +10,14 @@ PID COMM IP SADDR DADDR DPORT
1479 telnet 4 127.0.0.1 127.0.0.1 23
1479 telnet 4 127.0.0.1 127.0.0.1 23
1469 curl 4 10.201.219.236 54.245.105.25 80
1469 curl 4 10.201.219.236 54.245.105.25 80
1469 curl 4 10.201.219.236 54.67.101.145 80
1469 curl 4 10.201.219.236 54.67.101.145 80
11072 ssh 6 ...fe8203ac ...fe82abcd 22
1991 telnet 6 ::1 ::1 23
2015 ssh 6 fe80::2000:bff:fe82:3ac fe80::2000:bff:fe82:3ac 22
This output shows four connections, one from a "telnet" process, two from
This output shows four connections, one from a "telnet" process, two from
"curl", and one from "ssh". The output details shows the IP version, source
"curl", and one from "ssh". The output details shows the IP version, source
address, destination address, and destination port. This traces attempted
address, destination address, and destination port. This traces attempted
connections: these may have failed.
connections: these may have failed.
IPv4 addresses are printed as dotted quads. Only the last 4 bytes of IPv6
addresses are printed for now (check for updated versions of this tool).
The overhead of this tool should be negligible, since it is only tracing the
The overhead of this tool should be negligible, since it is only tracing the
kernel functions performing connect. It is not tracing every packet and then
kernel functions performing connect. It is not tracing every packet and then
filtering.
filtering.
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment