Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 90105
b: refs/heads/master
c: 17744ff
h: refs/heads/master
i:
  90103: 97793a0
v: v3
  • Loading branch information
Tomas Winkler authored and John W. Linville committed Mar 6, 2008
1 parent dbab4fa commit a254015
Show file tree
Hide file tree
Showing 11 changed files with 450 additions and 467 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: 8211ef78d9023a8772e5acf6b7934598156b2fc8
refs/heads/master: 17744ff6ae7eafe33dac9772f2ef9ab5fb738db8
17 changes: 16 additions & 1 deletion trunk/drivers/net/wireless/iwlwifi/iwl-3945-debug.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,14 +40,28 @@ do { if (iwl3945_debug_level & (level)) \
do { if ((iwl3945_debug_level & (level)) && net_ratelimit()) \
printk(KERN_ERR DRV_NAME": %c %s " fmt, \
in_interrupt() ? 'I' : 'U', __FUNCTION__ , ## args); } while (0)

static inline void iwl3945_print_hex_dump(int level, void *p, u32 len)
{
if (!(iwl3945_debug_level & level))
return;

print_hex_dump(KERN_DEBUG, "iwl data: ", DUMP_PREFIX_OFFSET, 16, 1,
p, len, 1);
}
#else
static inline void IWL_DEBUG(int level, const char *fmt, ...)
{
}
static inline void IWL_DEBUG_LIMIT(int level, const char *fmt, ...)
{
}
#endif /* CONFIG_IWL3945_DEBUG */
static inline void iwl3945_print_hex_dump(int level, void *p, u32 len)
{
}
#endif /* CONFIG_IWL3945_DEBUG */



/*
* To use the debug system;
Expand Down Expand Up @@ -143,6 +157,7 @@ static inline void IWL_DEBUG_LIMIT(int level, const char *fmt, ...)
IWL_DEBUG_LIMIT(IWL_DL_ASSOC | IWL_DL_INFO, f, ## a)
#define IWL_DEBUG_HT(f, a...) IWL_DEBUG(IWL_DL_HT, f, ## a)
#define IWL_DEBUG_STATS(f, a...) IWL_DEBUG(IWL_DL_STATS, f, ## a)
#define IWL_DEBUG_STATS_LIMIT(f, a...) IWL_DEBUG_LIMIT(IWL_DL_STATS, f, ## a)
#define IWL_DEBUG_TX_REPLY(f, a...) IWL_DEBUG(IWL_DL_TX_REPLY, f, ## a)
#define IWL_DEBUG_QOS(f, a...) IWL_DEBUG(IWL_DL_QOS, f, ## a)
#define IWL_DEBUG_RADIO(f, a...) IWL_DEBUG(IWL_DL_RADIO, f, ## a)
Expand Down
231 changes: 196 additions & 35 deletions trunk/drivers/net/wireless/iwlwifi/iwl-3945.c
Original file line number Diff line number Diff line change
Expand Up @@ -183,6 +183,16 @@ void iwl3945_disable_events(struct iwl3945_priv *priv)

}

static int iwl3945_hwrate_to_plcp_idx(u8 plcp)
{
int idx;

for (idx = 0; idx < IWL_RATE_COUNT; idx++)
if (iwl3945_rates[idx].plcp == plcp)
return idx;
return -1;
}

/**
* iwl3945_get_antenna_flags - Get antenna flags for RXON command
* @priv: eeprom and antenna fields are used to determine antenna flags
Expand Down Expand Up @@ -238,6 +248,156 @@ void iwl3945_hw_rx_statistics(struct iwl3945_priv *priv, struct iwl3945_rx_mem_b
priv->last_statistics_time = jiffies;
}

/******************************************************************************
*
* Misc. internal state and helper functions
*
******************************************************************************/
#ifdef CONFIG_IWL3945_DEBUG

/**
* iwl3945_report_frame - dump frame to syslog during debug sessions
*
* You may hack this function to show different aspects of received frames,
* including selective frame dumps.
* group100 parameter selects whether to show 1 out of 100 good frames.
*/
static void iwl3945_dbg_report_frame(struct iwl3945_priv *priv,
struct iwl3945_rx_packet *pkt,
struct ieee80211_hdr *header, int group100)
{
u32 to_us;
u32 print_summary = 0;
u32 print_dump = 0; /* set to 1 to dump all frames' contents */
u32 hundred = 0;
u32 dataframe = 0;
u16 fc;
u16 seq_ctl;
u16 channel;
u16 phy_flags;
u16 length;
u16 status;
u16 bcn_tmr;
u32 tsf_low;
u64 tsf;
u8 rssi;
u8 agc;
u16 sig_avg;
u16 noise_diff;
struct iwl3945_rx_frame_stats *rx_stats = IWL_RX_STATS(pkt);
struct iwl3945_rx_frame_hdr *rx_hdr = IWL_RX_HDR(pkt);
struct iwl3945_rx_frame_end *rx_end = IWL_RX_END(pkt);
u8 *data = IWL_RX_DATA(pkt);

/* MAC header */
fc = le16_to_cpu(header->frame_control);
seq_ctl = le16_to_cpu(header->seq_ctrl);

/* metadata */
channel = le16_to_cpu(rx_hdr->channel);
phy_flags = le16_to_cpu(rx_hdr->phy_flags);
length = le16_to_cpu(rx_hdr->len);

/* end-of-frame status and timestamp */
status = le32_to_cpu(rx_end->status);
bcn_tmr = le32_to_cpu(rx_end->beacon_timestamp);
tsf_low = le64_to_cpu(rx_end->timestamp) & 0x0ffffffff;
tsf = le64_to_cpu(rx_end->timestamp);

/* signal statistics */
rssi = rx_stats->rssi;
agc = rx_stats->agc;
sig_avg = le16_to_cpu(rx_stats->sig_avg);
noise_diff = le16_to_cpu(rx_stats->noise_diff);

to_us = !compare_ether_addr(header->addr1, priv->mac_addr);

/* if data frame is to us and all is good,
* (optionally) print summary for only 1 out of every 100 */
if (to_us && (fc & ~IEEE80211_FCTL_PROTECTED) ==
(IEEE80211_FCTL_FROMDS | IEEE80211_FTYPE_DATA)) {
dataframe = 1;
if (!group100)
print_summary = 1; /* print each frame */
else if (priv->framecnt_to_us < 100) {
priv->framecnt_to_us++;
print_summary = 0;
} else {
priv->framecnt_to_us = 0;
print_summary = 1;
hundred = 1;
}
} else {
/* print summary for all other frames */
print_summary = 1;
}

if (print_summary) {
char *title;
u32 rate;

if (hundred)
title = "100Frames";
else if (fc & IEEE80211_FCTL_RETRY)
title = "Retry";
else if (ieee80211_is_assoc_response(fc))
title = "AscRsp";
else if (ieee80211_is_reassoc_response(fc))
title = "RasRsp";
else if (ieee80211_is_probe_response(fc)) {
title = "PrbRsp";
print_dump = 1; /* dump frame contents */
} else if (ieee80211_is_beacon(fc)) {
title = "Beacon";
print_dump = 1; /* dump frame contents */
} else if (ieee80211_is_atim(fc))
title = "ATIM";
else if (ieee80211_is_auth(fc))
title = "Auth";
else if (ieee80211_is_deauth(fc))
title = "DeAuth";
else if (ieee80211_is_disassoc(fc))
title = "DisAssoc";
else
title = "Frame";

rate = iwl3945_hwrate_to_plcp_idx(rx_hdr->rate);
if (rate == -1)
rate = 0;
else
rate = iwl3945_rates[rate].ieee / 2;

/* print frame summary.
* MAC addresses show just the last byte (for brevity),
* but you can hack it to show more, if you'd like to. */
if (dataframe)
IWL_DEBUG_RX("%s: mhd=0x%04x, dst=0x%02x, "
"len=%u, rssi=%d, chnl=%d, rate=%u, \n",
title, fc, header->addr1[5],
length, rssi, channel, rate);
else {
/* src/dst addresses assume managed mode */
IWL_DEBUG_RX("%s: 0x%04x, dst=0x%02x, "
"src=0x%02x, rssi=%u, tim=%lu usec, "
"phy=0x%02x, chnl=%d\n",
title, fc, header->addr1[5],
header->addr3[5], rssi,
tsf_low - priv->scan_start_tsf,
phy_flags, channel);
}
}
if (print_dump)
iwl3945_print_hex_dump(IWL_DL_RX, data, length);
}
#else
static inline void iwl3945_dbg_report_frame(struct iwl3945_priv *priv,
struct iwl3945_rx_packet *pkt,
struct ieee80211_hdr *header, int group100)
{
}
#endif


static void iwl3945_add_radiotap(struct iwl3945_priv *priv,
struct sk_buff *skb,
struct iwl3945_rx_frame_hdr *rx_hdr,
Expand Down Expand Up @@ -376,24 +536,28 @@ static void iwl3945_handle_data_packet(struct iwl3945_priv *priv, int is_data,
static void iwl3945_rx_reply_rx(struct iwl3945_priv *priv,
struct iwl3945_rx_mem_buffer *rxb)
{
struct ieee80211_hdr *header;
struct ieee80211_rx_status rx_status;
struct iwl3945_rx_packet *pkt = (void *)rxb->skb->data;
struct iwl3945_rx_frame_stats *rx_stats = IWL_RX_STATS(pkt);
struct iwl3945_rx_frame_hdr *rx_hdr = IWL_RX_HDR(pkt);
struct iwl3945_rx_frame_end *rx_end = IWL_RX_END(pkt);
struct ieee80211_hdr *header;
int snr;
u16 rx_stats_sig_avg = le16_to_cpu(rx_stats->sig_avg);
u16 rx_stats_noise_diff = le16_to_cpu(rx_stats->noise_diff);
struct ieee80211_rx_status stats = {
.mactime = le64_to_cpu(rx_end->timestamp),
.freq = ieee80211chan2mhz(le16_to_cpu(rx_hdr->channel)),
.band = (rx_hdr->phy_flags & RX_RES_PHY_FLAGS_BAND_24_MSK) ?
IEEE80211_BAND_2GHZ : IEEE80211_BAND_5GHZ,
.antenna = 0,
.rate_idx = iwl3945_rate_index_from_plcp(rx_hdr->rate),
.flag = 0,
};
u8 network_packet;
int snr;

rx_status.antenna = 0;
rx_status.flag = 0;
rx_status.mactime = le64_to_cpu(rx_end->timestamp);
rx_status.freq = ieee80211chan2mhz(le16_to_cpu(rx_hdr->channel));
rx_status.band = (rx_hdr->phy_flags & RX_RES_PHY_FLAGS_BAND_24_MSK) ?
IEEE80211_BAND_2GHZ : IEEE80211_BAND_5GHZ;

rx_status.rate_idx = iwl3945_hwrate_to_plcp_idx(rx_hdr->rate);

if (rx_status.band == IEEE80211_BAND_5GHZ)
rx_status.rate_idx -= IWL_FIRST_OFDM_RATE;

if ((unlikely(rx_stats->phy_count > 20))) {
IWL_DEBUG_DROP
Expand All @@ -409,12 +573,12 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv *priv,
}

if (priv->iw_mode == IEEE80211_IF_TYPE_MNTR) {
iwl3945_handle_data_packet(priv, 1, rxb, &stats);
iwl3945_handle_data_packet(priv, 1, rxb, &rx_status);
return;
}

/* Convert 3945's rssi indicator to dBm */
stats.ssi = rx_stats->rssi - IWL_RSSI_OFFSET;
rx_status.ssi = rx_stats->rssi - IWL_RSSI_OFFSET;

/* Set default noise value to -127 */
if (priv->last_rx_noise == 0)
Expand All @@ -430,50 +594,47 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv *priv,
* signal-to-noise ratio (SNR) is (sig_avg / noise_diff).
* Convert linear SNR to dB SNR, then subtract that from rssi dBm
* to obtain noise level in dBm.
* Calculate stats.signal (quality indicator in %) based on SNR. */
* Calculate rx_status.signal (quality indicator in %) based on SNR. */
if (rx_stats_noise_diff) {
snr = rx_stats_sig_avg / rx_stats_noise_diff;
stats.noise = stats.ssi - iwl3945_calc_db_from_ratio(snr);
stats.signal = iwl3945_calc_sig_qual(stats.ssi, stats.noise);
rx_status.noise = rx_status.ssi -
iwl3945_calc_db_from_ratio(snr);
rx_status.signal = iwl3945_calc_sig_qual(rx_status.ssi,
rx_status.noise);

/* If noise info not available, calculate signal quality indicator (%)
* using just the dBm signal level. */
} else {
stats.noise = priv->last_rx_noise;
stats.signal = iwl3945_calc_sig_qual(stats.ssi, 0);
rx_status.noise = priv->last_rx_noise;
rx_status.signal = iwl3945_calc_sig_qual(rx_status.ssi, 0);
}


IWL_DEBUG_STATS("Rssi %d noise %d qual %d sig_avg %d noise_diff %d\n",
stats.ssi, stats.noise, stats.signal,
rx_status.ssi, rx_status.noise, rx_status.signal,
rx_stats_sig_avg, rx_stats_noise_diff);

/* can be covered by iwl3945_report_frame() in most cases */
/* IWL_DEBUG_RX("RX status: 0x%08X\n", rx_end->status); */

header = (struct ieee80211_hdr *)IWL_RX_DATA(pkt);

network_packet = iwl3945_is_network_packet(priv, header);

#ifdef CONFIG_IWL3945_DEBUG
if (iwl3945_debug_level & IWL_DL_STATS && net_ratelimit())
IWL_DEBUG_STATS
("[%c] %d RSSI: %d Signal: %u, Noise: %u, Rate: %u\n",
network_packet ? '*' : ' ',
le16_to_cpu(rx_hdr->channel),
stats.ssi, stats.ssi,
stats.ssi, stats.rate_idx);
IWL_DEBUG_STATS_LIMIT("[%c] %d RSSI:%d Signal:%u, Noise:%u, Rate:%u\n",
network_packet ? '*' : ' ',
le16_to_cpu(rx_hdr->channel),
rx_status.ssi, rx_status.ssi,
rx_status.ssi, rx_status.rate_idx);

#ifdef CONFIG_IWL3945_DEBUG
if (iwl3945_debug_level & (IWL_DL_RX))
/* Set "1" to report good data frames in groups of 100 */
iwl3945_report_frame(priv, pkt, header, 1);
iwl3945_dbg_report_frame(priv, pkt, header, 1);
#endif

if (network_packet) {
priv->last_beacon_time = le32_to_cpu(rx_end->beacon_timestamp);
priv->last_tsf = le64_to_cpu(rx_end->timestamp);
priv->last_rx_rssi = stats.ssi;
priv->last_rx_noise = stats.noise;
priv->last_rx_rssi = rx_status.ssi;
priv->last_rx_noise = rx_status.noise;
}

switch (le16_to_cpu(header->frame_control) & IEEE80211_FCTL_FTYPE) {
Expand Down Expand Up @@ -560,7 +721,7 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv *priv,
}
}

iwl3945_handle_data_packet(priv, 0, rxb, &stats);
iwl3945_handle_data_packet(priv, 0, rxb, &rx_status);
break;

case IEEE80211_FTYPE_CTL:
Expand All @@ -577,7 +738,7 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv *priv,
print_mac(mac2, header->addr2),
print_mac(mac3, header->addr3));
else
iwl3945_handle_data_packet(priv, 1, rxb, &stats);
iwl3945_handle_data_packet(priv, 1, rxb, &rx_status);
break;
}
}
Expand Down
20 changes: 0 additions & 20 deletions trunk/drivers/net/wireless/iwlwifi/iwl-3945.h
Original file line number Diff line number Diff line change
Expand Up @@ -558,16 +558,6 @@ extern int iwl3945_is_network_packet(struct iwl3945_priv *priv,
struct ieee80211_hdr *header);
extern int iwl3945_power_init_handle(struct iwl3945_priv *priv);
extern int iwl3945_eeprom_init(struct iwl3945_priv *priv);
#ifdef CONFIG_IWL3945_DEBUG
extern void iwl3945_report_frame(struct iwl3945_priv *priv,
struct iwl3945_rx_packet *pkt,
struct ieee80211_hdr *header, int group100);
#else
static inline void iwl3945_report_frame(struct iwl3945_priv *priv,
struct iwl3945_rx_packet *pkt,
struct ieee80211_hdr *header,
int group100) {}
#endif
extern void iwl3945_handle_data_packet_monitor(struct iwl3945_priv *priv,
struct iwl3945_rx_mem_buffer *rxb,
void *data, short len,
Expand Down Expand Up @@ -949,16 +939,6 @@ static inline int is_channel_ibss(const struct iwl3945_channel_info *ch)
return ((ch->flags & EEPROM_CHANNEL_IBSS)) ? 1 : 0;
}

static inline int iwl3945_rate_index_from_plcp(int plcp)
{
int i;

for (i = 0; i < IWL_RATE_COUNT; i++)
if (iwl3945_rates[i].plcp == plcp)
return i;
return -1;
}

extern const struct iwl3945_channel_info *iwl3945_get_channel_info(
const struct iwl3945_priv *priv, enum ieee80211_band band, u16 channel);

Expand Down
Loading

0 comments on commit a254015

Please sign in to comment.