]> andersk Git - moira.git/blame - server/qfollow.pc
eliminate use of the `register' keyword: let the compiler decide
[moira.git] / server / qfollow.pc
CommitLineData
73cf66ba 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 */
11
12#ifndef lint
13static char *rcsid_qsupport_dc = "$Header$";
14#endif lint
15
16#include <mit-copyright.h>
73cf66ba 17#include "mr_server.h"
03c05291 18#include "query.h"
73cf66ba 19#include <ctype.h>
03c05291 20#include <string.h>
73cf66ba 21#ifdef GDSS
22#include "gdss.h"
23#endif /* GDSS */
24EXEC SQL INCLUDE sqlca;
73cf66ba 25#include "qrtn.h"
26
03c05291 27extern char *whoami, *table_name[];
28extern int dbms_errno, mr_errcode;
73cf66ba 29
30EXEC SQL BEGIN DECLARE SECTION;
31extern char stmt_buf[];
32EXEC SQL END DECLARE SECTION;
33
03c05291 34static void hex_dump(unsigned char *p);
35
36EXEC SQL WHENEVER SQLERROR DO dbmserr();
73cf66ba 37
38
39/* FOLLOWUP ROUTINES */
40
03c05291 41/* generic set_modtime routine. This takes the table id from the query,
73cf66ba 42 * and will update the modtime, modby, and modwho fields in the entry in
43 * the table whose name field matches argv[0].
44 */
45
5eaef520 46int set_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 47{
5eaef520 48 char *name, *entity, *table;
49 int who;
73cf66ba 50
5eaef520 51 entity = cl->entity;
52 who = cl->client_id;
53 table = table_name[q->rtable];
54 name = argv[0];
73cf66ba 55
5eaef520 56 sprintf(stmt_buf, "UPDATE %s SET modtime = SYSDATE, modby = %d, "
57 "modwith = '%s' WHERE name = '%s'", table, who, entity, name);
58 EXEC SQL EXECUTE IMMEDIATE :stmt_buf;
73cf66ba 59
5eaef520 60 return MR_SUCCESS;
73cf66ba 61}
62
03c05291 63/* generic set_modtime_by_id routine. This takes the table id from
73cf66ba 64 * the query, and the id name from the validate record,
65 * and will update the modtime, modby, and modwho fields in the entry in
66 * the table whose id matches argv[0].
67 */
68
5eaef520 69int set_modtime_by_id(struct query *q, char *argv[], client *cl)
73cf66ba 70{
5eaef520 71 char *entity, *table, *id_name;
72 int who, id;
73
74 entity = cl->entity;
75 who = cl->client_id;
76 table = table_name[q->rtable];
77 id_name = q->validate->object_id;
78
79 id = *(int *)argv[0];
80 sprintf(stmt_buf, "UPDATE %s SET modtime = SYSDATE, modby = %d, "
81 "modwith = '%s' WHERE %s = %d", table, who, entity, id_name, id);
82 EXEC SQL EXECUTE IMMEDIATE :stmt_buf;
83 return MR_SUCCESS;
73cf66ba 84}
85
86
87/* Sets the finger modtime on a user record. The users_id will be in argv[0].
88 */
89
5eaef520 90int set_finger_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 91{
5eaef520 92 EXEC SQL BEGIN DECLARE SECTION;
93 int users_id, who;
94 char *entity;
95 EXEC SQL END DECLARE SECTION;
73cf66ba 96
5eaef520 97 entity = cl->entity;
98 who = cl->client_id;
99 users_id = *(int *)argv[0];
73cf66ba 100
5eaef520 101 EXEC SQL UPDATE users SET fmodtime = SYSDATE, fmodby = :who,
102 fmodwith = :entity WHERE users_id = :users_id;
73cf66ba 103
5eaef520 104 return MR_SUCCESS;
73cf66ba 105}
106
107
108/* Sets the pobox modtime on a user record. The users_id will be in argv[0].
109 */
110
5eaef520 111int set_pobox_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 112{
5eaef520 113 EXEC SQL BEGIN DECLARE SECTION;
114 int users_id, who;
115 char *entity;
116 EXEC SQL END DECLARE SECTION;
73cf66ba 117
5eaef520 118 entity = cl->entity;
119 who = cl->client_id;
120 users_id = *(int *)argv[0];
73cf66ba 121
5eaef520 122 EXEC SQL UPDATE users SET pmodtime = SYSDATE, pmodby = :who,
123 pmodwith = :entity WHERE users_id = :users_id;
73cf66ba 124
5eaef520 125 return MR_SUCCESS;
73cf66ba 126}
127
128
129/* Like set_modtime, but uppercases the name first.
130 */
131
5eaef520 132int set_uppercase_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 133{
5eaef520 134 char *name, *entity, *table;
135 int who;
73cf66ba 136
5eaef520 137 entity = cl->entity;
138 who = cl->client_id;
139 table = table_name[q->rtable];
140 name = argv[0];
73cf66ba 141
5eaef520 142 sprintf(stmt_buf, "UPDATE %s SET modtime = SYSDATE, modby = %d, "
143 "modwith = '%s' WHERE name = UPPER('%s')", table, who, entity, name);
144 EXEC SQL EXECUTE IMMEDIATE :stmt_buf;
73cf66ba 145
5eaef520 146 return MR_SUCCESS;
73cf66ba 147}
148
149
150/* Sets the modtime on the machine whose mach_id is in argv[0]. This routine
151 * is necessary for add_machine_to_cluster becuase the table that query
152 * operates on is "mcm", not "machine".
153 */
154
5eaef520 155int set_mach_modtime_by_id(struct query *q, char *argv[], client *cl)
73cf66ba 156{
5eaef520 157 EXEC SQL BEGIN DECLARE SECTION;
158 char *entity;
159 int who, id;
160 EXEC SQL END DECLARE SECTION;
161
162 entity = cl->entity;
163 who = cl->client_id;
164 id = *(int *)argv[0];
165 EXEC SQL UPDATE machine SET modtime = SYSDATE, modby = :who,
166 modwith = :entity WHERE mach_id = :id;
167
168 return MR_SUCCESS;
73cf66ba 169}
170
171
172/* Sets the modtime on the cluster whose mach_id is in argv[0]. This routine
173 * is necessary for add_cluster_data and delete_cluster_data becuase the
174 * table that query operates on is "svc", not "cluster".
175 */
176
5eaef520 177int set_cluster_modtime_by_id(struct query *q, char *argv[], client *cl)
73cf66ba 178{
5eaef520 179 EXEC SQL BEGIN DECLARE SECTION;
180 char *entity;
181 int who, id;
182 EXEC SQL END DECLARE SECTION;
183
184 entity = cl->entity;
185 who = cl->client_id;
186
187 id = *(int *)argv[0];
188 EXEC SQL UPDATE clusters SET modtime = SYSDATE, modby = :who,
189 modwith = :entity WHERE clu_id = :id;
190 return MR_SUCCESS;
73cf66ba 191}
192
193
194/* sets the modtime on the serverhost where the service name is in argv[0]
195 * and the mach_id is in argv[1].
196 */
197
5eaef520 198int set_serverhost_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 199{
5eaef520 200 EXEC SQL BEGIN DECLARE SECTION;
201 char *entity, *serv;
202 int who, id;
203 EXEC SQL END DECLARE SECTION;
204
205 entity = cl->entity;
206 who = cl->client_id;
207
208 serv = argv[0];
209 id = *(int *)argv[1];
210 EXEC SQL UPDATE serverhosts
211 SET modtime = SYSDATE, modby = :who, modwith = :entity
212 WHERE service = :serv AND mach_id = :id;
213 return MR_SUCCESS;
73cf66ba 214}
215
216
217/* sets the modtime on the nfsphys where the mach_id is in argv[0] and the
218 * directory name is in argv[1].
219 */
220
5eaef520 221int set_nfsphys_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 222{
5eaef520 223 EXEC SQL BEGIN DECLARE SECTION;
224 char *entity, *dir;
225 int who, id;
226 EXEC SQL END DECLARE SECTION;
227
228 entity = cl->entity;
229 who = cl->client_id;
230
231 id = *(int *)argv[0];
232 dir = argv[1];
233 EXEC SQL UPDATE nfsphys SET modtime = SYSDATE, modby = :who,
234 modwith = :entity WHERE dir = :dir AND mach_id = :id;
235 return MR_SUCCESS;
73cf66ba 236}
237
238
239/* sets the modtime on a filesystem, where argv[0] contains the filesys
240 * label.
241 */
242
5eaef520 243int set_filesys_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 244{
5eaef520 245 EXEC SQL BEGIN DECLARE SECTION;
246 char *label, *entity;
247 int who;
248 extern int _var_phys_id;
249 EXEC SQL END DECLARE SECTION;
250
251 entity = cl->entity;
252 who = cl->client_id;
253
254 label = argv[0];
255 if (!strcmp(q->shortname, "ufil"))
256 label = argv[1];
257
258 EXEC SQL UPDATE filesys SET modtime = SYSDATE, modby = :who,
259 modwith = :entity, phys_id = :_var_phys_id
260 WHERE label = :label;
261 return MR_SUCCESS;
73cf66ba 262}
263
264
265/* sets the modtime on a zephyr class, where argv[0] contains the class
266 * name.
267 */
268
5eaef520 269int set_zephyr_modtime(struct query *q, char *argv[], client *cl)
73cf66ba 270{
5eaef520 271 EXEC SQL BEGIN DECLARE SECTION;
272 char *class, *entity;
273 int who;
274 EXEC SQL END DECLARE SECTION;
73cf66ba 275
5eaef520 276 entity = cl->entity;
277 who = cl->client_id;
73cf66ba 278
5eaef520 279 class = argv[0];
73cf66ba 280
5eaef520 281 EXEC SQL UPDATE zephyr SET modtime = SYSDATE, modby = :who,
282 modwith = :entity WHERE class = :class;
73cf66ba 283
5eaef520 284 return MR_SUCCESS;
73cf66ba 285}
286
287
288/* fixes the modby field. This will be the second to last thing in the
289 * argv, the argv length is determined from the query structure. It is
290 * passed as a pointer to an integer. This will either turn it into a
291 * username, or # + the users_id.
292 */
5eaef520 293int followup_fix_modby(struct query *q, struct save_queue *sq,
294 struct validate *v, int (*action)(), int actarg,
295 client *cl)
73cf66ba 296{
44d12d58 297 int i, j;
5eaef520 298 char **argv;
299 int id, status;
300
301 i = q->vcnt - 2;
302 while (sq_get_data(sq, &argv))
303 {
304 id = atoi(argv[i]);
305 if (id > 0)
306 status = id_to_name(id, USERS_TABLE, &argv[i]);
307 else
308 status = id_to_name(-id, STRINGS_TABLE, &argv[i]);
309 if (status && status != MR_NO_MATCH)
310 return status;
311 (*action)(q->vcnt, argv, actarg);
312 for (j = 0; j < q->vcnt; j++)
313 free(argv[j]);
314 free(argv);
73cf66ba 315 }
5eaef520 316 sq_destroy(sq);
317 return MR_SUCCESS;
73cf66ba 318}
319
320
321/* After retrieving a user account, fix the modby field and signature.
322 * The modby field is the second to last thing in the
323 * argv, the argv length is determined from the query structure. It is
324 * passed as a pointer to an integer. This will either turn it into a
325 * username, or # + the users_id. Only "gua*" queries have a signature,
326 * these are ones with U_END return values. "gub*" queries also use this
327 * routine but don't have a signature.
328 */
5eaef520 329int followup_guax(struct query *q, struct save_queue *sq, struct validate *v,
330 int (*action)(), int actarg, client *cl)
73cf66ba 331{
44d12d58 332 int i, j;
5eaef520 333 char **argv;
73cf66ba 334#ifdef GDSS
5eaef520 335 unsigned char sigbuf[256];
336 char *kname;
337 SigInfo si;
338 EXEC SQL BEGIN DECLARE SECTION;
339 int timestamp, who, siglen;
340 char *login;
341 char rsig[256];
342 EXEC SQL VAR rsig IS STRING(256);
343 EXEC SQL END DECLARE SECTION;
73cf66ba 344#endif /* GDSS */
5eaef520 345 int id, status;
346
347 i = q->vcnt - 2;
348 while (sq_get_data(sq, &argv))
349 {
350 id = atoi(argv[i]);
351 if (id > 0)
352 status = id_to_name(id, USERS_TABLE, &argv[i]);
353 else
354 status = id_to_name(-id, STRINGS_TABLE, &argv[i]);
355 if (status && status != MR_NO_MATCH)
356 return status;
73cf66ba 357#ifdef GDSS
5eaef520 358 if (q->vcnt == U_END && strlen(argv[U_SIGNATURE]))
359 {
360 login = strtrim(argv[U_NAME]);
361 EXEC SQL SELECT signature, sigdate, sigwho
362 INTO :rsig, :timestamp, :who FROM users
363 WHERE login = :login;
364 if (dbms_errno)
365 return mr_errcode;
366 kname = malloc(1);
367 status = id_to_name(who, STRINGS_TABLE, &kname);
368 si.timestamp = timestamp;
369 si.SigInfoVersion = 0; /* XXXXX this isn't used */
370 kname_parse(si.pname, si.pinst, si.prealm, kname);
371 free(kname);
372 si.rawsig = (unsigned char *)strsave(rsig);
373 if (log_flags & LOG_GDSS)
374 com_err(whoami, 0, "rawsig length = %d, sig=\"%s\"",
375 strlen(si.rawsig), si.rawsig);
376 GDSS_Recompose(&si, sigbuf);
377 free(si.rawsig);
378 free(argv[U_SIGNATURE]);
379 argv[U_SIGNATURE] = strsave(sigbuf);
380 if (log_flags & LOG_GDSS)
381 com_err(whoami, 0, "generated signature length %d",
382 strlen(sigbuf));
73cf66ba 383 }
384#endif /* GDSS */
5eaef520 385 (*action)(q->vcnt, argv, actarg);
386 for (j = 0; j < q->vcnt; j++)
387 free(argv[j]);
388 free(argv);
73cf66ba 389 }
5eaef520 390 sq_destroy(sq);
391 return MR_SUCCESS;
73cf66ba 392}
393
394
395/**
396 ** followup_ausr - add finger and pobox entries, set_user_modtime
397 **
398 ** Inputs:
399 ** argv[0] - login (add_user)
400 ** argv[3] - last name
401 ** argv[4] - first name
402 ** argv[5] - middle name
403 **
404 **/
405
5eaef520 406int followup_ausr(struct query *q, char *argv[], client *cl)
73cf66ba 407{
5eaef520 408 EXEC SQL BEGIN DECLARE SECTION;
409 int who, status;
410 char *login, *entity, *name;
411 char fullname[129];
412 EXEC SQL END DECLARE SECTION;
73cf66ba 413#ifdef GDSS
5eaef520 414 char databuf[32], *kname_unparse();
415 EXEC SQL BEGIN DECLARE SECTION;
416 char rawsig[128];
417 int sigwho, timestamp;
418 EXEC SQL END DECLARE SECTION;
419 SigInfo si;
73cf66ba 420#endif /* GDSS */
421
5eaef520 422 /* build fullname */
423 if (strlen(argv[4]) && strlen(argv[5]))
424 sprintf(fullname, "%s %s %s", argv[4], argv[5], argv[3]);
425 else if (strlen(argv[4]))
426 sprintf(fullname, "%s %s", argv[4], argv[3]);
427 else
428 sprintf(fullname, "%s", argv[3]);
73cf66ba 429
430#ifdef GDSS
5eaef520 431 if (q->vcnt == U_END && *argv[U_SIGNATURE])
432 {
433 sprintf(databuf, "%s:%s", argv[U_NAME], argv[U_MITID]);
434 /* skip bytes for timestamp & kname */
435 si.rawsig = (unsigned char *) rawsig;
436 status = GDSS_Verify(databuf, strlen(databuf), argv[U_SIGNATURE], &si);
437 if (strlen(rawsig) > mr_sig_length)
438 {
439 com_err(whoami, 0, "GDSS signature would be truncated.");
440 return MR_INTERNAL;
73cf66ba 441 }
5eaef520 442 if (status == 0)
443 {
444 name = kname_unparse(si.pname, si.pinst, si.prealm);
445 status = name_to_id(name, STRINGS_TABLE, &sigwho);
446 if (status == MR_NO_MATCH)
447 sigwho = add_string(name);
448 else if (status)
449 return status;
450 timestamp = si.timestamp;
451 }
452 else
453 {
454 if (log_flags & LOG_GDSS)
455 hex_dump(argv[U_SIGNATURE]);
456 return gdss2et(status);
73cf66ba 457 }
5eaef520 458 }
459 else
460 {
461 rawsig[0] = '\0';
462 sigwho = 0;
463 timestamp = 0;
464 }
73cf66ba 465#endif /* GDSS */
466
5eaef520 467 login = argv[0];
468 who = cl->client_id;
469 entity = cl->entity;
73cf66ba 470
5eaef520 471 /* create finger entry, pobox & set modtime on user */
73cf66ba 472#ifdef GDSS
5eaef520 473 EXEC SQL UPDATE users
474 SET modtime = SYSDATE, modby = :who, modwith = :entity,
475 fullname = NVL(:fullname, CHR(0)), affiliation = type,
476 signature = NVL(:rawsig, CHR(0)), sigdate = :timestamp,
477 sigwho = :sigwho, fmodtime = SYSDATE, fmodby = :who,
478 fmodwith = :entity, potype = 'NONE', pmodtime = SYSDATE,
479 pmodby = :who, pmodwith = :entity
480 WHERE login = :login;
73cf66ba 481#else /* GDSS */
5eaef520 482 EXEC SQL UPDATE users
483 SET modtime = SYSDATE, modby = :who, modwith = :entity,
484 fullname = NVL(:fullname, CHR(0)), affiliation = type,
485 fmodtime = SYSDATE, fmodby = :who, fmodwith = :entity,
486 potype = 'NONE', pmodtime = SYSDATE, pmodby = :who, pmodwith = :entity
487 WHERE login = :login;
73cf66ba 488#endif /* GDSS */
489
5eaef520 490 return MR_SUCCESS;
73cf66ba 491}
492
493
494/**
03c05291 495 ** followup_uuac - do signature, set_user_modtime
73cf66ba 496 **
497 ** Inputs:
498 ** argv[0] - login (add_user)
499 ** argv[U_SIGNATURE] - sig
500 **
501 **/
502
5eaef520 503int followup_uuac(struct query *q, char *argv[], client *cl)
73cf66ba 504{
5eaef520 505 EXEC SQL BEGIN DECLARE SECTION;
506 int who, status, id;
507 char *entity, *name;
508 EXEC SQL END DECLARE SECTION;
73cf66ba 509#ifdef GDSS
5eaef520 510 char databuf[32], *kname_unparse();
511 EXEC SQL BEGIN DECLARE SECTION;
512 char rawsig[128];
513 char *login;
514 int sigwho, timestamp;
515 EXEC SQL END DECLARE SECTION;
516 SigInfo si;
73cf66ba 517#endif /* GDSS */
5eaef520 518
519 id = *(int *)argv[0];
520 who = cl->client_id;
521 entity = cl->entity;
522
73cf66ba 523#ifdef GDSS
5eaef520 524 if (q->vcnt == U_MODTIME && *argv[U_SIGNATURE + 1])
525 {
526 login = malloc(1);
527 status = id_to_name(id, USERS_TABLE, &login);
528 sprintf(databuf, "%s:%s", login, argv[U_MITID + 1]);
529 free(login);
530 /* skip bytes for timestamp & kname */
531 si.rawsig = (unsigned char *) rawsig;
532 status = GDSS_Verify(databuf, strlen(databuf), argv[U_SIGNATURE + 1],
533 &si);
534 if (strlen(rawsig) > mr_sig_length)
535 {
536 com_err(whoami, 0, "GDSS signature would be truncated.");
537 return MR_INTERNAL;
73cf66ba 538 }
5eaef520 539 if (status == 0)
540 {
541 name = kname_unparse(si.pname, si.pinst, si.prealm);
542 status = name_to_id(name, STRINGS_TABLE, &sigwho);
543 if (status == MR_NO_MATCH)
544 sigwho = add_string(name);
545 else if (status)
546 return status;
547 timestamp = si.timestamp;
548 }
549 else
550 {
551 if (log_flags & LOG_GDSS)
552 hex_dump(argv[U_SIGNATURE + 1]);
553 return gdss2et(status);
73cf66ba 554 }
5eaef520 555 }
556 else
557 {
558 rawsig[0] = '\0';
559 sigwho = 0;
560 timestamp = 0;
73cf66ba 561 }
562#endif /* GDSS */
5eaef520 563
564 /* create finger entry, pobox & set modtime on user */
73cf66ba 565
566#ifdef GDSS
5eaef520 567 EXEC SQL UPDATE users SET modtime = SYSDATE, modby = :who, modwith = :entity,
568 signature = NVL(:rawsig, CHR(0)), sigdate = :timestamp, sigwho = :sigwho
569 WHERE users_id = :id;
73cf66ba 570#else /* GDSS */
5eaef520 571 EXEC SQL UPDATE users SET modtime = SYSDATE, modby = :who, modwith = :entity
572 WHERE users_id = :id;
73cf66ba 573#endif /* GDSS */
5eaef520 574 return MR_SUCCESS;
73cf66ba 575}
5eaef520 576
73cf66ba 577/* followup_gpob: fixes argv[2] based on the IDs currently there and the
578 * type in argv[1]. Then completes the upcall to the user.
579 *
580 * argv[2] is of the form "123:234" where the first integer is the machine
581 * ID if it is a pop box, and the second is the string ID if it is an SMTP
582 * box. argv[1] should be "POP", "SMTP", or "NONE". Boxes of type NONE
583 * are skipped.
584 */
585
5eaef520 586int followup_gpob(struct query *q, struct save_queue *sq, struct validate *v,
587 int (*action)(), int actarg, client *cl)
73cf66ba 588{
5eaef520 589 char **argv;
590 char *ptype, *p;
591 int mid, sid, status, i;
592
593 /* for each row */
594 while (sq_get_data(sq, &argv))
595 {
596 mr_trim_args(2, argv);
597 ptype = argv[1];
598 p = strchr(argv[2], ':');
599 *p++ = '\0';
600 mid = atoi(argv[2]);
601 sid = atoi(p);
602
603 if (!strcmp(ptype, "POP"))
604 {
605 status = id_to_name(mid, MACHINE_TABLE, &argv[2]);
606 if (status == MR_NO_MATCH)
607 return MR_MACHINE;
608 }
609 else if (!strcmp(ptype, "SMTP"))
610 {
611 status = id_to_name(sid, STRINGS_TABLE, &argv[2]);
612 if (status == MR_NO_MATCH)
613 return MR_STRING;
73cf66ba 614 }
5eaef520 615 else /* ptype == "NONE" */
616 goto skip;
617 if (status)
618 return status;
619
620 if (!strcmp(q->shortname, "gpob"))
621 {
622 sid = atoi(argv[4]);
623 if (sid > 0)
624 status = id_to_name(sid, USERS_TABLE, &argv[4]);
625 else
626 status = id_to_name(-sid, STRINGS_TABLE, &argv[4]);
73cf66ba 627 }
5eaef520 628 if (status && status != MR_NO_MATCH)
629 return status;
73cf66ba 630
5eaef520 631 (*action)(q->vcnt, argv, actarg);
73cf66ba 632 skip:
5eaef520 633 /* free saved data */
634 for (i = 0; i < q->vcnt; i++)
635 free(argv[i]);
636 free(argv);
73cf66ba 637 }
638
5eaef520 639 sq_destroy(sq);
640 return MR_SUCCESS;
73cf66ba 641}
642
643
644/* followup_gsnt: fix the ace_name in argv[7]. argv[6] will contain the
645 * ace_type: "LIST", "USER", or "NONE". Decode the id in argv[7] into the
646 * proper name based on the type, and repace that string in the argv.
647 * Also fixes the modby field by called followup_fix_modby.
648 */
649
5eaef520 650int followup_gsnt(struct query *q, struct save_queue *sq, struct validate *v,
651 int (*action)(), int actarg, client *cl)
73cf66ba 652{
5eaef520 653 char **argv, *type;
654 int id, i, idx, status;
655
656 idx = 8;
657
658 while (sq_get_data(sq, &argv))
659 {
660 mr_trim_args(q->vcnt, argv);
661
662 id = atoi(argv[i = q->vcnt - 2]);
663 if (id > 0)
664 status = id_to_name(id, USERS_TABLE, &argv[i]);
665 else
666 status = id_to_name(-id, STRINGS_TABLE, &argv[i]);
667 if (status && status != MR_NO_MATCH)
668 return status;
669
670 id = atoi(argv[idx]);
671 type = argv[idx - 1];
672
673 if (!strcmp(type, "LIST"))
674 status = id_to_name(id, LIST_TABLE, &argv[idx]);
675 else if (!strcmp(type, "USER"))
676 status = id_to_name(id, USERS_TABLE, &argv[idx]);
677 else if (!strcmp(type, "KERBEROS"))
678 status = id_to_name(id, STRINGS_TABLE, &argv[idx]);
679 else if (!strcmp(type, "NONE"))
680 {
681 status = 0;
682 free(argv[idx]);
683 argv[idx] = strsave("NONE");
684 }
685 else
686 {
687 status = 0;
688 free(argv[idx]);
689 argv[idx] = strsave("???");
fde7313c 690 }
5eaef520 691 if (status && status != MR_NO_MATCH)
692 return status;
fde7313c 693
5eaef520 694 /* send the data */
695 (*action)(q->vcnt, argv, actarg);
fde7313c 696
5eaef520 697 /* free saved data */
698 for (i = 0; i < q->vcnt; i++)
699 free(argv[i]);
700 free(argv);
fde7313c 701 }
702
5eaef520 703 sq_destroy(sq);
704 return MR_SUCCESS;
fde7313c 705}
706
707
708/* followup_ghst: fix the ace_name in argv[12]. argv[11] will contain the
709 * ace_type: "LIST", "USER", or "NONE". Decode the id in argv[12] into the
710 * proper name based on the type, and repace that string in the argv.
711 * Also fixes the modby field by called followup_fix_modby.
712 */
713
5eaef520 714int followup_ghst(struct query *q, struct save_queue *sq, struct validate *v,
715 int (*action)(), int actarg, client *cl)
fde7313c 716{
5eaef520 717 char **argv, *type;
718 int id, i, idx, status;
719
720 while (sq_get_data(sq, &argv))
721 {
722 mr_trim_args(q->vcnt, argv);
723
724 id = atoi(argv[i = q->vcnt - 2]);
725 if (id > 0)
726 status = id_to_name(id, USERS_TABLE, &argv[i]);
727 else
728 status = id_to_name(-id, STRINGS_TABLE, &argv[i]);
729 if (status && status != MR_NO_MATCH)
730 return status;
731
732 id = atoi(argv[13]);
733 status = id_to_name(id, STRINGS_TABLE, &argv[13]);
734 if (status)
735 return status;
736 id = atoi(argv[14]);
737 status = id_to_name(id, STRINGS_TABLE, &argv[14]);
738 if (status)
739 return status;
740 id = atoi(argv[16]);
741 if (id < 0)
742 status = id_to_name(-id, STRINGS_TABLE, &argv[16]);
743 else
744 status = id_to_name(id, USERS_TABLE, &argv[16]);
745 if (status && status != MR_NO_MATCH)
746 return status;
747
748 idx = 12;
749 id = atoi(argv[idx]);
750 type = strtrim(argv[idx - 1]);
751
752 if (!strcmp(type, "LIST"))
753 status = id_to_name(id, LIST_TABLE, &argv[idx]);
754 else if (!strcmp(type, "USER"))
755 status = id_to_name(id, USERS_TABLE, &argv[idx]);
756 else if (!strcmp(type, "KERBEROS"))
757 status = id_to_name(id, STRINGS_TABLE, &argv[idx]);
758 else if (!strcmp(type, "NONE"))
759 {
760 status = 0;
761 free(argv[idx]);
762 argv[idx] = strsave("NONE");
73cf66ba 763 }
5eaef520 764 else
765 {
766 status = 0;
767 free(argv[idx]);
768 argv[idx] = strsave("???");
769 }
770 if (status && status != MR_NO_MATCH)
771 return status;
73cf66ba 772
5eaef520 773 /* send the data */
774 (*action)(q->vcnt, argv, actarg);
73cf66ba 775
5eaef520 776 /* free saved data */
777 for (i = 0; i < q->vcnt; i++)
778 free(argv[i]);
779 free(argv);
73cf66ba 780 }
781
5eaef520 782 sq_destroy(sq);
783 return MR_SUCCESS;
73cf66ba 784}
785
786
787/* followup_glin: fix the ace_name in argv[8]. argv[7] will contain the
788 * ace_type: "LIST", "USER", or "NONE". Decode the id in argv[8] into the
789 * proper name based on the type, and repace that string in the argv.
790 * Also fixes the modby field by called followup_fix_modby.
791 */
792
5eaef520 793int followup_glin(struct query *q, struct save_queue *sq, struct validate *v,
794 int (*action)(), int actarg, client *cl)
73cf66ba 795{
5eaef520 796 char **argv, *type;
797 int id, i, idx, status;
798
799 idx = 8;
800 if (!strcmp(q->shortname, "gsin"))
801 idx = 12;
802
803 while (sq_get_data(sq, &argv))
804 {
805 mr_trim_args(q->vcnt, argv);
806
807 id = atoi(argv[i = q->vcnt - 2]);
808 if (id > 0)
809 status = id_to_name(id, USERS_TABLE, &argv[i]);
810 else
811 status = id_to_name(-id, STRINGS_TABLE, &argv[i]);
812 if (status && status != MR_NO_MATCH)
813 return status;
814
815 id = atoi(argv[idx]);
816 type = argv[idx - 1];
817
818 if (!strcmp(type, "LIST"))
819 status = id_to_name(id, LIST_TABLE, &argv[idx]);
820 else if (!strcmp(type, "USER"))
821 status = id_to_name(id, USERS_TABLE, &argv[idx]);
822 else if (!strcmp(type, "KERBEROS"))
823 status = id_to_name(id, STRINGS_TABLE, &argv[idx]);
824 else if (!strcmp(type, "NONE"))
825 {
826 status = 0;
827 free(argv[idx]);
828 argv[idx] = strsave("NONE");
73cf66ba 829 }
5eaef520 830 else
831 {
832 status = 0;
833 free(argv[idx]);
834 argv[idx] = strsave("???");
835 }
836 if (status && status != MR_NO_MATCH)
837 return status;
73cf66ba 838
5eaef520 839 if (!strcmp(q->shortname, "glin") && atoi(argv[6]) == -1)
840 {
841 argv[6] = realloc(argv[6], strlen(UNIQUE_GID) + 1);
842 strcpy(argv[6], UNIQUE_GID);
73cf66ba 843 }
844
5eaef520 845 /* send the data */
846 (*action)(q->vcnt, argv, actarg);
73cf66ba 847
5eaef520 848 /* free saved data */
849 for (i = 0; i < q->vcnt; i++)
850 free(argv[i]);
851 free(argv);
73cf66ba 852 }
853
5eaef520 854 sq_destroy(sq);
855 return MR_SUCCESS;
73cf66ba 856}
857
858
859/* followup_gqot: Fix the entity name, directory name & modby fields
860 * argv[0] = filsys_id
861 * argv[1] = type
862 * argv[2] = entity_id
863 * argv[3] = ascii(quota)
864 */
865
5eaef520 866int followup_gqot(struct query *q, struct save_queue *sq, struct validate *v,
867 int (*action)(), int actarg, client *cl)
73cf66ba 868{
44d12d58 869 int j;
5eaef520 870 char **argv;
871 EXEC SQL BEGIN DECLARE SECTION;
872 int id;
873 char *name, *label;
874 EXEC SQL END DECLARE SECTION;
875 int status, idx;
876
877 if (!strcmp(q->name, "get_quota") ||
878 !strcmp(q->name, "get_quota_by_filesys"))
879 idx = 4;
880 else
881 idx = 3;
882 while (sq_get_data(sq, &argv))
883 {
884 if (idx == 4)
885 {
886 switch (argv[1][0])
887 {
73cf66ba 888 case 'U':
5eaef520 889 status = id_to_name(atoi(argv[2]), USERS_TABLE, &argv[2]);
890 break;
73cf66ba 891 case 'G':
892 case 'L':
5eaef520 893 status = id_to_name(atoi(argv[2]), LIST_TABLE, &argv[2]);
894 break;
73cf66ba 895 case 'A':
5eaef520 896 free(argv[2]);
897 argv[2] = strsave("system:anyuser");
898 break;
73cf66ba 899 default:
5eaef520 900 id = atoi(argv[2]);
901 argv[2] = malloc(8);
902 sprintf(argv[2], "%d", id);
73cf66ba 903 }
904 }
5eaef520 905 id = atoi(argv[idx]);
906 free(argv[idx]);
907 argv[idx] = malloc(256);
908 name = argv[idx];
909 if (id == 0)
910 {
911 label = argv[0];
912 EXEC SQL SELECT name INTO :name FROM filesys
913 WHERE label = :label;
73cf66ba 914 }
5eaef520 915 else
916 {
917 EXEC SQL SELECT dir INTO :name FROM nfsphys
918 WHERE nfsphys_id = :id;
73cf66ba 919 }
5eaef520 920 if (sqlca.sqlerrd[2] != 1)
921 sprintf(argv[idx], "#%d", id);
922
923 id = atoi(argv[idx + 3]);
924 if (id > 0)
925 status = id_to_name(id, USERS_TABLE, &argv[idx + 3]);
926 else
927 status = id_to_name(-id, STRINGS_TABLE, &argv[idx + 3]);
928 if (status && status != MR_NO_MATCH)
929 return status;
930 (*action)(q->vcnt, argv, actarg);
931 for (j = 0; j < q->vcnt; j++)
932 free(argv[j]);
933 free(argv);
73cf66ba 934 }
5eaef520 935 sq_destroy(sq);
936 return MR_SUCCESS;
73cf66ba 937}
938
939
940/* followup_aqot: Add allocation to nfsphys after creating quota.
941 * argv[0] = filsys_id
942 * argv[1] = type if "add_quota" or "update_quota"
943 * argv[2 or 1] = id
944 * argv[3 or 2] = ascii(quota)
945 */
946
5eaef520 947int followup_aqot(struct query *q, char *argv[], client *cl)
73cf66ba 948{
5eaef520 949 EXEC SQL BEGIN DECLARE SECTION;
950 int quota, id, fs, who, physid, table;
951 char *entity, *qtype, *tname;
952 EXEC SQL END DECLARE SECTION;
953 char incr_qual[60];
954 char *incr_argv[2];
955 int status;
956
957 table = q->rtable;
958 tname = table_name[table];
959 fs = *(int *)argv[0];
960 EXEC SQL SELECT phys_id INTO :physid FROM filesys
961 WHERE filsys_id = :fs;
962 if (dbms_errno)
963 return mr_errcode;
964
965 if (!strcmp(q->shortname, "aqot") || !strcmp(q->shortname, "uqot"))
966 {
967 qtype = argv[1];
968 id = *(int *)argv[2];
969 quota = atoi(argv[3]);
970 sprintf(incr_qual, "q.filsys_id = %d", fs);
971 }
972 else
973 {
974 qtype = "USER";
975 id = *(int *)argv[1];
976 quota = atoi(argv[2]);
977 sprintf(incr_qual, "q.filsys_id = %d AND q.type = '%s' AND "
978 "q.entity_id = %d", fs, qtype, id);
73cf66ba 979 }
980
5eaef520 981 /* quota case of incremental_{before|after} only looks at slot 1 */
982 incr_argv[1] = qtype;
983
984 /* Follows one of many possible gross hacks to fix these particular
985 * conflicts between what is possible in the query table and what
986 * is possible in SQL.
987 */
988 if (q->type == APPEND)
989 {
990 incremental_clear_before();
991 EXEC SQL INSERT INTO quota
992 (filsys_id, type, entity_id, quota, phys_id)
993 VALUES (:fs, NVL(:qtype, CHR(0)), :id, :quota, :physid);
994 incremental_after(table, incr_qual, incr_argv);
995 }
996 else
997 {
998 incremental_before(table, incr_qual, incr_argv);
999 EXEC SQL UPDATE quota SET quota = :quota
1000 WHERE filsys_id = :fs AND type = :qtype AND entity_id = :id;
1001 status = mr_errcode;
1002 incremental_after(table, incr_qual, incr_argv);
73cf66ba 1003 }
1004
5eaef520 1005 if (dbms_errno)
1006 return mr_errcode;
1007 flush_name(argv[0], table);
1008 if (q->type == APPEND)
1009 {
1010 EXEC SQL UPDATE tblstats SET appends = appends + 1, modtime = SYSDATE
1011 WHERE table_name = :tname;
1012 }
1013 else
1014 {
1015 EXEC SQL UPDATE tblstats SET updates = updates + 1, modtime = SYSDATE
1016 WHERE table_name = :tname;
73cf66ba 1017 }
5eaef520 1018
1019 /* Proceed with original followup */
1020 who = cl->client_id;
1021 entity = cl->entity;
1022
1023 EXEC SQL UPDATE quota
1024 SET modtime = SYSDATE, modby = :who, modwith = :entity
1025 WHERE filsys_id = :fs and type = :qtype and entity_id = :id;
1026 EXEC SQL UPDATE nfsphys SET allocated = allocated + :quota
1027 WHERE nfsphys_id = :physid;
1028 if (dbms_errno)
1029 return mr_errcode;
1030 return MR_SUCCESS;
73cf66ba 1031}
1032
1033
1034/* Necessitated by the requirement of a correlation name by the incremental
5eaef520 1035 * routines, since query table deletes don't provide one.
73cf66ba 1036 */
5eaef520 1037int followup_dqot(struct query *q, char **argv, client *cl)
73cf66ba 1038{
5eaef520 1039 char *qtype;
1040 int id, fs, table;
1041 char *incr_argv[2];
1042 EXEC SQL BEGIN DECLARE SECTION;
1043 char incr_qual[80], *tname;
1044 EXEC SQL END DECLARE SECTION;
1045
1046 table = q->rtable;
1047 tname = table_name[table];
1048 fs = *(int *)argv[0];
1049 if (!strcmp(q->shortname, "dqot"))
1050 {
1051 qtype = argv[1];
1052 id = *(int *)argv[2];
1053 }
1054 else
1055 {
1056 qtype = "USER";
1057 id = *(int *)argv[1];
73cf66ba 1058 }
5eaef520 1059 sprintf(incr_qual, "q.filsys_id = %d AND q.type = '%s' AND q.entity_id = %d",
1060 fs, qtype, id);
73cf66ba 1061
5eaef520 1062 /* quota case of incremental_{before|after} only looks at slot 1 */
1063 incr_argv[1] = qtype;
73cf66ba 1064
5eaef520 1065 incremental_before(table, incr_qual, incr_argv);
1066 EXEC SQL DELETE FROM quota q WHERE q.filsys_id = :fs AND q.type = :qtype
1067 AND q.entity_id = :id;
1068 incremental_clear_after();
73cf66ba 1069
5eaef520 1070 if (dbms_errno)
1071 return mr_errcode;
1072 flush_name(argv[0], table);
73cf66ba 1073
5eaef520 1074 EXEC SQL UPDATE tblstats SET deletes = deletes + 1, modtime = SYSDATE
1075 WHERE table_name = :tname;
1076 return MR_SUCCESS;
73cf66ba 1077}
1078
1079
5eaef520 1080int followup_gpce(struct query *q, struct save_queue *sq, struct validate *v,
1081 int (*action)(), int actarg, client *cl)
73cf66ba 1082{
44d12d58 1083 int i, j;
5eaef520 1084 char **argv;
1085 int id, status;
1086
1087 i = q->vcnt - 2;
1088 while (sq_get_data(sq, &argv))
1089 {
1090 id = atoi(argv[PCAP_QSERVER]);
1091 status = id_to_name(id, MACHINE_TABLE, &argv[PCAP_QSERVER]);
1092 if (status)
1093 return status;
1094 id = atoi(argv[i]);
1095 if (id > 0)
1096 status = id_to_name(id, USERS_TABLE, &argv[i]);
1097 else
1098 status = id_to_name(-id, STRINGS_TABLE, &argv[i]);
1099 if (status && status != MR_NO_MATCH)
1100 return status;
1101 (*action)(q->vcnt, argv, actarg);
1102 for (j = 0; j < q->vcnt; j++)
1103 free(argv[j]);
1104 free(argv);
73cf66ba 1105 }
5eaef520 1106 sq_destroy(sq);
1107 return MR_SUCCESS;
73cf66ba 1108}
1109
1110
1111/* followup_gzcl:
1112 */
1113
5eaef520 1114int followup_gzcl(struct query *q, struct save_queue *sq, struct validate *v,
1115 int (*action)(), int actarg, client *cl)
73cf66ba 1116{
5eaef520 1117 int id, i, status;
1118 char **argv;
1119
1120 while (sq_get_data(sq, &argv))
1121 {
1122 mr_trim_args(q->vcnt, argv);
1123
1124 id = atoi(argv[i = q->vcnt - 2]);
1125 if (id > 0)
1126 status = id_to_name(id, USERS_TABLE, &argv[i]);
1127 else
1128 status = id_to_name(-id, STRINGS_TABLE, &argv[i]);
1129 if (status && status != MR_NO_MATCH)
1130 return status;
1131
1132 for (i = 1; i < 8; i += 2)
1133 {
1134 id = atoi(argv[i + 1]);
1135 if (!strcmp(argv[i], "LIST"))
1136 status = id_to_name(id, LIST_TABLE, &argv[i + 1]);
1137 else if (!strcmp(argv[i], "USER"))
1138 status = id_to_name(id, USERS_TABLE, &argv[i + 1]);
1139 else if (!strcmp(argv[i], "KERBEROS"))
1140 status = id_to_name(id, STRINGS_TABLE, &argv[i + 1]);
1141 else if (!strcmp(argv[i], "NONE"))
1142 {
1143 status = 0;
1144 free(argv[i + 1]);
1145 argv[i + 1] = strsave("NONE");
73cf66ba 1146 }
5eaef520 1147 else
1148 {
1149 status = 0;
1150 free(argv[i + 1]);
1151 argv[i + 1] = strsave("???");
1152 }
1153 if (status && status != MR_NO_MATCH)
1154 return status;
73cf66ba 1155 }
1156
5eaef520 1157 /* send the data */
1158 (*action)(q->vcnt, argv, actarg);
73cf66ba 1159
5eaef520 1160 /* free saved data */
1161 for (i = 0; i < q->vcnt; i++)
1162 free(argv[i]);
1163 free(argv);
73cf66ba 1164 }
5eaef520 1165 sq_destroy(sq);
1166 return MR_SUCCESS;
73cf66ba 1167}
1168
1169
1170/* followup_gsha:
1171 */
1172
5eaef520 1173int followup_gsha(struct query *q, struct save_queue *sq, struct validate *v,
1174 int (*action)(), int actarg, client *cl)
73cf66ba 1175{
5eaef520 1176 char **argv;
1177 int i, id, status;
1178
1179 while (sq_get_data(sq, &argv))
1180 {
1181 mr_trim_args(q->vcnt, argv);
1182
1183 id = atoi(argv[4]);
1184 if (id > 0)
1185 status = id_to_name(id, USERS_TABLE, &argv[4]);
1186 else
1187 status = id_to_name(-id, STRINGS_TABLE, &argv[4]);
1188 if (status && status != MR_NO_MATCH)
1189 return status;
1190
1191 id = atoi(argv[2]);
1192 if (!strcmp(argv[1], "LIST"))
1193 status = id_to_name(id, LIST_TABLE, &argv[2]);
1194 else if (!strcmp(argv[1], "USER"))
1195 status = id_to_name(id, USERS_TABLE, &argv[2]);
1196 else if (!strcmp(argv[1], "KERBEROS"))
1197 status = id_to_name(id, STRINGS_TABLE, &argv[2]);
1198 else if (!strcmp(argv[1], "NONE"))
1199 {
1200 status = 0;
1201 free(argv[2]);
1202 argv[2] = strsave("NONE");
1203 }
1204 else
1205 {
1206 status = 0;
1207 free(argv[2]);
1208 argv[2] = strsave("???");
73cf66ba 1209 }
5eaef520 1210 if (status && status != MR_NO_MATCH)
1211 return status;
73cf66ba 1212
5eaef520 1213 /* send the data */
1214 (*action)(q->vcnt, argv, actarg);
73cf66ba 1215
5eaef520 1216 /* free saved data */
1217 for (i = 0; i < q->vcnt; i++)
1218 free(argv[i]);
1219 free(argv);
73cf66ba 1220 }
5eaef520 1221 sq_destroy(sq);
1222 return MR_SUCCESS;
73cf66ba 1223}
1224
1225
5eaef520 1226int _sdl_followup(struct query *q, char *argv[], client *cl)
73cf66ba 1227{
5eaef520 1228 int i;
1229 i = atoi(argv[0]);
1230 log_flags = i;
1231
1232 if (i & LOG_SQL)
1233 EXEC SQL ALTER SESSION SET SQL_TRACE TRUE;
1234 else
1235 EXEC SQL ALTER SESSION SET SQL_TRACE FALSE;
1236
1237 return MR_SUCCESS;
73cf66ba 1238}
1239
1240
5eaef520 1241static void hex_dump(unsigned char *p)
73cf66ba 1242{
5eaef520 1243 fprintf(stderr, "Size: %d\n", strlen(p));
1244 while (strlen(p) >= 8)
1245 {
1246 fprintf(stderr, "%02x %02x %02x %02x %02x %02x %02x %02x\n",
1247 p[0], p[1], p[2], p[3], p[4], p[5], p[6], p[7]);
1248 p += 8;
73cf66ba 1249 }
5eaef520 1250 switch (strlen(p))
1251 {
73cf66ba 1252 case 7:
5eaef520 1253 fprintf(stderr, "%02x %02x %02x %02x %02x %02x %02x\n",
1254 p[0], p[1], p[2], p[3], p[4], p[5], p[6]);
1255 break;
73cf66ba 1256 case 6:
5eaef520 1257 fprintf(stderr, "%02x %02x %02x %02x %02x %02x\n",
1258 p[0], p[1], p[2], p[3], p[4], p[5]);
1259 break;
73cf66ba 1260 case 5:
5eaef520 1261 fprintf(stderr, "%02x %02x %02x %02x %02x\n",
73cf66ba 1262 p[0], p[1], p[2], p[3], p[4]);
5eaef520 1263 break;
73cf66ba 1264 case 4:
5eaef520 1265 fprintf(stderr, "%02x %02x %02x %02x\n",
1266 p[0], p[1], p[2], p[3]);
73cf66ba 1267 break;
1268 case 3:
5eaef520 1269 fprintf(stderr, "%02x %02x %02x\n",
1270 p[0], p[1], p[2]);
1271 break;
73cf66ba 1272 case 2:
5eaef520 1273 fprintf(stderr, "%02x %02x\n",
1274 p[0], p[1]);
1275 break;
73cf66ba 1276 case 1:
5eaef520 1277 fprintf(stderr, "%02x\n",
1278 p[0]);
1279 break;
73cf66ba 1280 default:
5eaef520 1281 return;
73cf66ba 1282 }
1283}
This page took 0.254824 seconds and 5 git commands to generate.