Created
December 17, 2014 06:01
-
-
Save polymorphm/0e057402c9fa82547d72 to your computer and use it in GitHub Desktop.
test for catch infinite freezing (on TCP-sockets by default) on GNU/Linux
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// -*- mode: c; coding: utf-8 -*- | |
// | |
// $ gcc -Wall -Werror -o to-test to-test.c && sudo ./to-test | |
#include <stdlib.h> | |
#include <stdio.h> | |
#include <unistd.h> | |
#include <strings.h> | |
#include <arpa/inet.h> | |
#include <netdb.h> | |
#include <sys/types.h> | |
#include <sys/socket.h> | |
// ########## begin of configuration ########## | |
static const char * iface = "eth0"; // <--- !!! NEED TO CONFIG THIS !!! | |
static const char * remote_host = "google.com"; | |
static const uint16_t remote_port = 443; | |
// ########## end of configuration ########## | |
int main (int argc, char *argv[]) { | |
const size_t buf_size = 1024; | |
char buffer[buf_size]; | |
const size_t cmd_buf_size = 1024; | |
char cmd_buf[cmd_buf_size]; | |
int sock_fd = -1; | |
int is_error = 0; | |
int sock_optval; | |
socklen_t sock_optlen = sizeof sock_optval; | |
struct hostent *sock_hostent = 0; | |
struct sockaddr_in sock_serv_addr = {0}; | |
printf("***** %s *****\n", "begin of test"); | |
printf("%s\n", "[step 1] creating socket..."); | |
sock_fd = socket(AF_INET, SOCK_STREAM, 0); | |
if (sock_fd < 0) { | |
printf("%s\n", "socket() error"); | |
return EXIT_FAILURE; | |
} | |
is_error = getsockopt(sock_fd, SOL_SOCKET, SO_KEEPALIVE, &sock_optval, &sock_optlen); | |
if (is_error) { | |
printf("%s\n", "getsockopt() error"); | |
return EXIT_FAILURE; | |
} | |
printf( | |
"***** %s%d *****\n", | |
"INFO: is used SO_KEEPALIVE by default for TCP-sockets? answer: ", | |
sock_optval | |
); | |
printf("%s\n", "[step 2] connecting socket..."); | |
sock_hostent = gethostbyname(remote_host); | |
if (!sock_hostent) { | |
printf("%s\n", "gethostbyname() error"); | |
return EXIT_FAILURE; | |
} | |
bzero((char *)&sock_serv_addr, sizeof(sock_serv_addr)); | |
sock_serv_addr.sin_family = AF_INET; | |
bcopy( | |
(char *)sock_hostent->h_addr, | |
(char *)&sock_serv_addr.sin_addr.s_addr, | |
sock_hostent->h_length | |
); | |
sock_serv_addr.sin_port = htons(remote_port); | |
is_error = connect(sock_fd, (struct sockaddr *)&sock_serv_addr, sizeof(sock_serv_addr)); | |
if (is_error) { | |
printf("%s\n", "connect() error"); | |
return EXIT_FAILURE; | |
} | |
printf("%s\n", "[step 3] time waiting (1s)..."); | |
sleep(1); | |
printf("%s\t[%s]\n", "[step 4] breaking down network...", iface); | |
bzero(cmd_buf, sizeof(cmd_buf)); | |
sprintf(cmd_buf, "%s %s", "ip link set down dev", iface); | |
printf("# %s\n", cmd_buf); | |
system(cmd_buf); | |
printf("%s\n", "[step 5] time waiting (15s)..."); | |
sleep(15); | |
printf("%s\t[%s]\n", "[step 6] reestablishing up network...", iface); | |
bzero(cmd_buf, sizeof(cmd_buf)); | |
sprintf(cmd_buf, "%s %s", "ip link set up dev", iface); | |
printf("# %s\n", cmd_buf); | |
system(cmd_buf); | |
printf("%s\n", "[step 7] time waiting (1s)..."); | |
sleep(1); | |
printf("%s\n", "[step 8] waiting of socket timeout (or we are freezed *infinity*?)..."); | |
recv(sock_fd, &buffer, sizeof(buffer), 0); | |
printf("%s\n", "[step 9] closing socket..."); | |
is_error = close(sock_fd); | |
if (is_error) { | |
printf("%s\n", "close() error"); | |
return EXIT_FAILURE; | |
} | |
printf("***** %s *****\n", "end of test"); | |
return EXIT_SUCCESS; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment