UNIX & GNU/Linux - System calls - Using accept()

The accept() system call waits a connection from a client. For the example above, we are going to take the nc tool (you can use telnet, it is the same). If we reach the server through the nc connection, the server will shutdown. But that’s what we want to do. Let’s see it in this accept() tutorial. Using accept() server.c /* server.c */ #include #include #include #include #include #include #include #include #include "h.h" void my_socket(t_s *s) { s->name = "TCP"; s->domain = AF_INET; s->type = SOCK_STREAM; s->pe = getprotobyname(s->name); s->fd = socket(s->domain, s->type, s->pe->p_proto); check_error(s->fd, -1); } void my_bind(t_s *s, int port) { s->sockfd = s->fd; s->addr.sin_family = s->domain; s->addr.sin_addr.s_addr = INADDR_ANY; s->addr.sin_port = htons(port); s->addrlen = sizeof(s->addr); s->bindValue = bind(s->fd, (const struct sockaddr *)&s->addr, s->addrlen); check_error(s->bindValue, -1); } void my_listen(t_s *s, int backlog) { s->listenValue = listen(s->sockfd, backlog); check_error(s->listenValue, -1); } void my_accept(t_s *s) { s->addrlenAccept = sizeof(s->addrAccept); s->acceptValue = accept(s->sockfd, (struct sockaddr *)&s->addrAccept, &s->addrlenAccept); check_error(s->acceptValue, -1); } int main(int ac, char *av[]) { t_s s; check_arg(ac, ARG_SIZE); my_socket(&s); my_bind(&s, atoi(av[1])); my_listen(&s, BACKLOG); my_accept(&s); debug(&s); check_error(close(s.acceptValue), -1); check_error(close(s.fd), -1); return 0; } debug.c /* debug.c */ #include #include #include #include #include #include "h.h" void debug(t_s *s) { printf("\n===== socket() =====\n"); printf("domain = %d\n", s->domain); printf("type = %d\n", s->type); printf("fd = %d\n", s->fd); printf("name = %s\n", s->name); printf("p_proto = %d\n", s->pe->p_proto); printf("\n===== bind() =====\n"); printf("sockfd = %d\n", s->sockfd); printf("sin_family = %d\n", s->addr.sin_family); printf("sin_addr.s_addr = %d\n", s->addr.sin_addr.s_addr); printf("sin_port = %d\n", s->addr.sin_port); printf("addrlen = %d\n", s->addrlen); printf("bindValue = %d\n", s->bindValue); printf("\n===== listen() =====\n"); printf("listenValue = %d\n", s->listenValue); printf("\n===== accept() =====\n"); printf("addrlenAccept = %d\n", s->addrlenAccept); printf("acceptValue = %d\n\n", s->acceptValue); } void check_error(int test, int error) { if (test == error) { fprintf(stderr, "ERROR: %s\n", strerror(errno)); exit(EXIT_FAILURE); } } void check_arg(int ac, int number) { if (ac < number) { printf("Usage: ./server [PORT]\n"); exit(EXIT_FAILURE); } } h.h #ifndef H_H_ #define H_H_ #include /** * Define */ #define ARG_SIZE 2 #define BACKLOG 10 #define BUF_SIZE 255 /** * Structure */ typedef struct mystruct { /* socket */ int domain; int type; int fd; char *name; struct protoent *pe; /* bind */ int sockfd; socklen_t addrlen; struct sockaddr_in addr; int bindValue; /* listen */ int listenValue; /* accept */ int acceptValue; socklen_t addrlenAccept; struct sockaddr_in addrAccept; } t_s; /** * Prototype */ void debug(t_s *); void check_error(int, int); void check_arg(int, int); #endif /* H_H_ */ Compiling $ gcc server.c debug.c -o server ; ./server 5000 Now that the server is launched, it’s waiting a connection from a client on the port 5000. ...

April 19, 2012

UNIX & GNU/Linux - System calls - Using bind()

The bind() system call function is used with socket(). It assigns the address of the second argument to the file descriptor retrieved by socket(). Of course before using bind(), we must have a valid fd generated by socket(). Using bind() server.c /* server.c */ #include #include #include #include #include #include #include #include #include "h.h" void my_socket(t_s *s) { s->name = "TCP"; s->domain = AF_INET; s->type = SOCK_STREAM; s->pe = getprotobyname(s->name); s->fd = socket(s->domain, s->type, s->pe->p_proto); check_error(s->fd, -1); } void my_bind(t_s *s, int port) { s->sockfd = s->fd; s->addr.sin_family = s->domain; s->addr.sin_addr.s_addr = INADDR_ANY; s->addr.sin_port = htons(port); s->addrlen = sizeof(s->addr); s->bindValue = bind(s->fd, (const struct sockaddr *)&s->addr, s->addrlen); check_error(s->bindValue, -1); } int main(int ac, char *av[]) { t_s s; check_arg(ac, 2); my_socket(&s); my_bind(&s, atoi(av[1])); debug(&s); check_error(close(s.fd), -1); return 0; } debug.c /* debug.c */ #include #include #include #include #include #include "h.h" void debug(t_s *s) { printf("\n===== socket() =====\n"); printf("domain = %d\n", s->domain); printf("type = %d\n", s->type); printf("fd = %d\n", s->fd); printf("name = %s\n", s->name); printf("p_proto = %d\n", s->pe->p_proto); printf("\n===== bind() =====\n"); printf("sockfd = %d\n", s->sockfd); printf("sin_family = %d\n", s->addr.sin_family); printf("sin_addr.s_addr = %d\n", s->addr.sin_addr.s_addr); printf("sin_port = %d\n", s->addr.sin_port); printf("addrlen = %d\n", s->addrlen); printf("bindValue = %d\n\n", s->bindValue); } void check_error(int test, int error) { if (test == error) { fprintf(stderr, "ERROR: %s\n", strerror(errno)); exit(EXIT_FAILURE); } } void check_arg(int ac, int number) { if (ac < number) { printf("Usage: ./server [PORT]\n"); exit(EXIT_FAILURE); } } h.h #ifndef H_H_ #define H_H_ #include /** * Structure */ typedef struct mystruct { int domain; int type; int fd; char *name; struct protoent *pe; int sockfd; socklen_t addrlen; struct sockaddr_in addr; int bindValue; } t_s; /** * Prototype */ void debug(t_s *); void check_error(int, int); void check_arg(int, int); #endif /* H_H_ */ Compiling $ gcc server.c debug.c -o server ; ./server 5000 Result ===== socket() ===== domain = 2 type = 1 fd = 3 name = TCP p_proto = 6 ===== bind() ===== sockfd = 3 sin_family = 2 sin_addr.s_addr = 0 sin_port = 34835 addrlen = 16 bindValue = 0 Good job! 😈

April 19, 2012

UNIX & GNU/Linux - System calls - Using listen()

The listen() system call is designed to tell that a socket is ready to accept incoming connection. Of course, we need first implementing the socket() and bind() system calls. We are talking here about the server side. Let’s see how to use the listen() system call with this tutorial. Using listen() server.c /* server.c */ #include #include #include #include #include #include #include #include #include "h.h" void my_socket(t_s *s) { s->name = "TCP"; s->domain = AF_INET; s->type = SOCK_STREAM; s->pe = getprotobyname(s->name); s->fd = socket(s->domain, s->type, s->pe->p_proto); check_error(s->fd, -1); } void my_bind(t_s *s, int port) { s->sockfd = s->fd; s->addr.sin_family = s->domain; s->addr.sin_addr.s_addr = INADDR_ANY; s->addr.sin_port = htons(port); s->addrlen = sizeof(s->addr); s->bindValue = bind(s->fd, (const struct sockaddr *)&s->addr, s->addrlen); check_error(s->bindValue, -1); } void my_listen(t_s *s, int backlog) { s->listenValue = listen(s->sockfd, backlog); check_error(s->listenValue, -1); } int main(int ac, char *av[]) { t_s s; check_arg(ac, ARG_SIZE); my_socket(&s); my_bind(&s, atoi(av[1])); my_listen(&s, BACKLOG); debug(&s); check_error(close(s.fd), -1); return 0; } debug.c /* debug.c */ #include #include #include #include #include #include "h.h" void debug(t_s *s) { printf("\n===== socket() =====\n"); printf("domain = %d\n", s->domain); printf("type = %d\n", s->type); printf("fd = %d\n", s->fd); printf("name = %s\n", s->name); printf("p_proto = %d\n", s->pe->p_proto); printf("\n===== bind() =====\n"); printf("sockfd = %d\n", s->sockfd); printf("sin_family = %d\n", s->addr.sin_family); printf("sin_addr.s_addr = %d\n", s->addr.sin_addr.s_addr); printf("sin_port = %d\n", s->addr.sin_port); printf("addrlen = %d\n", s->addrlen); printf("bindValue = %d\n", s->bindValue); printf("\n===== listen() =====\n"); printf("listenValue = %d\n\n", s->listenValue); } void check_error(int test, int error) { if (test == error) { fprintf(stderr, "ERROR: %s\n", strerror(errno)); exit(EXIT_FAILURE); } } void check_arg(int ac, int number) { if (ac < number) { printf("Usage: ./server [PORT]\n"); exit(EXIT_FAILURE); } } h.h #ifndef H_H_ #define H_H_ #include /** * Define */ #define ARG_SIZE 2 #define BACKLOG 10 /** * Structure */ typedef struct mystruct { int domain; int type; int fd; char *name; struct protoent *pe; int sockfd; socklen_t addrlen; struct sockaddr_in addr; int bindValue; int listenValue; } t_s; /** * Prototype */ void debug(t_s *); void check_error(int, int); void check_arg(int, int); #endif /* H_H_ */ Compiling $ gcc server.c debug.c -o server ; ./server 5000 Result ===== socket() ===== domain = 2 type = 1 fd = 3 name = TCP p_proto = 6 ===== bind() ===== sockfd = 3 sin_family = 2 sin_addr.s_addr = 0 sin_port = 34835 addrlen = 16 bindValue = 0 ===== listen() ===== listenValue = 0 Great! 😱

April 19, 2012

UNIX & GNU/Linux - System calls - Using socket()

The socket() system call function will help us to create an end point. This end point will allow for example to connect a client to a server. Indeed, both of them (client and server) will have a socket() system call function on their implementation. In this tutorial of socket() we are going to see how to create a socket for a client and for a server. Let’s see first of all with the server snippet. ...

April 19, 2012

UNIX & GNU/Linux - System calls - Using read()

We are going to use the read() function to read on the standard input from our favorite shell. So each time you will write something then type ENTER, the text written will be display on the shell. Let’s see this, with this tiny tutorial of the read() function with a C example. #include #include #include #include #include #define BUF_SIZE 1024 void empty_buf(char *buf) { int i; i = 0; while (buf[i]) { buf[i] = '\0'; ++i; } buf[i] = '\0'; } int main(void) { int gogogo; int fd; char *buf; buf = malloc(sizeof(*buf) * BUF_SIZE + 1); if (buf == NULL) { fprintf(stderr, "Error: %s\n", strerror(errno)); exit(EXIT_FAILURE); } fd = 0; gogogo = 1; while (gogogo) { read(fd, buf, BUF_SIZE); printf("buf = %s\n", buf); empty_buf(buf); } exit(EXIT_SUCCESS); } Good job. 😜

April 10, 2012

UNIX & GNU/Linux - System calls - Using gettimeofday()

The system call function gettimeofday() is a really helpful one. Indeed, we can retrieve milliseconds of the time. But in this tutorial, we are going to see how to generate random numbers every millisecond. Here the code: #include #include #include #include #include int my_random() { double seed; struct timeval tv; gettimeofday(&tv, NULL); seed = (tv.tv_sec) * 1000 + (tv.tv_usec) / 1000; srand(seed); usleep(10000); return (rand() % 255); } int main () { int i = 0; while (i < 10) { printf("R = %d\n", my_random()); ++i; } return (0); } Nice example of random every millisecond.

March 22, 2012

UNIX & GNU/Linux - System calls - Using semget()

Today a tutorial to learn how to use semget(), semctl() and semop() system calls. What are these functions? They help to share data and control access to these data. One calls them semaphore. We can for example use them to access a data from different process. In the example below, we will create two process with the same code, except for the sb.sem_op value. For the first program the value will be 1 and for the second, this value will be -1. ...

March 21, 2012

UNIX & GNU/Linux - System calls - Using time()

It is sometimes useful to display the current date in your terminal. For that the time() system call function is the best one. Let’s see an example within this tiny tutorial of C programming language: // main.c #include #include int main () { time_t myTime; time(&myTime); printf("The time is: %s", ctime(&myTime)); return 0; } Compiling and executing. And the result is: $ The time is: Wed Feb 22 14:36:43 2012 All simply!

February 22, 2012

UNIX & GNU/Linux - Emacs - Auto-completion with Auto-complete

We all agree, without any auto-completion, write always the same functions is really annoying. A guy named Tomohiro Matsuyama has created an auto-completion plugin, really helpful. Let’s install it together in this tutorial. First of all, download the latest auto-complete’s version. We have now to extract it: $ tar xjf auto-complete-1.3.1.tar.bz2 Open a new file with Emacs: $ emacs badprog Wihtin, type ALT + X and write load-file. Type RETURN. And write it: ...

May 3, 2011

UNIX & GNU/Linux - User commands - Using info

The info user command is designed to display all information about a command. It is more detailled than the man user command with several menu. For example you can go throw a menu and click ENTER to enter in this menu: $ info open In this info you can see this: * Menu: * Linked Channels:: Dealing with channels sharing a file position. * Independent Channels:: Dealing with separately opened, unlinked channels. * Cleaning Streams:: Cleaning a stream makes it safe to use another channel. Put your cursor on: ...

April 8, 2011