-
Notifications
You must be signed in to change notification settings - Fork 2.1k
drivers/slipmux: Add to RIOT #21418
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
drivers/slipmux: Add to RIOT #21418
Conversation
I don't quite understand the purpose if this. Sure, with this approach you can omit the IP and UDP header, but is that really worth the hassle? |
From the byte-wise overhead, it is not that much of a difference yes. I don't think it is that much of a hassle tho. Beside, as soon as you use IP+UDP you have endpoints in a network and those need to be configured (I need to know the IP I want to talk to). Doing slipmux configuration frames you have a guaranteed point to point channel with no configuration nor hassle ;) |
I can't comment on the code right now, but maybe for the open aspects:
|
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.
First round of review.
drivers/include/slipdev.h
Outdated
#if IS_USED(MODULE_SLIPDEV_STDIO) | ||
chunk_ringbuf_t rb_config; /**< Ringbuffer to store received CONFIG frames.*/ | ||
uint8_t rxmem_config[CONFIG_SLIPDEV_BUFSIZE]; /**< memory used by RX buffer */ | ||
kernel_pid_t coap_server_pid; |
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.
kernel_pid_t coap_server_pid; | |
kernel_pid_t coap_server_pid; /**< The PID of the CoAP server */ |
Wrt to future extensions, maybe that can be more generalized so that, e.g., also a gcoap or unicoap queue could be put here, if they exist to not have to provide an extra server then.
Again, mainly a comment for future improvements, this does not have to be addressed in this PR.
(edit: but would also address @chrysn's comment)
e203f61
to
7af6c9c
Compare
drivers/slipdev/slipdev.c
Outdated
void slipdev_setup(slipdev_t *dev, const slipdev_params_t *params, uint8_t index) | ||
{ | ||
#if IS_USED(MODULE_SLIPDEV_STDIO) |
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.
Please use a separate pseudo-module for this, normal slipdev stdio multiplex should not require a CoAP server.
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.
You are repeating yourself ;)
I am not sure yet if "just a separate pseudo-module" is the correct call. What do you think about making the driver "slipmux" with no functionality (not even slip). One can then add the pseudomodules slipmux_ip
, slipmux_configuration
and slipmux_stdio
which add their respective functions. This way, one could use configuration frames (-> coap) without needing IP/gnrc as a dependency.
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.
If you desire to do so go ahead.
I just want to avoid bloating the slipdev driver for simple device to device links that might have a multiplexed debug interface for convenience.
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.
That will be much more work than I thought. I'll move that task to a followup PR. For this one, I adopted your wish and guarded it with its own pseudomodule.
In addition, I changed the way the parsing is guarded with the #if IS_USED(..)
. Before: The whole case of stdio was removed if the module was not selected. Now: Only the data processing is removed, the cases for parsing remain. (Same for configuration frames). Reason is simple: If you remove the parsing + states, any byte received will be treated as a IP packet and then dropped by gnrc as "undefined packet type". This no-longer the case, instead, receiving a diagnostic/configuration frame without their pseudomodules enabled, they will be silently ignored.
88d8ca1
to
12435ec
Compare
@benpicco I think this is ready for another review. If that is positive, I will drop the shell/example related commit and squash the others. |
@benpicco ping :) |
12435ec
to
99211c0
Compare
Some high-level comments from my side:
Isn't it also missing diagnostic transfer? Just had a quick glance at the code, but could only find references to configuration frames.
|
That's because those were already implemented in RIOT and are just called stdio via slip. Blame @miri64 for that :p If you enable this, every
Eventually, yes. There is still work to be done on the coap-handling/server side. If I can get away with minimal documentation this time, I would appreciate. I fear it will be duplicated work if I re-implement it later (for example with unicoap). Plus, as mentioned in a comment with benpicco, the handling of the pseudomodule is not ideal in the moment. For example, it is not possible to enable configuration transfer without packet transfer. And even if you could, nanocoap depends on udp, which means you would still pull in a lot of wasted code & bytes. Both issues are scheduled for follow-up work.
That is correct.
That's nanocoap specific, I do not interact with them myself (beside the shell stuff but thats just an example of what one could do and will be dropped before merging). Afaik it is just a XFA defining names and callbacks. The nanocoap server just magically knows that XFA and looks up the endpoints on the fly. |
Okay, I get your point and also don't want you to spend time inefficiently. However, I would appreciate some very short documentation for now (probably in the pseudomodule file then) just mentioning:
Just trying to safeguard against follow-up work being stalled at some point, where we would end up with yet another feature not documented at all.
Ah, so |
Yes, that's your job :p Speaking of non documentation, I am either overlooking something or slip has already been poorly documented :/ Either way, I roughly agree with you but there are remarks.
I opted against that and followed the example of the already existing documentation for slipdev_stdio.
Yes, I added the links. Fun fact, I also fixed the broken link of SLIP dev itself :D
Not sure tbh. So far, it not claimed anywhere this is "rfc conform", as such, it can not be incomplete. It might be considered WIP? But what would that even mean for a pseudomodule that already works exactly like one would imagine? (still, you could persuade me to add that)
There are no shortcomings for the user as "slipmux conform" is not claimed. Things would look different if one would enable a In future work, one will have to flip it on it's head. There will be one module called 'slipmux' that will enable all three frame types and be slipmux-draft-conform. There will be three sub-modules each guarding one of the three frame types, enabling you to only have partial slipmux. There will be a module called |
Thanks for adding some documentation!
Maybe not shortcomings, but some things users should be aware of when using your module: there is an extra thread spawned, incoming coap requests over the wire are handled according to any
Sounds reasonable to me. Then why not briefly mention this in the documentation as well, so that users are aware this is probably only a temporary API (as in "module names" etc.) |
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.
Did not test this and did not look into the whole state machine, but I trust @benpicco's review on that (though please reply if @Teufelchen1 answers were to your liking). So from my side, we can go, if @mguetschow does not find anything else :-)
Looks good from my side now, haven't tested it though. Do you have suggestions for slipmux implementations to test this with? |
I have been testing against this one: https://crates.io/crates/slipmux (disclaimer, I am the author). tl;dr: I've been actively using this for weeks now in my SeCrEt PrOjEcT. Works well for config+diagnostic. Never used networking but I didn't touch that code meaningful so I am confident that didn't degrade. |
6bcfc2c
to
8bb3747
Compare
8bb3747
to
166ffcb
Compare
a, The notion of a CoAP server is loosely defined. A driver can open any number of sockets or for that matter 'concepts' similar to sockets. Each driver then forwards all packets to 'the unicoap server' after having removed the outer frame (UDP headers, etc). Information on what transport has been used is retained and optionally used to restrict resources to certain transports. I you really want to, you can handle this manually. There is an API for that. Right, now you can only have one ' b, Is this also what Lasse wants?: multiple ports and thus multiple sockets? I yes, I talked to Lasse off channel and we agreed on solution I have yet to implement. But, adding this to |
Awesome, unicoap will fit perfectly into this. |
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.
Alright, if there's no other tools available, interoperability tests are somehow mood. Trusting your testing therefore.
@miri64 you are still requesting change |
while (crb_get_chunk_size(&dev->rb_config, &len)) { | ||
crb_consume_chunk(&dev->rb_config, buf, len); |
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.
@mguetschow @benpicco I think we had brain damage when we reviewed & merged this. It's an obvious buffer overflow waiting to happen.
if (len > sizeof(buf)) { goto Fail }
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.
fun 👀
Contribution description
Hey 🪼,
this adds an (incomplete) implementation of Slipmux to RIOT. It extends the current slip driver and is backwards compatible.
The second commit adds an usage example, where the shell commands are exposed to coap and through it to slipmux. That commit will be dropped prio merging.
It is incomplete as frame abort is missing.
Testing procedure
Grab your favorite slipmux tool and connect RIOTs stdio to it. Make sure to build RIOT with
USEMODULE += slipdev_stdio
and optionally setCFLAGS += "-DCONFIG_NANOCOAP_BLOCK_SIZE_EXP_MAX=10"
to be able to handle coap packets that are longer than 64 bytes. See the changes I made to the default example.Feedback wanted: coap server
My current approach spawns a new thread with a nanocoap server to handle the incoming and outgoing configuration frames. This might cause issues when another coap server is in use (one that is connected to the network instead of just the uart). For example, the
NANOCOAP_RESOURCE(..)
s will be shared between them.I also experimented with sending the coap messages with a fake ip6+udp header into gnrc. One can then only run one single coap server (and it is no longer bound to nanocoap) who listens for such packets. The outgoing way is a bit more annoying, here a new dummy interface must be created, to which gnrc can direct those fake ip6+udp headers. Very similar to how it is already done with the current slip implementation.
What alternative approaches do you see? Any idea is appreciated.