| 1160 | } |
| 1161 | |
| 1162 | static int |
| 1163 | ng_ksocket_accept(priv_p priv) |
| 1164 | { |
| 1165 | struct socket *const head = priv->so; |
| 1166 | struct socket *so; |
| 1167 | struct sockaddr *sa = NULL; |
| 1168 | struct ng_mesg *resp; |
| 1169 | struct ng_ksocket_accept *resp_data; |
| 1170 | node_p node; |
| 1171 | priv_p priv2; |
| 1172 | int len; |
| 1173 | int error; |
| 1174 | |
| 1175 | SOLISTEN_LOCK(head); |
| 1176 | error = solisten_dequeue(head, &so, SOCK_NONBLOCK); |
| 1177 | if (error == EWOULDBLOCK) { |
| 1178 | priv->flags |= KSF_ACCEPTING; |
| 1179 | return (error); |
| 1180 | } |
| 1181 | priv->flags &= ~KSF_ACCEPTING; |
| 1182 | if (error) |
| 1183 | return (error); |
| 1184 | |
| 1185 | if ((error = soaccept(so, &sa)) != 0) |
| 1186 | return (error); |
| 1187 | |
| 1188 | len = OFFSETOF(struct ng_ksocket_accept, addr); |
| 1189 | if (sa != NULL) |
| 1190 | len += sa->sa_len; |
| 1191 | |
| 1192 | NG_MKMESSAGE(resp, NGM_KSOCKET_COOKIE, NGM_KSOCKET_ACCEPT, len, |
| 1193 | M_NOWAIT); |
| 1194 | if (resp == NULL) { |
| 1195 | soclose(so); |
| 1196 | goto out; |
| 1197 | } |
| 1198 | resp->header.flags |= NGF_RESP; |
| 1199 | resp->header.token = priv->response_token; |
| 1200 | |
| 1201 | /* Clone a ksocket node to wrap the new socket */ |
| 1202 | error = ng_make_node_common(&ng_ksocket_typestruct, &node); |
| 1203 | if (error) { |
| 1204 | free(resp, M_NETGRAPH); |
| 1205 | soclose(so); |
| 1206 | goto out; |
| 1207 | } |
| 1208 | |
| 1209 | if (ng_ksocket_constructor(node) != 0) { |
| 1210 | NG_NODE_UNREF(node); |
| 1211 | free(resp, M_NETGRAPH); |
| 1212 | soclose(so); |
| 1213 | goto out; |
| 1214 | } |
| 1215 | |
| 1216 | priv2 = NG_NODE_PRIVATE(node); |
| 1217 | priv2->so = so; |
| 1218 | priv2->flags |= KSF_CLONED | KSF_EMBRYONIC; |
| 1219 |
no test coverage detected