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

Function sosend_generic

freebsd/kern/uipc_socket.c:1542–1802  ·  view source on GitHub ↗

* Send on a socket. If send must go all at once and message is larger than * send buffering, then hard error. Lock against other senders. If must go * all at once and not enough room now, then inform user that this would * block and do nothing. Otherwise, if nonblocking, send as much as * possible. The data to be sent is described by "uio" if nonzero, otherwise * by the mbuf chain "top"

Source from the content-addressed store, hash-verified

1540 * on return.
1541 */
1542int
1543sosend_generic(struct socket *so, struct sockaddr *addr, struct uio *uio,
1544 struct mbuf *top, struct mbuf *control, int flags, struct thread *td)
1545{
1546 long space;
1547 ssize_t resid;
1548 int clen = 0, error, dontroute;
1549 int atomic = sosendallatonce(so) || top;
1550 int pru_flag;
1551#ifdef KERN_TLS
1552 struct ktls_session *tls;
1553 int tls_enq_cnt, tls_pruflag;
1554 uint8_t tls_rtype;
1555
1556 tls = NULL;
1557 tls_rtype = TLS_RLTYPE_APP;
1558#endif
1559 if (uio != NULL)
1560 resid = uio->uio_resid;
1561 else if ((top->m_flags & M_PKTHDR) != 0)
1562 resid = top->m_pkthdr.len;
1563 else
1564 resid = m_length(top, NULL);
1565 /*
1566 * In theory resid should be unsigned. However, space must be
1567 * signed, as it might be less than 0 if we over-committed, and we
1568 * must use a signed comparison of space and resid. On the other
1569 * hand, a negative resid causes us to loop sending 0-length
1570 * segments to the protocol.
1571 *
1572 * Also check to make sure that MSG_EOR isn't used on SOCK_STREAM
1573 * type sockets since that's an error.
1574 */
1575 if (resid < 0 || (so->so_type == SOCK_STREAM && (flags & MSG_EOR))) {
1576 error = EINVAL;
1577 goto out;
1578 }
1579
1580 dontroute =
1581 (flags & MSG_DONTROUTE) && (so->so_options & SO_DONTROUTE) == 0 &&
1582 (so->so_proto->pr_flags & PR_ATOMIC);
1583 if (td != NULL)
1584 td->td_ru.ru_msgsnd++;
1585 if (control != NULL)
1586 clen = control->m_len;
1587
1588 error = sblock(&so->so_snd, SBLOCKWAIT(flags));
1589 if (error)
1590 goto out;
1591
1592#ifdef KERN_TLS
1593 tls_pruflag = 0;
1594 tls = ktls_hold(so->so_snd.sb_tls_info);
1595 if (tls != NULL) {
1596 if (tls->mode == TCP_TLS_MODE_SW)
1597 tls_pruflag = PRUS_NOTREADY;
1598
1599 if (control != NULL) {

Callers

nothing calls this directly

Calls 10

m_lengthFunction · 0.85
sblockFunction · 0.85
ktls_holdFunction · 0.85
sbwaitFunction · 0.85
ktls_frameFunction · 0.85
ktls_enqueueFunction · 0.85
sbunlockFunction · 0.85
ktls_freeFunction · 0.85
m_freemFunction · 0.70
sbspaceFunction · 0.50

Tested by

no test coverage detected