MCPcopy Create free account
hub / github.com/F-Stack/f-stack / ip_pcbopts

Function ip_pcbopts

freebsd/netinet/ip_options.c:600–699  ·  view source on GitHub ↗

* Set up IP options in pcb for insertion in output packets. Store in mbuf * with pointer in pcbopt, adding pseudo-option with destination address if * source routed. */

Source from the content-addressed store, hash-verified

598 * source routed.
599 */
600int
601ip_pcbopts(struct inpcb *inp, int optname, struct mbuf *m)
602{
603 int cnt, optlen;
604 u_char *cp;
605 struct mbuf **pcbopt;
606 u_char opt;
607
608 INP_WLOCK_ASSERT(inp);
609
610 pcbopt = &inp->inp_options;
611
612 /* turn off any old options */
613 if (*pcbopt)
614 (void)m_free(*pcbopt);
615 *pcbopt = NULL;
616 if (m == NULL || m->m_len == 0) {
617 /*
618 * Only turning off any previous options.
619 */
620 if (m != NULL)
621 (void)m_free(m);
622 return (0);
623 }
624
625 if (m->m_len % sizeof(int32_t))
626 goto bad;
627 /*
628 * IP first-hop destination address will be stored before actual
629 * options; move other options back and clear it when none present.
630 */
631 if (m->m_data + m->m_len + sizeof(struct in_addr) >= &m->m_dat[MLEN])
632 goto bad;
633 cnt = m->m_len;
634 m->m_len += sizeof(struct in_addr);
635 cp = mtod(m, u_char *) + sizeof(struct in_addr);
636 bcopy(mtod(m, void *), cp, (unsigned)cnt);
637 bzero(mtod(m, void *), sizeof(struct in_addr));
638
639 for (; cnt > 0; cnt -= optlen, cp += optlen) {
640 opt = cp[IPOPT_OPTVAL];
641 if (opt == IPOPT_EOL)
642 break;
643 if (opt == IPOPT_NOP)
644 optlen = 1;
645 else {
646 if (cnt < IPOPT_OLEN + sizeof(*cp))
647 goto bad;
648 optlen = cp[IPOPT_OLEN];
649 if (optlen < IPOPT_OLEN + sizeof(*cp) || optlen > cnt)
650 goto bad;
651 }
652 switch (opt) {
653 default:
654 break;
655
656 case IPOPT_LSRR:
657 case IPOPT_SSRR:

Callers 1

ip_ctloutputFunction · 0.85

Calls 1

m_freeFunction · 0.50

Tested by

no test coverage detected