echo_client / echo_server hop limit

Diana Rivera


I am currently working on an OpenThread app based on the echo_client and echo_server. I am currently trying to use the hop-limit field by setting it as follows:

In the echo_client udp.c file:
static void send_udp_data(struct net_app_ctx *ctx, struct data *data)
    struct net_pkt *pkt;
    size_t len;
    int ret;

    data->expecting_udp = ipsum_len;

    pkt = prepare_send_pkt(ctx, data->proto, &data->expecting_udp);
    if (!pkt) {
    net_pkt_set_ipv6_hop_limit(pkt, 8);
    NET_INFO("Hop limit set to: %d", net_pkt_ipv6_hop_limit(pkt));
    len = net_pkt_get_len(pkt);

    NET_ASSERT_INFO(data->expecting_udp == len,
            "Data to send %d bytes, real len %zu",
            data->expecting_udp, len);

    ret = net_app_send_pkt(ctx, pkt, NULL, 0, K_FOREVER,
    if (ret < 0) {
        NET_ERR("Cannot send %s data to peer (%d)", data->proto, ret);


    k_delayed_work_submit(&data->recv, WAIT_TIME);

In the echo_server udp.c:

struct net_pkt *build_reply_pkt(const char *name,
                struct net_app_ctx *ctx,
                struct net_pkt *pkt)
    struct net_pkt *reply_pkt;
    struct net_buf *frag, *tmp;
    int header_len = 0, recv_len, reply_len;
    u8_t *ptr = net_pkt_appdata(pkt);
    // hop_lim = pkt->ipv6_hop_limit;
    hop_lim = net_pkt_ipv6_hop_limit(pkt);

    NET_INFO("Application message received: %s, hop limit: %d\n", ptr, hop_lim);
    NET_INFO("%s received %d bytes", name, net_pkt_appdatalen(pkt));

    if (net_pkt_appdatalen(pkt) == 0) {
        return NULL;

    reply_pkt = net_app_get_net_pkt(ctx, net_pkt_family(pkt), K_FOREVER);

    NET_ASSERT(net_pkt_family(reply_pkt) == net_pkt_family(pkt));

    recv_len = net_pkt_get_len(pkt);

    tmp = pkt->frags;

    /* If we have link layer headers, then get rid of them here. */
    if (recv_len != net_pkt_appdatalen(pkt)) {
        /* First fragment will contain IP header so move the data
         * down in order to get rid of it.
        header_len = net_pkt_appdata(pkt) - tmp->data;

        NET_ASSERT(header_len < CONFIG_NET_BUF_DATA_SIZE);

        /* After this pull, the tmp->data points directly to application
         * data.
        net_buf_pull(tmp, header_len);

    net_pkt_set_appdatalen(reply_pkt, net_pkt_appdatalen(pkt));

    while (tmp) {
        frag = net_app_get_net_buf(ctx, reply_pkt, K_FOREVER);

        if (net_buf_headroom(tmp) == 0) {
            /* If there is no link layer headers in the
             * received fragment, then get rid of that also
             * in the sending fragment. We end up here
             * if MTU is larger than fragment size, this
             * is typical for ethernet.
            net_buf_push(frag, net_buf_headroom(frag));

            frag->len = 0; /* to make fragment empty */

            /* Make sure to set the reserve so that
             * in sending side we add the link layer
             * header if needed.
            net_pkt_set_ll_reserve(reply_pkt, 0);

        NET_ASSERT_INFO(net_buf_tailroom(frag) >= tmp->len,
                "tail %zd longer than len %d",
                net_buf_tailroom(frag), tmp->len);

        memcpy(net_buf_add(frag, tmp->len), tmp->data, tmp->len);

        tmp = net_pkt_frag_del(pkt, NULL, tmp);

    reply_len = net_pkt_get_len(reply_pkt);

    NET_ASSERT_INFO((recv_len - header_len) == reply_len,
            "Received %d bytes, sending %d bytes",
            recv_len - header_len, reply_len);

    return reply_pkt;

On the client side, I'm able to observe that the hop limit has been set to 8; however, by the time I read the hop limit field at the server, this value returns zero, instead of having decreased by just 1 as expected.
Am I making a mistake in the way I'm using the   net_pkt_set_ipv6_hop_limit and   net_pkt_ipv6_hop_limit functions? Or is there another way to be able to use the hop limit field in OT?

Thank you in advance for your answer,

Join to automatically receive all group messages.