|
1 | 1 | #include "tlv-decoder.h"
|
2 | 2 |
|
| 3 | +void |
| 4 | +TlvDecoder_Truncate(TlvDecoder* d) { |
| 5 | + uint32_t length = d->length; |
| 6 | + NDNDPDK_ASSERT(length > 0); |
| 7 | + |
| 8 | + if (unlikely(d->m != d->p)) { // d->m is not the first segment |
| 9 | + // move 1 octet from d->m to d->p so that the first segment is non-empty |
| 10 | + NDNDPDK_ASSERT(d->p->data_len >= 1); |
| 11 | + d->p->pkt_len -= (d->p->data_len - 1); |
| 12 | + d->p->data_len = 1; |
| 13 | + d->p->data_off = RTE_PKTMBUF_HEADROOM; |
| 14 | + TlvDecoder_Copy(d, rte_pktmbuf_mtod(d->p, uint8_t*), 1); |
| 15 | + rte_mbuf_sanity_check(d->p, true); |
| 16 | + |
| 17 | + if (unlikely(d->length == 0)) { // 1-octet packet, already in d->p |
| 18 | + d->p->nb_segs -= Mbuf_FreeSegs(&d->p->next, NULL, &d->p->pkt_len); |
| 19 | + goto FINISH; |
| 20 | + } |
| 21 | + |
| 22 | + // delete segments after d->p and before d->m |
| 23 | + d->p->nb_segs -= Mbuf_FreeSegs(&d->p->next, d->m, &d->p->pkt_len); |
| 24 | + rte_mbuf_sanity_check(d->p, true); |
| 25 | + } |
| 26 | + |
| 27 | + // delete d->m[:d->offset] range |
| 28 | + d->p->pkt_len -= d->offset; |
| 29 | + d->m->data_len -= d->offset; |
| 30 | + d->m->data_off += d->offset; |
| 31 | + d->offset = 0; |
| 32 | + rte_mbuf_sanity_check(d->p, true); |
| 33 | + |
| 34 | + // skip over to end of fragment |
| 35 | + struct rte_mbuf* last = d->m; |
| 36 | + TlvDecoder_Skip_(d, d->length, &last); |
| 37 | + if (d->offset == 0) { // d->m does not contain useful octets |
| 38 | + // delete d->m and segments after d->m |
| 39 | + d->p->nb_segs -= Mbuf_FreeSegs(&last->next, NULL, &d->p->pkt_len); |
| 40 | + } else { // d->m contains useful octets |
| 41 | + // delete d->m[d->offset:] range |
| 42 | + d->p->pkt_len -= (d->m->data_len - d->offset); |
| 43 | + d->m->data_len = d->offset; |
| 44 | + |
| 45 | + // delete segments after d->m |
| 46 | + d->p->nb_segs -= Mbuf_FreeSegs(&d->m->next, NULL, &d->p->pkt_len); |
| 47 | + } |
| 48 | + |
| 49 | +FINISH:; |
| 50 | + rte_mbuf_sanity_check(d->p, true); |
| 51 | + NDNDPDK_ASSERT(d->p->pkt_len == length); |
| 52 | + POISON(d); |
| 53 | +} |
| 54 | + |
3 | 55 | void
|
4 | 56 | TlvDecoder_Copy_(TlvDecoder* d, uint8_t* output, uint16_t count) {
|
5 | 57 | for (uint16_t remain = count; remain > 0;) {
|
@@ -122,13 +174,8 @@ TlvDecoder_Fragment(TlvDecoder* d, uint32_t count, struct rte_mbuf* frames[], ui
|
122 | 174 |
|
123 | 175 | __attribute__((nonnull)) static void
|
124 | 176 | Linearize_Delete_(TlvDecoder* d, struct rte_mbuf* c) {
|
125 |
| - for (struct rte_mbuf* seg = c->next; seg != d->m;) { |
126 |
| - struct rte_mbuf* next = seg->next; |
127 |
| - rte_pktmbuf_free_seg(seg); |
128 |
| - --d->p->nb_segs; |
129 |
| - seg = next; |
130 |
| - } |
131 |
| - c->next = d->m; |
| 177 | + uint32_t unusedPktLen = UINT32_MAX; |
| 178 | + d->p->nb_segs -= Mbuf_FreeSegs(&c->next, d->m, &unusedPktLen); |
132 | 179 | if (likely(d->m != NULL)) {
|
133 | 180 | d->m->data_len -= d->offset;
|
134 | 181 | d->m->data_off += d->offset;
|
|
0 commit comments