110d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly/* 210d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** Copyright 2009 The Android Open Source Project 310d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** 410d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** Licensed under the Apache License, Version 2.0 (the "License"); 510d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** you may not use this file except in compliance with the License. 610d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** You may obtain a copy of the License at 710d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** 810d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** http://www.apache.org/licenses/LICENSE-2.0 910d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** 1010d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** Unless required by applicable law or agreed to in writing, software 1110d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** distributed under the License is distributed on an "AS IS" BASIS, 1210d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1310d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** See the License for the specific language governing permissions and 1410d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly** limitations under the License. 1510d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly*/ 1610d31b957a35d4ac084be33b0f136568039c9c14Nick Pelly 179baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly/** testing behavior of shutdown() */ 1847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 1947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <stdlib.h> 2047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <stdio.h> 2147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <errno.h> 2247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <sys/uio.h> 2347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <unistd.h> 2447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <pthread.h> 2647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <stdio.h> 2747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <stdlib.h> 2847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <errno.h> 2947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <unistd.h> 3047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <sys/socket.h> 3147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <sys/ioctl.h> 3247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <sys/poll.h> 3347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <sys/un.h> 3447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <netinet/in.h> 3547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 3647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <bluetooth/bluetooth.h> 3747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <bluetooth/rfcomm.h> 3847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <bluetooth/sco.h> 3947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly#include <bluetooth/l2cap.h> 4047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 4147653588a022190d4b3e20194ef643dfb7b90632Nick Pellyenum sock_type { 4247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly UNIX = 0, 4347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly RFCOMM, 4447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly SCO, 4547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly L2CAP, 4647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly TCP, 4747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly}; 4847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 499baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct thread_args { 509baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int fd; 519baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int type; 529baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int delay; 539baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly}; 5447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 559baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_un local_addr_un = {AF_UNIX, "/tmp/foo"}; 569baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_rc local_addr_rc = {AF_BLUETOOTH, *BDADDR_ANY, 4}; 579baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_sco local_addr_sco = {AF_BLUETOOTH, *BDADDR_LOCAL}; 589baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_l2 local_addr_l2 = {AF_BLUETOOTH, htobs(0x1001), *BDADDR_ANY, 0}; 599baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_in local_addr_in = {AF_INET, 9999, {0}, {0}}; 609baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 619baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_un remote_addr_un ; 629baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_rc remote_addr_rc ; 639baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_sco remote_addr_sco ; 649baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_l2 remote_addr_l2 ; 659baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct sockaddr_in remote_addr_in ; 6647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 6747653588a022190d4b3e20194ef643dfb7b90632Nick Pellystatic int _socket(int type) { 6847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int ret; 6947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int family = -1; 7047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int typ = -1; 7147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int protocol = -1; 7247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 7347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly switch (type) { 7447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly case UNIX: 7547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly family = PF_UNIX; 7647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly typ = SOCK_STREAM; 7747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly protocol = 0; 7847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly break; 7947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly case RFCOMM: 8047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly family = PF_BLUETOOTH; 8147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly typ = SOCK_STREAM; 8247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly protocol = BTPROTO_RFCOMM; 8347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly break; 8447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly case SCO: 8547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly family = PF_BLUETOOTH; 8647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly typ = SOCK_SEQPACKET; 8747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly protocol = BTPROTO_SCO; 8847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly break; 8947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly case L2CAP: 9047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly family = PF_BLUETOOTH; 9147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly typ = SOCK_SEQPACKET; 9247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly protocol = BTPROTO_L2CAP; 9347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly break; 9447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly case TCP: 9547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly family = PF_INET; 9647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly typ = SOCK_STREAM; 9747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly protocol = 0; 9847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly break; 9947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly } 10047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 10147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("%d: socket()\n", gettid()); 10247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly ret = socket(family, typ, protocol); 10347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("%d: socket() = %d\n", gettid(), ret); 10447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly if (ret < 0) printf("\terr %d (%s)\n", errno, strerror(errno)); 10547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 10647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly return ret; 10747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 10847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 10947653588a022190d4b3e20194ef643dfb7b90632Nick Pellystatic int _close(int fd) { 11047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int ret; 11147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 11247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("%d: close(%d)\n", gettid(), fd); 11347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly ret = close(fd); 11447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("%d: close(%d) = %d\n", gettid(), fd, ret); 11547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly if (ret < 0) printf("\terr %d (%s)\n", errno, strerror(errno)); 11647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 11747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly return ret; 11847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 11947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 1209baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystatic int _bind(int fd, int type) { 1219baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int len = 0; 12247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int ret; 1239baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly struct sockaddr *addr = NULL; 12447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 1259baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly switch (type) { 1269baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case UNIX: 1279baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly unlink(local_addr_un.sun_path); 1289baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &local_addr_un; 1299baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(local_addr_un); 1309baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1319baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case RFCOMM: 1329baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &local_addr_rc; 1339baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(local_addr_rc); 1349baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1359baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case SCO: 1369baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &local_addr_sco; 1379baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(local_addr_sco); 1389baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1399baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case L2CAP: 1409baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &local_addr_l2; 1419baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(local_addr_l2); 1429baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1439baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case TCP: 1449baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &local_addr_in; 1459baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(local_addr_in); 1469baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1479baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly } 1489baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 1499baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: bind(%d)\n", gettid(), fd); 1509baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly ret = bind(fd, addr, len); 1519baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: bind(%d) = %d\n", gettid(), fd, ret); 15247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly if (ret < 0) printf("\terr %d (%s)\n", errno, strerror(errno)); 15347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 15447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly return ret; 15547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 15647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 1579baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystatic int _listen(int fd, int type) { 15847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int ret; 15947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 1609baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: listen(%d)\n", gettid(), fd); 1619baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly ret = listen(fd, 1); 1629baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: listen(%d) = %d\n", gettid(), fd, ret); 16347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly if (ret < 0) printf("\terr %d (%s)\n", errno, strerror(errno)); 1649baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 1659baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly return ret; 1669baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly} 1679baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 1689baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystatic int _accept(int fd, int type) { 1699baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int ret; 1709baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int len; 1719baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly struct sockaddr *addr = NULL; 1729baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 1739baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly switch (type) { 1749baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case UNIX: 1759baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &remote_addr_un; 1769baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(remote_addr_un); 1779baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1789baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case RFCOMM: 1799baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &remote_addr_rc; 1809baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(remote_addr_rc); 1819baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1829baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case SCO: 1839baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &remote_addr_sco; 1849baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(remote_addr_sco); 1859baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1869baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case L2CAP: 1879baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &remote_addr_l2; 1889baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(remote_addr_l2); 1899baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1909baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly case TCP: 1919baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly addr = (struct sockaddr *) &remote_addr_in; 1929baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly len = sizeof(remote_addr_in); 1939baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 1949baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly } 1959baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 1969baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: accept(%d)\n", gettid(), fd); 1979baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly ret = accept(fd, addr, &len); 1989baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: accept(%d) = %d\n", gettid(), fd, ret); 1999baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (ret < 0) printf("\terr %d (%s)\n", errno, strerror(errno)); 2009baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly else { 2019baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("\tlen = %d\n", len); 20247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly } 2039baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 20447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly return ret; 20547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 20647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2079baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystatic int _shutdown(int fd, int how) { 2089baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int ret; 2099baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 2109baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: shutdown(%d)\n", gettid(), fd); 2119baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly ret = shutdown(fd, how); 2129baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("%d: shutdown(%d) = %d\n", gettid(), fd, ret); 2139baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (ret < 0) printf("\terr %d (%s)\n", errno, strerror(errno)); 2149baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 2159baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly return ret; 2169baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly} 2179baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 2189baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystatic void thread_accept(struct thread_args *args) { 21947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("%d: START\n", gettid()); 2209baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly sleep(args->delay); 2219baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly _accept(args->fd, args->type); 22247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("%d: END\n", gettid()); 22347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 22447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2259baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystatic int do_accept_shutdown(int type) { 22647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int fd; 2279baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly pthread_t thread; 2289baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly struct thread_args args = {-1, type, 0}; 22947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 23047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly fd = _socket(type); 2319baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (fd < 0) goto error; 2329baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 2339baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (_bind(fd, type) < 0) goto error; 23447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2359baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (_listen(fd, type) < 0) goto error; 23647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2379baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly args.fd = fd; 2389baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly pthread_create(&thread, NULL, (void *)thread_accept, (void *)&args); 23947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2409baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly sleep(2); 2419baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly _shutdown(fd, SHUT_RDWR); 24247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2439baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly pthread_join(thread, NULL); 24447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 24547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly _close(fd); 24647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 24747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly return 0; 2489baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 2499baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellyerror: 2509baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly return -1; 25147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 25247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 25347653588a022190d4b3e20194ef643dfb7b90632Nick Pellystruct { 25447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly char *name; 2559baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly int (*ptr)(int); 2569baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly} action_table[] = { 2579baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly {"accept_shutdown", do_accept_shutdown}, 2589baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly {NULL, NULL}, 2599baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly}; 2609baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly 2619baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pellystruct { 2629baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly char *name; 26347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly enum sock_type type; 26447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} type_table[] = { 26547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly {"unix", UNIX}, 26647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly {"rfcomm", RFCOMM}, 26747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly {"sco", SCO}, 26847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly {"l2cap", L2CAP}, 26947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly {"tcp", TCP}, 27047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly {NULL, -1}, 27147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly}; 27247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 27347653588a022190d4b3e20194ef643dfb7b90632Nick Pellystatic void usage() { 27447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int i; 27547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2769baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("sock_shutdown_test TYPE ACTION\n"); 27747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("\nTYPE:\n"); 27847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly for (i = 0; type_table[i].name; i++) { 27947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly printf("\t%s\n", type_table[i].name); 28047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly } 2819baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("\nACTION:\n"); 2829baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly for (i = 0; action_table[i].name; i++) { 2839baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("\t%s\n", action_table[i].name); 2849baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly } 28547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 28647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 28747653588a022190d4b3e20194ef643dfb7b90632Nick Pellyint main(int argc, char **argv) { 28847653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int i; 28947653588a022190d4b3e20194ef643dfb7b90632Nick Pelly int type = -1; 29047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly 2919baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (argc != 3) { 29247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly usage(); 29347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly return -1; 29447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly } 29547653588a022190d4b3e20194ef643dfb7b90632Nick Pelly for (i = 0; type_table[i].name; i++) { 29647653588a022190d4b3e20194ef643dfb7b90632Nick Pelly if (!strcmp(argv[1], type_table[i].name)) { 29747653588a022190d4b3e20194ef643dfb7b90632Nick Pelly type = type_table[i].type; 2989baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly break; 2999baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly } 3009baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly } 3019baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (type == -1) { 3029baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly usage(); 3039baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly return -1; 3049baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly } 3059baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly for (i = 0; action_table[i].name; i++) { 3069baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly if (!strcmp(argv[2], action_table[i].name)) { 3079baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly printf("TYPE = %s ACTION = %s\n", type_table[type].name, 3089baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly action_table[i].name); 3099baad993d9788e544c3a30fcc5dae23fe8b1d074Nick Pelly return (*action_table[i].ptr)(type); 31047653588a022190d4b3e20194ef643dfb7b90632Nick Pelly } 31147653588a022190d4b3e20194ef643dfb7b90632Nick Pelly } 31247653588a022190d4b3e20194ef643dfb7b90632Nick Pelly usage(); 31347653588a022190d4b3e20194ef643dfb7b90632Nick Pelly return -1; 31447653588a022190d4b3e20194ef643dfb7b90632Nick Pelly} 315