Ejemplo n.º 1
0
void etx_update(etx_neighbor_t *candidate)
{
    DEBUG("update!\n");
    /*
     * Update the current ETX value of a candidate
     */
    double d_f;
    double d_r;

    if (reached_window != 1 || candidate == NULL) {
        //We will wait at least ETX_WINDOW beacons until we decide to
        //calculate an ETX value, so that we have a good estimate
        return;
    }

    /*
     * Calculate d_f (the forward PDR) from ME to this candidate.
     */
    d_f = candidate->packets_rx / (double) ETX_WINDOW;

    /*
     * Calculate d_r (the backwards PDR) from this candidate to ME
     */
    d_r = etx_count_packet_tx(candidate) / (double) ETX_WINDOW;

    /*
     * Calculate the current ETX value for my link to this candidate.
     */
    if (d_f * d_r != 0) {
        candidate->cur_etx = 1 / (d_f * d_r);
    }
    else {
        candidate->cur_etx = 0;
    }

    DEBUG(
        "Estimated ETX Metric  is %f for candidate w/ addr %d\n"
        "Estimated PDR_forward is %f\n"
        "Estimated PDR_backwrd is %f\n"
        "\n"
        "Received Packets: %d\n"
        "Sent Packets    : %d\n\n",
        candidate->cur_etx, candidate->addr.uint8[ETX_IPV6_LAST_BYTE],
        d_f, d_r, candidate->packets_rx, etx_count_packet_tx(candidate));
}
Ejemplo n.º 2
0
static void *etx_beacon(void *arg)
{
    (void) arg;

    /*
     * Sends a message every ETX_INTERVAL +/- a jitter-value (default is 10%) .
     * A correcting variable is needed to stay at a base interval of
     * ETX_INTERVAL between the wakeups. It takes the old jittervalue in account
     * and modifies the time to wait accordingly.
     */
    etx_probe_t *packet = etx_get_send_buf();
    uint8_t p_length = 0;

    while (true) {
        thread_sleep();
        mutex_lock(&etx_mutex);
        //Build etx packet
        p_length = 0;

        for (uint8_t i = 0; i < ETX_BEST_CANDIDATES; i++) {
            if (candidates[i].used != 0) {
                packet->data[i * ETX_TUPLE_SIZE] =
                    candidates[i].addr.uint8[ETX_IPV6_LAST_BYTE];
                packet->data[i * ETX_TUPLE_SIZE + ETX_PKT_REC_OFFSET] =
                    etx_count_packet_tx(&candidates[i]);
                p_length = p_length + ETX_PKT_HDR_LEN;
            }
        }

        packet->length = p_length;
        /* will be send broadcast, so if_id and destination address will be
         * ignored (see documentation)
         */
        sixlowpan_mac_send_ieee802154_frame(0, NULL, 8, &etx_send_buf[0],
                                            ETX_DATA_MAXLEN + ETX_PKT_HDR_LEN, 1);
        DEBUG("sent beacon!\n");
        etx_set_packets_received();
        cur_round++;

        if (cur_round == ETX_WINDOW) {
            if (reached_window != 1) {
                //first round is through
                reached_window = 1;
            }

            cur_round = 0;
        }

        mutex_unlock(&etx_mutex);
    }

    return NULL;
}
Ejemplo n.º 3
0
double etx_get_metric(ipv6_addr_t * address) {
    etx_neighbor_t * candidate = etx_find_candidate(address);
    if (candidate != NULL ) {
        if (etx_count_packet_tx(candidate) > 0) {
            //this means the current etx_value is not outdated
            return candidate->cur_etx;
        } else {
            //The last time I received a packet is too long ago to give a
            //good estimate of the etx value
            return 0;
        }
    }
    return 0;
}
Ejemplo n.º 4
0
void etx_beacon(void) {
    /*
     * Sends a message every ETX_INTERVAL +/- a jitter-value (default is 10%) .
     * A correcting variable is needed to stay at a base interval of
     * ETX_INTERVAL between the wakeups. It takes the old jittervalue in account
     * and modifies the time to wait accordingly.
     */
    etx_probe_t * packet = etx_get_send_buf();
    uint8_t p_length = 0;

    /*
     * xxx If you get a -Wmissing-braces warning here:
     * A -Wmissing-braces warning at this point is a gcc-bug!
     * Please delete this information once it's fixed
     * See: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=53119
     */
    ieee_802154_long_t empty_addr = { 0 };

    while (true) {
        thread_sleep();
        mutex_lock(&etx_mutex);
        //Build etx packet
        p_length = 0;
        for (uint8_t i = 0; i < ETX_BEST_CANDIDATES; i++) {
            if (candidates[i].used != 0) {
                packet->data[i * ETX_TUPLE_SIZE] =
                        candidates[i].addr.uint8[ETX_IPV6_LAST_BYTE];
                packet->data[i * ETX_TUPLE_SIZE + ETX_PKT_REC_OFFSET] =
                        etx_count_packet_tx(&candidates[i]);
                p_length = p_length + ETX_PKT_HDR_LEN;
            }
        }
        packet->length = p_length;
        send_ieee802154_frame(&empty_addr, &etx_send_buf[0],
                ETX_DATA_MAXLEN+ETX_PKT_HDR_LEN, 1);
        DEBUG("sent beacon!\n");
        etx_set_packets_received();
        cur_round++;
        if (cur_round == ETX_WINDOW) {
            if (reached_window != 1) {
                //first round is through
                reached_window = 1;
            }
            cur_round = 0;
        }
        mutex_unlock(&etx_mutex,0);
    }
}
Ejemplo n.º 5
0
void show_candidates(void) {
    etx_neighbor_t * candidate;
    etx_neighbor_t *end;

    for (candidate = &candidates[0], end = candidates
            + ETX_MAX_CANDIDATE_NEIGHBORS; candidate < end;
            candidate++) {
        if (candidate->used == 0) {
            break;
        }
        printf("Candidates Addr:%d\n"
                "\t cur_etx:%f\n"
                "\t packets_rx:%d\n"
                "\t packets_tx:%d\n"
                "\t used:%d\n", candidate->addr.uint8[ETX_IPV6_LAST_BYTE],
                candidate->cur_etx, candidate->packets_rx,
                etx_count_packet_tx(candidate),
                candidate->used);
    }
}