From 967a91dce57e30bd4d9b884ff7490a790a2d1355 Mon Sep 17 00:00:00 2001 From: Robert Lubos Date: Thu, 17 Nov 2022 14:33:07 +0100 Subject: [PATCH] net: icmp: Allow to autogenerate Echo Request payload Let net_icmpv4_send_echo_request() and net_icmpv6_send_echo_request() autogenerate Echo Request payload, in case data length is specified but no data pointer provided. The autogenerated payload includes timestamp (if payload size permits) so that the turnround time can be calculated. Signed-off-by: Robert Lubos --- subsys/net/ip/icmpv4.c | 19 ++++++++++++++++++- subsys/net/ip/icmpv4.h | 6 ++++-- subsys/net/ip/icmpv6.c | 19 ++++++++++++++++++- subsys/net/ip/icmpv6.h | 6 ++++-- 4 files changed, 44 insertions(+), 6 deletions(-) diff --git a/subsys/net/ip/icmpv4.c b/subsys/net/ip/icmpv4.c index 23d101e725..5c3d844be8 100644 --- a/subsys/net/ip/icmpv4.c +++ b/subsys/net/ip/icmpv4.c @@ -555,7 +555,24 @@ int net_icmpv4_send_echo_request(struct net_if *iface, echo_req->sequence = htons(sequence); net_pkt_set_data(pkt, &icmpv4_access); - net_pkt_write(pkt, data, data_size); + + if (data != NULL && data_size > 0) { + net_pkt_write(pkt, data, data_size); + } else if (data == NULL && data_size > 0) { + /* Generate payload. */ + if (data_size >= sizeof(uint32_t)) { + uint32_t time_stamp = htonl(k_cycle_get_32()); + + net_pkt_write(pkt, &time_stamp, sizeof(time_stamp)); + data_size -= sizeof(time_stamp); + } + + for (size_t i = 0; i < data_size; i++) { + net_pkt_write_u8(pkt, (uint8_t)i); + } + } else { + /* No payload. */ + } net_pkt_cursor_init(pkt); diff --git a/subsys/net/ip/icmpv4.h b/subsys/net/ip/icmpv4.h index d927920c64..bfce2e8d9e 100644 --- a/subsys/net/ip/icmpv4.h +++ b/subsys/net/ip/icmpv4.h @@ -69,8 +69,10 @@ int net_icmpv4_send_error(struct net_pkt *pkt, uint8_t type, uint8_t code); * @param tos IPv4 Type-of-service field value. Represents combined DSCP and ECN * values. * @param data Arbitrary payload data that will be included in the - * Echo Reply verbatim. May be zero. - * @param data_size Size of the Payload Data in bytes. May be zero. + * Echo Reply verbatim. May be NULL. + * @param data_size Size of the Payload Data in bytes. May be zero. In case data + * pointer is NULL, the function will generate the payload up to the requested + * size. * * @return Return 0 if the sending succeed, <0 otherwise. */ diff --git a/subsys/net/ip/icmpv6.c b/subsys/net/ip/icmpv6.c index 8b81f3f6c4..c327d8752a 100644 --- a/subsys/net/ip/icmpv6.c +++ b/subsys/net/ip/icmpv6.c @@ -380,7 +380,24 @@ int net_icmpv6_send_echo_request(struct net_if *iface, echo_req->sequence = htons(sequence); net_pkt_set_data(pkt, &icmpv6_access); - net_pkt_write(pkt, data, data_size); + + if (data != NULL && data_size > 0) { + net_pkt_write(pkt, data, data_size); + } else if (data == NULL && data_size > 0) { + /* Generate payload. */ + if (data_size >= sizeof(uint32_t)) { + uint32_t time_stamp = htonl(k_cycle_get_32()); + + net_pkt_write(pkt, &time_stamp, sizeof(time_stamp)); + data_size -= sizeof(time_stamp); + } + + for (size_t i = 0; i < data_size; i++) { + net_pkt_write_u8(pkt, (uint8_t)i); + } + } else { + /* No payload. */ + } net_pkt_cursor_init(pkt); net_ipv6_finalize(pkt, IPPROTO_ICMPV6); diff --git a/subsys/net/ip/icmpv6.h b/subsys/net/ip/icmpv6.h index 5f34b3cc50..078b2fb659 100644 --- a/subsys/net/ip/icmpv6.h +++ b/subsys/net/ip/icmpv6.h @@ -201,8 +201,10 @@ int net_icmpv6_send_error(struct net_pkt *pkt, uint8_t type, uint8_t code, * @param tc IPv6 Traffic Class field value. Represents combined DSCP and * ECN values. * @param data Arbitrary payload data that will be included in the - * Echo Reply verbatim. May be zero. - * @param data_size Size of the Payload Data in bytes. May be zero. + * Echo Reply verbatim. May be NULL. + * @param data_size Size of the Payload Data in bytes. May be zero. In case data + * pointer is NULL, the function will generate the payload up to the requested + * size. * * @return Return 0 if the sending succeed, <0 otherwise. */