Skip to content

Commit ada26ca

Browse files
committed
Merge branch 'udp_receive_hostname_port'
by passing :datagram to the Supply method on a IO::Socket::Async in udp mode, you can get the hostname and port of the sending socket with every message.
2 parents 8d95402 + b406b32 commit ada26ca

File tree

1 file changed

+32
-8
lines changed

1 file changed

+32
-8
lines changed

src/core/IO/Socket/Async.pm6

Lines changed: 32 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -42,17 +42,33 @@ my class IO::Socket::Async {
4242
$p
4343
}
4444

45+
my class Datagram {
46+
has $.data;
47+
has str $.hostname;
48+
has int $.port;
49+
50+
method decode(|c) {
51+
die "Cannot decode a datagram with Str data" if $!data ~~ Str;
52+
return self.clone(data => $!data.decode(|c));
53+
}
54+
method encode(|c) {
55+
die "Cannot encode a datagram with Blob data" if $!data ~~ Blob;
56+
return self.clone(data => $!data.encode(|c));
57+
}
58+
}
59+
4560
my class SocketReaderTappable does Tappable {
4661
has $!VMIO;
4762
has $!scheduler;
4863
has $!buf;
4964
has $!close-promise;
65+
has $!udp;
5066

51-
method new(Mu :$VMIO!, :$scheduler!, :$buf!, :$close-promise!) {
52-
self.CREATE!SET-SELF($VMIO, $scheduler, $buf, $close-promise)
67+
method new(Mu :$VMIO!, :$scheduler!, :$buf!, :$close-promise!, :$udp!) {
68+
self.CREATE!SET-SELF($VMIO, $scheduler, $buf, $close-promise, $udp)
5369
}
5470

55-
method !SET-SELF(Mu $!VMIO, $!scheduler, $!buf, $!close-promise) { self }
71+
method !SET-SELF(Mu $!VMIO, $!scheduler, $!buf, $!close-promise, $!udp) { self }
5672

5773
method tap(&emit, &done, &quit, &tap) {
5874
my $buffer := nqp::list();
@@ -76,7 +92,7 @@ my class IO::Socket::Async {
7692
$lock.protect: {
7793
my $cancellation := nqp::asyncreadbytes(nqp::decont($!VMIO),
7894
$!scheduler.queue(:hint-affinity),
79-
-> Mu \seq, Mu \data, Mu \err {
95+
-> Mu \seq, Mu \data, Mu \err, Mu \hostname = Str, Mu \port = Int {
8096
$lock.protect: {
8197
unless $finished {
8298
if err {
@@ -85,7 +101,15 @@ my class IO::Socket::Async {
85101
}
86102
elsif nqp::isconcrete(data) {
87103
my int $insert-pos = seq - $buffer-start-seq;
88-
nqp::bindpos($buffer, $insert-pos, data);
104+
if $!udp && nqp::isconcrete(hostname) && nqp::isconcrete(port) {
105+
nqp::bindpos($buffer, $insert-pos, Datagram.new(
106+
data => data,
107+
hostname => hostname,
108+
port => port
109+
));
110+
} else {
111+
nqp::bindpos($buffer, $insert-pos, data);
112+
}
89113
emit-events();
90114
}
91115
else {
@@ -116,13 +140,13 @@ my class IO::Socket::Async {
116140
method serial(--> True) { }
117141
}
118142

119-
multi method Supply(IO::Socket::Async:D: :$bin, :$buf = buf8.new, :$enc, :$scheduler = $*SCHEDULER) {
143+
multi method Supply(IO::Socket::Async:D: :$bin, :$buf = buf8.new, :$datagram, :$enc, :$scheduler = $*SCHEDULER) {
120144
if $bin {
121145
Supply.new: SocketReaderTappable.new:
122-
:$!VMIO, :$scheduler, :$buf, :$!close-promise
146+
:$!VMIO, :$scheduler, :$buf, :$!close-promise, udp => $!udp && $datagram
123147
}
124148
else {
125-
my $bin-supply = self.Supply(:bin);
149+
my $bin-supply = self.Supply(:bin, :$datagram);
126150
if $!udp {
127151
supply {
128152
whenever $bin-supply {

0 commit comments

Comments
 (0)