-
Notifications
You must be signed in to change notification settings - Fork 2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
gnrc conn: enqueue packets if noone's waiting #4327
Conversation
There must be another way of doing this without changing gnrc_udp. Because this is somewhat beside the point of conn, IMHO. |
The only way to keep gnrc_udp completely untouched would require to run conn or POSIX in its own thread which would be worse. I'm also unhappy with this dependency but without this patch sockets won't work properly. On 23 November 2015 09:17:02 CET, Martine Lenders notifications@github.com wrote:
Join the RIOT |
@@ -132,7 +133,15 @@ static void _receive(gnrc_pktsnip_t *pkt) | |||
/* send payload to receivers */ | |||
if (!gnrc_netapi_dispatch_receive(GNRC_NETTYPE_UDP, port, pkt)) { | |||
DEBUG("udp: unable to forward packet as no one is interested in it\n"); | |||
#ifdef MODULE_GNRC_CONN |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
GNRC_CONN_UDP
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can one include GNRC_CONN
and GNRC_UDP
without GNRC_CONN_UDP
?
Then we need a similar solution for conn_ip |
This seems like a hack. @OlegHahm Could you elaborate on the problem? |
msg_receive(&msg); | ||
int idx = -1; | ||
/* first check if there's packet waiting in the queue */ | ||
if ((idx = cib_get(&_conn_buf_cib)) != -1) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wouldn't this also dequeue packets destined for other ports since you use only one universal cib?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, but an (unbound) POSIX recvfrom()
doesn't specify a port to receive on. However, this rises two questions:
1.) do we want this queue only in combination with POSIX sockets?
2.) what to do with bound sockets here?
If a library uses POSIX sockets (like ccn-lite or tinydtls) and calls sendto(...);
do_some_computation();
recvfrom(...); expecting to receive the response to the sendto-call even if |
545d805
to
1723874
Compare
@cgundogan, what about the proposed solution in OlegHahm@65506e5 ? |
@OlegHahm thanks, I get it. This points to something that should be solved at the core IPC: decouple message endpoints from threads. That way conn_* could have it's own message queue and register that when *_bind()ing. I've got code lying around for that, but that will probably need time to get in, as it's at the heart of core/. If this PR fixes posix sockets for now, I'd say, lets get it in. |
I thought about it, too. This doesn't necessarily have to be a replacement for msg but can also be an alternative (maybe a good idea for a first step anyway). I'm thinking of something like lwIPs mboxes. |
I agree that this is a workaround for now, but we would need a more generic (no pun intended) concept to solve this. However, if you agree to take this workaround for now, I would implement the missing RAW IP part and we can merge this. |
@OlegHahm I am fine with your proposed enqueuing strategy. However: In case of multiple threads that use |
@cgundogan, probably you're right, but I guess this can already happen without this patch, if there's an RAW IP and a UDP socket opened. I think we need to find a better solution in the long run anyway. |
As long as this woraround is somehow marked as such in the code I join the others and ACK it |
Okay, will do. |
Are you okay with these comments? Should I squash? |
int gnrc_conn_recvfrom(conn_t *conn, void *data, size_t max_len, void *addr, size_t *addr_len, | ||
uint16_t *port) | ||
{ | ||
msg_t msg; | ||
/* TODO: this is a rather arbirtrary value and creates the risk of starvation. */ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
arbitrary (non-commit comment)
Hm, still don't know how to garbage collect enqueued datagrams? |
on closing of socket? |
Might be way too late. One may open a socket just for sending period packets without ever calling receive. I think the best way is to switch to a different data structure, e.g. a lifo, and call a timer based garbage collector. |
Thanks to the discussion with @cgundogan in #4320 I came to the conclusion that this is actually not required if you do the implicit binding during the |
Currently gnrc in combination with POSIX sockets will discard packets if
recvfrom()
is not called before.Another part for fixing #4320.