* allocate a sctp_inpcb and setup a temporary binding to a port/all * addresses. This way if we don't get a bind we by default pick a ephemeral * port with all addresses bound. */
| 2381 | * port with all addresses bound. |
| 2382 | */ |
| 2383 | int |
| 2384 | sctp_inpcb_alloc(struct socket *so, uint32_t vrf_id) |
| 2385 | { |
| 2386 | /* |
| 2387 | * we get called when a new endpoint starts up. We need to allocate |
| 2388 | * the sctp_inpcb structure from the zone and init it. Mark it as |
| 2389 | * unbound and find a port that we can use as an ephemeral with |
| 2390 | * INADDR_ANY. If the user binds later no problem we can then add in |
| 2391 | * the specific addresses. And setup the default parameters for the |
| 2392 | * EP. |
| 2393 | */ |
| 2394 | int i, error; |
| 2395 | struct sctp_inpcb *inp; |
| 2396 | struct sctp_pcb *m; |
| 2397 | struct timeval time; |
| 2398 | sctp_sharedkey_t *null_key; |
| 2399 | |
| 2400 | error = 0; |
| 2401 | |
| 2402 | SCTP_INP_INFO_WLOCK(); |
| 2403 | inp = SCTP_ZONE_GET(SCTP_BASE_INFO(ipi_zone_ep), struct sctp_inpcb); |
| 2404 | if (inp == NULL) { |
| 2405 | SCTP_PRINTF("Out of SCTP-INPCB structures - no resources\n"); |
| 2406 | SCTP_INP_INFO_WUNLOCK(); |
| 2407 | SCTP_LTRACE_ERR_RET(inp, NULL, NULL, SCTP_FROM_SCTP_PCB, ENOBUFS); |
| 2408 | return (ENOBUFS); |
| 2409 | } |
| 2410 | /* zap it */ |
| 2411 | memset(inp, 0, sizeof(*inp)); |
| 2412 | |
| 2413 | /* bump generations */ |
| 2414 | /* setup socket pointers */ |
| 2415 | inp->sctp_socket = so; |
| 2416 | inp->ip_inp.inp.inp_socket = so; |
| 2417 | inp->ip_inp.inp.inp_cred = crhold(so->so_cred); |
| 2418 | #ifdef INET6 |
| 2419 | if (INP_SOCKAF(so) == AF_INET6) { |
| 2420 | if (MODULE_GLOBAL(ip6_auto_flowlabel)) { |
| 2421 | inp->ip_inp.inp.inp_flags |= IN6P_AUTOFLOWLABEL; |
| 2422 | } |
| 2423 | if (MODULE_GLOBAL(ip6_v6only)) { |
| 2424 | inp->ip_inp.inp.inp_flags |= IN6P_IPV6_V6ONLY; |
| 2425 | } |
| 2426 | } |
| 2427 | #endif |
| 2428 | inp->sctp_associd_counter = 1; |
| 2429 | inp->partial_delivery_point = SCTP_SB_LIMIT_RCV(so) >> SCTP_PARTIAL_DELIVERY_SHIFT; |
| 2430 | inp->sctp_frag_point = SCTP_DEFAULT_MAXSEGMENT; |
| 2431 | inp->max_cwnd = 0; |
| 2432 | inp->sctp_cmt_on_off = SCTP_BASE_SYSCTL(sctp_cmt_on_off); |
| 2433 | inp->ecn_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_ecn_enable); |
| 2434 | inp->prsctp_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_pr_enable); |
| 2435 | inp->auth_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_auth_enable); |
| 2436 | inp->asconf_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_asconf_enable); |
| 2437 | inp->reconfig_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_reconfig_enable); |
| 2438 | inp->nrsack_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_nrsack_enable); |
| 2439 | inp->pktdrop_supported = (uint8_t)SCTP_BASE_SYSCTL(sctp_pktdrop_enable); |
| 2440 | inp->idata_supported = 0; |
no test coverage detected