コード例 #1
0
ファイル: ieee80211_rrm_sta.c プロジェクト: KHATEEBNSIT/AP
/**
 * @brief 
 *
 * @param vap
 * @param ni
 * @param req
 * @param rm_token
 *
 * @return 
 * @return on success return 0.
 *         on failure returns -ve value.
 */
int ieee80211_rrm_recv_beacon_req(wlan_if_t vap, wlan_node_t ni, 
                struct ieee80211_measreq_ie *req,u_int8_t rm_token)
{
    struct ieee80211_rrmreq_info *params=NULL;
    struct ieee80211_beaconreq *bcnreq=NULL;

    RRM_FUNCTION_ENTER;


    bcnreq = (struct ieee80211_beaconreq *)(&(req->req[0]));
    params = (struct ieee80211_rrmreq_info *)
           OS_MALLOC(vap->rrm->rrm_osdev, sizeof(struct ieee80211_rrmreq_info), 0);

    if(NULL == params)
        return -EBUSY;
    params->rm_dialogtoken = rm_token;
    params->rep_dialogtoken= req->token;
    params->duration=bcnreq->duration;
    params->chnum = bcnreq->channum;
 
    RRM_DEBUG(vap, RRM_DEBUG_INFO, 
              "%s : duration %d chnum %d regclass %d\n", __func__,  
               params->duration, params->chnum, params->regclass);

    IEEE80211_ADDR_COPY(params->bssid,bcnreq->bssid);
    ieee80211_rrm_set_report_pending(vap,IEEE80211_MEASREQ_BR_TYPE,(void *)params);

    if(vap->rrm->rrm_last_scan == 0)
    {
        ieee80211_rrm_scan(vap, bcnreq->mode);
        return EOK;
    }
    else 
    {
        u_int32_t last_scan_time=0,msec_current_time = 0;
        last_scan_time = (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(vap->rrm->rrm_last_scan);
        msec_current_time = (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(OS_GET_TIMESTAMP());
        msec_current_time -= last_scan_time;
    
        if(msec_current_time <  60*1000)
        {
            if(vap->rrm->pending_report)
                ieee80211_send_report(vap->rrm);
        }
        else
        {
            ieee80211_rrm_scan(vap, bcnreq->mode);
        }
    }

    RRM_FUNCTION_EXIT;
    return EOK;
}
コード例 #2
0
static bool ieee80211_assoc_state_run_event(void *ctx, u_int16_t event, u_int16_t event_data_len, void *event_data) 
{
    wlan_assoc_sm_t sm = (wlan_assoc_sm_t) ctx;
    wlan_if_t vap = sm->vap_handle;
    u_int32_t time_elapsed;

    switch(event) {
    case IEEE80211_ASSOC_EVENT_BEACON_MISS:
        sm->last_failure = WLAN_ASSOC_SM_REASON_BEACON_MISS;    /* beacon miss */ 
        ieee80211_sm_transition_to(sm->hsm_handle,IEEE80211_ASSOC_STATE_INIT); 
        return true;
        break;
    case IEEE80211_ASSOC_EVENT_DISASSOC:
        time_elapsed = CONVERT_SYSTEM_TIME_TO_MS(OS_GET_TIMESTAMP() - sm->last_connected_time);
        if ((sm->last_reason == IEEE80211_REASON_AUTH_EXPIRE || sm->last_reason == IEEE80211_REASON_ASSOC_EXPIRE) &&
            (vap->auto_assoc)) {
            ieee80211_send_event(sm, WLAN_ASSOC_SM_EVENT_REJOINING, WLAN_ASSOC_SM_REASON_DISASSOC);
            ieee80211_sm_transition_to(sm->hsm_handle,IEEE80211_ASSOC_STATE_JOIN); 
#if ATH_SUPPORT_WPA_SUPPLICANT_CHECK_TIME
        } else if(sm->cur_rejoin_attempts < vap->iv_rejoint_attemp_time ) {
            sm->cur_rejoin_attempts++;
            ieee80211_send_event(sm, WLAN_ASSOC_SM_EVENT_REJOINING, WLAN_ASSOC_SM_REASON_DISASSOC);
            ieee80211_sm_transition_to(sm->hsm_handle, IEEE80211_ASSOC_STATE_JOIN); 
        } else {
#else
        } else if(sm->cur_rejoin_attempts < REJOIN_ATTEMP_TIME && time_elapsed < REJOIN_CHECKING_TIME) {
            sm->cur_rejoin_attempts++;
            ieee80211_send_event(sm, WLAN_ASSOC_SM_EVENT_REJOINING, WLAN_ASSOC_SM_REASON_DISASSOC);
            ieee80211_sm_transition_to(sm->hsm_handle, IEEE80211_ASSOC_STATE_JOIN); 
        } else {
#endif 
            ieee80211_sm_transition_to(sm->hsm_handle,IEEE80211_ASSOC_STATE_INIT); 
        }
        return true;
        break;

    case IEEE80211_ASSOC_EVENT_DEAUTH:
        time_elapsed = CONVERT_SYSTEM_TIME_TO_MS(OS_GET_TIMESTAMP() - sm->last_connected_time);
        if ((sm->last_reason == IEEE80211_REASON_AUTH_EXPIRE || sm->last_reason == IEEE80211_REASON_ASSOC_EXPIRE) &&
            (vap->auto_assoc)) {
            ieee80211_send_event(sm, WLAN_ASSOC_SM_EVENT_REJOINING, WLAN_ASSOC_SM_REASON_DEAUTH);
           ieee80211_sm_transition_to(sm->hsm_handle,IEEE80211_ASSOC_STATE_JOIN); 
#if ATH_SUPPORT_WPA_SUPPLICANT_CHECK_TIME
        } else if(sm->cur_rejoin_attempts < vap->iv_rejoint_attemp_time ) {
            sm->cur_rejoin_attempts++;
            ieee80211_send_event(sm, WLAN_ASSOC_SM_EVENT_REJOINING, WLAN_ASSOC_SM_REASON_DEAUTH);
            ieee80211_sm_transition_to(sm->hsm_handle, IEEE80211_ASSOC_STATE_JOIN);
        } else {
#else
        } else if(sm->cur_rejoin_attempts < REJOIN_ATTEMP_TIME && time_elapsed < REJOIN_CHECKING_TIME) {
コード例 #3
0
ファイル: ieee80211_mlme_sta.c プロジェクト: jorneytu/wlan
void ieee80211_inact_timeout_sta(struct ieee80211vap *vap)
{

    struct ieee80211_mlme_priv    *mlme_priv = vap->iv_mlme_priv;

    if (!mlme_priv->im_connection_up) {
        return;
    }
    /*
     * if there was an activity in the last IEEE80211_INACT_WAIT period.
     * then reset the counter.
     */
    if (CONVERT_SYSTEM_TIME_TO_MS(OS_GET_TIMESTAMP() - vap->iv_last_directed_frame) < (IEEE80211_INACT_WAIT * 1000)) {
        vap->iv_inact_count = (vap->iv_keep_alive_timeout + IEEE80211_INACT_WAIT -1)/IEEE80211_INACT_WAIT;
    }
    if (vap->iv_inact_count) {
        --vap->iv_inact_count;
        if (vap->iv_inact_count == 0) {
            if (ieee80211_sta_power_send_keepalive(vap->iv_pwrsave_sta) == ENXIO) {
                ieee80211_send_nulldata(vap->iv_bss,false); 
            }
            if (vap->iv_keep_alive_timeout) {
                vap->iv_inact_count =  (vap->iv_keep_alive_timeout + IEEE80211_INACT_WAIT -1)/IEEE80211_INACT_WAIT;
            }
        }
    }
} 
コード例 #4
0
ファイル: pktlog.c プロジェクト: KHATEEBNSIT/AP
static void
pktlog_getbuf_intsafe(struct ath_pktlog_arg *plarg)
{
    struct ath_pktlog_buf *log_buf;
    int32_t buf_size;
    struct ath_pktlog_hdr *log_hdr;
    int32_t cur_wr_offset;
    char *log_ptr;
    struct ath_pktlog_info *pl_info = plarg->pl_info;
    u_int16_t log_type = plarg->log_type;
    size_t log_size = plarg->log_size;
    u_int32_t flags = plarg->flags;

    log_buf = pl_info->buf;
    buf_size = pl_info->buf_size;

    cur_wr_offset = log_buf->wr_offset;
    /* Move read offset to the next entry if there is a buffer overlap */
    if (log_buf->rd_offset >= 0) {
        if ((cur_wr_offset <= log_buf->rd_offset)
            && (cur_wr_offset + sizeof(struct ath_pktlog_hdr)) >
            log_buf->rd_offset)
            PKTLOG_MOV_RD_IDX(log_buf->rd_offset, log_buf, buf_size);
    } else {
        log_buf->rd_offset = cur_wr_offset;
    }

    log_hdr =
        (struct ath_pktlog_hdr *) (log_buf->log_data + cur_wr_offset);
    log_hdr->log_type = log_type;
    log_hdr->flags = flags;
    log_hdr->timestamp = (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(OS_GET_TIMESTAMP());
    log_hdr->size = (u_int16_t)log_size;

    cur_wr_offset += sizeof(*log_hdr);

    if ((buf_size - cur_wr_offset) < log_size) {
        while ((cur_wr_offset <= log_buf->rd_offset)
               && (log_buf->rd_offset < buf_size))
            PKTLOG_MOV_RD_IDX(log_buf->rd_offset, log_buf, buf_size);
        cur_wr_offset = 0;
    }

    while ((cur_wr_offset <= log_buf->rd_offset)
           && (cur_wr_offset + log_size) > log_buf->rd_offset)
        PKTLOG_MOV_RD_IDX(log_buf->rd_offset, log_buf, buf_size);

    log_ptr = &(log_buf->log_data[cur_wr_offset]);

    cur_wr_offset += log_hdr->size;

    log_buf->wr_offset =
        ((buf_size - cur_wr_offset) >=
         sizeof(struct ath_pktlog_hdr)) ? cur_wr_offset : 0;

    plarg->buf = log_ptr;
}
コード例 #5
0
ファイル: ath_vap_pause.c プロジェクト: KHATEEBNSIT/AP
/*
 * set vap pause in progress flag .
 */
static inline void 
ath_vap_pause_set_in_progress(struct ath_softc *sc)
{
    int iter_count=0;
    systime_t           start_timestamp  = OS_GET_TIMESTAMP(); 
    systime_t           cur_timestamp ; 
    
    while(atomic_read(&sc->sc_txq_use_cnt)) {
        OS_DELAY(10);                            
        ++ iter_count;                           
        if ((iter_count % 1000) == 0) {          
            cur_timestamp  = OS_GET_TIMESTAMP();    
            if (CONVERT_SYSTEM_TIME_TO_MS(cur_timestamp - start_timestamp) >= VAP_PAUSE_SYNCHRONIZATION_TIMEOUT) { 
                ASSERT(0);                         
            }                                      
        }                                        
    }
    atomic_set(&sc->sc_vap_pause_in_progress, 1);
}
コード例 #6
0
ファイル: pktlog.c プロジェクト: KHATEEBNSIT/AP
/*
 * count PER and stop pktlog if it's over a threshold. Clear the count per an interval.
 */
static void pktlog_trigger_thruput(HAL_BOOL pkt_good, u_int32_t pktlen, struct ath_pktlog_info *pl_info)
{
    static u_int32_t total = 0; // in bytes
	u_int32_t now;

	if (pkt_good)
		total += pktlen;
	now = OS_GET_TIMESTAMP();
	if (CONVERT_SYSTEM_TIME_TO_MS(now - pl_info->start_time_thruput) > pl_info->trigger_interval) {
		if (total < pl_info->thruput_thresh) {
			//trigger stop
	        DPRINTF(pl_info->pl_sc, ATH_DEBUG_ANY, "pktlog stopped: only %d bytes thruput in past %dms\n", total, pl_info->trigger_interval);
			if (pl_info->log_state) {
			    pl_info->saved_state = pl_info->log_state;
			    pl_info->log_state = 0;
			}
		}
		total = 0;
		pl_info->start_time_thruput = now;
	}
}
コード例 #7
0
ファイル: pktlog.c プロジェクト: KHATEEBNSIT/AP
/*
 * count PER and stop pktlog if it's over a threshold. Clear the count per an interval.
 */
static void pktlog_trigger_per(HAL_BOOL pkt_good, struct ath_pktlog_info *pl_info, int failcount, int nframes, int nbad)
{
    static u_int32_t pkt_err = 0, pkt_cnt = 0;
	u_int32_t now;

	if(nframes > 1) {
		/* 
		 * this is a tx aggregate packet 
		 * failcount: number of tx retries due to not seeing Block ACK
		 * nframes:   number of subframes in an aggregate
		 */
		pkt_cnt += failcount * nframes;
		pkt_err += failcount * nframes;
		if (pkt_good) {
			pkt_cnt += nframes;
		    pkt_err += nbad;
		}
	} else {
	    pkt_cnt += failcount;
	    pkt_err += failcount;
	    if (pkt_good)
		    pkt_cnt++;
	}
	now = OS_GET_TIMESTAMP();
	if (CONVERT_SYSTEM_TIME_TO_MS(now - pl_info->start_time_per) > pl_info->trigger_interval) {
		if (pkt_err * 100 > pkt_cnt * pl_info->per_thresh) {
			//trigger stop
	        DPRINTF(pl_info->pl_sc, ATH_DEBUG_ANY, "pktlog stopped: seen %d bad packets out of %d in past %dms\n",
				pkt_err, pkt_cnt, pl_info->trigger_interval);
			if (pl_info->log_state) {
			    pl_info->saved_state = pl_info->log_state;
			    pl_info->log_state = 0;
			}
		}
		pkt_err = 0;
		pkt_cnt = 0;
		pl_info->start_time_per = now;
	}
}
コード例 #8
0
ファイル: ath_vap_pause.c プロジェクト: jorneytu/wlan
/*
 * set vap pause in progress flag .
 */
static inline void 
ath_vap_pause_set_in_progress(struct ath_softc *sc)
{
    int iter_count=0;
    systime_t           start_timestamp  = OS_GET_TIMESTAMP(); 
    systime_t           cur_timestamp ; 
    spin_lock(&(sc)->sc_vap_pause_lock);
    while(sc->sc_txq_use_cnt) {
        spin_unlock(&(sc)->sc_vap_pause_lock);
        OS_DELAY(10);                            
        ++ iter_count;                           
        if ((iter_count % 1000) == 0) {          
            cur_timestamp  = OS_GET_TIMESTAMP();    
            if (CONVERT_SYSTEM_TIME_TO_MS(cur_timestamp - start_timestamp) >= VAP_PAUSE_SYNCHRONIZATION_TIMEOUT) { 
                ASSERT(0);                         
            }                                      
        }                                        
        spin_lock(&(sc)->sc_vap_pause_lock);
    }
    sc->sc_vap_pause_in_progress=1;
    spin_unlock(&(sc)->sc_vap_pause_lock);
}
コード例 #9
0
ファイル: ieee80211_mlme.c プロジェクト: KHATEEBNSIT/AP
/*
 * Calculate maximum allowed scan_entry age, in ms.
 * Reference_time specifies the timestamp of the oldest accepted entry.
 */
u_int32_t ieee80211_mlme_maximum_scan_entry_age(wlan_if_t vaphandle, 
                                                systime_t reference_time)
{
#define IEEE80211_SCAN_LATENCY_TIME                 1000
    u_int32_t    maximum_age  = 0;
    systime_t    current_time = OS_GET_TIMESTAMP();

    if (reference_time == 0) {
        /* Make all entries old if there's no record of the last scan */
        maximum_age = 0;
    }
    else {
        maximum_age = CONVERT_SYSTEM_TIME_TO_MS(current_time - reference_time);

        /* 
         * Make all entries in the table "old" by setting the maximum age
         * to 0 if last scan occurred too long ago. This can happen when 
         * system is resuming from S3/S4.
         */
        if (maximum_age > IEEE80211_SCAN_ENTRY_EXPIRE_TIME) {
            maximum_age = IEEE80211_SCAN_ENTRY_EXPIRE_TIME;
        }
    }
    
    /* 
     * Add a latency time to account for the delay from the time the
     * maximum age is calculated to the time it's actually used.
     * Failing to account for this latency time can cause the oldest
     * entries in the scan list to be skipped.
     */
    if (maximum_age > 0) {
        maximum_age += IEEE80211_SCAN_LATENCY_TIME;
    }

    return maximum_age;
#undef IEEE80211_SCAN_LATENCY_TIME
}
コード例 #10
0
ファイル: ieee80211_mlme_sta.c プロジェクト: jorneytu/wlan
void
ieee80211_vap_iter_beacon_miss(void *arg, wlan_if_t vap) 
{
    systime_t              tstamp;
    systime_t              last_link_time;
    systime_t              last_traffic_time;
    struct ieee80211com    *ic = vap->iv_ic;    
    struct ieee80211_mlme_priv    *mlme_priv = vap->iv_mlme_priv;
    ieee80211_mlme_event   event;

    IEEE80211_DPRINTF(vap, IEEE80211_MSG_SCAN,
                      "%s: %s iv_bmiss_count=%d reset=%d max=%d arg=%08p swbmiss=%d\n",
                      __func__,
                      (arg != NULL) ? "SW" : "HW",
                      vap->iv_bmiss_count,
                      vap->iv_bmiss_count_for_reset,
                      vap->iv_bmiss_count_max,
                      arg,
                      mlme_sta_swbmiss_active(vap));

    /*
     * Our handling is only meaningful for stations that are
     * associated; any other conditions else will be handled
     * through different means (e.g. the tx timeout on mgt frames).
     */
    if ((vap->iv_opmode != IEEE80211_M_STA) ||
        !ieee80211_vap_ready_is_set(vap)) {
        mlme_sta_swbmiss_timer_print_status(vap); /* print the status of sw bmiss */
        return;
    }

    /* 
     * ignore HW beacon miss if SW beacon miss is enabled.
     * and completely rely on SW beacon miss.
     */
    if ((arg == NULL) && mlme_sta_swbmiss_active(vap)) {
        return;
    }

    /*
     * WAR for excessive beacon miss problem on SoC.
     * Consider a beacon miss only when we have two consecutive
     * beacon misses and there are no rx activities in between.
     *
     * Count beacon misses only if we gave the AP a chance by sending a
     * directed Probe Request.
     *
     * Don't do anything if we are scanning a foreign channel.
     * Trying to transmit a frame (Probe Request) during a channel change 
     * (which includes a channel reset) can cause a NMI due to invalid HW 
     * addresses. 
     * Trying to transmit a Probe Request while in a foreign channel 
     * wouldn't do us any good either.
     *
     * Query current time only after retrieving LastLinkTime. This avoids 
     * possible negative values if this routine is preempted by reception of 
     * a beacon or directed frame which would update the fields used to 
     * calculate LastLinkTime.
     */

    last_traffic_time = ieee80211_get_directed_frame_timestamp(vap);
    last_link_time = (vap->iv_last_beacon_time > last_traffic_time) ? 
        vap->iv_last_beacon_time : last_traffic_time;
    tstamp = OS_GET_TIMESTAMP();

    {
        IEEE80211_DPRINTF(vap, IEEE80211_MSG_SCAN,
            "%d.%03d | %s: count=%d probe=%d beacon:%lums directed:%lums data:%lums ap_frame:%lums traffic_ind:%lums\n",
            ((u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(tstamp)) / 1000,
            ((u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(tstamp)) % 1000,
            __func__, vap->iv_bmiss_count,
            ieee80211_scan_can_transmit(ic->ic_scanner),
            (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(tstamp - vap->iv_last_beacon_time),
            (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(tstamp - last_traffic_time),
            (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(tstamp - vap->iv_lastdata),
            (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(tstamp - vap->iv_last_ap_frame),
            (u_int32_t) CONVERT_SYSTEM_TIME_TO_MS(tstamp - vap->iv_last_traffic_indication));
    }

    /*
     * Do not count beacon misses received when we're off-channel, or
     * within IEEE80211_MINIMUM_BMISS_TIME ms of the last valid beacon.
     */ 
    if ((! ieee80211_scan_in_home_channel(ic->ic_scanner)) || 
        (CONVERT_SYSTEM_TIME_TO_MS(tstamp - last_link_time) < IEEE80211_MINIMUM_BMISS_TIME)) {
        mlme_sta_swbmiss_timer_start(vap); /* restart beacon miss timer */
        return;
    }

    vap->iv_bmiss_count++;
    
  
    event.u.event_bmiss.cur_bmiss_count = vap->iv_bmiss_count;
    event.u.event_bmiss.max_bmiss_count = vap->iv_bmiss_count_for_reset;
    event.type = IEEE80211_MLME_EVENT_BEACON_MISS;

    ieee80211_mlme_deliver_event(mlme_priv,&event);

    if (vap->iv_bmiss_count < vap->iv_bmiss_count_for_reset) {
#ifdef ATH_SWRETRY
        /* Turn off the sw retry mechanism until we receive
         * any data frame or probe response for the BSS we are
         * associated to.
         */
        ic->ic_set_swretrystate(vap->iv_bss, FALSE);
#endif                        

        /*
         * It is possible that the hardware gets into
         * deaf mode. Reset the hardware to see if it can recover
         * from the condition.
         */

        /* indicate device error */
        IEEE80211_DPRINTF(vap, IEEE80211_MSG_SCAN, "%s: Beacon miss, do internal reset!!\n", __func__);
        IEEE80211_DELIVER_EVENT_DEVICE_ERROR(vap);
                
        mlme_sta_swbmiss_timer_start(vap); /* restart beacon miss timer */
        return;
    }

    /*  max bmiss count reached */

    vap->iv_bmiss_count = 0;    /* reset bmiss counter */

    IEEE80211_DPRINTF(vap, IEEE80211_MSG_ANY, "%s: Beacon miss, will indicate to OS!!\n", __func__);
    /* indicate beacon miss */
    IEEE80211_DELIVER_EVENT_BEACON_MISS(vap);
}