]> andersk Git - moira.git/blob - server/mr_glue.c
Oracle and Solaris/POSIX changes
[moira.git] / server / mr_glue.c
1 /*
2  *      $Source$
3  *      $Author$
4  *      $Header$
5  *
6  *      Copyright (C) 1987 by the Massachusetts Institute of Technology
7  *      For copying and distribution information, please see the file
8  *      <mit-copyright.h>.
9  *
10  *      Glue routines to allow the database stuff to be linked in to
11  *      a program expecting a library level interface.
12  */
13
14 #ifndef lint
15 static char *rcsid_mr_glue_c = "$Header$";
16 #endif lint
17
18 #include <mit-copyright.h>
19 #include <sys/types.h>
20 #include <sys/signal.h>
21 #include <sys/wait.h>
22 #include <krb_et.h>
23 #include <pwd.h>
24 #include "mr_server.h"
25 #include "query.h"
26
27 static int already_connected = 0;
28
29 #define CHECK_CONNECTED { if (!already_connected) return MR_NOT_CONNECTED; }
30
31 static client pseudo_client;
32 extern int errno;
33 extern char *whoami;
34 extern time_t now;
35 void reapchild();
36
37 mr_connect(server)
38 char *server;
39 {
40     register int status;
41     extern int query_timeout;
42     struct sigaction action;
43
44     if (already_connected) return MR_ALREADY_CONNECTED;
45
46     initialize_sms_error_table();
47     initialize_krb_error_table();
48     memset((char *)&pseudo_client, 0, sizeof(pseudo_client)); /* XXX */
49
50     query_timeout = 0;
51     status =  mr_open_database();
52     if (!status) already_connected = 1;
53
54     action.sa_flags = 0;
55     sigemptyset(&action.sa_mask);
56     sigaddset(&action.sa_mask, SIGCHLD);
57     action.sa_handler = reapchild;
58     if (sigaction(SIGCHLD, &action, NULL) < 0) {
59       com_err(whoami, errno, "Unable to establish signal handlers.");
60       exit(1);
61     }
62     return status;
63 }
64
65 mr_disconnect()
66 {
67     CHECK_CONNECTED;
68     mr_close_database();
69     already_connected = 0;
70     return 0;
71 }
72
73 mr_noop()
74 {
75     CHECK_CONNECTED;
76     return 0;
77 }
78 /*
79  * This routine is rather bogus, as it only fills in who you claim to be.
80  */
81 mr_auth(prog)
82 char *prog;
83 {
84     struct passwd *pw;
85     extern char *krb_realm;
86     char buf[1024], *strsave();
87     
88     CHECK_CONNECTED;
89     pw = getpwuid(getuid());
90     if (!pw) return (KDC_PR_UNKNOWN + ERROR_TABLE_BASE_krb); /* XXX hack (we 
91                                                     * need an extended 
92                                                     * error code table)
93                                                     */
94     strcpy(pseudo_client.kname.name, pw->pw_name);
95     krb_get_lrealm(pseudo_client.kname.realm, 1);
96     krb_realm = pseudo_client.kname.realm;
97
98     strcpy(buf, pw->pw_name);
99     strcat(buf, "@");
100     strcat(buf, pseudo_client.kname.realm);
101     strcpy(pseudo_client.clname, buf);
102     pseudo_client.users_id = 0;
103     name_to_id(pseudo_client.kname.name, USERS_TABLE, &pseudo_client.users_id);
104     pseudo_client.client_id = pseudo_client.users_id;
105     strncpy(pseudo_client.entity, prog, 8);
106     pseudo_client.args = (mr_params *) malloc(sizeof(mr_params));
107     pseudo_client.args->mr_version_no = MR_VERSION_2;
108     return 0;
109 }
110
111 struct hint {
112     int (*proc)();
113     char *hint;
114 };
115
116 callback(argc, argv, arg)
117 int argc;
118 char **argv;
119 struct hint *arg;
120 {
121     if (mr_trim_args(argc, argv) == MR_NO_MEM) {
122         com_err(whoami, MR_NO_MEM, "while trimmming args");
123     }
124     (*arg->proc)(argc, argv, arg->hint);
125 }
126
127
128 int mr_query(name, argc, argv, callproc, callarg)
129     char *name;         /* Query name */
130     int argc;           /* Arg count */
131     char **argv;                /* Args */
132     int (*callproc)();  /* Callback procedure */
133     char *callarg;              /* Callback argument */
134 {
135     struct hint hints;
136
137     time(&now);
138     hints.proc = callproc;
139     hints.hint = callarg;
140     next_incremental();
141     return mr_process_query(&pseudo_client, name, argc,
142                             mr_copy_args(argv, argc), callback, &hints);
143
144 }
145
146 int mr_access(name, argc, argv)
147     char *name;                 /* Query name */
148     int argc;                   /* Arg count */
149     char **argv;                /* Args */
150 {
151     time(&now);
152     return mr_check_access(&pseudo_client, name, argc,
153                            mr_copy_args(argv, argc));
154 }
155
156 int mr_query_internal(argc, argv, callproc, callarg)
157     int argc;
158     char **argv;
159     int (*callproc)();
160     char *callarg;
161 {
162     struct hint hints;
163
164     time(&now);
165     hints.proc = callproc;
166     hints.hint = callarg;
167     next_incremental();
168     return mr_process_query(&pseudo_client, argv[0], argc-1,
169                             mr_copy_args(argv+1, argc-1), callback, &hints);
170 }
171
172 int mr_access_internal(argc, argv)
173     int argc;
174     char **argv;
175 {
176     time(&now);
177     return mr_check_access(&pseudo_client, argv[0], argc-1,
178                            mr_copy_args(argv+1, argc-1));
179 }
180
181 mr_shutdown(why)
182     char *why;
183 {
184     fprintf(stderr, "Sorry, not implemented\n");
185 }
186
187
188 /* trigger_dcm is also used as a followup routine to the 
189  * set_server_host_override query, hence the two dummy arguments.
190  */
191
192 struct query pseudo_query = {
193         "trigger_dcm",
194         "tdcm",
195 };
196
197 trigger_dcm(dummy0, dummy1, cl)
198         int dummy0, dummy1;
199         client *cl;
200 {
201         register int pid, status;
202         char prog[128];
203         
204         if (status = check_query_access(&pseudo_query, 0, cl))
205             return(status);
206
207         sprintf(prog, "%s/startdcm", BIN_DIR);
208         pid = vfork();
209         switch (pid) {
210         case 0:
211                 execl(prog, "startdcm", 0);
212                 exit(1);
213                 
214         case -1:
215                 return(errno);
216
217         default:
218                 return(MR_SUCCESS);
219         }
220 }
221
222
223 void reapchild()
224 {
225     int status, pid;
226
227     while ((pid = waitpid(-1, &status, WNOHANG)) > 0) {
228         if (pid == inc_pid) {
229             inc_running = 0;
230             next_incremental();
231         }
232         if  (WTERMSIG(status) != 0 || WEXITSTATUS(status) != 0)
233           com_err(whoami, 0, "%d: child exits with signal %d status %d",
234                   pid, WTERMSIG(status), WEXITSTATUS(status));
235     }
236 }
This page took 0.048276 seconds and 5 git commands to generate.