+
+static int
+mptcp_usr_preconnect(struct socket *mp_so)
+{
+ struct mptsub *mpts = NULL;
+ struct mppcb *mpp = sotomppcb(mp_so);
+ struct mptses *mpte;
+ struct socket *so;
+ struct tcpcb *tp = NULL;
+
+ mpte = mptompte(mpp);
+ VERIFY(mpte != NULL);
+ MPTE_LOCK_ASSERT_HELD(mpte); /* same as MP socket lock */
+
+ mpts = mptcp_get_subflow(mpte, NULL, NULL);
+ if (mpts == NULL) {
+ mptcplog((LOG_ERR, "MPTCP Socket: "
+ "%s: mp_so 0x%llx invalid preconnect ", __func__,
+ (u_int64_t)VM_KERNEL_ADDRPERM(mp_so)),
+ MPTCP_SOCKET_DBG, MPTCP_LOGLVL_ERR);
+ return (EINVAL);
+ }
+ MPTS_LOCK(mpts);
+ mpts->mpts_flags &= ~MPTSF_TFO_REQD;
+ so = mpts->mpts_socket;
+ socket_lock(so, 0);
+ tp = intotcpcb(sotoinpcb(so));
+ tp->t_mpflags &= ~TMPF_TFO_REQUEST;
+ int error = tcp_output(sototcpcb(so));
+ socket_unlock(so, 0);
+ MPTS_UNLOCK(mpts);
+ mp_so->so_flags1 &= ~SOF1_PRECONNECT_DATA;
+ return (error);
+}