| 2801 | } |
| 2802 | |
| 2803 | static void |
| 2804 | unp_scan(struct mbuf *m0, void (*op)(struct filedescent **, int)) |
| 2805 | { |
| 2806 | struct mbuf *m; |
| 2807 | struct cmsghdr *cm; |
| 2808 | void *data; |
| 2809 | socklen_t clen, datalen; |
| 2810 | |
| 2811 | while (m0 != NULL) { |
| 2812 | for (m = m0; m; m = m->m_next) { |
| 2813 | if (m->m_type != MT_CONTROL) |
| 2814 | continue; |
| 2815 | |
| 2816 | cm = mtod(m, struct cmsghdr *); |
| 2817 | clen = m->m_len; |
| 2818 | |
| 2819 | while (cm != NULL) { |
| 2820 | if (sizeof(*cm) > clen || cm->cmsg_len > clen) |
| 2821 | break; |
| 2822 | |
| 2823 | data = CMSG_DATA(cm); |
| 2824 | datalen = (caddr_t)cm + cm->cmsg_len |
| 2825 | - (caddr_t)data; |
| 2826 | |
| 2827 | if (cm->cmsg_level == SOL_SOCKET && |
| 2828 | cm->cmsg_type == SCM_RIGHTS) { |
| 2829 | (*op)(data, datalen / |
| 2830 | sizeof(struct filedescent *)); |
| 2831 | } |
| 2832 | |
| 2833 | if (CMSG_SPACE(datalen) < clen) { |
| 2834 | clen -= CMSG_SPACE(datalen); |
| 2835 | cm = (struct cmsghdr *) |
| 2836 | ((caddr_t)cm + CMSG_SPACE(datalen)); |
| 2837 | } else { |
| 2838 | clen = 0; |
| 2839 | cm = NULL; |
| 2840 | } |
| 2841 | } |
| 2842 | } |
| 2843 | m0 = m0->m_nextpkt; |
| 2844 | } |
| 2845 | } |
| 2846 | |
| 2847 | /* |
| 2848 | * A helper function called by VFS before socket-type vnode reclamation. |
no outgoing calls
no test coverage detected