From: Paolo Ornati <ornati@fastwebnet.it>
To: Paolo Ornati <ornati@fastwebnet.it>
Cc: "Theodore Ts'o" <tytso@mit.edu>,
Linux Kernel Mailing List <linux-kernel@vger.kernel.org>
Subject: Re: Lack of Documentation about SA_RESTART...
Date: Tue, 12 Jul 2005 12:10:34 +0200 [thread overview]
Message-ID: <20050712121034.3f0e84c8@localhost> (raw)
In-Reply-To: <20050712103811.0087a7e3@localhost>
[-- Attachment #1: Type: text/plain, Size: 1259 bytes --]
On Tue, 12 Jul 2005 10:38:11 +0200
Paolo Ornati <ornati@fastwebnet.it> wrote:
> The particular case you analized (blocking connect interrupted by a
> SA_RESTART signal) is interesting... and since SUSV3 says
> "but the connection request shall not be aborted, and the
> connection shall be established asynchronously" (with select()
> or poll()...)
> both for EINPROGRESS and EINTR, I think it's quite stupit to
> automatically restart it and then return EALREADY.
>
> The logically correct behaviur with blocking connect interrupted and
> then restarted should be to continue the blocking wait... IHMO.
it seems that Linux is doing the Right Thing... see the attached
program...
$ make
gcc -O2 -Wall -o conntest connect_test.c
FROM ANOTHER CONSOLE: this is needed to block connect()...
# iptables -A OUTPUT -p tcp --dport 3500 -m state --state NEW -j DROP
$ ./conntest WITHOUT_SA_RESTART
connect(): errno = 4 # EINTR, as expected
Cannot setup client!
$ ./conntest # connect is restarted after SIGALRM, and then it blocks again
FROM ANOTHER CONSOLE:
# iptables -D OUTPUT -p tcp --dport 3500 -m state --state NEW -j DROP
and then "conntest" (thanks to TCP protocol retries) will terminate.
:-)
--
Paolo Ornati
Linux 2.6.12.2 on x86_64
[-- Attachment #2: connect_test.c --]
[-- Type: text/x-csrc, Size: 1692 bytes --]
#include <stdio.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <netinet/tcp.h>
#include <signal.h>
#include <unistd.h>
void sighandler(int sig)
{
/* nothing :) */
}
int setup_alarm_handler(int flags)
{
struct sigaction sa = {
.sa_handler = &sighandler,
.sa_flags = flags
};
return sigaction(SIGALRM, &sa, NULL);
}
int setup_server(int port)
{
int sock;
struct sockaddr_in sa = {
.sin_family = AF_INET,
.sin_port = htons(port),
.sin_addr.s_addr = htonl(INADDR_ANY)
};
if ((sock=socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0)
goto error;
if (bind(sock, (struct sockaddr*)&sa, sizeof(sa)) < 0)
goto error_clean;
if (listen(sock, 16) < 0)
goto error_clean;
return sock;
error_clean:
close(sock);
error:
return -1;
}
int setup_client(const char *server, int port)
{
int sock;
struct sockaddr_in sa = {
.sin_family = AF_INET,
.sin_port = htons(port),
.sin_addr.s_addr = inet_addr(server)
};
if ((sock=socket(AF_INET, SOCK_STREAM, IPPROTO_TCP)) < 0)
goto error;
if (connect(sock, (struct sockaddr*)&sa, sizeof(sa)) < 0) {
printf("connect(): errno = %d\n", errno);
goto error_clean;
}
return sock;
error_clean:
close(sock);
error:
return -1;
}
int main(int argc, char *argv[])
{
int server, client;
int flags = SA_RESTART;
if (argc > 1)
flags = 0;
if (setup_alarm_handler(flags))
return 1;
server = setup_server(3500);
if (server < 0) {
printf("Cannot setup server!\n");
return 1;
}
alarm(1);
client = setup_client("127.0.0.1", 3500);
if (client < 0) {
printf("Cannot setup client!\n");
return 1;
}
printf("Ok!\n");
return 0;
}
[-- Attachment #3: Makefile --]
[-- Type: application/octet-stream, Size: 49 bytes --]
conntest: connect_test.c
gcc -O2 -Wall -o $@ $<
next prev parent reply other threads:[~2005-07-12 10:13 UTC|newest]
Thread overview: 14+ messages / expand[flat|nested] mbox.gz Atom feed top
2005-07-11 10:32 Lack of Documentation about SA_RESTART Paolo Ornati
2005-07-11 14:34 ` Theodore Ts'o
2005-07-12 3:30 ` Philippe Troin
2005-07-12 8:43 ` Paolo Ornati
2005-07-12 8:38 ` Paolo Ornati
2005-07-12 10:10 ` Paolo Ornati [this message]
2005-07-12 12:04 ` Theodore Ts'o
2005-07-12 15:25 ` Paolo Ornati
2005-07-12 18:16 ` Theodore Ts'o
2005-07-13 7:45 ` Paolo Ornati
2005-07-24 0:30 ` Linus Torvalds
2005-07-24 7:28 ` Paolo Ornati
2005-07-24 14:56 ` Theodore Ts'o
2005-07-25 8:02 ` Paolo Ornati
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20050712121034.3f0e84c8@localhost \
--to=ornati@fastwebnet.it \
--cc=linux-kernel@vger.kernel.org \
--cc=tytso@mit.edu \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.