preparing for release of alpha-2.6
[Samba/gbeck.git] / source / lib / msrpc-agent.c
blobaa4641b70b299f2ca626ad781a40806b0b88bba5
1 /*
2 Unix SMB/Netbios implementation.
3 Version 2
4 SMB agent/socket plugin
5 Copyright (C) Andrew Tridgell 1999
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 #include "includes.h"
23 #include "rpc_parse.h"
24 #include "smb.h"
26 extern int DEBUGLEVEL;
28 static char packet[BUFFER_SIZE];
30 /****************************************************************************
31 terminate sockent connection
32 ****************************************************************************/
33 static void free_sock(void *sock)
35 if (sock != NULL)
37 struct msrpc_local *n = (struct msrpc_local*)sock;
38 msrpc_use_del(n->pipe_name, False, NULL);
42 static struct msrpc_local *init_client_connection(int c)
44 pstring buf;
45 fstring pipe_name;
46 int rl;
47 uint32 len;
48 BOOL new_con = False;
49 struct msrpc_local *n = NULL;
51 CREDS_CMD cmd;
52 prs_struct ps;
54 ZERO_STRUCT(cmd);
56 DEBUG(10,("init_client_connection: first request\n"));
58 rl = read(c, &buf, sizeof(len));
60 if (rl != sizeof(len))
62 DEBUG(0,("Unable to read length\n"));
63 dump_data(0, buf, sizeof(len));
64 return NULL;
67 len = IVAL(buf, 0);
69 if (len > sizeof(buf))
71 DEBUG(0,("length %d too long\n", len));
72 return NULL;
75 rl = read(c, buf, len);
77 if (rl < 0)
79 DEBUG(0,("Unable to read from connection\n"));
80 return NULL;
83 #ifdef DEBUG_PASSWORD
84 dump_data(100, buf, rl);
85 #endif
87 /* make a static data parsing structure from the api_fd_reply data */
88 prs_create(&ps, buf, len, 4, True);
90 if (!creds_io_cmd("creds", &cmd, &ps, 0))
92 DEBUG(0,("Unable to parse credentials\n"));
93 prs_free_data(&ps);
94 return NULL;
97 prs_free_data(&ps);
99 if (ps.offset != rl)
101 DEBUG(0,("Buffer size %d %d!\n", ps.offset, rl));
102 return NULL;
105 switch (cmd.command)
107 case AGENT_CMD_CON:
108 case AGENT_CMD_CON_ANON:
110 new_con = True;
111 break;
113 case AGENT_CMD_CON_REUSE:
115 new_con = True;
116 break;
118 default:
120 DEBUG(0,("unknown command %d\n", cmd.command));
121 return NULL;
125 if (new_con)
127 uint32 status = 0;
128 n = msrpc_use_add(pipe_name, &cmd.key, False);
130 if (n == NULL)
132 DEBUG(0,("Unable to connect to %s\n", pipe_name));
133 status = 0x1;
135 else
137 fstrcpy(n->pipe_name, pipe_name);
140 if (write(c, &status, sizeof(status)) != sizeof(status))
142 DEBUG(0,("Could not write connection down pipe.\n"));
143 if (n != NULL)
145 msrpc_use_del(pipe_name, False, NULL);
146 n = NULL;
150 return n;
153 static BOOL process_cli_sock(struct sock_redir **socks, uint32 num_socks,
154 struct sock_redir *sock)
156 struct msrpc_local *n = (struct msrpc_local*)sock->n;
157 if (n == NULL)
159 n = init_client_connection(sock->c);
160 if (n == NULL)
162 return False;
164 sock->n = (void*)n;
165 sock->s = n->fd;
167 else
169 if (!receive_smb(sock->c, packet, 0))
171 DEBUG(0,("client closed connection\n"));
172 return False;
175 if (!send_smb(sock->s, packet))
177 DEBUG(0,("server is dead\n"));
178 return False;
181 return True;
184 static BOOL process_srv_sock(struct sock_redir **socks, uint32 num_socks,
185 int fd)
187 int i;
188 if (!receive_smb(fd, packet, 0))
190 DEBUG(0,("server closed connection\n"));
191 return False;
194 DEBUG(10,("process_srv_sock:\tfd:\t%d\n", fd));
196 for (i = 0; i < num_socks; i++)
198 struct msrpc_local *n;
199 if (socks[i] == NULL || socks[i]->n == NULL)
201 continue;
203 n = (struct msrpc_local*)socks[i]->n;
204 DEBUG(10,("list:\tfd:\t%d\n",
205 socks[i]->s));
206 if (!send_smb(socks[i]->c, packet))
208 DEBUG(0,("client is dead\n"));
209 return False;
211 return True;
213 return False;
216 static int get_agent_sock(char *pipe_name)
218 fstring path;
219 fstring dir;
221 slprintf(dir, sizeof(dir)-1, "/tmp/.msrpc/.%s", pipe_name);
222 slprintf(path, sizeof(path)-1, "%s/agent", dir);
224 return create_pipe_socket(dir, S_IRUSR|S_IWUSR|S_IXUSR, path, 0);
227 void start_msrpc_agent(char *pipe_name)
229 struct vagent_ops va =
231 free_sock,
232 get_agent_sock,
233 process_cli_sock,
234 process_srv_sock,
235 NULL,
236 NULL,
240 if (sys_fork() == 0)
242 /* child */
243 va.id = pipe_name;
244 start_agent(&va);