/*
* Copyright (c) 2002-2005 Sendmail, Inc. and its suppliers.
* All rights reserved.
*
* By using this file, you agree to the terms and conditions set
* forth in the LICENSE file which can be found at the top level of
* the sendmail distribution.
*/
#include "sm/generic.h"
SM_RCSID("@(#)$Id: t-net-0.c,v 1.24 2005/05/31 21:00:28 ca Exp $")
#include "sm/assert.h"
#include "sm/error.h"
#include "sm/test.h"
#include "sm/io.h"
#include "sm/ctype.h"
#include "smi-net.h"
#include "sm/unixsock.h"
#include "timing.h"
#include <stdio.h>
#define SM_CHECK_NET_UNIX 1
static char *nsocket = "./cltsrv";
#include "t-net-common.c"
/*
** CLIENT -- write wr characters to localhost:port
**
** Parameters:
** ip -- IP address to use
** port -- port
** wr -- number of chars to send
** delay -- sleep time before close
** bsize -- buffer size to use
** timeout -- timeout
** both -- if >0: do write and read ("both" times)
** sets double buffering
** iter -- number of iterations (writing data)
** net -- use an INET (or LOCAL) socket
**
** Returns:
** none
*/
static void
client(char *ip, int port, int wr, int delay, int bsize, int timeout, int both, int iter, bool net)
{
int fd;
sm_ret_T ret;
if (Verbose > 1)
fprintf(stderr, "clt: connect\n");
if (net)
(void) net_client_connect(ip, port, &fd);
else
(void) unix_client_connect(nsocket, &fd);
if (Verbose > 1)
fprintf(stderr, "clt: connected=%d\n", fd);
SM_TEST(fd >= 0);
if (fd < 0)
return;
while (iter-- > 0)
{
ret = write_sock(fd, wr, delay, bsize, timeout, both);
SM_TEST(sm_is_success(ret));
if (!sm_is_success(ret))
{
if (Verbose > 0)
fprintf(stderr, "client: error %x\n", ret);
return;
}
}
}
/*
** SERVER -- receive rd characters on localhost:port
**
** Parameters:
** ip -- IP address to use
** port -- port
** rd -- number of chars to receive
** rep -- loop through all of this rep times
** delay -- sleep time before close
** bsize -- buffer size to use
** backlog -- size of listen queue
** timeout -- timeout
** both -- if >0: do write and read ("both" times)
** sets double buffering
** iter -- number of iterations (reading data)
** net -- use an INET (or LOCAL) socket
**
** Returns:
** none
*/
static void
server(char *ip, int port, int rd, int rep, int delay, int bsize, int backlog, int timeout, int both, int iter, bool net)
{
int fd, lfd;
sm_ret_T res;
struct sockaddr addr;
sockaddr_len_T addrlen;
res = 0;
lfd = fd = -1;
if (net)
lfd = netserverlisten(ip, port, backlog);
else
lfd = unix_server_listen(nsocket, 10);
SM_TEST(lfd >= 0);
if (lfd < 0)
return;
while (rep-- > 0)
{
addrlen = sizeof(addr);
if (Verbose > 1)
fprintf(stderr, "srv: accept\n");
if (net)
fd = net_server_accept(lfd, &addr, &addrlen);
else
fd = unix_server_accept(lfd, &addr, &addrlen);
SM_TEST(fd >= 0);
if (fd < 0)
goto err;
while (iter-- > 0)
{
res = read_sock(fd, rd, delay, bsize, timeout, both);
if (sm_is_err(res))
goto err;
}
fd = -1;
if (Verbose > 0)
fprintf(stderr, "srv: read_sock done=%x\n", res);
if (sm_is_err(res))
goto err;
}
err:
if (fd >= 0)
close(fd);
if (lfd >= 0)
close(lfd);
}
int
main(int argc, char *argv[])
{
bool clt, any;
int c, port, rd, wr, rep, delay, backlog, bsize, timeout, both, iter;
char *ip;
bool net;
sm_ret_T res;
opterr = 0;
clt = true;
any = false;
port = SM_DEFPORT;
rd = wr = 0;
rep = 1;
delay = 0;
bsize = 0;
backlog = 20;
timeout = 5;
Verbose = 0;
both = 0;
iter = 1;
ip = "127.0.0.1";
net = true;
while ((c = getopt(argc, argv, "b:Bc:d:i:I:l:p:r:R:s:St:TuU:V")) != -1)
{
any = true;
switch (c)
{
case 'B':
both++;
break;
case 'b':
bsize = atoi(optarg);
break;
case 'c':
clt = true;
wr = atoi(optarg);
break;
case 'd':
delay = atoi(optarg);
break;
case 'i':
iter = atoi(optarg);
break;
case 'I':
ip = strdup(optarg);
if (ip == NULL)
{
fprintf(stderr, "out of memory");
return 1;
}
break;
case 'l':
backlog = atoi(optarg);
break;
case 'p':
port = atoi(optarg);
break;
case 'r':
rep = atoi(optarg);
break;
case 'R':
both = atoi(optarg);
break;
case 's':
clt = false;
rd = atoi(optarg);
break;
case 't':
timeout = atoi(optarg);
break;
case 'u':
net = false;
break;
case 'S':
fprintf(stderr, "sizeof sm_file_T: %d\n", sizeof(sm_file_T));
fprintf(stderr, "sizeof sm_stream_T: %d\n", sizeof(sm_stream_T));
fprintf(stderr, "sizeof smbuf_T: %d\n", sizeof(smbuf_T));
break;
case 'T':
Timing = true;
break;
case 'U':
nsocket = strdup(optarg);
if (nsocket == NULL)
{
fprintf(stderr, "out of memory");
return 1;
}
break;
case 'V':
++Verbose;
break;
default:
usage(argv[0]);
return 1;
}
}
sm_test_begin(argc, argv, "test net 0");
res = net_startup();
SM_TEST(sm_is_success(res));
if (!sm_is_success(res))
return sm_test_end();
if (!any)
goto end;
if (clt)
client(ip, port, wr, delay, bsize, timeout, both, iter, net);
else
{
(void) unlink(nsocket);
server(ip, port, rd, rep, delay, bsize, backlog, timeout, both, iter, net);
}
end:
net_shutdown();
(void) unlink(nsocket);
return sm_test_end();
}
syntax highlighted by Code2HTML, v. 0.9.1