1*4901Swnj /* udp_usrreq.c 4.4 81/11/15 */ 24784Swnj 34784Swnj #include "../h/param.h" 44887Swnj #include "../h/dir.h" 54887Swnj #include "../h/user.h" 64784Swnj #include "../h/mbuf.h" 74805Swnj #include "../h/protosw.h" 84887Swnj #include "../h/socket.h" 94887Swnj #include "../h/socketvar.h" 104805Swnj #include "../net/inet.h" 114887Swnj #include "../net/inet_host.h" 124887Swnj #include "../net/inet_pcb.h" 134805Swnj #include "../net/inet_systm.h" 14*4901Swnj #include "../net/ip.h" 15*4901Swnj #include "../net/ip_var.h" 164887Swnj #include "../net/udp.h" 174887Swnj #include "../net/udp_var.h" 184784Swnj 194805Swnj udp_init() 204805Swnj { 214805Swnj 22*4901Swnj udb.inp_next = udb.inp_prev = &udb; 234805Swnj } 244805Swnj 25*4901Swnj int udpcksum; 26*4901Swnj 274784Swnj udp_input(m) 284784Swnj struct mbuf *m; 294784Swnj { 30*4901Swnj register struct udpiphdr *ui; 314887Swnj register struct inpcb *inp; 32*4901Swnj u_short lport, fport; 33*4901Swnj int ulen; 344784Swnj 35*4901Swnj ui = mtod(m, struct udpiphdr *); 36*4901Swnj if (ui->ui_len > sizeof (struct ip)) /* XXX */ 37*4901Swnj ip_stripoptions((struct ip *)ui); 38*4901Swnj ulen = ((struct ip *)ui)->ip_len; 39*4901Swnj ui->ui_len = htons(ulen); 40*4901Swnj ui->ui_prev = ui->ui_next = 0; 41*4901Swnj ui->ui_x1 = 0; 42*4901Swnj lport = ntohs(ui->ui_dport); 43*4901Swnj fport = ntohs(ui->ui_sport); 44*4901Swnj if (sizeof (struct udpiphdr) > m->m_len) 45*4901Swnj { printf("udp header overflow\n"); m_freem(m); return; } 46*4901Swnj if (udpcksum) { 47*4901Swnj inet_cksum(m, sizeof (struct ip) + ulen); 48*4901Swnj if (ui->ui_sum) { 49*4901Swnj printf("udp cksum %x\n", ui->ui_sum); 50*4901Swnj m_freem(m); 51*4901Swnj return; 52*4901Swnj } 53*4901Swnj } 54*4901Swnj inp = inpcb_lookup(&ui->ui_src, fport, &ui->ui_dst, lport); 554887Swnj if (inp == 0) 56*4901Swnj goto notwanted; 57*4901Swnj /* stuff on queue using some subroutine */ 584887Swnj return; 59*4901Swnj notwanted: 604887Swnj m_freem(m); 614887Swnj /* gen icmp? */ 624784Swnj } 634784Swnj 644887Swnj udp_ctlinput(m) 654887Swnj struct mbuf *m; 664887Swnj { 674887Swnj 684887Swnj m_freem(m); 694887Swnj } 704887Swnj 714784Swnj udp_advise(m) 724784Swnj struct mbuf *m; 734784Swnj { 744784Swnj 754784Swnj m_freem(m); 764784Swnj } 774784Swnj 784887Swnj udp_output(raddr, rport, m) 794887Swnj int raddr, rport; 804784Swnj struct mbuf *m; 814784Swnj { 824784Swnj 834887Swnj /* setup header */ 844887Swnj ip_output(m); 854784Swnj } 864784Swnj 874887Swnj udp_usrreq(so, req, m, addr) 884887Swnj struct socket *so; 894784Swnj int req; 904784Swnj struct mbuf *m; 914784Swnj struct in_addr *addr; 924784Swnj { 934887Swnj struct inpcb *inp = sotoinpcb(so); 944887Swnj int error; 954784Swnj 964784Swnj switch (req) { 974784Swnj 984784Swnj case PRU_ATTACH: 994887Swnj if (inp != 0) 1004887Swnj return (EINVAL); 101*4901Swnj inp = inpcb_alloc(); 1024887Swnj if (inp == NULL) 1034887Swnj return (ENOBUFS); 1044887Swnj so->so_pcb = (caddr_t)inp; 1054887Swnj break; 1064784Swnj 1074784Swnj case PRU_DETACH: 1084887Swnj if (inp == 0) 1094887Swnj return (ENOTCONN); 1104887Swnj sofree(inp->inp_socket); 1114887Swnj udp_detach(inp); 1124887Swnj break; 1134784Swnj 1144784Swnj case PRU_CONNECT: 1154887Swnj if (inp->inp_fhost) 1164887Swnj return (EISCONN); 1174887Swnj inp->inp_fhost = in_hmake((struct in_addr *)addr, &error); 1184887Swnj if (inp->inp_fhost == 0) 1194887Swnj return (error); 1204887Swnj soisconnected(so); 1214887Swnj break; 1224784Swnj 1234784Swnj case PRU_DISCONNECT: 1244887Swnj if (inp->inp_fhost == 0) 1254887Swnj return (ENOTCONN); 1264887Swnj h_free(inp->inp_fhost); 1274887Swnj inp->inp_fhost = 0; 1284887Swnj soisdisconnected(so); 1294784Swnj break; 1304784Swnj 1314784Swnj case PRU_SEND: 1324887Swnj #if 0 1334887Swnj if (addr) { 1344887Swnj if (inp->inp_fhost) 1354887Swnj return (EISCONN); 1364887Swnj udp_output(addr->in_fhost, addr->in_fport, m); 1374887Swnj } else 1384887Swnj udp_output(inp->inp_fhost->h_addr, ip->inp_fport, m); 1394887Swnj #endif 1404784Swnj break; 1414784Swnj 1424784Swnj case PRU_ABORT: 1434887Swnj in_pcbfree(inp); 1444887Swnj sofree(so); 1454887Swnj soisdisconnected(so); 1464784Swnj break; 1474784Swnj 1484784Swnj case PRU_CONTROL: 1494887Swnj return (EOPNOTSUPP); 1504784Swnj 1514784Swnj default: 1524784Swnj panic("udp_usrreq"); 1534805Swnj } 1544887Swnj return (0); 1554784Swnj } 1564805Swnj 1574805Swnj udp_sense() 1584805Swnj { 1594805Swnj 1604805Swnj } 161