r1277: rename struct server_context to smbsrv_ontext
[jelmer/samba4-debian.git] / source / smbd / process_single.c
1 /* 
2    Unix SMB/CIFS implementation.
3    process model: process (1 process handles all client connections)
4    Copyright (C) Andrew Tridgell 2003
5    Copyright (C) James J Myers 2003 <myersjj@samba.org>
6    
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.
11    
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.
16    
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.
20 */
21
22 #include "includes.h"
23
24 /*
25   called when the process model is selected
26 */
27 static void model_startup(void)
28 {
29         smbd_process_init();
30 }
31
32 /*
33   called when a listening socket becomes readable
34 */
35 static void accept_connection(struct event_context *ev, struct fd_event *fde, time_t t, uint16_t flags)
36 {
37         int accepted_fd;
38         struct sockaddr addr;
39         socklen_t in_addrlen = sizeof(addr);
40         struct model_ops *model_ops = fde->private;
41         
42         /* accept an incoming connection. */
43         accepted_fd = accept(fde->fd,&addr,&in_addrlen);
44         if (accepted_fd == -1) {
45                 DEBUG(0,("accept_connection_single: accept: %s\n",
46                          strerror(errno)));
47                 return;
48         }
49
50         /* create a smb server context and add it to out event
51            handling */
52         init_smbsession(ev, model_ops, accepted_fd, smbd_read_handler); 
53
54         /* return to event handling */
55 }
56
57
58 /*
59   called when a rpc listening socket becomes readable
60 */
61 static void accept_rpc_connection(struct event_context *ev, struct fd_event *fde, time_t t, uint16_t flags)
62 {
63         int accepted_fd;
64         struct sockaddr addr;
65         socklen_t in_addrlen = sizeof(addr);
66         
67         /* accept an incoming connection. */
68         accepted_fd = accept(fde->fd,&addr,&in_addrlen);
69         if (accepted_fd == -1) {
70                 DEBUG(0,("accept_connection_single: accept: %s\n",
71                          strerror(errno)));
72                 return;
73         }
74
75         init_rpc_session(ev, fde->private, accepted_fd); 
76 }
77
78 /* called when a SMB connection goes down */
79 static void terminate_connection(struct smbsrv_context *server, const char *reason) 
80 {
81         server_terminate(server);
82 }
83
84 /* called when a rpc connection goes down */
85 static void terminate_rpc_connection(void *r, const char *reason) 
86 {
87         rpc_server_terminate(r);
88 }
89
90 static int get_id(struct request_context *req)
91 {
92         return (int)req->smb_ctx->pid;
93 }
94
95 static void single_exit_server(struct smbsrv_context *smb, const char *reason)
96 {
97         DEBUG(1,("single_exit_server: reason[%s]\n",reason));
98 }
99
100 /*
101   initialise the single process model, registering ourselves with the process model subsystem
102  */
103 NTSTATUS process_model_single_init(void)
104 {
105         NTSTATUS ret;
106         struct model_ops ops;
107
108         ZERO_STRUCT(ops);
109
110         /* fill in our name */
111         ops.name = "single";
112
113         /* fill in all the operations */
114         ops.model_startup = model_startup;
115         ops.accept_connection = accept_connection;
116         ops.accept_rpc_connection = accept_rpc_connection;
117         ops.terminate_connection = terminate_connection;
118         ops.terminate_rpc_connection = terminate_rpc_connection;
119         ops.exit_server = single_exit_server;
120         ops.get_id = get_id;
121
122         /* register ourselves with the PROCESS_MODEL subsystem. */
123         ret = register_backend("process_model", &ops);
124         if (!NT_STATUS_IS_OK(ret)) {
125                 DEBUG(0,("Failed to register process_model 'single'!\n"));
126                 return ret;
127         }
128
129         return ret;
130 }