Index: share/man/man9/Makefile =================================================================== --- share/man/man9/Makefile +++ share/man/man9/Makefile @@ -1053,6 +1053,7 @@ mbuf.9 m_append.9 \ mbuf.9 m_apply.9 \ mbuf.9 m_cat.9 \ + mbuf.9 m_catpkt.9 \ mbuf.9 MCHTYPE.9 \ mbuf.9 MCLGET.9 \ mbuf.9 m_collapse.9 \ Index: share/man/man9/mbuf.9 =================================================================== --- share/man/man9/mbuf.9 +++ share/man/man9/mbuf.9 @@ -24,7 +24,7 @@ .\" .\" $FreeBSD$ .\" -.Dd March 11, 2015 +.Dd February 29, 2016 .Dt MBUF 9 .Os .\" @@ -122,6 +122,8 @@ .Fc .Ft void .Fn m_cat "struct mbuf *m" "struct mbuf *n" +.Ft void +.Fn m_catpkt "struct mbuf *m" "struct mbuf *n" .Ft u_int .Fn m_fixhdr "struct mbuf *mbuf" .Ft void @@ -907,12 +909,26 @@ Both .Vt mbuf chains must be of the same type. -.Fa N -is still valid after the function returned. -.Sy Note : -It does not handle -.Dv M_PKTHDR -and friends. +.Fa n +is not guaranteed to be valid after +.Fn m_cat +returns. +.Fn m_cat +does not update any packet header fields or free mbuf tags. +.\" +.It Fn m_catpkt m n +A variant of +.Fn m_cat +that operates on packets. +Both +.Fa m +and +.Fa n +must contain packet headers. +.Fa n +is not guaranteed to be valid after +.Fn m_catpkt +returns. .\" .It Fn m_split mbuf len how Partition an Index: sys/dev/usb/net/uhso.c =================================================================== --- sys/dev/usb/net/uhso.c +++ sys/dev/usb/net/uhso.c @@ -1666,7 +1666,7 @@ struct ip6_hdr *ip6; #endif uint16_t iplen; - int len, isr; + int isr; m = NULL; mwait = sc->sc_mwait; @@ -1686,13 +1686,8 @@ UHSO_DPRINTF(3, "partial m0=%p(%d), concat w/ m=%p(%d)\n", m0, m0->m_len, m, m->m_len); - len = m->m_len + m0->m_len; - - /* Concat mbufs and fix headers */ - m_cat(m0, m); - m0->m_pkthdr.len = len; - m->m_flags &= ~M_PKTHDR; + m_catpkt(m0, m); m = m_pullup(m0, sizeof(struct ip)); if (m == NULL) { if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); Index: sys/kern/uipc_socket.c =================================================================== --- sys/kern/uipc_socket.c +++ sys/kern/uipc_socket.c @@ -2047,10 +2047,6 @@ if (mp0 != NULL) { /* Dequeue as many mbufs as possible. */ if (!(flags & MSG_PEEK) && len >= sb->sb_mb->m_len) { - if (*mp0 == NULL) - *mp0 = sb->sb_mb; - else - m_cat(*mp0, sb->sb_mb); for (m = sb->sb_mb; m != NULL && m->m_len <= len; m = m->m_next) { @@ -2062,6 +2058,10 @@ n = m; } n->m_next = NULL; + if (*mp0 == NULL) + *mp0 = sb->sb_mb; + else + m_cat(*mp0, sb->sb_mb); sb->sb_mb = m; sb->sb_lastrecord = sb->sb_mb; if (sb->sb_mb == NULL) Index: sys/net80211/ieee80211_input.c =================================================================== --- sys/net80211/ieee80211_input.c +++ sys/net80211/ieee80211_input.c @@ -249,9 +249,7 @@ mfrag = m; } else { /* concatenate */ m_adj(m, hdrspace); /* strip header */ - m_cat(mfrag, m); - /* NB: m_cat doesn't update the packet header */ - mfrag->m_pkthdr.len += m->m_pkthdr.len; + m_catpkt(mfrag, m); /* track last seqnum and fragno */ lwh = mtod(mfrag, struct ieee80211_frame *); *(uint16_t *) lwh->i_seq = *(uint16_t *) wh->i_seq; Index: sys/netipsec/key.c =================================================================== --- sys/netipsec/key.c +++ sys/netipsec/key.c @@ -3490,6 +3490,7 @@ } m_cat(result, tres); + tres = NULL; if (result->m_len < sizeof(struct sadb_msg)) { result = m_pullup(result, sizeof(struct sadb_msg)); if (result == NULL)