Path: blob/main/tools/regression/sockets/reconnect/reconnect.c
101200 views
/*-1* Copyright (c) 2005 Maxim Sobolev2* All rights reserved.3*4* Redistribution and use in source and binary forms, with or without5* modification, are permitted provided that the following conditions6* are met:7* 1. Redistributions of source code must retain the above copyright8* notice, this list of conditions and the following disclaimer.9* 2. Redistributions in binary form must reproduce the above copyright10* notice, this list of conditions and the following disclaimer in the11* documentation and/or other materials provided with the distribution.12*13* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND14* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE15* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE16* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE17* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL18* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS19* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)20* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT21* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY22* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF23* SUCH DAMAGE.24*/2526/*27* The reconnect regression test is designed to catch kernel bug that may28* prevent changing association of already associated datagram unix domain29* socket when server side of connection has been closed.30*/3132#include <sys/types.h>33#include <sys/socket.h>34#include <sys/uio.h>35#include <sys/un.h>36#include <err.h>37#include <errno.h>38#include <fcntl.h>39#include <stdio.h>40#include <stdlib.h>41#include <signal.h>42#include <string.h>43#include <unistd.h>4445static char uds_name1[] = "reconnect.XXXXXXXX";46static char uds_name2[] = "reconnect.XXXXXXXX";4748#define sstosa(ss) ((struct sockaddr *)(ss))4950static void51prepare_ifsun(struct sockaddr_un *ifsun, const char *path)52{5354memset(ifsun, '\0', sizeof(*ifsun));55#if !defined(__linux__) && !defined(__solaris__)56ifsun->sun_len = strlen(path);57#endif58ifsun->sun_family = AF_LOCAL;59strcpy(ifsun->sun_path, path);60}6162static int63create_uds_server(const char *path)64{65struct sockaddr_un ifsun;66int sock;6768prepare_ifsun(&ifsun, path);6970unlink(ifsun.sun_path);7172sock = socket(PF_LOCAL, SOCK_DGRAM, 0);73if (sock == -1)74err(1, "can't create socket");75setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &sock, sizeof(sock));76if (bind(sock, sstosa(&ifsun), sizeof(ifsun)) < 0)77err(1, "can't bind to a socket");7879return sock;80}8182static void83connect_uds_server(int sock, const char *path)84{85struct sockaddr_un ifsun;86int e;8788prepare_ifsun(&ifsun, path);8990e = connect(sock, sstosa(&ifsun), sizeof(ifsun));91if (e < 0)92err(1, "can't connect to a socket");93}9495static void96cleanup(void)97{9899unlink(uds_name1);100unlink(uds_name2);101}102103int104main(void)105{106int s_sock1, s_sock2, c_sock;107108atexit(cleanup);109110if (mkstemp(uds_name1) == -1)111err(1, "mkstemp");112unlink(uds_name1);113s_sock1 = create_uds_server(uds_name1);114115if (mkstemp(uds_name2) == -1)116err(1, "mkstemp");117unlink(uds_name2);118s_sock2 = create_uds_server(uds_name2);119120c_sock = socket(PF_LOCAL, SOCK_DGRAM, 0);121if (c_sock < 0)122err(1, "can't create socket");123124connect_uds_server(c_sock, uds_name1);125close(s_sock1);126connect_uds_server(c_sock, uds_name2);127close(s_sock2);128129exit (0);130}131132133