コード例 #1
0
/*
 * lacp_init_port
 *
 * LACP Agent is being enabled/disabled.
 *
 * Start/Stop the necessay timers and enable/disable agent states.
 */
extern void
lacpa_init_port (lacpa_system_t *system, lacpa_info_t *info,
                 uint8_t lacp_enabled)
{
    lacpa_port_t *port = NULL;

    if (!info || !system)  return;

    /*
     * Find any port corresponding to the info received
     */
    port = lacpa_find_port(system, info->port_no);
    if (!port) return;

    AIM_LOG_TRACE("LACP %s received for port: %d", lacp_enabled?
                  "ENABLE": "DISABLE", port->actor.port_no);

    lacpa_copy_info(info, &port->actor);
    lacpa_dump_port(port);

    if (lacp_enabled) {
        port->lacp_event = LACPA_EVENT_ENABLED;
    } else {
        port->lacp_event = LACPA_EVENT_DISABLED;
    }

    port->system = system;
    lacpa_machine(port, NULL);
}
コード例 #2
0
/*
 * lacpa_current_while_expiration_timer_cb
 *
 * Current while Expiration callback
 */
static void
lacpa_current_while_expiration_timer_cb (void *cookie)
{
    lacpa_event_t event;

    if (!cookie) return;

    lacpa_port_t *port = (lacpa_port_t *)cookie;
    if (!port) return;

    AIM_LOG_TRACE("current_while timer callback for port: %d",
                  port->actor.port_no);

    if (port->lacp_state == LACPA_MACHINE_AGENT_CURRENT) {
        event = LACPA_EVENT_CURRENT_TIMER_EXPIRED;
    } else if (port->lacp_state == LACPA_MACHINE_AGENT_EXPIRED) {
        event = LACPA_EVENT_EXPIRY_TIMER_EXPIRED;
    } else {

        /*
         * Sanity check, disable the timer
         */
        lacpa_stop_current_while_timer(port);
        return;
    }

    lacpa_machine(port, NULL, event);
}
コード例 #3
0
/*
 * lacpa_churn_expiration_timer_cb
 *
 * Churn Detection Timer Expiration callback
 */
static void
lacpa_churn_expiration_timer_cb (void *cookie)
{
    if (!cookie) return;

    lacpa_port_t *port = (lacpa_port_t *)cookie;
    if (!port) return;

    AIM_LOG_TRACE("Churn Detection timer callback for port: %d",
                  port->actor.port_no);

    lacpa_machine(port, NULL, LACPA_EVENT_CHURN_DETECTION_EXPIRED);
}
コード例 #4
0
/*
 * lacpa_receive
 *
 * Process incoming LACPDU and take appropriate action
 */
extern bool
lacpa_receive (lacpa_port_t *port, uint8_t *data, uint32_t bytes)
{
    lacpa_pdu_t  pdu;
    ppe_packet_t ppep;

	if (!port || !data) return FALSE;

    if (!port->lacp_enabled) {
        AIM_LOG_ERROR("LACPDU-Rx-FAILED - Agent is Disabled on port: %d",
                      port->actor.port_no);
		return FALSE;
    }

    LACPA_MEMSET(&pdu, DEFAULT_ZERO, sizeof(lacpa_pdu_t));
    AIM_LOG_TRACE("LACPDU Received on port: %d", port->actor.port_no);

    /*
     * Use ppe api's to fill info from data in our pdu
     */
    ppe_packet_init(&ppep, data, bytes);
    if (ppe_parse(&ppep) < 0) {
        AIM_LOG_ERROR("Packet parsing failed. packet=%{data}", data, bytes);
        return FALSE;
    }

    if (!ppe_header_get(&ppep, PPE_HEADER_LACP)) {
        AIM_LOG_ERROR("Not a Valid LCAP Packet");
        return FALSE;
    }

	/*
     * Retrieve the information from the LCAP packet
     */
    if (!lacpa_parse_pdu(&ppep, &pdu)) {
		AIM_LOG_ERROR("Packet parsing failed.");
        return FALSE;
    }

    port->lacp_event = LACPA_EVENT_PDU_RECEIVED;
    lacpa_machine(port, &pdu);

    return TRUE;
}
コード例 #5
0
/*
 * lacpa_update_convergence
 *
 * Decide Protocol Converged/Unconverged based on following:
 * 1. If Partner aggregation state = FALSE; Unconverged
 * 2. If Partner sync state = FALSE; Unconverged
 * 3. If Partner collecting state = FALSE; Unconverged
 * 4. If Partner distributing state = FALSE; Unconverged
 * Else, Converged
 */
static void
lacpa_update_convergence (lacpa_port_t *port, bool *ntt)
{
    lacpa_error_t prev_error = port->error;

	if (!port || !ntt) return;

    if (!LACPA_IS_STATE_AGGREGATION(port->partner.state)) {
        if (prev_error != LACPA_ERROR_PARTNER_AGGREGATION_OFF) {
        	AIM_LOG_ERROR("Setting unconverged, Mis-match in aggregation state");
        	port->error = LACPA_ERROR_PARTNER_AGGREGATION_OFF;
        	port->lacp_event = LACPA_EVENT_PROTOCOL_UNCONVERGED;
        	lacpa_machine(port, NULL);
        } else {
			AIM_LOG_ERROR("Protocol Already Unconverged..No action required");
        }
        return;
    }

    if (!LACPA_IS_STATE_SYNCHRONIZATION(port->actor.state)) {
        AIM_LOG_TRACE("Setting Actor sync state for Port: %d",
                      port->actor.port_no);
        LACPA_SET_STATE_SYNCHRONIZATION(port->actor.state);
        port->ntt_reason = LACPA_TRANSMIT_SYNCHRONIZATION_SET;
        *ntt = TRUE;
    }

	if (!LACPA_IS_STATE_SYNCHRONIZATION(port->partner.state)) {
        port->error = LACPA_ERROR_PARTNER_INSYNC;
        goto unconverged;
    }

    if (!LACPA_IS_STATE_COLLECTING(port->actor.state)) {
		AIM_LOG_TRACE("Setting Actor collection state for Port: %d",
                      port->actor.port_no);
        LACPA_SET_STATE_COLLECTING(port->actor.state);
        port->ntt_reason = LACPA_TRANSMIT_COLLECTING_SET;
        *ntt = TRUE;
    }

    if (!LACPA_IS_STATE_COLLECTING(port->partner.state)) {
        port->error = LACPA_ERROR_PARTNER_COLLECTION_OFF;
        goto unconverged;
    }

    if (!LACPA_IS_STATE_DISTRIBUTING(port->actor.state)) {
        AIM_LOG_TRACE("Setting Actor distribution state Port: %d",
                      port->actor.port_no);
		LACPA_SET_STATE_DISTRIBUTING(port->actor.state);
        port->ntt_reason = LACPA_TRANSMIT_DISTRIBUTING_SET;
        *ntt = TRUE;
    }

    if (!LACPA_IS_STATE_DISTRIBUTING(port->partner.state)) {
        port->error = LACPA_ERROR_PARTNER_DISTRIBUTION_OFF;
        goto unconverged;
    }

    AIM_LOG_TRACE("Setting Port: %d to Converged, ntt_reason: %{lacpa_transmit}",
                  port->actor.port_no, port->ntt_reason);
    port->error = LACPA_ERROR_NONE;
    port->is_converged = TRUE;
    return;

unconverged:
    AIM_LOG_TRACE("Setting Port: %d to Unconverged, reason: %{lacpa_error}, "
                  "ntt_reason: %{lacpa_transmit}", port->actor.port_no,
                  port->error, port->ntt_reason);
	port->is_converged = FALSE;
}