gnrc: Add priority packet queue module to gnrc#5950
Conversation
| * @{ | ||
| * @ingroup net_gnrc_mac | ||
| * @file | ||
| * @brief Wrapper for priority_queue that holds gnrc_pktsnip_t* and is |
There was a problem hiding this comment.
What's wrong with gnrc_pktqueue that you introduce another packet queue?
There was a problem hiding this comment.
@daniel-k Can you help explain here? I remember, as you have stated somewhere, was it first due to the unawareness of "gnrc_pktqueue " when creating the packet queue module for Lw-MAC, or does it due to that we want the queue to be aware of its length?
There was a problem hiding this comment.
Then the preferred way would be to expand the gnrc_pktqueue module not write your own.
There was a problem hiding this comment.
Can you help explain here? I remember, as you have stated somewhere, was it first due to the unawareness of "gnrc_pktqueue " when creating the packet queue module for Lw-MAC
Yes, that's right.
or does it due to that we want the queue to be aware of its length?
This definetely helps during runtime, but the queues should be quite small anyway.
All in all my packet queue implementation was something I was planning to refactor and maybe merge with the existing one, so in general I'm with @miri64.
| packet_queue_node_t* buffer; | ||
| size_t buffer_size; | ||
| } packet_queue_t; | ||
|
|
There was a problem hiding this comment.
By the way, @miri64 , I think the packet_queue introduced here is more attached to the priority_queue but not gnrc_pktqueue, since the packet_queue_t here support priority while gnrc_pktqueue does not. So, it is a more wrapper to priority_queue.
Also, do you think we can leave this issue here and currently only use it in MAC layer, and solve it (i.e., extand gnrc_pktqueue or priority_queue and delete this new packet_queue module) after the merge of Lw-MAC?
There was a problem hiding this comment.
You're right! Though it is documented that gnrc_pktqueue is based on priority queue it isn't. Will fix. So maybe (since this might not just be of interest to MAC) rename this module gnrc_priority_pktqueue?
There was a problem hiding this comment.
I think this packet_queue module here is still not ready for universal usage yet. Just my opinion. This is because, if you check the packet_queue_t structure above, it contains a buffer (type of packet_queue_node_t, which is actually priority_queue_node_t). This means that you need to define a packet buffer first for holding your packets before using queue management.
In short, the queue management module here relies on a predefined packet buffer which is assumed to be created and initiated before start using the queue management provided here. check the example case in Lw-MAC: buffer define, init function and init before use.
So, currently it is more MAC-oriented... and I tend to revise it after the merge of the Lw-MAC.
There was a problem hiding this comment.
I think that because of this the contrary is the case: it is even more suitable for general use. Compare e.g. the packet buffer which only allows for one central array to be the packet buffer. The implementation here can however be cleaned up a little bit. That I agree. But I still don't see any reason why this makes it dependent on MAC ;-).
There was a problem hiding this comment.
OK, with your support, I will update it now, move it out of gnrc_mac. :-)
There was a problem hiding this comment.
By the way, @miri64 where do you think I can place this gnrc_priority_pktqueue.c, in /RIOT/sys/net/gnrc/pkt?
There was a problem hiding this comment.
No, it's its own module, so I would suggest to pout it into sys/net/gnrc/priority_pktqueue (you need to add a makefile to that directory and also need to update sys/net/gnrc/Makefile)
There was a problem hiding this comment.
OK, I see. Will do it now.
2e37a41 to
55d6818
Compare
|
@miri64 Updated. |
| @@ -0,0 +1,68 @@ | |||
| /* | |||
There was a problem hiding this comment.
please remove the leading gnrc_ in the headers name. It is already reflected in the sub-directory gnrc/
|
|
||
| /** | ||
| * @{ | ||
| * @ingroup net_gnrc_oriority_pktqueue Priority packet queue |
There was a problem hiding this comment.
* @defgroup net_gnrc_priority_pktqueue Priority packet queue
* @ingroup net_gnrc
| uint32_t length; | ||
| packet_queue_node_t* buffer; | ||
| size_t buffer_size; | ||
| } packet_queue_t; |
There was a problem hiding this comment.
Can you please harmonize the type's name with the modules name? Also I think that having both length and buffer_size is superfluous.
There was a problem hiding this comment.
Well, the buffer_size reflects the central buffer size which is needed when initializing the queue, while the length is the queue's length..
There was a problem hiding this comment.
Ah... I would store neither in this struct... ^^
There was a problem hiding this comment.
Haha, what is why I thought it may not be ready for general usage..:-)
| uint32_t priority); | ||
|
|
||
| void packet_queue_init(packet_queue_t* q, | ||
| packet_queue_node_t buffer[], |
There was a problem hiding this comment.
After thinking about it, I don't see any benefit in doing this way. A user of this API can just as well have their buffer stored somewhere instead of wasting up to 8 byte on buffer and buffer size...
There was a problem hiding this comment.
so, what do you suggest now? :-)
There was a problem hiding this comment.
@miri64 so I still keep this in my gnrc_mac module and revise it in the future? Just put this issue aside?
There was a problem hiding this comment.
No, let's find some API we both are happy with.
There was a problem hiding this comment.
Will try to rework this PR.
55d6818 to
cf3b7da
Compare
| priority_queue_t queue; | ||
| packet_queue_node_t* buffer; | ||
| size_t buffer_size; | ||
| } gnrc_priority_pktqueue_t; |
There was a problem hiding this comment.
@miri64 Updated, deleted length and updated the method for getting the queue length.
But I still keep the buffer_size parameter for queue initialization, since I couldn't think up a way to initialize the queue without it, i.e., how to be aware of the buffer size if we only pass in the *buffer when doing initialization.
Do you have some tips for this? :-)
|
|
||
| #define PRIORITY_PKTQUEUE_NODE_INIT(priority, pkt) { NULL, priority, pkt } | ||
|
|
||
| static inline void priority_pktqueue_node_init(gnrc_priority_pktqueue_node_t *node, |
There was a problem hiding this comment.
Please prefix these functions and macros with gnrc_. I know I introduced some of these, but I tried to keep style with the current status of this PR.
| *q = qn; | ||
| } | ||
|
|
||
| static inline uint32_t priority_pktqueue_length(gnrc_priority_pktqueue_t *q) |
There was a problem hiding this comment.
This function is quiet big for an inline function. Please un-inline.
|
|
||
| static inline uint32_t priority_pktqueue_length(gnrc_priority_pktqueue_t *q) | ||
| { | ||
| uint32_t length = 0; |
There was a problem hiding this comment.
Just to ensure, you mean I should use four spaces here? instead of a tab, right? :-)
There was a problem hiding this comment.
Yes, sorry thought I already replied 😄
|
|
||
| gnrc_pktsnip_t* priority_pktqueue_pop(gnrc_priority_pktqueue_t* q) | ||
| { | ||
| if(!q || (priority_pktqueue_length(q) == 0)) |
There was a problem hiding this comment.
Here, I should add a braces right?
|
|
||
| gnrc_pktsnip_t* priority_pktqueue_head(gnrc_priority_pktqueue_t* q) | ||
| { | ||
| if(!q || (priority_pktqueue_length(q) == 0)) |
|
|
||
| void priority_pktqueue_flush(gnrc_priority_pktqueue_t* q) | ||
| { | ||
| if(priority_pktqueue_length(q) == 0) |
| return; | ||
|
|
||
| gnrc_priority_pktqueue_node_t* node; | ||
| while( (node = (gnrc_priority_pktqueue_node_t *)priority_queue_remove_head(q)) ) |
There was a problem hiding this comment.
Style: Please put the brace on the same line as the while and remove the whitespaces between the parans.
04fa627 to
dd96570
Compare
|
Sure, just follow the steps in https://github.com/RIOT-OS/RIOT/blob/master/tests/unittests/README.md. To build for a dedicated board you need to define it as an environment variable variable (as you normally would do with other applications) and flash in between build and term step. |
|
@miri64 Thanks! |
a24527a to
2c09a67
Compare
|
@miri64 Updated, corrected style and added unittests. |
miri64
left a comment
There was a problem hiding this comment.
I think the assertion in the unittests are far to excessive. oO but the line below caught my eye in particular
| res = gnrc_priority_pktqueue_pop(&pkt_queue); | ||
|
|
||
| TEST_ASSERT(res == &pkt2); | ||
| TEST_ASSERT_EQUAL_INT(0,((priority_queue_node_t *)&elem2)->data); |
There was a problem hiding this comment.
The compiler flags for the boards do not allow for such type-punning. Also, why is this line even here? And shouldn't this be the address value of pkt2?
There was a problem hiding this comment.
I did this assert since, inside gnrc_priority_pktqueue_pop, it will call _free_node() in which priority_queue_node_init() will be further called to initialize the popped elem. So I want to check the result of initialization of elem. I checked that priority_queue_node_init() will set the data to 0, that's why I did this kind of assert..
But, you are right, I should do this more concisely by TEST_ASSERT_NULL(elem2.pkt);
There was a problem hiding this comment.
Ah right, and yes: TEST_ASSERT_NULL() should is the better option.
|
@miri64 sorry, I tried to be more careful when building tests. Will reduce assertions. |
2c09a67 to
7b941a6
Compare
|
Updated. |
|
Let's try to get this into the release. |
| */ | ||
| static inline void gnrc_priority_pktqueue_node_init(gnrc_priority_pktqueue_node_t *node, | ||
| uint32_t priority, | ||
| gnrc_pktsnip_t *pkt) |
| * @param[in] node the node to add. | ||
| */ | ||
| void gnrc_priority_pktqueue_push(gnrc_priority_pktqueue_t* queue, | ||
| gnrc_priority_pktqueue_node_t *node); |
7b941a6 to
0ebe2a0
Compare
|
@miri64 Fixed style and squashed commits. :-) |
miri64
left a comment
There was a problem hiding this comment.
ACK and go when Travis is happy
|
Congrats on your first feature PR! :-) |
|
Congrats Shuguo! ;-) (@miri64 it wasn't Murdock who helped? :P ) |
|
Congrats from my side too! And thanks for messing with my code 😃 |
This PR aim to priority packet queue module to gnrc.
PS: this module here is extracted/sorted from the packet queue management block of Lw-MAC.