Subversion Repositories planix.SVN

Rev

Rev 2 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 - 1
#include "all.h"
2
 
3
typedef struct Rpcconn	Rpcconn;
4
 
5
struct Rpcconn
6
{
7
	int	data;
8
	int	ctl;
9
	Rpccall	cmd;
10
	Rpccall	reply;
11
	uchar	rpcbuf[8192];
12
	uchar	argbuf[8192];
13
};
14
 
15
void	putauth(char*, Auth*);
16
int	rpccall(Rpcconn*, int);
17
 
18
int	rpcdebug;
19
 
20
Rpcconn	r;
21
char *	mach;
22
 
23
void
24
main(int argc, char **argv)
25
{
26
	char addr[64], dir[64], name[128];
27
	char buf[33], *p;
28
	uchar *dataptr, *argptr;
29
	int i, fd, n, remport;
30
 
31
	ARGBEGIN{
32
	case 'm':
33
		mach = ARGF();
34
		break;
35
	case 'D':
36
		++rpcdebug;
37
		break;
38
	}ARGEND
39
	if(argc != 1)
40
		exits("usage");
41
 
42
	snprint(addr, sizeof addr, "udp!%s!111", argv[0]);
43
	r.data = dial(addr, 0, dir, &r.ctl);
44
	if(r.data < 0){
45
		fprint(2, "dial %s: %r\n", addr);
46
		exits("dial");
47
	}
48
	if(rpcdebug)
49
		fprint(2, "dial %s: dir=%s\n", addr, dir);
50
	if(fprint(r.ctl, "headers") < 0){
51
		fprint(2, "can't set header mode: %r\n");
52
		exits("headers");
53
	}
54
	sprint(name, "%s/remote", dir);
55
	fd = open(name, OREAD);
56
	if(fd < 0){
57
		fprint(2, "can't open %s: %r\n", name);
58
		exits("remote");
59
	}
60
	n = read(fd, buf, sizeof buf-1);
61
	if(n < 0){
62
		fprint(2, "can't read %s: %r\n", name);
63
		exits("remote");
64
	}
65
	close(fd);
66
	buf[n] = 0;
67
	p = buf;
68
	r.cmd.host = 0;
69
	for(i=0; i<4; i++, p++)
70
		r.cmd.host = (r.cmd.host<<8)|strtol(p, &p, 10);
71
	r.cmd.port = strtol(p, 0, 10);
72
	fprint(2, "host=%ld.%ld.%ld.%ld, port=%lud\n",
73
		(r.cmd.host>>24)&0xff, (r.cmd.host>>16)&0xff,
74
		(r.cmd.host>>8)&0xff, r.cmd.host&0xff, r.cmd.port);
75
	fprint(r.ctl, "disconnect");
76
 
77
	r.cmd.xid = time(0);
78
	r.cmd.mtype = CALL;
79
	r.cmd.rpcvers = 2;
80
	r.cmd.args = r.argbuf;
81
	if(mach)
82
		putauth(mach, &r.cmd.cred);
83
 
84
	r.cmd.prog = 100000;	/* portmapper */
85
	r.cmd.vers = 2;		/* vers */
86
	r.cmd.proc = 3;		/* getport */
87
	dataptr = r.cmd.args;
88
 
89
	PLONG(100005);		/* mount */
90
	PLONG(1);		/* vers */
91
	PLONG(IPPROTO_UDP);
92
	PLONG(0);
93
 
94
	i = rpccall(&r, dataptr-(uchar*)r.cmd.args);
95
	if(i != 4)
96
		exits("trouble");
97
	argptr = r.reply.results;
98
	remport = GLONG();
99
	fprint(2, "remote port = %d\n", remport);
100
 
101
	r.cmd.port = remport;
102
	r.cmd.prog = 100005;	/* mount */
103
	r.cmd.vers = 1;		/* vers */
104
	r.cmd.proc = 0;		/* null */
105
	dataptr = r.cmd.args;
106
 
107
	i = rpccall(&r, dataptr-(uchar*)r.cmd.args);
108
	if(i != 0)
109
		exits("trouble");
110
	fprint(2, "OK ping mount\n");
111
 
112
	r.cmd.prog = 100005;	/* mount */
113
	r.cmd.vers = 1;		/* vers */
114
	r.cmd.proc = 5;		/* export */
115
	dataptr = r.cmd.args;
116
 
117
	i = rpccall(&r, dataptr-(uchar*)r.cmd.args);
118
	fprint(2, "export: %d bytes returned\n", i);
119
	argptr = r.reply.results;
120
	while (GLONG() != 0) {
121
		n = GLONG();
122
		p = GPTR(n);
123
		print("%.*s\n", utfnlen(p, n), p);
124
		while (GLONG() != 0) {
125
			n = GLONG();
126
			p = GPTR(n);
127
			print("\t%.*s\n", utfnlen(p, n), p);
128
		}
129
	}
130
 
131
	exits(0);
132
}
133
 
134
void
135
putauth(char *mach, Auth *a)
136
{
137
	uchar *dataptr;
138
	long stamp = time(0);
139
	int n = strlen(mach);
140
 
141
	dataptr = realloc(a->data, 2*4+ROUNDUP(n)+4*4);
142
	a->data = dataptr;
143
	a->flavor = AUTH_UNIX;
144
	PLONG(stamp);
145
	PLONG(n);
146
	PPTR(mach, n);
147
	PLONG(0);
148
	PLONG(1);
149
	PLONG(1);
150
	PLONG(0);
151
	a->count = dataptr - (uchar*)a->data;
152
}
153
 
154
int
155
rpccall(Rpcconn *r, int narg)
156
{
157
	int n;
158
 
159
	r->cmd.xid++;
160
	n = rpcS2M(&r->cmd, narg, r->rpcbuf);
161
	if(rpcdebug)
162
		rpcprint(2, &r->cmd);
163
	if(write(r->data, r->rpcbuf, n) < 0){
164
		fprint(2, "rpc write: %r\n");
165
		exits("rpc");
166
	}
167
	n = read(r->data, r->rpcbuf, sizeof r->rpcbuf);
168
	if(n < 0){
169
		fprint(2, "rpc read: %r\n");
170
		exits("rpc");
171
	}
172
	if(rpcM2S(r->rpcbuf, &r->reply, n) != 0){
173
		fprint(2, "rpc reply format error\n");
174
		exits("rpc");
175
	}
176
	if(rpcdebug)
177
		rpcprint(2, &r->reply);
178
	if(r->reply.mtype != REPLY || r->reply.stat != MSG_ACCEPTED ||
179
	   r->reply.astat != SUCCESS){
180
		fprint(2, "rpc mtype, stat, astat = %ld, %ld, %ld\n",
181
			r->reply.mtype, r->reply.stat, r->reply.astat);
182
		exits("rpc");
183
	}
184
	return n - (((uchar *)r->reply.results) - r->rpcbuf);
185
}