On Mon, Jun 03, 2002 at 03:54:02PM -0700, Archie Cobbs wrote:
[...]
> If you don't mind, I'll let you deal with the -current case, since
> I'm not familiar enough with -current locking. Below is my proposed
> patch for -stable.

  -current does not have this "problem."

> It should be clear that in -stable at least, there can be a race
> between an interrupt handler that free's a cluster mbuf and mid-level
> code that is free'ing the same mbuf, for example.
> 
> -Archie
> 
> __________________________________________________________________________
> Archie Cobbs     *     Packet Design     *     http://www.packetdesign.com
> 
> --- sys/kern/uipc_mbuf.c.orig Mon Jun  3 15:43:25 2002
> +++ sys/kern/uipc_mbuf.c      Mon Jun  3 15:52:28 2002
> @@ -707,11 +707,16 @@
>               n->m_len = min(len, m->m_len - off);
>               if (m->m_flags & M_EXT) {
>                       n->m_data = m->m_data + off;
> -                     if(!m->m_ext.ext_ref)
> -                             mclrefcnt[mtocl(m->m_ext.ext_buf)]++;
> -                     else
> -                             (*(m->m_ext.ext_ref))(m->m_ext.ext_buf,
> -                                                     m->m_ext.ext_size);
> +                     if (m->m_ext.ext_ref == NULL) {
> +                             atomic_add_char(
> +                                 &mclrefcnt[mtocl(m->m_ext.ext_buf)], 1);
> +                     } else {
> +                             int s = splimp();
> +
> +                             (*m->m_ext.ext_ref)(m->m_ext.ext_buf,
> +                                 m->m_ext.ext_size);
> +                             splx(s);
> +                     }
>                       n->m_ext = m->m_ext;
>                       n->m_flags |= M_EXT;
>               } else
> @@ -754,11 +759,15 @@
>       n->m_len = m->m_len;
>       if (m->m_flags & M_EXT) {
>               n->m_data = m->m_data;
> -             if(!m->m_ext.ext_ref)
> -                     mclrefcnt[mtocl(m->m_ext.ext_buf)]++;
> -             else
> -                     (*(m->m_ext.ext_ref))(m->m_ext.ext_buf,
> -                                             m->m_ext.ext_size);
> +             if (m->m_ext.ext_ref == NULL)
> +                     atomic_add_char(&mclrefcnt[mtocl(m->m_ext.ext_buf)], 1);
> +             else {
> +                     int s = splimp();
> +
> +                     (*m->m_ext.ext_ref)(m->m_ext.ext_buf,
> +                         m->m_ext.ext_size);
> +                     splx(s);
> +             }
>               n->m_ext = m->m_ext;
>               n->m_flags |= M_EXT;
>       } else {
> @@ -777,11 +786,16 @@
>               n->m_len = m->m_len;
>               if (m->m_flags & M_EXT) {
>                       n->m_data = m->m_data;
> -                     if(!m->m_ext.ext_ref)
> -                             mclrefcnt[mtocl(m->m_ext.ext_buf)]++;
> -                     else
> -                             (*(m->m_ext.ext_ref))(m->m_ext.ext_buf,
> -                                                     m->m_ext.ext_size);
> +                     if (m->m_ext.ext_ref == NULL) {
> +                             atomic_add_char(
> +                                 &mclrefcnt[mtocl(m->m_ext.ext_buf)], 1);
> +                     } else {
> +                             int s = splimp();
> +
> +                             (*m->m_ext.ext_ref)(m->m_ext.ext_buf,
> +                                 m->m_ext.ext_size);
> +                             splx(s);
> +                     }
>                       n->m_ext = m->m_ext;
>                       n->m_flags |= M_EXT;
>               } else {
> @@ -1125,11 +1139,15 @@
>       if (m->m_flags & M_EXT) {
>               n->m_flags |= M_EXT;
>               n->m_ext = m->m_ext;
> -             if(!m->m_ext.ext_ref)
> -                     mclrefcnt[mtocl(m->m_ext.ext_buf)]++;
> -             else
> -                     (*(m->m_ext.ext_ref))(m->m_ext.ext_buf,
> -                                             m->m_ext.ext_size);
> +             if (m->m_ext.ext_ref == NULL)
> +                     atomic_add_char(&mclrefcnt[mtocl(m->m_ext.ext_buf)], 1);
> +             else {
> +                     int s = splimp();
> +
> +                     (*m->m_ext.ext_ref)(m->m_ext.ext_buf,
> +                         m->m_ext.ext_size);
> +                     splx(s);
> +             }
>               m->m_ext.ext_size = 0; /* For Accounting XXXXXX danger */
>               n->m_data = m->m_data + len;
>       } else {

 It would be better if the thing was in a macro to allow for consistent
 ref. count manipulation, like in -CURRENT.  But whatever, I don't
 really care.

-- 
Bosko Milekic
[EMAIL PROTECTED]
[EMAIL PROTECTED]


To Unsubscribe: send mail to [EMAIL PROTECTED]
with "unsubscribe freebsd-net" in the body of the message

Reply via email to