blob: 1fc5b8f71eab32c8f8a768760038750dd69019bf [file] [log] [blame]
Jeremy Kerr3d36ee22019-05-30 11:15:37 +08001/* SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later */
Jeremy Kerrba076942019-03-13 16:20:34 +08002
3#include <assert.h>
4#include <stdlib.h>
5#include <stdio.h>
6#include <string.h>
7
8#include <libmctp.h>
9
10#include "test-utils.h"
11
12#define ARRAY_SIZE(a) (sizeof(a) / sizeof(a[0]))
13
14struct test_ctx {
15 struct mctp *mctp;
16 struct mctp_binding_test *binding;
17 int rx_count;
18 uint8_t rx_data[4];
19 size_t rx_len;
20};
21
22static void test_rx(uint8_t eid, void *data, void *msg, size_t len)
23{
24 struct test_ctx *ctx = data;
25
26 (void)eid;
27
28 ctx->rx_count++;
29
30 /* append incoming message data to the existing rx_data */
31 assert(len <= sizeof(ctx->rx_data));
32 assert(ctx->rx_len + len <= sizeof(ctx->rx_data));
33
34 memcpy(ctx->rx_data + ctx->rx_len, msg, len);
35 ctx->rx_len += len;
36}
37
38#define SEQ(x) (x << MCTP_HDR_SEQ_SHIFT)
39
40struct test {
41 int n_packets;
42 uint8_t flags_seq_tags[4];
43 int exp_rx_count;
44 size_t exp_rx_len;
45} tests[] = {
46 {
47 /* single packet */
48 .n_packets = 1,
49 .flags_seq_tags = {
50 SEQ(1) | MCTP_HDR_FLAG_SOM | MCTP_HDR_FLAG_EOM,
51 },
52 .exp_rx_count = 1,
53 .exp_rx_len = 1,
54 },
Jeremy Kerr8ab4a6c2019-03-13 16:31:33 +080055 {
56 /* two packets: one start, one end */
57 .n_packets = 2,
58 .flags_seq_tags = {
59 SEQ(1) | MCTP_HDR_FLAG_SOM,
60 SEQ(2) | MCTP_HDR_FLAG_EOM,
61 },
62 .exp_rx_count = 1,
63 .exp_rx_len = 2,
64 },
65 {
66 /* three packets: one start, one no flags, one end */
67 .n_packets = 3,
68 .flags_seq_tags = {
69 SEQ(1) | MCTP_HDR_FLAG_SOM,
70 SEQ(2),
71 SEQ(3) | MCTP_HDR_FLAG_EOM,
72 },
73 .exp_rx_count = 1,
74 .exp_rx_len = 3,
75 },
Jeremy Kerr6328ffb2019-03-13 16:34:41 +080076 {
77 /* two packets, wrapping sequence numbers */
78 .n_packets = 2,
79 .flags_seq_tags = {
80 SEQ(3) | MCTP_HDR_FLAG_SOM,
81 SEQ(0) | MCTP_HDR_FLAG_EOM,
82 },
83 .exp_rx_count = 1,
84 .exp_rx_len = 2,
85 },
86 {
87 /* two packets, invalid sequence number */
88 .n_packets = 2,
89 .flags_seq_tags = {
90 SEQ(1) | MCTP_HDR_FLAG_SOM,
91 SEQ(3) | MCTP_HDR_FLAG_EOM,
92 },
93 .exp_rx_count = 0,
94 .exp_rx_len = 0,
95 },
Jeremy Kerrba076942019-03-13 16:20:34 +080096};
97
98static void run_one_test(struct test_ctx *ctx, struct test *test)
99{
100 const mctp_eid_t local_eid = 8;
101 const mctp_eid_t remote_eid = 9;
102 struct {
103 struct mctp_hdr hdr;
104 uint8_t payload[1];
105 } pktbuf;
106 int i;
107
108 ctx->rx_count = 0;
109 ctx->rx_len = 0;
110
111 mctp_test_stack_init(&ctx->mctp, &ctx->binding, local_eid);
112
113 mctp_set_rx_all(ctx->mctp, test_rx, ctx);
114
115 for (i = 0; i < test->n_packets; i++) {
116 memset(&pktbuf, 0, sizeof(pktbuf));
117 pktbuf.hdr.dest = local_eid;
118 pktbuf.hdr.src = remote_eid;
119 pktbuf.hdr.flags_seq_tag = test->flags_seq_tags[i];
120 pktbuf.payload[0] = i;
121
122 mctp_binding_test_rx_raw(ctx->binding,
123 &pktbuf, sizeof(pktbuf));
124 }
125
126 assert(ctx->rx_count == test->exp_rx_count);
127 assert(ctx->rx_len == test->exp_rx_len);
128
129 /* ensure the payload data was reconstructed correctly */
130 for (i = 0; i < (int)ctx->rx_len; i++)
131 assert(ctx->rx_data[i] == i);
132}
133
134
135int main(void)
136{
137 struct test_ctx ctx;
138 unsigned int i;
139
140 for (i = 0; i < ARRAY_SIZE(tests); i++)
141 run_one_test(&ctx, &tests[i]);
142
143 return EXIT_SUCCESS;
144}