From cfbd5a025c8e9955dec99a1e833f1099adee80fd Mon Sep 17 00:00:00 2001 From: cvs2git Date: Sun, 7 Mar 2010 17:11:25 +0000 Subject: This commit was manufactured by cvs2svn to create tag 'R_20100318_p1'. Sprout from base 2009-04-22 22:06:58 UTC Till Straumann ' - importing updated version from SLAC as of 20090422' Cherrypick from master 2010-03-07 17:11:23 UTC Till Straumann '2010-03-07 Till Straumann ': bsd_eth_drivers/.cvsignore bsd_eth_drivers/ChangeLog bsd_eth_drivers/Makefile.am bsd_eth_drivers/if_bge/.cvsignore bsd_eth_drivers/if_bge/Makefile.am bsd_eth_drivers/if_bge/if_bge.c bsd_eth_drivers/if_bge/if_bgereg.h bsd_eth_drivers/if_em/.cvsignore bsd_eth_drivers/if_em/Makefile.am bsd_eth_drivers/if_em/e1000_manage.c bsd_eth_drivers/if_em/e1000_manage.h bsd_eth_drivers/if_em/e1000_osdep.h bsd_eth_drivers/if_em/if_em.c bsd_eth_drivers/if_fxp/.cvsignore bsd_eth_drivers/if_fxp/Makefile.am bsd_eth_drivers/if_fxp/if_fxp.c bsd_eth_drivers/if_fxp/if_fxpvar.h bsd_eth_drivers/if_le/.cvsignore bsd_eth_drivers/if_pcn/.cvsignore bsd_eth_drivers/if_pcn/if_pcn.c bsd_eth_drivers/if_re/.cvsignore bsd_eth_drivers/if_re/Makefile.am bsd_eth_drivers/if_re/if_re.c bsd_eth_drivers/if_re/if_rl.c bsd_eth_drivers/if_re/if_rlreg.h bsd_eth_drivers/libbsdport/.cvsignore bsd_eth_drivers/libbsdport/Makefile.am bsd_eth_drivers/libbsdport/alldrv.c bsd_eth_drivers/libbsdport/bus.h bsd_eth_drivers/libbsdport/callout.h bsd_eth_drivers/libbsdport/devicet.c bsd_eth_drivers/libbsdport/ifmedia.c bsd_eth_drivers/libbsdport/libbsdport.h bsd_eth_drivers/libbsdport/libbsdport_api.h bsd_eth_drivers/libbsdport/libbsdport_post.h bsd_eth_drivers/libbsdport/miistuff.c bsd_eth_drivers/libbsdport/misc.c bsd_eth_drivers/libbsdport/mutex.h bsd_eth_drivers/libbsdport/rtems_callout.c bsd_eth_drivers/libbsdport/sysbus.c bsd_eth_drivers/libbsdport/taskqueue.h bsd_eth_drivers/links.am Cherrypick from freebsd_orig 2009-04-23 04:52:05 UTC Till Straumann ' - importing original 'releng_7_1' version of FXP driver from FreeBSD.': bsd_eth_drivers/if_fxp/if_fxpreg.h bsd_eth_drivers/if_fxp/rcvbundl.h Delete: INSTALL Makefile.am bootstrap config.h.in configure.ac m4/acinclude.m4 m4/config-if-present.m4 m4/cvstag.m4 m4/multilib-fix.m4 m4/multilib-installdir.m4 m4/rtems-bsp-postlink.m4 m4/rtems-bsplist.m4 m4/rtems-check-libargs.m4 m4/rtems-checkprog.m4 m4/rtems-checktool.m4 m4/rtems-checktop.m4 m4/rtems-fixup-prefix.m4 m4/rtems-isml.m4 m4/rtems-ismultibsp.m4 m4/rtems-isrtems.m4 m4/rtems-makevars.m4 m4/rtems-multilib.m4 m4/rtems-options.m4 m4/rtems-setup-recurse.m4 m4/rtems-tools.m4 m4/rtems-trim-builddir.m4 m4/rtems-verscheck.m4 makefile.top.am makefile.top.in rtems-pre.am rtems.am ssrlApps.components.in --- bsd_eth_drivers/libbsdport/misc.c | 179 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 179 insertions(+) create mode 100644 bsd_eth_drivers/libbsdport/misc.c (limited to 'bsd_eth_drivers/libbsdport/misc.c') diff --git a/bsd_eth_drivers/libbsdport/misc.c b/bsd_eth_drivers/libbsdport/misc.c new file mode 100644 index 0000000..68e3c03 --- /dev/null +++ b/bsd_eth_drivers/libbsdport/misc.c @@ -0,0 +1,179 @@ + +#include + +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +#include + +int libbsdport_bootverbose = 0; + +#ifdef WITNESS +#define MBUF_CHECKSLEEP(how) do {\ + if (how == M_WAITOK)\ + WITNESS_WARN(WARN_GIANTOK | WARN_SLEEPOK, NULL,\ + "Sleeping in \"%s\"", __func__);\ + } while (0) +#else +#define MBUF_CHECKSLEEP(how) +#endif + +#define MBTOM(how)(how) + +u_int +m_length(struct mbuf *m0, struct mbuf **last) +{ + struct mbuf *m; + u_int len; + + len = 0; + for (m = m0; m != NULL; m = m->m_next) { + len += m->m_len; + if (m->m_next == NULL) + break; + } + if (last != NULL) + *last = m; + return (len); +} + +/* + * Duplicate "from"'s mbuf pkthdr in "to". + * "from" must have M_PKTHDR set, and "to" must be empty. + * In particular, this does a deep copy of the packet tags. + */ +int +m_dup_pkthdr(struct mbuf *to, struct mbuf *from, int how) +{ + + #if 0 + /* + * The mbuf allocator only initializes the pkthdr + * when the mbuf is allocated with MGETHDR. Many users + * (e.g. m_copy*, m_prepend) use MGET and then + * smash the pkthdr as needed causing these + * assertions to trip. For now just disable them. + */ + M_ASSERTPKTHDR(to); + /* Note: with MAC, this may not be a good assertion. */ + KASSERT(SLIST_EMPTY(&to->m_pkthdr.tags), ("m_dup_pkthdr: to has tags")); + #endif + MBUF_CHECKSLEEP(how); + #ifdef MAC + if (to->m_flags & M_PKTHDR) + m_tag_delete_chain(to, NULL); + #endif + to->m_flags = (from->m_flags & M_COPYFLAGS) | (to->m_flags & M_EXT); + if ((to->m_flags & M_EXT) == 0) + to->m_data = to->m_pktdat; + to->m_pkthdr = from->m_pkthdr; + return 1; +} + +u_int +m_fixhdr(struct mbuf *m0) +{ + u_int len; + + len = m_length(m0, NULL); + m0->m_pkthdr.len = len; + return (len); +} + +/* + * Defragment a mbuf chain, returning the shortest possible + * chain of mbufs and clusters. If allocation fails and + * this cannot be completed, NULL will be returned, but + * the passed in chain will be unchanged. Upon success, + * the original chain will be freed, and the new chain + * will be returned. + * + * If a non-packet header is passed in, the original + * mbuf (chain?) will be returned unharmed. + */ +struct mbuf * +m_defrag(struct mbuf *m0, int how) +{ + struct mbuf *m_new = NULL, *m_final = NULL; + int progress = 0, length; + + MBUF_CHECKSLEEP(how); + if (!(m0->m_flags & M_PKTHDR)) + return (m0); + + m_fixhdr(m0); /* Needed sanity check */ + + #ifdef MBUF_STRESS_TEST + if (m_defragrandomfailures) { + int temp = arc4random() & 0xff; + if (temp == 0xba) + goto nospace; + } + #endif + + if (m0->m_pkthdr.len > MHLEN) + m_final = m_getcl(how, MT_DATA, M_PKTHDR); + else + m_final = m_gethdr(how, MT_DATA); + + if (m_final == NULL) + goto nospace; + + if (m_dup_pkthdr(m_final, m0, how) == 0) + goto nospace; + + m_new = m_final; + + while (progress < m0->m_pkthdr.len) { + length = m0->m_pkthdr.len - progress; + if (length > MCLBYTES) + length = MCLBYTES; + + if (m_new == NULL) { + if (length > MLEN) + m_new = m_getcl(how, MT_DATA, 0); + else + m_new = m_get(how, MT_DATA); + if (m_new == NULL) + goto nospace; + } + + m_copydata(m0, progress, length, mtod(m_new, caddr_t)); + progress += length; + m_new->m_len = length; + if (m_new != m_final) + m_cat(m_final, m_new); + m_new = NULL; + } + #ifdef MBUF_STRESS_TEST + if (m0->m_next == NULL) + m_defraguseless++; + #endif + m_freem(m0); + m0 = m_final; + #ifdef MBUF_STRESS_TEST + m_defragpackets++; + m_defragbytes += m0->m_pkthdr.len; + #endif + return (m0); + nospace: + #ifdef MBUF_STRESS_TEST + m_defragfailure++; + #endif + if (m_final) + m_freem(m_final); + return (NULL); +} + -- cgit v1.2.3