1 /* Low-level protocol for MCFS.
3 Copyright (C) 1995, 1996 Miguel de Icaza
5 This program is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Library General Public License
7 as published by the Free Software Foundation; either version 2 of
8 the License, or (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU Library General Public License for more details.
15 You should have received a copy of the GNU Library General Public
16 License along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
28 #include <sys/types.h>
30 #include <sys/socket.h>
31 #include <netinet/in.h>
32 #ifdef HAVE_ARPA_INET_H
33 #include <arpa/inet.h>
38 #include <rpc/pmap_prot.h>
39 #ifdef HAVE_RPC_PMAP_CLNT_H
40 #include <rpc/pmap_clnt.h>
50 #define CHECK_SIG_PIPE(sock) if (got_sigpipe) \
51 { tcp_invalidate_socket (sock); return got_sigpipe = 0; }
53 extern void tcp_invalidate_socket (int);
54 extern void vfs_die (char *);
56 /* Reads a block on dest for len bytes from sock */
57 /* Returns a boolean indicating the success status */
59 socket_read_block (int sock
, char *dest
, int len
)
63 for (nread
= 0; nread
< len
;) {
64 n
= read (sock
, dest
+ nread
, len
- nread
);
66 tcp_invalidate_socket (sock
);
75 socket_write_block (int sock
, char *buffer
, int len
)
79 for (left
= len
; left
> 0;) {
80 status
= write (sock
, buffer
, left
);
81 CHECK_SIG_PIPE (sock
);
91 rpc_send (int sock
, ...)
93 long int tmp
, len
, cmd
;
100 cmd
= va_arg (ap
, int);
107 tmp
= htonl (va_arg (ap
, int));
108 write (sock
, &tmp
, sizeof (tmp
));
109 CHECK_SIG_PIPE (sock
);
113 text
= va_arg (ap
, char *);
116 write (sock
, &tmp
, sizeof (tmp
));
117 CHECK_SIG_PIPE (sock
);
118 write (sock
, text
, len
);
119 CHECK_SIG_PIPE (sock
);
123 len
= va_arg (ap
, int);
124 text
= va_arg (ap
, char *);
126 write (sock
, text
, len
);
127 CHECK_SIG_PIPE (sock
);
131 vfs_die ("Unknown rpc message\n");
137 rpc_get (int sock
, ...)
140 char *text
, **str_dest
;
147 cmd
= va_arg (ap
, int);
154 if (socket_read_block (sock
, (char *) &tmp
, sizeof (tmp
)) == 0) {
158 dest
= va_arg (ap
, int *);
162 /* returns an allocated string */
163 case RPC_LIMITED_STRING
:
165 if (socket_read_block (sock
, (char *) &tmp
, sizeof (tmp
)) == 0) {
170 if (cmd
== RPC_LIMITED_STRING
)
171 if (len
> 16 * 1024) {
175 if (len
> 128 * 1024)
178 /* Don't use glib functions here - this code is used by mcserv */
179 text
= malloc (len
+ 1);
180 if (socket_read_block (sock
, text
, len
) == 0) {
187 str_dest
= va_arg (ap
, char **);
192 len
= va_arg (ap
, int);
193 text
= va_arg (ap
, char *);
194 if (socket_read_block (sock
, text
, len
) == 0) {
201 vfs_die ("Unknown rpc message\n");
205 #endif /* WITH_MCFS */