Page MenuHomeFreeBSD

D4077.diff
No OneTemporary

D4077.diff

Index: sys/net80211/ieee80211_freebsd.h
===================================================================
--- sys/net80211/ieee80211_freebsd.h
+++ sys/net80211/ieee80211_freebsd.h
@@ -272,6 +272,7 @@
#define time_before_eq(a,b) time_after_eq(b,a)
struct mbuf *ieee80211_getmgtframe(uint8_t **frm, int headroom, int pktlen);
+struct mbuf *ieee80211_mbuf_defrag(struct mbuf *, int, int);
/* tx path usage */
#define M_ENCAP M_PROTO1 /* 802.11 encap done */
Index: sys/net80211/ieee80211_freebsd.c
===================================================================
--- sys/net80211/ieee80211_freebsd.c
+++ sys/net80211/ieee80211_freebsd.c
@@ -384,6 +384,41 @@
return m;
}
+struct mbuf *
+ieee80211_mbuf_defrag(struct mbuf *m0, int reserved, int maxfrags)
+{
+ struct mbuf *m;
+ int curfrags;
+
+ curfrags = 0;
+ for (m = m0; m != NULL; m = m->m_next)
+ curfrags++;
+
+ if (curfrags <= maxfrags)
+ return (m0); /* Nothing to do. */
+
+ /* Do not free the reserved space. */
+ M_PREPEND(m0, reserved, M_NOWAIT);
+
+ /* Workaround m_collapse(9) limitations. */
+ if (maxfrags == 1 ||
+ (maxfrags == 2 && (m0->m_pkthdr.len - m0->m_len) > MCLBYTES))
+ m = m_defrag(m0, M_NOWAIT);
+ else
+ m = m_collapse(m0, M_NOWAIT, maxfrags);
+
+ if (m == NULL) {
+ m_freem(m0);
+ return (NULL);
+ }
+ m0 = m;
+
+ /* Revert modifications made by M_PREPEND(). */
+ m_adj(m0, reserved);
+
+ return (m0);
+}
+
#ifndef __NO_STRICT_ALIGNMENT
/*
* Re-align the payload in the mbuf. This is mainly used (right now)
Index: sys/net80211/ieee80211_output.c
===================================================================
--- sys/net80211/ieee80211_output.c
+++ sys/net80211/ieee80211_output.c
@@ -1080,7 +1080,9 @@
struct ieee80211_key *key, struct mbuf *m)
{
#define TO_BE_RECLAIMED (sizeof(struct ether_header) - sizeof(struct llc))
- int needed_space = vap->iv_ic->ic_headroom + hdrsize;
+ struct ieee80211com *ic = vap->iv_ic;
+ int needed_space = ic->ic_headroom + hdrsize;
+ int reserved_space;
if (key != NULL) {
/* XXX belongs in crypto code? */
@@ -1111,7 +1113,8 @@
* 802.11 header and any crypto header.
*/
/* XXX check trailing space and copy instead? */
- if (M_LEADINGSPACE(m) < needed_space - TO_BE_RECLAIMED) {
+ reserved_space = needed_space - TO_BE_RECLAIMED;
+ if (M_LEADINGSPACE(m) < reserved_space) {
struct mbuf *n = m_gethdr(M_NOWAIT, m->m_type);
if (n == NULL) {
IEEE80211_DPRINTF(vap, IEEE80211_MSG_OUTPUT,
@@ -1148,6 +1151,16 @@
n->m_next = m;
m = n;
}
+
+ if (ic->ic_seglimit != 0) {
+ /* Adjust length of the mbuf chain. */
+ m = ieee80211_mbuf_defrag(m, reserved_space, ic->ic_seglimit);
+ if (m == NULL) {
+ vap->iv_stats.is_tx_nobuf++;
+ return NULL;
+ }
+ }
+
return m;
#undef TO_BE_RECLAIMED
}
Index: sys/net80211/ieee80211_var.h
===================================================================
--- sys/net80211/ieee80211_var.h
+++ sys/net80211/ieee80211_var.h
@@ -164,6 +164,7 @@
uint16_t ic_lintval; /* listen interval */
uint16_t ic_holdover; /* PM hold over duration */
uint16_t ic_txpowlimit; /* global tx power limit */
+ uint16_t ic_seglimit; /* maximum scatter/gather */
struct ieee80211_rateset ic_sup_rates[IEEE80211_MODE_MAX];
/*

File Metadata

Mime Type
text/plain
Expires
Thu, Apr 2, 5:31 PM (5 h, 39 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
30731618
Default Alt Text
D4077.diff (3 KB)

Event Timeline