Subject: Re: accept(2) and evanescent connections
To: None <castor@geocast.com>
From: Atsushi Onoe <onoe@sm.sony.co.jp>
List: tech-net
Date: 07/28/2000 05:15:16
> On NetBSD right now, if I have a socket which is listening for connections
> and someone sends me data and closes the connection, accept(2)
> will return success, and reads will give me the residual data,
> but the data in the sockaddr structure returned is garbage.

I cannot figure out your problem.  Since you use accept(2), it would be
SOCK_STREAM.  But I can get the correct sockaddr from accept(2) for
PF_INET case.  For PF_UNIX case, the client's sockname would be anonymous.

Atsushi Onoe
----------------------------------------------------------------------
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>

#include <err.h>
#include <stdio.h>
#include <unistd.h>
#include <arpa/inet.h>

int
main()
{
	int s, c, ns;
	int i, len;
	struct sockaddr_in sin;
	u_char buf[10];

	s = socket(PF_INET, SOCK_STREAM, 0);
	c = socket(PF_INET, SOCK_STREAM, 0);
	memset(&sin, 0, sizeof(sin));
	sin.sin_family = AF_INET;
	bind(s, (struct sockaddr *)&sin, sizeof(sin));
	len = sizeof(sin);
	getsockname(s, (struct sockaddr *)&sin, &len);
	printf("bind to %s port %u\n",
	    inet_ntoa(sin.sin_addr), ntohs(sin.sin_port));
	listen(s, 1);
	connect(c, (struct sockaddr *)&sin, sizeof(sin));
	send(c, "abc\n", 4, 0);
	close(c);
	len = sizeof(sin);
	ns = accept(s, (struct sockaddr *)&sin, &len);
	if (ns == -1)
		err(1, "accept");
	printf("accept from %s port %u (len %d)\n",
	    inet_ntoa(sin.sin_addr), ntohs(sin.sin_port), len);
	len = recv(ns, buf, sizeof(buf), 0);
	printf("recv len %d,", len);
	for (i = 0; i < len; i++)
		printf(" %02x", buf[i]);
	printf("\n");
	exit(0);
}