|
|
1.1 root 1: /* modify.c - */
2:
3: #ifndef lint
4: static char *rcsid = "$Header: /f/osi/quipu/dish/RCS/modify.c,v 7.3 90/07/09 14:47:17 mrose Exp $";
5: #endif
6:
7: /*
8: * $Header: /f/osi/quipu/dish/RCS/modify.c,v 7.3 90/07/09 14:47:17 mrose Exp $
9: *
10: *
11: * $Log: modify.c,v $
12: * Revision 7.3 90/07/09 14:47:17 mrose
13: * sync
14: *
15: * Revision 7.2 90/01/11 23:57:20 mrose
16: * lint
17: *
18: * Revision 7.1 90/01/11 18:37:41 mrose
19: * real-sync
20: *
21: * Revision 7.0 89/11/23 22:20:13 mrose
22: * Release 6.0
23: *
24: */
25:
26: /*
27: * NOTICE
28: *
29: * Acquisition, use, and distribution of this module and related
30: * materials are subject to the restrictions of a license agreement.
31: * Consult the Preface in the User's Manual for the full terms of
32: * this agreement.
33: *
34: */
35:
36:
37: #include "quipu/util.h"
38: #include "quipu/modify.h"
39: #include "quipu/read.h"
40: #include "quipu/entry.h"
41: #include "quipu/dua.h"
42:
43: extern DN dn;
44:
45: #define OPT (!frompipe || rps -> ps_byteno == 0 ? opt : rps)
46: #define RPS (!frompipe || opt -> ps_byteno == 0 ? rps : opt)
47: extern char frompipe;
48: extern PS opt, rps;
49:
50: extern Entry current_entry;
51: static char new_draft;
52:
53: call_modify (argc, argv)
54: int argc;
55: char **argv;
56: {
57: struct ds_modifyentry_arg mod_arg;
58:
59: struct DSError error;
60: struct entrymod *emnew, *ems_append(), *modify_avs();
61: Attr_Sequence as,
62: get_attributes (),
63: temp,
64: trail = NULLATTR;
65: AV_Sequence avst = NULLAV;
66: extern AttributeType at_objectclass;
67: extern char fname[];
68: extern int parse_status;
69: Entry entry_ptr;
70: FILE *fd;
71: char draft_flag = FALSE;
72: char noedit_flag = FALSE;
73: int x;
74: DN moddn;
75: char *home;
76: RDN new_rdn;
77:
78: if ((argc = service_control (OPT, argc, argv, &mod_arg.mea_common)) == -1)
79: return;
80:
81: mod_arg.mea_changes = NULLMOD;
82: new_draft = FALSE;
83:
84: if (home = getenv ("DISHDRAFT"))
85: (void) strcpy (fname, home);
86: else
87: if (home = getenv ("HOME"))
88: (void) sprintf (fname, "%s/.dishdraft", home);
89: else
90: (void) strcpy (fname, "./.dishdraft");
91:
92: for (x=1; x<argc; x++) {
93: if (test_arg (argv[x], "-draft",1)) {
94: draft_flag = 1;
95: shuffle_up (argc--,argv,x);
96: if (x == argc) {
97: ps_printf (OPT, "Draft file name missing\n");
98: Usage (argv[0]);
99: return;
100: }
101: (void) strcpy (fname, argv[x]);
102: shuffle_up (argc--,argv,x--);
103: } else if (test_arg (argv[x], "-newdraft",2)) {
104: new_draft = TRUE;
105: shuffle_up (argc--,argv,x--);
106: } else if (test_arg (argv[x], "-noedit",3)) {
107: noedit_flag = TRUE;
108: shuffle_up (argc--,argv,x--);
109: } else if (move (argv[x]) == OK)
110: shuffle_up (argc--,argv,x--);
111: }
112:
113: /* read attributes we want to modify */
114: if ((argc = read_cache_aux (argc, argv, FALSE, &mod_arg.mea_common)) <0 )
115: return;
116:
117: if (argc != 1) {
118: ps_printf (OPT,"Unknown option %s\n",argv[1]);
119: Usage (argv[0]);
120: return;
121: }
122:
123: if (!draft_flag) {
124: if (mod_template (fname,noedit_flag) != OK)
125: return;
126: noedit_flag = FALSE;
127: } else {
128: new_draft = TRUE; /* Ugh ! */
129: (void) mod_template ("/dev/null",TRUE);
130: }
131:
132: if (! noedit_flag)
133: if (editentry (1, argv) != OK) {
134: make_old (fname,draft_flag);
135: return;
136: }
137:
138: /* now parse the files */
139:
140: if ((fd = fopen (fname, "r")) == (FILE *) NULL) {
141: ps_printf (OPT, "Can't open draft entry %s\n", fname);
142: return;
143: }
144:
145: entry_ptr = get_default_entry (NULLENTRY);
146: entry_ptr->e_attributes = get_attributes (fd);
147:
148: (void) fclose (fd);
149: if (parse_status != 0)
150: return;
151:
152: mod_arg.mea_object = dn;
153: for (moddn = dn ; moddn->dn_parent != NULLDN; moddn=moddn->dn_parent)
154: ;
155: entry_ptr->e_name = rdn_cpy (moddn->dn_rdn);
156:
157: /* add rdn as attribute */
158: for (new_rdn = entry_ptr->e_name; new_rdn != NULLRDN; new_rdn = new_rdn->rdn_next) {
159: avst = avs_comp_new (AttrV_cpy (&new_rdn->rdn_av));
160: temp = as_comp_new (AttrT_cpy (&new_rdn->rdn_at), avst, NULLACL_INFO);
161: entry_ptr->e_attributes = as_merge (entry_ptr->e_attributes, temp);
162: }
163:
164: for (as = entry_ptr->e_attributes; as != NULLATTR; as = as->attr_link) {
165: emnew = NULLMOD;
166: trail = as->attr_link;
167: as->attr_link = NULLATTR;
168:
169: temp = current_entry->e_attributes;
170: for (; temp != NULLATTR; temp = temp->attr_link)
171: if (AttrT_cmp (as->attr_type, temp->attr_type) == 0) {
172: /* found it - does it need changing ? */
173: if (avs_cmp (as->attr_value, temp->attr_value) != 0)
174: emnew = modify_avs (as->attr_value, temp->attr_value,as->attr_type);
175: break;
176: }
177:
178: if (temp == NULLATTR) {
179: emnew = em_alloc ();
180: emnew->em_type = EM_ADDATTRIBUTE;
181: emnew->em_what = as_cpy(as);
182: emnew->em_next = NULLMOD;
183: }
184:
185: if (emnew != NULLMOD)
186: mod_arg.mea_changes = ems_append (mod_arg.mea_changes,emnew);
187:
188: as->attr_link = trail;
189: }
190:
191: /* remove attribute missing in new entry */
192: for (as = current_entry->e_attributes; as != NULLATTR; as = as->attr_link) {
193: emnew = NULLMOD;
194:
195: temp = entry_ptr->e_attributes;
196: for (; temp != NULLATTR; temp = temp->attr_link)
197: if (AttrT_cmp (as->attr_type, temp->attr_type) == 0)
198: break;
199:
200: if (temp == NULLATTR) {
201: emnew = em_alloc ();
202: emnew->em_type = EM_REMOVEATTRIBUTE;
203: emnew->em_what = as_comp_new(as->attr_type,NULLAV,NULLACL_INFO);
204: emnew->em_next = NULLMOD;
205: }
206:
207: if (emnew != NULLMOD)
208: mod_arg.mea_changes = ems_append (mod_arg.mea_changes,emnew);
209: }
210:
211:
212: if (mod_arg.mea_changes == NULLMOD) {
213: ps_print (RPS, "The draft entry and the entry for ");
214: dn_print (RPS, dn, EDBOUT);
215: ps_print (RPS, "\nare exactly the same - no change made!!!\n");
216: entry_free (entry_ptr);
217: make_old (fname,draft_flag);
218: return;
219: }
220:
221: if (rebind () != OK) {
222: entry_free (entry_ptr);
223: return;
224: }
225: /*
226: * If this operation is time-stamped, it may have expired while the user
227: * was editing the entry. Re-calculate the time-stamp. Modify is the only
228: * dish command where this needs to be done.
229: */
230:
231: if ((mod_arg.mea_common.ca_security != (struct security_parms *) 0)
232: && (mod_arg.mea_common.ca_security->sp_time != NULLCP)) {
233: char *new_version();
234:
235: free(mod_arg.mea_common.ca_security->sp_time);
236: mod_arg.mea_common.ca_security->sp_time = new_version();
237: }
238:
239: /* If security parameters are present, take this to mean that strong
240: * authentication is required. This disallows 'parms + no signature'
241: * (pointless) and 'signature + no parms' (security risk).
242: */
243: if (mod_arg.mea_common.ca_security != (struct security_parms *) 0)
244: {
245: int encode_DAS_ModifyEntryArgumentData();
246: struct signature *sign_operation();
247: mod_arg.mea_common.ca_sig =
248: sign_operation((caddr_t)&mod_arg,
249: encode_DAS_ModifyEntryArgumentData);
250: }
251:
252: while (ds_modifyentry (&mod_arg, &error) != DS_OK) {
253: if (dish_error (OPT, &error) == 0) {
254: entry_free (entry_ptr);
255: return;
256: }
257: mod_arg.mea_object = error.ERR_REFERRAL.DSE_ref_candidates->cr_name;
258: }
259: ps_print (RPS, "Modified ");
260: dn_print (RPS, dn, EDBOUT);
261: ps_print (RPS, "\n");
262: delete_cache (dn); /* re-cache when next read */
263:
264: entry_free (entry_ptr);
265: ems_part_free (mod_arg.mea_changes);
266:
267: make_old (fname,draft_flag);
268: }
269:
270:
271: struct entrymod * ems_append (a,b)
272: struct entrymod *a;
273: struct entrymod *b;
274: {
275: struct entrymod *ptr;
276:
277: if ((ptr = a) == NULLMOD)
278: return b;
279:
280: for ( ; ptr->em_next != NULLMOD; ptr = ptr->em_next)
281: ;
282:
283: ptr->em_next = b;
284: return a;
285: }
286:
287:
288:
289: struct entrymod * modify_avs (a,b,at)
290: AV_Sequence a;
291: AV_Sequence b;
292: AttributeType at;
293: {
294: AV_Sequence x;
295: AV_Sequence y;
296: struct entrymod *em = NULLMOD, *emnew;
297: int removed_all = TRUE;
298: extern short oc_sntx;
299: static OID top = NULLOID;
300:
301: for (x=b; x != NULLAV; x=x->avseq_next) {
302: emnew = NULLMOD;
303: for (y=a; y != NULLAV; y=y->avseq_next)
304: if (AttrV_cmp (&x->avseq_av,&y->avseq_av) == 0)
305: break;
306: if (y == NULLAV) {
307: emnew = em_alloc ();
308: emnew->em_type = EM_REMOVEVALUES;
309: emnew->em_what = as_comp_new (at,avs_comp_new(&x->avseq_av),NULLACL_INFO);
310: emnew->em_next = NULLMOD;
311: } else
312: removed_all = FALSE;
313: if (emnew != NULLMOD)
314: em = ems_append (em,emnew);
315: }
316:
317: if (removed_all) {
318: ems_part_free (em);
319: emnew = em_alloc ();
320: emnew->em_type = EM_REMOVEATTRIBUTE;
321: emnew->em_what = as_comp_new (at,b,NULLACL_INFO);
322: emnew->em_next = em_alloc();
323: emnew->em_next->em_type = EM_ADDATTRIBUTE;
324: emnew->em_next->em_what = as_comp_new (at,avs_cpy(a),NULLACL_INFO);
325: emnew->em_next->em_next = NULLMOD;
326: return (emnew);
327: }
328:
329: for (x=a; x != NULLAV; x=x->avseq_next) {
330: emnew = NULLMOD;
331: for (y=b; y != NULLAV; y=y->avseq_next)
332: if (AttrV_cmp (&x->avseq_av,&y->avseq_av) == 0)
333: break;
334: if (y == NULLAV) {
335: if (at->oa_syntax == oc_sntx) {
336: /* Don't add 'top' if missing */
337: objectclass * oc;
338: if (!top)
339: top = oid_cpy(str2oid (TOP_OC));
340:
341: if (oc = (objectclass *) x->avseq_av.av_struct) /* assign */
342: if (oid_cmp(oc->oc_ot.ot_oid, top) == 0)
343: continue;
344: }
345: emnew = em_alloc ();
346: emnew->em_type = EM_ADDVALUES;
347: emnew->em_what = as_comp_new (at,avs_comp_new(&x->avseq_av),NULLACL_INFO);
348: emnew->em_next = NULLMOD;
349: }
350: if (emnew != NULLMOD)
351: em = ems_append (em,emnew);
352: }
353:
354:
355: return (em);
356: }
357:
358: ems_part_free(emp)
359: struct entrymod *emp;
360: {
361: if(emp == NULLMOD)
362: return;
363: ems_part_free(emp->em_next);
364: free((char *)emp);
365: }
366:
367: static int raboof = 0;
368:
369: static char *foobar (string)
370: char *string;
371: {
372: DN fb;
373: PS ps;
374: static char buffer[BUFSIZ];
375: DN sequence_dn ();
376:
377: if (!isdigit (*string))
378: return string;
379: if ((fb = sequence_dn (atoi (string))) == NULLDN) {
380: ps_printf (OPT, "Invalid sequence in directive %s\n", string);
381: you_lose: ;
382: raboof = 1;
383: return string;
384: }
385:
386: if ((ps = ps_alloc (str_open)) == NULLPS) {
387: ps_printf (OPT, "ps_alloc: failed");
388: goto you_lose;
389: }
390: if (str_setup (ps, buffer, sizeof buffer - 2, 1) == NOTOK) {
391: ps_printf (OPT, "str_setup: %s", ps_error (ps -> ps_errno));
392: ps_free (ps);
393: goto you_lose;
394: }
395:
396: dn_print (ps, fb, EDBOUT);
397: ps_print (ps, " ");
398: *--ps -> ps_ptr = NULL, ps -> ps_cnt++;
399:
400: ps_free (ps);
401:
402: return buffer;
403: }
404:
405: dsa_control (argc, argv)
406: int argc;
407: char **argv;
408: {
409: static struct entrymod mod = {
410: EM_ADDATTRIBUTE,
411: NULLATTR,
412: NULLMOD
413: };
414:
415: static struct ds_modifyentry_arg mod_arg =
416: {
417: default_common_args,
418: NULLDN,
419: &mod
420: };
421:
422: AttributeType at;
423: struct DSError error;
424: char buffer[100];
425: char * msg = "Done\n";
426:
427: if (argc < 2) {
428: Usage(argv[0]);
429: return;
430: }
431:
432: if (test_arg (argv[1], "-dump",1))
433: (void) sprintf (buffer, "d %s", argv[2]);
434: else if (test_arg (argv[1], "-tailor",1))
435: (void) sprintf (buffer, "t %s", argv[2]);
436: else if (test_arg (argv[1], "-abort",1)) {
437: (void) strcpy (buffer,"a");
438: argc++; /* to get through if (argc != 3) */
439: }
440: else if (test_arg (argv[1], "-restart",1)) {
441: (void) strcpy (buffer,"b");
442: argc++; /* to get through if (argc != 3) */
443: }
444: else if (test_arg (argv[1], "-refresh",3))
445: (void) sprintf (buffer, "r %s", foobar (argv[2]));
446: else if (test_arg (argv[1], "-resync",2))
447: (void) sprintf (buffer, "f %s", foobar (argv[2]));
448: else if (test_arg (argv[1], "-lock",1))
449: (void) sprintf (buffer, "l %s", foobar (argv[2]));
450: else if (test_arg (argv[1], "-unlock",1))
451: (void) sprintf (buffer, "u %s", foobar (argv[2]));
452: else if (test_arg (argv[1], "-info",1)) {
453: dsa_control_info();
454: return;
455: } else if (test_arg (argv[1], "-slave",1)) {
456: msg = "Scheduled\n";
457: if (argc == 2) {
458: (void) strcpy (buffer,"s");
459: argc++; /* to get through if (argc != 3) */
460: }
461: else
462: (void) sprintf (buffer, "s %s", foobar (argv[2]));
463: }
464: else
465: argc = 1; /* to force error */
466:
467: if (raboof) {
468: raboof = 0;
469: return;
470: }
471:
472: if (argc != 3) {
473: Usage (argv[0]);
474: return;
475: }
476: mod_arg.mea_object = dn;
477: at = AttrT_new (CONTROL_OID);
478: mod_arg.mea_changes->em_what = as_comp_new (at, avs_comp_new (str_at2AttrV (buffer, at)), NULLACL_INFO);
479:
480: if (rebind () != OK)
481: return;
482:
483: if (ds_modifyentry (&mod_arg, &error) != DS_OK) {
484: /* deal with error */
485: (void) dish_error (OPT, &error);
486: } else {
487: ps_print (RPS, msg);
488: return;
489: }
490: /* as_free (mod_arg.mea_changes->em_what); */
491: }
492:
493: dsa_control_info ()
494: {
495: struct ds_read_arg read_arg;
496: struct DSError error;
497: struct ds_read_result result;
498: static CommonArgs ca = default_common_args;
499:
500: read_arg.rda_eis.eis_infotypes = EIS_ATTRIBUTESANDVALUES;
501: read_arg.rda_eis.eis_allattributes = FALSE;
502: read_arg.rda_eis.eis_select = as_comp_new (AttrT_new (CONTROL_OID), NULLAV, NULLACL_INFO);
503: read_arg.rda_common = ca; /* struct copy */
504: read_arg.rda_object = NULLDN;
505:
506: if (rebind () != OK)
507: return;
508:
509: if (ds_read (&read_arg, &error, &result) != DS_OK) {
510: (void) dish_error (OPT, &error);
511: return;
512: }
513:
514: if (result.rdr_entry.ent_attr) {
515: avs_print (RPS,result.rdr_entry.ent_attr->attr_value,READOUT);
516: } else
517: ps_printf (OPT, "No information !!!\n");
518: }
519:
520: mod_template (name,noedit)
521: char *name;
522: char noedit;
523: {
524: FILE *fptr;
525: PS ps;
526: extern oid_table_attr * tab_objectclass;
527: Attr_Sequence as;
528: Attr_Sequence nas, tas, make_template_as ();
529: int um;
530:
531: if (! new_draft)
532: if ((fptr = fopen (name, "r")) != NULL) {
533: (void) fclose (fptr);
534: if (!noedit) {
535: if (yesno ("Use existing draft file ? "))
536: return OK;
537: else
538: make_old (fname,FALSE);
539: } else
540: return (OK); /* template already exists ! */
541:
542: }
543:
544: um = umask (0177);
545: if ((fptr = fopen (name, "w")) == NULL) {
546: ps_printf (OPT, "Can't open template entry %s\n", name);
547: return (-1);
548: }
549: (void) umask (um);
550:
551: if ((ps = ps_alloc (std_open)) == NULLPS) {
552: return (-1);
553: }
554: if (std_setup (ps, fptr) == NOTOK) {
555: return (-1);
556: }
557: for (as = current_entry->e_attributes; as != NULLATTR; as = as->attr_link)
558: if (as->attr_type == tab_objectclass)
559: break;
560:
561: tas = make_template_as (as->attr_value);
562: nas = as_cpy(current_entry->e_attributes);
563:
564: tas = as_merge (tas,nas);
565:
566: as_print (ps,tas,EDBOUT);
567:
568: as_free (tas);
569: ps_free (ps);
570: (void) fclose (fptr);
571:
572: return (OK);
573: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.