2 * Copyright (c) 2016-2017 Intel Corporation.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at:
7 * http://www.apache.org/licenses/LICENSE-2.0
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
26 * Common structure that must be present as first field in all partcular
27 * L4 (UDP/TCP, etc.) stream implementations.
31 STAILQ_ENTRY(tle_stream) link;
34 uint8_t type; /* TLE_V4 or TLE_V6 */
36 /* Stream address information. */
42 union ipv4_addrs addr;
43 union ipv4_addrs mask;
46 union ipv6_addrs addr;
47 union ipv6_addrs mask;
52 static inline uint32_t
53 get_streams(struct tle_ctx *ctx, struct tle_stream *s[], uint32_t num)
58 rte_spinlock_lock(&ctx->streams.lock);
60 n = RTE_MIN(ctx->streams.nb_free, num);
61 for (i = 0, p = STAILQ_FIRST(&ctx->streams.free);
63 i++, p = STAILQ_NEXT(p, link))
67 /* we retrieved all free entries */
68 STAILQ_INIT(&ctx->streams.free);
70 STAILQ_FIRST(&ctx->streams.free) = p;
72 ctx->streams.nb_free -= n;
73 rte_spinlock_unlock(&ctx->streams.lock);
77 static inline struct tle_stream *
78 get_stream(struct tle_ctx *ctx)
83 if (ctx->streams.nb_free == 0)
86 get_streams(ctx, &s, 1);
91 put_stream(struct tle_ctx *ctx, struct tle_stream *s, int32_t head)
94 rte_spinlock_lock(&ctx->streams.lock);
96 STAILQ_INSERT_HEAD(&ctx->streams.free, s, link);
98 STAILQ_INSERT_TAIL(&ctx->streams.free, s, link);
99 ctx->streams.nb_free++;
100 rte_spinlock_unlock(&ctx->streams.lock);
103 /* calculate number of drbs per stream. */
104 static inline uint32_t
105 calc_stream_drb_num(const struct tle_ctx *ctx, uint32_t obj_num)
109 num = (ctx->prm.max_stream_sbufs + obj_num - 1) / obj_num;
111 num = RTE_MAX(num, RTE_DIM(ctx->dev) + 1);
115 static inline uint32_t
116 drb_nb_elem(const struct tle_ctx *ctx)
118 return (ctx->prm.send_bulk_size != 0) ?
119 ctx->prm.send_bulk_size : MAX_PKT_BURST;
122 static inline int32_t
123 stream_get_dest(struct tle_stream *s, const void *dst_addr,
124 struct tle_dest *dst)
127 const struct in_addr *d4;
128 const struct in6_addr *d6;
134 /* it is here just to keep gcc happy. */
138 if (s->type == TLE_V4) {
140 rc = ctx->prm.lookup4(ctx->prm.lookup4_data, d4, dst);
141 } else if (s->type == TLE_V6) {
143 rc = ctx->prm.lookup6(ctx->prm.lookup6_data, d6, dst);
147 if (rc < 0 || dst->dev == NULL || dst->dev->ctx != ctx)
151 dst->ol_flags = dev->tx.ol_flags[s->type];
153 if (s->type == TLE_V4) {
154 struct rte_ipv4_hdr *l3h;
155 l3h = (struct rte_ipv4_hdr *)(dst->hdr + dst->l2_len);
156 l3h->src_addr = dev->prm.local_addr4.s_addr;
157 l3h->dst_addr = d4->s_addr;
159 struct rte_ipv6_hdr *l3h;
160 l3h = (struct rte_ipv6_hdr *)(dst->hdr + dst->l2_len);
161 rte_memcpy(l3h->src_addr, &dev->prm.local_addr6,
162 sizeof(l3h->src_addr));
163 rte_memcpy(l3h->dst_addr, d6, sizeof(l3h->dst_addr));
166 return dev - ctx->dev;
173 #endif /* _STREAM_H_ */