xref: /dragonfly/usr.sbin/installer/libdfui/form.c (revision 86d7f5d305c6adaa56ff4582ece9859d73106103)
1 /*
2  * Copyright (c)2004 Cat's Eye Technologies.  All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
8  *   Redistributions of source code must retain the above copyright
9  *   notice, this list of conditions and the following disclaimer.
10  *
11  *   Redistributions in binary form must reproduce the above copyright
12  *   notice, this list of conditions and the following disclaimer in
13  *   the documentation and/or other materials provided with the
14  *   distribution.
15  *
16  *   Neither the name of Cat's Eye Technologies nor the names of its
17  *   contributors may be used to endorse or promote products derived
18  *   from this software without specific prior written permission.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
25  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
26  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
27  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
29  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
30  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
31  * OF THE POSSIBILITY OF SUCH DAMAGE.
32  */
33 
34 /*
35  * form.c
36  * $Id: form.c,v 1.18 2005/03/04 21:26:20 cpressey Exp $
37  */
38 
39 #include <stdarg.h>
40 #include <stdlib.h>
41 #include <string.h>
42 
43 #include <libaura/mem.h>
44 
45 #define   NEEDS_DFUI_STRUCTURE_DEFINITIONS
46 #include "dfui.h"
47 #undef    NEEDS_DFUI_STRUCTURE_DEFINITIONS
48 #include "dump.h"
49 
50 /*** INFOS ***/
51 
52 struct dfui_info *
dfui_info_new(const char * name,const char * short_desc,const char * long_desc)53 dfui_info_new(const char *name, const char *short_desc, const char *long_desc)
54 {
55           struct dfui_info *i;
56 
57           AURA_MALLOC(i, dfui_info);
58           i->name = aura_strdup(name);
59           i->short_desc = aura_strdup(short_desc);
60           i->long_desc = aura_strdup(long_desc);
61 
62           return(i);
63 }
64 
65 void
dfui_info_free(struct dfui_info * i)66 dfui_info_free(struct dfui_info *i)
67 {
68           free(i->name);
69           free(i->short_desc);
70           free(i->long_desc);
71           AURA_FREE(i, dfui_info);
72 }
73 
74 const char *
dfui_info_get_name(const struct dfui_info * i)75 dfui_info_get_name(const struct dfui_info *i)
76 {
77           if (i == NULL)
78                     return("");
79           return(i->name);
80 }
81 
82 const char *
dfui_info_get_short_desc(const struct dfui_info * i)83 dfui_info_get_short_desc(const struct dfui_info *i)
84 {
85           if (i == NULL)
86                     return("");
87           return(i->short_desc);
88 }
89 
90 const char *
dfui_info_get_long_desc(const struct dfui_info * i)91 dfui_info_get_long_desc(const struct dfui_info *i)
92 {
93           if (i == NULL)
94                     return("");
95           return(i->long_desc);
96 }
97 
98 void
dfui_info_set_name(struct dfui_info * i,const char * name)99 dfui_info_set_name(struct dfui_info *i, const char *name)
100 {
101           if (i == NULL)
102                     return;
103           if (i->name != NULL)
104                     free(i->name);
105           i->name = aura_strdup(name);
106 }
107 
108 void
dfui_info_set_short_desc(struct dfui_info * i,const char * short_desc)109 dfui_info_set_short_desc(struct dfui_info *i, const char *short_desc)
110 {
111           if (i == NULL)
112                     return;
113           if (i->short_desc != NULL)
114                     free(i->short_desc);
115           i->short_desc = aura_strdup(short_desc);
116 }
117 
118 void
dfui_info_set_long_desc(struct dfui_info * i,const char * long_desc)119 dfui_info_set_long_desc(struct dfui_info *i, const char *long_desc)
120 {
121           if (i == NULL)
122                     return;
123           if (i->long_desc != NULL)
124                     free(i->long_desc);
125           i->long_desc = aura_strdup(long_desc);
126 }
127 
128 /*** PROPERTIES ***/
129 
130 struct dfui_property *
dfui_property_new(const char * name,const char * value)131 dfui_property_new(const char *name, const char *value)
132 {
133           struct dfui_property *p;
134 
135           AURA_MALLOC(p, dfui_property);
136           p->name = aura_strdup(name);
137           p->value = aura_strdup(value);
138 
139           return(p);
140 }
141 
142 void
dfui_property_free(struct dfui_property * p)143 dfui_property_free(struct dfui_property *p)
144 {
145           if (p == NULL)
146                     return;
147           free(p->name);
148           free(p->value);
149           AURA_FREE(p, dfui_property);
150 }
151 
152 void
dfui_properties_free(struct dfui_property * head)153 dfui_properties_free(struct dfui_property *head)
154 {
155           struct dfui_property *p;
156 
157           for (p = head; p != NULL; ) {
158                     head = p->next;
159                     dfui_property_free(p);
160                     p = head;
161           }
162 }
163 
164 struct dfui_property *
dfui_property_find(struct dfui_property * head,const char * name)165 dfui_property_find(struct dfui_property *head, const char *name)
166 {
167           struct dfui_property *p;
168 
169           for (p = head; p != NULL; p = p->next) {
170                     if (strcmp(name, p->name) == 0)
171                               return(p);
172           }
173 
174           return(NULL);
175 }
176 
177 const char *
dfui_property_get(struct dfui_property * head,const char * name)178 dfui_property_get(struct dfui_property *head, const char *name)
179 {
180           struct dfui_property *p;
181 
182           if ((p = dfui_property_find(head, name)) != NULL)
183                     return(p->value);
184           return("");
185 }
186 
187 struct dfui_property *
dfui_property_set(struct dfui_property ** head,const char * name,const char * value)188 dfui_property_set(struct dfui_property **head, const char *name, const char *value)
189 {
190           struct dfui_property *p;
191 
192           if (head == NULL)
193                     return(NULL);
194 
195           if ((p = dfui_property_find(*head, name)) != NULL) {
196                     free(p->value);
197                     p->value = aura_strdup(value);
198                     return(p);
199           }
200 
201           p = dfui_property_new(name, value);
202           p->next = *head;
203           *head = p;
204 
205           return(p);
206 }
207 
208 const char *
dfui_property_get_name(const struct dfui_property * p)209 dfui_property_get_name(const struct dfui_property *p)
210 {
211           return(p->name);
212 }
213 
214 const char *
dfui_property_get_value(const struct dfui_property * p)215 dfui_property_get_value(const struct dfui_property *p)
216 {
217           return(p->value);
218 }
219 
220 /*** FIELDS ***/
221 
222 struct dfui_field *
dfui_field_new(const char * id,struct dfui_info * info)223 dfui_field_new(const char *id, struct dfui_info *info)
224 {
225           struct dfui_field *fi;
226 
227           AURA_MALLOC(fi, dfui_field);
228           fi->id = aura_strdup(id);
229           fi->info = info;
230           fi->option_head = NULL;
231           fi->property_head = NULL;
232           fi->next = NULL;
233 
234           dfui_field_property_set(fi, "editable", "true");
235 
236           return(fi);
237 }
238 
239 void
dfui_field_free(struct dfui_field * fi)240 dfui_field_free(struct dfui_field *fi)
241 {
242           free(fi->id);
243           dfui_info_free(fi->info);
244           dfui_options_free(fi->option_head);
245           dfui_properties_free(fi->property_head);
246           AURA_FREE(fi, dfui_field);
247 }
248 
249 void
dfui_fields_free(struct dfui_field * head)250 dfui_fields_free(struct dfui_field *head)
251 {
252           struct dfui_field *fi;
253 
254           fi = head;
255           while (fi != NULL) {
256                     head = fi->next;
257                     dfui_field_free(fi);
258                     fi = head;
259           }
260 }
261 
262 struct dfui_field *
dfui_field_get_next(const struct dfui_field * fi)263 dfui_field_get_next(const struct dfui_field *fi)
264 {
265           if (fi == NULL)
266                     return(NULL);
267           return(fi->next);
268 }
269 
270 const char *
dfui_field_get_id(const struct dfui_field * fi)271 dfui_field_get_id(const struct dfui_field *fi)
272 {
273           if (fi == NULL)
274                     return(NULL);
275           return(fi->id);
276 }
277 
278 struct dfui_info *
dfui_field_get_info(const struct dfui_field * fi)279 dfui_field_get_info(const struct dfui_field *fi)
280 {
281           if (fi == NULL)
282                     return(NULL);
283           return(fi->info);
284 }
285 
286 struct dfui_option *
dfui_field_option_add(struct dfui_field * fi,const char * value)287 dfui_field_option_add(struct dfui_field *fi, const char *value)
288 {
289           struct dfui_option *o;
290 
291           if (fi == NULL)
292                     return(NULL);
293           o = dfui_option_new(value);
294           o->next = fi->option_head;
295           fi->option_head = o;
296 
297           return(o);
298 }
299 
300 struct dfui_option *
dfui_field_option_get_first(const struct dfui_field * fi)301 dfui_field_option_get_first(const struct dfui_field *fi)
302 {
303           if (fi == NULL)
304                     return(NULL);
305           return(fi->option_head);
306 }
307 
308 struct dfui_property *
dfui_field_property_set(struct dfui_field * fi,const char * name,const char * value)309 dfui_field_property_set(struct dfui_field *fi, const char *name, const char *value)
310 {
311           return(dfui_property_set(&fi->property_head, name, value));
312 }
313 
314 const char *
dfui_field_property_get(const struct dfui_field * fi,const char * name)315 dfui_field_property_get(const struct dfui_field *fi, const char *name)
316 {
317           return(dfui_property_get(fi->property_head, name));
318 }
319 
320 int
dfui_field_property_is(const struct dfui_field * fi,const char * name,const char * value)321 dfui_field_property_is(const struct dfui_field *fi, const char *name, const char *value)
322 {
323           struct dfui_property *h;
324 
325           if (fi == NULL)
326                     return(0);
327           if ((h = dfui_property_find(fi->property_head, name)) == NULL)
328                     return(0);
329           return(!strcmp(h->value, value));
330 }
331 
332 /*** OPTIONS ***/
333 
334 struct dfui_option *
dfui_option_new(const char * value)335 dfui_option_new(const char *value)
336 {
337           struct dfui_option *o;
338 
339           AURA_MALLOC(o, dfui_option);
340           o->value = aura_strdup(value);
341           o->next = NULL;
342 
343           return(o);
344 }
345 
346 void
dfui_option_free(struct dfui_option * o)347 dfui_option_free(struct dfui_option *o)
348 {
349           if (o == NULL)
350                     return;
351           free(o->value);
352           AURA_FREE(o, dfui_option);
353 }
354 
355 void
dfui_options_free(struct dfui_option * head)356 dfui_options_free(struct dfui_option *head)
357 {
358           struct dfui_option *o;
359 
360           o = head;
361           while (o != NULL) {
362                     head = o->next;
363                     dfui_option_free(o);
364                     o = head;
365           }
366 }
367 
368 struct dfui_option *
dfui_option_get_next(const struct dfui_option * o)369 dfui_option_get_next(const struct dfui_option *o)
370 {
371           if (o == NULL)
372                     return(NULL);
373           return(o->next);
374 }
375 
376 const char *
dfui_option_get_value(const struct dfui_option * o)377 dfui_option_get_value(const struct dfui_option *o)
378 {
379           if (o == NULL)
380                     return("");
381           return(o->value);
382 }
383 
384 /*** ACTIONS ***/
385 
386 struct dfui_action *
dfui_action_new(const char * id,struct dfui_info * info)387 dfui_action_new(const char *id, struct dfui_info *info)
388 {
389           struct dfui_action *a;
390 
391           AURA_MALLOC(a, dfui_action);
392           a->id = aura_strdup(id);
393           a->info = info;
394           a->next = NULL;
395           a->property_head = NULL;
396 
397           return(a);
398 }
399 
400 void
dfui_action_free(struct dfui_action * a)401 dfui_action_free(struct dfui_action *a)
402 {
403           free(a->id);
404           dfui_info_free(a->info);
405           dfui_properties_free(a->property_head);
406           AURA_FREE(a, dfui_action);
407 }
408 
409 void
dfui_actions_free(struct dfui_action * head)410 dfui_actions_free(struct dfui_action *head)
411 {
412           struct dfui_action *a;
413 
414           a = head;
415           while (a != NULL) {
416                     head = a->next;
417                     dfui_action_free(a);
418                     a = head;
419           }
420 }
421 
422 struct dfui_action *
dfui_action_get_next(const struct dfui_action * a)423 dfui_action_get_next(const struct dfui_action *a)
424 {
425           if (a == NULL)
426                     return(NULL);
427           return(a->next);
428 }
429 
430 const char *
dfui_action_get_id(const struct dfui_action * a)431 dfui_action_get_id(const struct dfui_action *a)
432 {
433           if (a == NULL)
434                     return(NULL);
435           return(a->id);
436 }
437 
438 struct dfui_info *
dfui_action_get_info(const struct dfui_action * a)439 dfui_action_get_info(const struct dfui_action *a)
440 {
441           if (a == NULL)
442                     return(NULL);
443           return(a->info);
444 }
445 
446 struct dfui_property *
dfui_action_property_set(struct dfui_action * a,const char * name,const char * value)447 dfui_action_property_set(struct dfui_action *a, const char *name, const char *value)
448 {
449           return(dfui_property_set(&a->property_head, name, value));
450 }
451 
452 const char *
dfui_action_property_get(const struct dfui_action * a,const char * name)453 dfui_action_property_get(const struct dfui_action *a, const char *name)
454 {
455           return(dfui_property_get(a->property_head, name));
456 }
457 
458 int
dfui_action_property_is(const struct dfui_action * a,const char * name,const char * value)459 dfui_action_property_is(const struct dfui_action *a, const char *name, const char *value)
460 {
461           struct dfui_property *h;
462 
463           if (a == NULL)
464                     return(0);
465           if ((h = dfui_property_find(a->property_head, name)) == NULL)
466                     return(0);
467           return(!strcmp(h->value, value));
468 }
469 
470 /*** FORMS ***/
471 
472 struct dfui_form *
dfui_form_new(const char * id,struct dfui_info * info)473 dfui_form_new(const char *id, struct dfui_info *info)
474 {
475           struct dfui_form *f;
476 
477           AURA_MALLOC(f, dfui_form);
478           f->id = aura_strdup(id);
479           f->info = info;
480           f->multiple = 0;
481           f->extensible = 0;
482           f->field_head = NULL;
483           f->action_head = NULL;
484           f->dataset_head = NULL;
485           f->property_head = NULL;
486 
487           return(f);
488 };
489 
490 /*
491  * Convenience function for creating a form.
492  * This function takes a list of any number of strings.
493  * This list MUST be terminated by a NULL pointer.
494  * The first four strings are the id, name, short description, and long
495  * description of the form.
496  * Each subsequent string determines what the strings following it represent:
497  *    "f": create a field (id, name, short desc, long desc).
498  *    "o": add an option to the last field (value).
499  *    "a": create an action (id, name, short desc, long desc).
500  *    "p": add a property to the last object (name, value).
501  */
502 struct dfui_form *
dfui_form_create(const char * id,const char * name,const char * short_desc,const char * long_desc,...)503 dfui_form_create(const char *id, const char *name,
504                      const char *short_desc, const char *long_desc, ...)
505 {
506 #define DFUI_FORM_CREATE_FORM 0
507 #define DFUI_FORM_CREATE_FIELD          1
508 #define DFUI_FORM_CREATE_ACTION         2
509 
510           struct dfui_form *f;
511           struct dfui_info *i;
512           va_list args;
513           int state = DFUI_FORM_CREATE_FORM;
514           char *arg;
515           void *object = NULL;
516           const char *a_id;
517           char *a_name, *a_short_desc, *a_long_desc;
518 
519           i = dfui_info_new(name, short_desc, long_desc);
520           f = dfui_form_new(id, i);
521 
522           va_start(args, long_desc);
523           while ((arg = va_arg(args, char *)) != NULL) {
524                     switch (arg[0]) {
525                     case 'f':
526                               a_id = va_arg(args, const char *);
527                               a_name = va_arg(args, char *);
528                               a_short_desc = va_arg(args, char *);
529                               a_long_desc = va_arg(args, char *);
530                               i = dfui_info_new(a_name, a_short_desc, a_long_desc);
531                               object = (void *)dfui_form_field_add(f, a_id, i);
532                               state = DFUI_FORM_CREATE_FIELD;
533                               break;
534                     case 'a':
535                               a_id = va_arg(args, const char *);
536                               a_name = va_arg(args, char *);
537                               a_short_desc = va_arg(args, char *);
538                               a_long_desc = va_arg(args, char *);
539                               i = dfui_info_new(a_name, a_short_desc, a_long_desc);
540                               object = (void *)dfui_form_action_add(f, a_id, i);
541                               state = DFUI_FORM_CREATE_ACTION;
542                               break;
543                     case 'o':
544                               a_name = va_arg(args, char *);
545                               if (state == DFUI_FORM_CREATE_FIELD) {
546                                         dfui_field_option_add(object, a_name);
547                               } else {
548                                         dfui_debug("form_create: can't add option to non-field\n");
549                               }
550                               break;
551                     case 'h':
552                     case 'p':
553                               a_id = va_arg(args, char *);
554                               a_short_desc = va_arg(args, char *);
555 
556                               if (state == DFUI_FORM_CREATE_FIELD) {
557                                         dfui_field_property_set(object, a_id, a_short_desc);
558                               } else if (state == DFUI_FORM_CREATE_ACTION) {
559                                         dfui_action_property_set(object, a_id, a_short_desc);
560                               } else if (state == DFUI_FORM_CREATE_FORM) {
561                                         dfui_form_property_set(f, a_id, a_short_desc);
562                               } else {
563                                         dfui_debug("form_create: can't add property in this state\n");
564                               }
565                               break;
566 
567                     default:
568                               dfui_debug("form_create: unknown option `%c'\n", arg[0]);
569                               break;
570                     }
571           }
572 
573           va_end(args);
574           return(f);
575 }
576 
577 void
dfui_form_free(struct dfui_form * f)578 dfui_form_free(struct dfui_form *f)
579 {
580           free(f->id);
581           dfui_info_free(f->info);
582           dfui_fields_free(f->field_head);
583           dfui_actions_free(f->action_head);
584           dfui_datasets_free(f->dataset_head);
585           dfui_properties_free(f->property_head);
586           AURA_FREE(f, dfui_form);
587 }
588 
589 struct dfui_field *
dfui_form_field_add(struct dfui_form * f,const char * id,struct dfui_info * info)590 dfui_form_field_add(struct dfui_form *f, const char *id, struct dfui_info *info)
591 {
592           struct dfui_field *fi;
593 
594           if (f == NULL)
595                     return(NULL);
596           fi = dfui_field_new(id, info);
597           fi->next = f->field_head;
598           f->field_head = fi;
599 
600           return(fi);
601 }
602 
603 struct dfui_field *
dfui_form_field_attach(struct dfui_form * f,struct dfui_field * fi)604 dfui_form_field_attach(struct dfui_form *f, struct dfui_field *fi)
605 {
606           if (f == NULL)
607                     return(NULL);
608           fi->next = f->field_head;
609           f->field_head = fi;
610 
611           return(fi);
612 }
613 
614 struct dfui_action *
dfui_form_action_add(struct dfui_form * f,const char * id,struct dfui_info * info)615 dfui_form_action_add(struct dfui_form *f, const char *id, struct dfui_info *info)
616 {
617           struct dfui_action *a;
618 
619           if (f == NULL)
620                     return(NULL);
621           a = dfui_action_new(id, info);
622           a->next = f->action_head;
623           f->action_head = a;
624 
625           return(a);
626 }
627 
628 struct dfui_action *
dfui_form_action_attach(struct dfui_form * f,struct dfui_action * a)629 dfui_form_action_attach(struct dfui_form *f, struct dfui_action *a)
630 {
631           if (f == NULL)
632                     return(NULL);
633           a->next = f->action_head;
634           f->action_head = a;
635 
636           return(a);
637 }
638 
639 void
dfui_form_dataset_add(struct dfui_form * f,struct dfui_dataset * ds)640 dfui_form_dataset_add(struct dfui_form *f, struct dfui_dataset *ds)
641 {
642           if (f == NULL || ds == NULL)
643                     return;
644           ds->next = f->dataset_head;
645           f->dataset_head = ds;
646 }
647 
648 struct dfui_dataset *
dfui_form_dataset_get_first(const struct dfui_form * f)649 dfui_form_dataset_get_first(const struct dfui_form *f)
650 {
651           if (f == NULL)
652                     return(NULL);
653           return(f->dataset_head);
654 }
655 
656 int
dfui_form_dataset_count(const struct dfui_form * f)657 dfui_form_dataset_count(const struct dfui_form *f)
658 {
659           int n = 0;
660           struct dfui_dataset *ds;
661 
662           if (f == NULL)
663                     return(0);
664 
665           ds = f->dataset_head;
666           while (ds != NULL) {
667                     n++;
668                     ds = ds->next;
669           }
670 
671           return(n);
672 }
673 
674 void
dfui_form_datasets_free(struct dfui_form * f)675 dfui_form_datasets_free(struct dfui_form *f)
676 {
677           if (f == NULL)
678                     return;
679           dfui_datasets_free(f->dataset_head);
680           f->dataset_head = NULL;
681 }
682 
683 struct dfui_field *
dfui_form_field_find(const struct dfui_form * f,const char * id)684 dfui_form_field_find(const struct dfui_form *f, const char *id)
685 {
686           struct dfui_field *fi;
687 
688           if (f == NULL)
689                     return(NULL);
690 
691           fi = f->field_head;
692           while (fi != NULL) {
693                     if (!strcmp(id, fi->id))
694                               return(fi);
695                     fi = fi->next;
696           }
697 
698           return(NULL);
699 }
700 
701 struct dfui_field *
dfui_form_field_get_first(const struct dfui_form * f)702 dfui_form_field_get_first(const struct dfui_form *f)
703 {
704           if (f == NULL)
705                     return(NULL);
706           return(f->field_head);
707 }
708 
709 int
dfui_form_field_count(const struct dfui_form * f)710 dfui_form_field_count(const struct dfui_form *f)
711 {
712           int n = 0;
713           struct dfui_field *fi;
714 
715           if (f == NULL)
716                     return(0);
717 
718           fi = f->field_head;
719           while (fi != NULL) {
720                     n++;
721                     fi = fi->next;
722           }
723 
724           return(n);
725 }
726 
727 struct dfui_action *
dfui_form_action_find(const struct dfui_form * f,const char * id)728 dfui_form_action_find(const struct dfui_form *f, const char *id)
729 {
730           struct dfui_action *a = f->action_head;
731 
732           while (a != NULL) {
733                     if (!strcmp(id, a->id))
734                               return(a);
735                     a = a->next;
736           }
737 
738           return(NULL);
739 }
740 
741 struct dfui_action *
dfui_form_action_get_first(const struct dfui_form * f)742 dfui_form_action_get_first(const struct dfui_form *f)
743 {
744           if (f == NULL)
745                     return(NULL);
746           return(f->action_head);
747 }
748 
749 int
dfui_form_action_count(const struct dfui_form * f)750 dfui_form_action_count(const struct dfui_form *f)
751 {
752           int n = 0;
753           struct dfui_action *a;
754 
755           if (f == NULL)
756                     return(0);
757 
758           a = f->action_head;
759           while (a != NULL) {
760                     n++;
761                     a = a->next;
762           }
763 
764           return(n);
765 }
766 
767 struct dfui_property *
dfui_form_property_set(struct dfui_form * f,const char * name,const char * value)768 dfui_form_property_set(struct dfui_form *f, const char *name, const char *value)
769 {
770           return(dfui_property_set(&f->property_head, name, value));
771 }
772 
773 const char *
dfui_form_property_get(const struct dfui_form * f,const char * name)774 dfui_form_property_get(const struct dfui_form *f, const char *name)
775 {
776           return(dfui_property_get(f->property_head, name));
777 }
778 
779 int
dfui_form_property_is(const struct dfui_form * f,const char * name,const char * value)780 dfui_form_property_is(const struct dfui_form *f, const char *name, const char *value)
781 {
782           struct dfui_property *h;
783 
784           if (f == NULL)
785                     return(0);
786           if ((h = dfui_property_find(f->property_head, name)) == NULL)
787                     return(0);
788           return(!strcmp(h->value, value));
789 }
790 
791 const char *
dfui_form_get_id(const struct dfui_form * f)792 dfui_form_get_id(const struct dfui_form *f)
793 {
794           if (f == NULL)
795                     return(NULL);       /* XXX ? */
796           return(f->id);
797 }
798 
799 struct dfui_info *
dfui_form_get_info(const struct dfui_form * f)800 dfui_form_get_info(const struct dfui_form *f)
801 {
802           if (f == NULL)
803                     return(NULL);
804           return(f->info);
805 }
806 
807 void
dfui_form_set_multiple(struct dfui_form * f,int multiple)808 dfui_form_set_multiple(struct dfui_form *f, int multiple)
809 {
810           if (f == NULL)
811                     return;
812           f->multiple = multiple;
813 }
814 
815 int
dfui_form_is_multiple(const struct dfui_form * f)816 dfui_form_is_multiple(const struct dfui_form *f)
817 {
818           if (f == NULL)
819                     return(0);
820           return(f->multiple);
821 }
822 
823 void
dfui_form_set_extensible(struct dfui_form * f,int extensible)824 dfui_form_set_extensible(struct dfui_form *f, int extensible)
825 {
826           if (f == NULL)
827                     return;
828           f->extensible = extensible;
829 }
830 
831 int
dfui_form_is_extensible(const struct dfui_form * f)832 dfui_form_is_extensible(const struct dfui_form *f)
833 {
834           if (f == NULL)
835                     return(0);
836           return(f->extensible);
837 }
838 
839 /*** CELLDATAS ***/
840 
841 struct dfui_celldata *
dfui_celldata_new(const char * field_id,const char * value)842 dfui_celldata_new(const char *field_id, const char *value)
843 {
844           struct dfui_celldata *c;
845 
846           AURA_MALLOC(c, dfui_celldata);
847           c->field_id = aura_strdup(field_id);
848           c->value = aura_strdup(value);
849 
850           return(c);
851 }
852 
853 void
dfui_celldata_free(struct dfui_celldata * c)854 dfui_celldata_free(struct dfui_celldata *c)
855 {
856           if (c == NULL)
857                     return;
858           free(c->field_id);
859           free(c->value);
860           AURA_FREE(c, dfui_celldata);
861 }
862 
863 void
dfui_celldatas_free(struct dfui_celldata * head)864 dfui_celldatas_free(struct dfui_celldata *head)
865 {
866           struct dfui_celldata *c;
867 
868           c = head;
869           while (c != NULL) {
870                     head = c->next;
871                     dfui_celldata_free(c);
872                     c = head;
873           }
874 }
875 
876 struct dfui_celldata *
dfui_celldata_find(struct dfui_celldata * head,const char * id)877 dfui_celldata_find(struct dfui_celldata *head, const char *id)
878 {
879           struct dfui_celldata *c;
880 
881           c = head;
882           while (c != NULL) {
883                     if (!strcmp(id, c->field_id))
884                               return(c);
885                     c = c->next;
886           }
887 
888           return(NULL);
889 }
890 
891 struct dfui_celldata *
dfui_celldata_get_next(const struct dfui_celldata * cd)892 dfui_celldata_get_next(const struct dfui_celldata *cd)
893 {
894           if (cd != NULL) {
895                     return(cd->next);
896           } else {
897                     return(NULL);
898           }
899 }
900 
901 const char *
dfui_celldata_get_field_id(const struct dfui_celldata * cd)902 dfui_celldata_get_field_id(const struct dfui_celldata *cd)
903 {
904           if (cd != NULL) {
905                     return(cd->field_id);
906           } else {
907                     return(NULL);
908           }
909 }
910 
911 const char *
dfui_celldata_get_value(const struct dfui_celldata * cd)912 dfui_celldata_get_value(const struct dfui_celldata *cd)
913 {
914           if (cd != NULL) {
915                     return(cd->value);
916           } else {
917                     return("");
918           }
919 }
920 
921 /*** DATASETS ***/
922 
923 struct dfui_dataset *
dfui_dataset_new(void)924 dfui_dataset_new(void)
925 {
926           struct dfui_dataset *ds;
927 
928           AURA_MALLOC(ds, dfui_dataset);
929           ds->celldata_head = NULL;
930           ds->next = NULL;
931 
932           return(ds);
933 }
934 
935 struct dfui_dataset *
dfui_dataset_dup(const struct dfui_dataset * ds)936 dfui_dataset_dup(const struct dfui_dataset *ds)
937 {
938           struct dfui_dataset *nds;
939           struct dfui_celldata *cd;
940 
941           nds = dfui_dataset_new();
942 
943           for (cd = ds->celldata_head; cd != NULL; cd = cd->next) {
944                     dfui_dataset_celldata_add(nds,
945                         cd->field_id, cd->value);
946           }
947 
948           return(nds);
949 }
950 
951 void
dfui_dataset_free(struct dfui_dataset * ds)952 dfui_dataset_free(struct dfui_dataset *ds)
953 {
954           dfui_celldatas_free(ds->celldata_head);
955           AURA_FREE(ds, dfui_dataset);
956 }
957 
958 void
dfui_datasets_free(struct dfui_dataset * head)959 dfui_datasets_free(struct dfui_dataset *head)
960 {
961           struct dfui_dataset *ds;
962 
963           ds = head;
964           while (ds != NULL) {
965                     head = ds->next;
966                     dfui_dataset_free(ds);
967                     ds = head;
968           }
969 }
970 
971 struct dfui_celldata *
dfui_dataset_celldata_add(struct dfui_dataset * ds,const char * field_id,const char * value)972 dfui_dataset_celldata_add(struct dfui_dataset *ds, const char *field_id, const char *value)
973 {
974           struct dfui_celldata *c;
975 
976           if (ds == NULL)
977                     return(NULL);
978 
979           c = dfui_celldata_new(field_id, value);
980           c->next = ds->celldata_head;
981           ds->celldata_head = c;
982 
983           return(c);
984 }
985 
986 struct dfui_celldata *
dfui_dataset_celldata_get_first(const struct dfui_dataset * ds)987 dfui_dataset_celldata_get_first(const struct dfui_dataset *ds)
988 {
989           if (ds == NULL)
990                     return(NULL);
991           return(ds->celldata_head);
992 }
993 
994 struct dfui_celldata *
dfui_dataset_celldata_find(const struct dfui_dataset * ds,const char * field_id)995 dfui_dataset_celldata_find(const struct dfui_dataset *ds, const char *field_id)
996 {
997           if (ds == NULL)
998                     return(NULL);
999           return(dfui_celldata_find(ds->celldata_head, field_id));
1000 }
1001 
1002 struct dfui_dataset *
dfui_dataset_get_next(const struct dfui_dataset * ds)1003 dfui_dataset_get_next(const struct dfui_dataset *ds)
1004 {
1005           if (ds == NULL)
1006                     return(NULL);
1007           return(ds->next);
1008 }
1009 
1010 /*
1011  * Returns the value of the celldata with the given id found in the
1012  * given dataset.  If no such celldata is found, a constant zero-length
1013  * string is returned.  As such, the return value of this function is
1014  * guaranteed to not be NULL and must NEVER be freed after use.
1015  */
1016 const char *
dfui_dataset_get_value(const struct dfui_dataset * ds,const char * id)1017 dfui_dataset_get_value(const struct dfui_dataset *ds, const char *id)
1018 {
1019           struct dfui_celldata *cd;
1020 
1021           if ((cd = dfui_dataset_celldata_find(ds, id)) != NULL) {
1022                     return(dfui_celldata_get_value(cd));
1023           } else {
1024                     return("");
1025           }
1026 }
1027 
1028 /*
1029  * Allocates a string to hold the value of the celldata with the
1030  * given id found in the given dataset.  Even if no such celldata
1031  * is found, an allocated, zero-length string is returned.  As such,
1032  * the return value of this function is guaranteed to not be NULL,
1033  * and must ALWAYS be freed after use.
1034  */
1035 char *
dfui_dataset_dup_value(const struct dfui_dataset * ds,const char * id)1036 dfui_dataset_dup_value(const struct dfui_dataset *ds, const char *id)
1037 {
1038           return(aura_strdup(dfui_dataset_get_value(ds, id)));
1039 }
1040 
1041 /*** RESPONSES ***/
1042 
1043 struct dfui_response *
dfui_response_new(const char * form_id,const char * action_id)1044 dfui_response_new(const char *form_id, const char *action_id)
1045 {
1046           struct dfui_response *r;
1047 
1048           AURA_MALLOC(r, dfui_response);
1049           r->form_id = aura_strdup(form_id);
1050           r->action_id = aura_strdup(action_id);
1051           r->dataset_head = NULL;
1052 
1053           return(r);
1054 }
1055 
1056 void
dfui_response_free(struct dfui_response * r)1057 dfui_response_free(struct dfui_response *r)
1058 {
1059           free(r->form_id);
1060           free(r->action_id);
1061           dfui_datasets_free(r->dataset_head);
1062           AURA_FREE(r, dfui_response);
1063 }
1064 
1065 void
dfui_response_dataset_add(struct dfui_response * r,struct dfui_dataset * ds)1066 dfui_response_dataset_add(struct dfui_response *r, struct dfui_dataset *ds)
1067 {
1068           if (ds == NULL || r == NULL)
1069                     return;
1070           ds->next = r->dataset_head;
1071           r->dataset_head = ds;
1072 }
1073 
1074 struct dfui_dataset *
dfui_response_dataset_get_first(const struct dfui_response * r)1075 dfui_response_dataset_get_first(const struct dfui_response *r)
1076 {
1077           if (r == NULL)
1078                     return(NULL);
1079           return(r->dataset_head);
1080 }
1081 
1082 int
dfui_response_dataset_count(const struct dfui_response * r)1083 dfui_response_dataset_count(const struct dfui_response *r)
1084 {
1085           int n = 0;
1086           struct dfui_dataset *ds;
1087 
1088           if (r == NULL)
1089                     return(0);
1090 
1091           ds = r->dataset_head;
1092           while (ds != NULL) {
1093                     n++;
1094                     ds = ds->next;
1095           }
1096 
1097           return(n);
1098 }
1099 
1100 const char *
dfui_response_get_form_id(const struct dfui_response * r)1101 dfui_response_get_form_id(const struct dfui_response *r)
1102 {
1103           if (r == NULL)
1104                     return(NULL);       /* XXX ? */
1105           return(r->form_id);
1106 }
1107 
1108 const char *
dfui_response_get_action_id(const struct dfui_response * r)1109 dfui_response_get_action_id(const struct dfui_response *r)
1110 {
1111           if (r == NULL)
1112                     return(NULL);       /* XXX ? */
1113           return(r->action_id);
1114 }
1115 
1116 /* PROGRESS BARS */
1117 
1118 struct dfui_progress *
dfui_progress_new(struct dfui_info * info,int amount)1119 dfui_progress_new(struct dfui_info *info, int amount)
1120 {
1121           struct dfui_progress *pr;
1122 
1123           AURA_MALLOC(pr, dfui_progress);
1124           pr->info = info;
1125           pr->amount = amount;
1126           pr->streaming = 0;
1127           pr->msg_line = NULL;
1128 
1129           return(pr);
1130 }
1131 
1132 void
dfui_progress_free(struct dfui_progress * pr)1133 dfui_progress_free(struct dfui_progress *pr)
1134 {
1135           if (pr == NULL)
1136                     return;
1137           dfui_info_free(pr->info);
1138           if (pr->msg_line != NULL)
1139                     free(pr->msg_line);
1140           AURA_FREE(pr, dfui_progress);
1141 }
1142 
1143 struct dfui_info *
dfui_progress_get_info(const struct dfui_progress * pr)1144 dfui_progress_get_info(const struct dfui_progress *pr)
1145 {
1146           if (pr == NULL)
1147                     return(NULL);
1148           return(pr->info);
1149 }
1150 
1151 void
dfui_progress_set_amount(struct dfui_progress * pr,int amount)1152 dfui_progress_set_amount(struct dfui_progress *pr, int amount)
1153 {
1154           if (pr == NULL)
1155                     return;
1156           pr->amount = amount;
1157 }
1158 
1159 int
dfui_progress_get_amount(const struct dfui_progress * pr)1160 dfui_progress_get_amount(const struct dfui_progress *pr)
1161 {
1162           if (pr == NULL)
1163                     return(0);
1164           return(pr->amount);
1165 }
1166 
1167 void
dfui_progress_set_streaming(struct dfui_progress * pr,int streaming)1168 dfui_progress_set_streaming(struct dfui_progress *pr, int streaming)
1169 {
1170           if (pr == NULL)
1171                     return;
1172           pr->streaming = streaming;
1173 }
1174 
1175 int
dfui_progress_get_streaming(const struct dfui_progress * pr)1176 dfui_progress_get_streaming(const struct dfui_progress *pr)
1177 {
1178           if (pr == NULL)
1179                     return(0);
1180           return(pr->streaming);
1181 }
1182 
1183 void
dfui_progress_set_msg_line(struct dfui_progress * pr,const char * msg_line)1184 dfui_progress_set_msg_line(struct dfui_progress *pr, const char *msg_line)
1185 {
1186           if (pr == NULL)
1187                     return;
1188           if (pr->msg_line != NULL)
1189                     free(pr->msg_line);
1190           pr->msg_line = aura_strdup(msg_line);
1191 }
1192 
1193 const char *
dfui_progress_get_msg_line(const struct dfui_progress * pr)1194 dfui_progress_get_msg_line(const struct dfui_progress *pr)
1195 {
1196           if (pr == NULL)
1197                     return("");
1198           if (pr->msg_line == NULL)
1199                     return("");
1200           return(pr->msg_line);
1201 }
1202