Add tests for HW RX timestamping. Also add test that sends large packets to test ISO fragmentation. Add tests: ISO Receive - HW Timestamping ISO Receive Fragmented - Success ISO Receive Fragmented - HW Timestamping --- tools/iso-tester.c | 53 +++++++++++++++++++++++++++++++++++++++++++--- tools/tester.h | 45 +++++++++++++++++++++++++++++---------- 2 files changed, 84 insertions(+), 14 deletions(-) diff --git a/tools/iso-tester.c b/tools/iso-tester.c index 6aefb5196..40465a5f7 100644 --- a/tools/iso-tester.c +++ b/tools/iso-tester.c @@ -1013,6 +1013,12 @@ static const struct iovec send_48_2_1 = { .iov_len = sizeof(data_48_2_1), }; +static const uint8_t data_large[512] = { [0 ... 511] = 0xff }; +static const struct iovec send_large = { + .iov_base = (void *)data_large, + .iov_len = sizeof(data_large), +}; + static const struct iso_client_data connect_16_2_1_send = { .qos = QOS_16_2_1, .expect_err = 0, @@ -1049,6 +1055,13 @@ static const struct iso_client_data listen_16_2_1_recv = { .server = true, }; +static const struct iso_client_data listen_16_2_1_recv_frag = { + .qos = QOS_16_2_1, + .expect_err = 0, + .recv = &send_large, + .server = true, +}; + static const struct iso_client_data listen_16_2_1_recv_ts = { .qos = QOS_16_2_1, .expect_err = 0, @@ -1082,6 +1095,26 @@ static const struct iso_client_data listen_16_2_1_recv_rx_timestamping = { SOF_TIMESTAMPING_RX_SOFTWARE), }; +static const struct iso_client_data listen_16_2_1_recv_hw_timestamping = { + .qos = QOS_16_2_1, + .expect_err = 0, + .recv = &send_16_2_1, + .server = true, + .ts = true, + .so_timestamping = (SOF_TIMESTAMPING_RAW_HARDWARE | + SOF_TIMESTAMPING_RX_HARDWARE), +}; + +static const struct iso_client_data listen_16_2_1_recv_frag_hw_timestamping = { + .qos = QOS_16_2_1, + .expect_err = 0, + .recv = &send_large, + .server = true, + .ts = true, + .so_timestamping = (SOF_TIMESTAMPING_RAW_HARDWARE | + SOF_TIMESTAMPING_RX_HARDWARE), +}; + static const struct iso_client_data defer_16_2_1 = { .qos = QOS_16_2_1, .expect_err = 0, @@ -2247,8 +2280,10 @@ static gboolean iso_recv_data(GIOChannel *io, GIOCondition cond, } } - if (isodata->so_timestamping & SOF_TIMESTAMPING_RX_SOFTWARE) - rx_timestamp_check(&msg); + if (rx_timestamp_check(&msg, isodata->so_timestamping, 1000) < 0) { + tester_test_failed(); + return FALSE; + } if (data->step) { data->step--; @@ -2290,7 +2325,7 @@ static void iso_recv(struct test_data *data, GIOChannel *io) count = isodata->pkt_seqnum ? 2 : 1; for (j = 0; j < count; ++j) { - bthost_send_iso(host, data->handle, isodata->ts, sn++, 0, + bthost_send_iso(host, data->handle, isodata->ts, sn++, j + 1, isodata->pkt_status, isodata->recv, 1); data->step++; } @@ -3718,6 +3753,10 @@ int main(int argc, char *argv[]) test_iso("ISO Receive - Success", &listen_16_2_1_recv, setup_powered, test_listen); + test_iso("ISO Receive Fragmented - Success", &listen_16_2_1_recv_frag, + setup_powered, + test_listen); + test_iso("ISO Receive Timestamped - Success", &listen_16_2_1_recv_ts, setup_powered, test_listen); @@ -3734,6 +3773,14 @@ int main(int argc, char *argv[]) &listen_16_2_1_recv_rx_timestamping, setup_powered, test_listen); + test_iso("ISO Receive - HW Timestamping", + &listen_16_2_1_recv_hw_timestamping, + setup_powered, test_listen); + + test_iso("ISO Receive Fragmented - HW Timestamping", + &listen_16_2_1_recv_frag_hw_timestamping, + setup_powered, test_listen); + test_iso("ISO Defer - Success", &defer_16_2_1, setup_powered, test_defer); diff --git a/tools/tester.h b/tools/tester.h index 647c35485..896475110 100644 --- a/tools/tester.h +++ b/tools/tester.h @@ -204,11 +204,14 @@ static inline int tx_tstamp_recv(struct tx_tstamp_data *data, int sk, int len) return data->count - data->pos; } -static inline int rx_timestamp_check(struct msghdr *msg) +static inline int rx_timestamp_check(struct msghdr *msg, uint32_t flags, + int64_t expect_t_hw) { + bool soft_tstamp = flags & SOF_TIMESTAMPING_RX_SOFTWARE; + bool hw_tstamp = flags & SOF_TIMESTAMPING_RX_HARDWARE; struct cmsghdr *cmsg; struct timespec now; - int64_t t = 0; + int64_t t = 0, t_hw = 0; for (cmsg = CMSG_FIRSTHDR(msg); cmsg; cmsg = CMSG_NXTHDR(msg, cmsg)) { struct scm_timestamping *tss; @@ -220,21 +223,40 @@ static inline int rx_timestamp_check(struct msghdr *msg) tss = (struct scm_timestamping *)CMSG_DATA(cmsg); t = TS_NSEC(&tss->ts[0]); + t_hw = TS_NSEC(&tss->ts[2]); break; } + if (!cmsg) { + if (!soft_tstamp && !hw_tstamp) + return 0; tester_warn("RX timestamp missing"); return -EINVAL; - } - - clock_gettime(CLOCK_REALTIME, &now); - - if (TS_NSEC(&now) < t || TS_NSEC(&now) > t + SEC_NSEC(10)) { - tester_warn("RX timestamp bad time"); + } else if (!soft_tstamp && !hw_tstamp) { + tester_warn("Spurious RX timestamp"); return -EINVAL; } - tester_print("Got valid RX timestamp"); + if (soft_tstamp) { + clock_gettime(CLOCK_REALTIME, &now); + + if (TS_NSEC(&now) < t || TS_NSEC(&now) > t + SEC_NSEC(10)) { + tester_warn("Software RX timestamp bad time"); + return -EINVAL; + } + + tester_print("Got valid RX software timestamp"); + } + + if (hw_tstamp) { + if (t_hw != expect_t_hw) { + tester_warn("Bad hardware RX timestamp: %d != %d", + (int)t_hw, (int)expect_t_hw); + return -EINVAL; + } + tester_print("Got valid hardware RX timestamp"); + } + return 0; } @@ -260,7 +282,7 @@ static inline ssize_t recv_tstamp(int sk, void *buf, size_t size, bool tstamp) if (ret < 0 || !tstamp) return ret; - if (rx_timestamp_check(&msg)) { + if (rx_timestamp_check(&msg, SOF_TIMESTAMPING_RX_SOFTWARE, 0)) { errno = EIO; return -1; } @@ -272,7 +294,8 @@ static inline int rx_timestamping_init(int fd, int flags) { socklen_t len = sizeof(flags); - if (!(flags & SOF_TIMESTAMPING_RX_SOFTWARE)) + if (!(flags & (SOF_TIMESTAMPING_RX_SOFTWARE | + SOF_TIMESTAMPING_RX_HARDWARE))) return 0; if (setsockopt(fd, SOL_SOCKET, SO_TIMESTAMPING, &flags, len) < 0) { -- 2.50.1