blob: fb469870bdb5694505b7380a5728b1c2980a740b [file] [log] [blame]
#include <sys/ioctl.h>
#include <stdio.h>
#include <netdb.h>
#include <errno.h>
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>
#include <rpc/rpc.h>
int debug = 0;
int program = 2000333;
int version = 10;
char host_name[100];
long host_address;
struct data {
long address;
long request_id;
long data_length;
char *data;
};
void breakpoint(void);
void service_request(struct svc_req *rqstp, SVCXPRT *transp);
int xdr_receive_data(XDR *xdrs, struct data **buffer);
int xdr_send_data(XDR *xdrs, struct data *buffer);
int
main (int argc, char *argv[])
{
SVCXPRT *transp;
struct hostent *hp;
int i, n;
for (i=1; i<argc; i++) {
if (!strcmp(argv[i], "-d"))
debug = 1;
if (!strcmp(argv[i], "-p")) {
if (++i >= argc) {
fprintf(stderr, "%s: -p requires an argument\n", argv[0]);
exit(1);
}
n = sscanf(argv[i], "%d", &program);
if (n != 1) {
fprintf(stderr, "%s: -p requires an numeric argument\n",
argv[0]);
exit(1);
}
}
if (!strcmp(argv[i], "-v")) {
if (++i >= argc) {
fprintf(stderr, "%s: -v requires an argument\n", argv[0]);
exit(1);
}
n = sscanf(argv[i], "%d", &version);
if (n != 1) {
fprintf(stderr, "%s: -v requires an numeric argument\n",
argv[0]);
exit(1);
}
}
}
if (!debug) {
if ((n=fork()) < 0) {
fprintf(stderr, "%s: Can't fork\n", argv[0]);
exit(1);
}
if (n > 0)
exit(0);
i = 50;
while (--i >= 0)
close(i);
open("/dev/null", O_RDONLY);
open("/dev/null", O_WRONLY);
dup(1);
if ((i=open("/dev/tty", O_RDWR)) >= 0) {
ioctl(i, TIOCNOTTY, 0);
close(i);
}
}
gethostname(host_name, 100);
if (hp=gethostbyname(host_name))
host_address = *((long *) hp->h_addr_list[0]);
pmap_unset(program, version);
transp = svcudp_create(RPC_ANYSOCK);
svc_register(transp, program, version, service_request, IPPROTO_UDP);
transp = svctcp_create(RPC_ANYSOCK, 0, 0);
svc_register(transp, program, version, service_request, IPPROTO_TCP);
svc_run();
exit(1);
}
void
service_request(struct svc_req *rqstp, SVCXPRT *transp)
{
struct data *buffer;
switch (rqstp->rq_proc) {
case 0:
svc_sendreply(transp, xdr_void, (char *) 0);
breakpoint();
return;
case 99:
exit(0);
case 1:
svc_getargs(transp, xdr_receive_data, (unsigned char *) &buffer);
svc_sendreply(transp, xdr_send_data, (unsigned char *) buffer);
free(buffer->data);
free(buffer);
return;
default:
svcerr_noproc(transp);
return;
}
}
int
xdr_receive_data(XDR *xdrs, struct data **buffer)
{
struct data *bp;
int i, rc;
char *p;
bp = *buffer = (struct data *) malloc(sizeof(struct data));
rc = xdr_long(xdrs, &(bp->address));
rc = rc && xdr_long(xdrs, &bp->request_id);
rc = rc && xdr_long(xdrs, &bp->data_length);
p = (*buffer)->data = (char *) malloc(bp->data_length);
for (i=0; rc && i < bp->data_length; p++, i++)
rc = xdr_char(xdrs, p);
return(rc);
}
int
xdr_send_data(XDR *xdrs, struct data *buffer)
{
int i, rc;
char *p;
rc = xdr_long(xdrs, &buffer->address);
rc = rc && xdr_long(xdrs, &buffer->request_id);
rc = rc && xdr_long(xdrs, &buffer->data_length);
for (i=0, p=buffer->data; rc && i < buffer->data_length; i++, p++)
rc = xdr_char(xdrs, p);
return(rc);
}
void breakpoint(void)
{
if (debug)
printf("breakpoint\n");
}