Annotation of src/usr.bin/tmux/options.c, Revision 1.8
1.8 ! nicm 1: /* $OpenBSD: options.c,v 1.7 2012/01/21 11:12:13 nicm Exp $ */
1.1 nicm 2:
3: /*
4: * Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
5: *
6: * Permission to use, copy, modify, and distribute this software for any
7: * purpose with or without fee is hereby granted, provided that the above
8: * copyright notice and this permission notice appear in all copies.
9: *
10: * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11: * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12: * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13: * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14: * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
15: * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
16: * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
17: */
18:
19: #include <sys/types.h>
20:
21: #include <stdarg.h>
1.8 ! nicm 22: #include <stdlib.h>
1.1 nicm 23: #include <string.h>
24:
25: #include "tmux.h"
26:
27: /*
28: * Option handling; each option has a name, type and value and is stored in
29: * a splay tree.
30: */
31:
1.7 nicm 32: RB_GENERATE(options_tree, options_entry, entry, options_cmp);
1.1 nicm 33:
34: int
35: options_cmp(struct options_entry *o1, struct options_entry *o2)
36: {
37: return (strcmp(o1->name, o2->name));
38: }
39:
40: void
41: options_init(struct options *oo, struct options *parent)
42: {
1.7 nicm 43: RB_INIT(&oo->tree);
1.1 nicm 44: oo->parent = parent;
45: }
46:
47: void
48: options_free(struct options *oo)
49: {
50: struct options_entry *o;
51:
1.7 nicm 52: while (!RB_EMPTY(&oo->tree)) {
53: o = RB_ROOT(&oo->tree);
54: RB_REMOVE(options_tree, &oo->tree, o);
1.8 ! nicm 55: free(o->name);
1.1 nicm 56: if (o->type == OPTIONS_STRING)
1.8 ! nicm 57: free(o->str);
! 58: free(o);
1.1 nicm 59: }
60: }
61:
62: struct options_entry *
63: options_find1(struct options *oo, const char *name)
64: {
65: struct options_entry p;
66:
67: p.name = (char *) name;
1.7 nicm 68: return (RB_FIND(options_tree, &oo->tree, &p));
1.1 nicm 69: }
70:
71: struct options_entry *
72: options_find(struct options *oo, const char *name)
73: {
74: struct options_entry *o, p;
75:
76: p.name = (char *) name;
1.7 nicm 77: o = RB_FIND(options_tree, &oo->tree, &p);
1.1 nicm 78: while (o == NULL) {
79: oo = oo->parent;
80: if (oo == NULL)
81: break;
1.7 nicm 82: o = RB_FIND(options_tree, &oo->tree, &p);
1.1 nicm 83: }
84: return (o);
85: }
86:
1.2 nicm 87: void
1.1 nicm 88: options_remove(struct options *oo, const char *name)
89: {
90: struct options_entry *o;
91:
92: if ((o = options_find1(oo, name)) == NULL)
1.2 nicm 93: return;
1.1 nicm 94:
1.7 nicm 95: RB_REMOVE(options_tree, &oo->tree, o);
1.8 ! nicm 96: free(o->name);
1.1 nicm 97: if (o->type == OPTIONS_STRING)
1.8 ! nicm 98: free(o->str);
! 99: free(o);
1.1 nicm 100: }
101:
1.4 nicm 102: struct options_entry *printflike3
1.1 nicm 103: options_set_string(struct options *oo, const char *name, const char *fmt, ...)
104: {
105: struct options_entry *o;
106: va_list ap;
107:
108: if ((o = options_find1(oo, name)) == NULL) {
109: o = xmalloc(sizeof *o);
110: o->name = xstrdup(name);
1.7 nicm 111: RB_INSERT(options_tree, &oo->tree, o);
1.1 nicm 112: } else if (o->type == OPTIONS_STRING)
1.8 ! nicm 113: free(o->str);
1.1 nicm 114:
115: va_start(ap, fmt);
116: o->type = OPTIONS_STRING;
1.3 nicm 117: xvasprintf(&o->str, fmt, ap);
1.1 nicm 118: va_end(ap);
1.4 nicm 119: return (o);
1.1 nicm 120: }
121:
122: char *
123: options_get_string(struct options *oo, const char *name)
124: {
125: struct options_entry *o;
126:
127: if ((o = options_find(oo, name)) == NULL)
128: fatalx("missing option");
129: if (o->type != OPTIONS_STRING)
130: fatalx("option not a string");
1.3 nicm 131: return (o->str);
1.1 nicm 132: }
133:
1.4 nicm 134: struct options_entry *
1.1 nicm 135: options_set_number(struct options *oo, const char *name, long long value)
136: {
137: struct options_entry *o;
138:
139: if ((o = options_find1(oo, name)) == NULL) {
140: o = xmalloc(sizeof *o);
141: o->name = xstrdup(name);
1.7 nicm 142: RB_INSERT(options_tree, &oo->tree, o);
1.1 nicm 143: } else if (o->type == OPTIONS_STRING)
1.8 ! nicm 144: free(o->str);
1.1 nicm 145:
146: o->type = OPTIONS_NUMBER;
1.3 nicm 147: o->num = value;
1.4 nicm 148: return (o);
1.1 nicm 149: }
150:
151: long long
152: options_get_number(struct options *oo, const char *name)
153: {
154: struct options_entry *o;
155:
156: if ((o = options_find(oo, name)) == NULL)
157: fatalx("missing option");
158: if (o->type != OPTIONS_NUMBER)
159: fatalx("option not a number");
1.3 nicm 160: return (o->num);
1.1 nicm 161: }