options-table.c revision 1.60
1/* $OpenBSD: options-table.c,v 1.60 2015/05/12 15:29:29 nicm Exp $ */
2
3/*
4 * Copyright (c) 2011 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 <string.h>
22#include <paths.h>
23
24#include "tmux.h"
25
26/*
27 * This file has a tables with all the server, session and window
28 * options. These tables are the master copy of the options with their real
29 * (user-visible) types, range limits and default values. At start these are
30 * copied into the runtime global options trees (which only has number and
31 * string types). These tables are then used to look up the real type when the
32 * user sets an option or its value needs to be shown.
33 */
34
35/* Choice option type lists. */
36const char *options_table_mode_keys_list[] = {
37	"emacs", "vi", NULL
38};
39const char *options_table_clock_mode_style_list[] = {
40	"12", "24", NULL
41};
42const char *options_table_status_keys_list[] = {
43	"emacs", "vi", NULL
44};
45const char *options_table_status_justify_list[] = {
46	"left", "centre", "right", NULL
47};
48const char *options_table_status_position_list[] = {
49	"top", "bottom", NULL
50};
51const char *options_table_bell_action_list[] = {
52	"none", "any", "current", "other", NULL
53};
54
55/* Server options. */
56const struct options_table_entry server_options_table[] = {
57	{ .name = "buffer-limit",
58	  .type = OPTIONS_TABLE_NUMBER,
59	  .minimum = 1,
60	  .maximum = INT_MAX,
61	  .default_num = 20
62	},
63
64	{ .name = "default-terminal",
65	  .type = OPTIONS_TABLE_STRING,
66	  .default_str = "screen"
67	},
68
69	{ .name = "escape-time",
70	  .type = OPTIONS_TABLE_NUMBER,
71	  .minimum = 0,
72	  .maximum = INT_MAX,
73	  .default_num = 500
74	},
75
76	{ .name = "exit-unattached",
77	  .type = OPTIONS_TABLE_FLAG,
78	  .default_num = 0
79	},
80
81	{ .name = "focus-events",
82	  .type = OPTIONS_TABLE_FLAG,
83	  .default_num = 0
84	},
85
86	{ .name = "message-limit",
87	  .type = OPTIONS_TABLE_NUMBER,
88	  .minimum = 0,
89	  .maximum = INT_MAX,
90	  .default_num = 100
91	},
92
93	{ .name = "quiet",
94	  .type = OPTIONS_TABLE_FLAG,
95	  .default_num = 0
96	},
97
98	{ .name = "set-clipboard",
99	  .type = OPTIONS_TABLE_FLAG,
100	  .default_num = 1
101	},
102
103	{ .name = "terminal-overrides",
104	  .type = OPTIONS_TABLE_STRING,
105	  .default_str = "*256col*:colors=256"
106	                 ",xterm*:XT:Ms=\\E]52;%p1%s;%p2%s\\007"
107	                 ":Cs=\\E]12;%p1%s\\007:Cr=\\E]112\\007"
108			 ":Ss=\\E[%p1%d q:Se=\\E[2 q,screen*:XT"
109	},
110
111	{ .name = NULL }
112};
113
114/* Session options. */
115const struct options_table_entry session_options_table[] = {
116	{ .name = "assume-paste-time",
117	  .type = OPTIONS_TABLE_NUMBER,
118	  .minimum = 0,
119	  .maximum = INT_MAX,
120	  .default_num = 1,
121	},
122
123	{ .name = "base-index",
124	  .type = OPTIONS_TABLE_NUMBER,
125	  .minimum = 0,
126	  .maximum = INT_MAX,
127	  .default_num = 0
128	},
129
130	{ .name = "bell-action",
131	  .type = OPTIONS_TABLE_CHOICE,
132	  .choices = options_table_bell_action_list,
133	  .default_num = BELL_ANY
134	},
135
136	{ .name = "bell-on-alert",
137	  .type = OPTIONS_TABLE_FLAG,
138	  .default_num = 0
139	},
140
141	{ .name = "default-command",
142	  .type = OPTIONS_TABLE_STRING,
143	  .default_str = ""
144	},
145
146	{ .name = "default-shell",
147	  .type = OPTIONS_TABLE_STRING,
148	  .default_str = _PATH_BSHELL
149	},
150
151	{ .name = "destroy-unattached",
152	  .type = OPTIONS_TABLE_FLAG,
153	  .default_num = 0
154	},
155
156	{ .name = "detach-on-destroy",
157	  .type = OPTIONS_TABLE_FLAG,
158	  .default_num = 1
159	},
160
161	{ .name = "display-panes-active-colour",
162	  .type = OPTIONS_TABLE_COLOUR,
163	  .default_num = 1
164	},
165
166	{ .name = "display-panes-colour",
167	  .type = OPTIONS_TABLE_COLOUR,
168	  .default_num = 4
169	},
170
171	{ .name = "display-panes-time",
172	  .type = OPTIONS_TABLE_NUMBER,
173	  .minimum = 1,
174	  .maximum = INT_MAX,
175	  .default_num = 1000
176	},
177
178	{ .name = "display-time",
179	  .type = OPTIONS_TABLE_NUMBER,
180	  .minimum = 1,
181	  .maximum = INT_MAX,
182	  .default_num = 750
183	},
184
185	{ .name = "history-limit",
186	  .type = OPTIONS_TABLE_NUMBER,
187	  .minimum = 0,
188	  .maximum = INT_MAX,
189	  .default_num = 2000
190	},
191
192	{ .name = "lock-after-time",
193	  .type = OPTIONS_TABLE_NUMBER,
194	  .minimum = 0,
195	  .maximum = INT_MAX,
196	  .default_num = 0
197	},
198
199	{ .name = "lock-command",
200	  .type = OPTIONS_TABLE_STRING,
201	  .default_str = "lock -np"
202	},
203
204	{ .name = "lock-server",
205	  .type = OPTIONS_TABLE_FLAG,
206	  .default_num = 1
207	},
208
209	{ .name = "message-attr",
210	  .type = OPTIONS_TABLE_ATTRIBUTES,
211	  .default_num = 0,
212	  .style = "message-style"
213	},
214
215	{ .name = "message-bg",
216	  .type = OPTIONS_TABLE_COLOUR,
217	  .default_num = 3,
218	  .style = "message-style"
219	},
220
221	{ .name = "message-command-attr",
222	  .type = OPTIONS_TABLE_ATTRIBUTES,
223	  .default_num = 0,
224	  .style = "message-command-style"
225	},
226
227	{ .name = "message-command-bg",
228	  .type = OPTIONS_TABLE_COLOUR,
229	  .default_num = 0,
230	  .style = "message-command-style"
231	},
232
233	{ .name = "message-command-fg",
234	  .type = OPTIONS_TABLE_COLOUR,
235	  .default_num = 3,
236	  .style = "message-command-style"
237	},
238
239	{ .name = "message-command-style",
240	  .type = OPTIONS_TABLE_STYLE,
241	  .default_str = "bg=black,fg=yellow"
242	},
243
244	{ .name = "message-fg",
245	  .type = OPTIONS_TABLE_COLOUR,
246	  .default_num = 0,
247	  .style = "message-style"
248	},
249
250	{ .name = "message-style",
251	  .type = OPTIONS_TABLE_STYLE,
252	  .default_str = "bg=yellow,fg=black"
253	},
254
255	{ .name = "mouse",
256	  .type = OPTIONS_TABLE_FLAG,
257	  .default_num = 0
258	},
259
260	{ .name = "mouse-utf8",
261	  .type = OPTIONS_TABLE_FLAG,
262	  .default_num = 0
263	},
264
265	{ .name = "prefix",
266	  .type = OPTIONS_TABLE_KEY,
267	  .default_num = '\002',
268	},
269
270	{ .name = "prefix2",
271	  .type = OPTIONS_TABLE_KEY,
272	  .default_num = KEYC_NONE,
273	},
274
275	{ .name = "renumber-windows",
276	  .type = OPTIONS_TABLE_FLAG,
277	  .default_num = 0
278	},
279
280	{ .name = "repeat-time",
281	  .type = OPTIONS_TABLE_NUMBER,
282	  .minimum = 0,
283	  .maximum = SHRT_MAX,
284	  .default_num = 500
285	},
286
287	{ .name = "set-remain-on-exit",
288	  .type = OPTIONS_TABLE_FLAG,
289	  .default_num = 0
290	},
291
292	{ .name = "set-titles",
293	  .type = OPTIONS_TABLE_FLAG,
294	  .default_num = 0
295	},
296
297	{ .name = "set-titles-string",
298	  .type = OPTIONS_TABLE_STRING,
299	  .default_str = "#S:#I:#W - \"#T\" #{session_alerts}"
300	},
301
302	{ .name = "status",
303	  .type = OPTIONS_TABLE_FLAG,
304	  .default_num = 1
305	},
306
307	{ .name = "status-attr",
308	  .type = OPTIONS_TABLE_ATTRIBUTES,
309	  .default_num = 0,
310	  .style = "status-style"
311	},
312
313	{ .name = "status-bg",
314	  .type = OPTIONS_TABLE_COLOUR,
315	  .default_num = 2,
316	  .style = "status-style"
317	},
318
319	{ .name = "status-fg",
320	  .type = OPTIONS_TABLE_COLOUR,
321	  .default_num = 0,
322	  .style = "status-style"
323	},
324
325	{ .name = "status-interval",
326	  .type = OPTIONS_TABLE_NUMBER,
327	  .minimum = 0,
328	  .maximum = INT_MAX,
329	  .default_num = 15
330	},
331
332	{ .name = "status-justify",
333	  .type = OPTIONS_TABLE_CHOICE,
334	  .choices = options_table_status_justify_list,
335	  .default_num = 0
336	},
337
338	{ .name = "status-keys",
339	  .type = OPTIONS_TABLE_CHOICE,
340	  .choices = options_table_status_keys_list,
341	  .default_num = MODEKEY_EMACS
342	},
343
344	{ .name = "status-left",
345	  .type = OPTIONS_TABLE_STRING,
346	  .default_str = "[#S] "
347	},
348
349	{ .name = "status-left-attr",
350	  .type = OPTIONS_TABLE_ATTRIBUTES,
351	  .default_num = 0,
352	  .style = "status-left-style"
353	},
354
355	{ .name = "status-left-bg",
356	  .type = OPTIONS_TABLE_COLOUR,
357	  .default_num = 8,
358	  .style = "status-left-style"
359	},
360
361	{ .name = "status-left-fg",
362	  .type = OPTIONS_TABLE_COLOUR,
363	  .default_num = 8,
364	  .style = "status-left-style"
365	},
366
367	{ .name = "status-left-length",
368	  .type = OPTIONS_TABLE_NUMBER,
369	  .minimum = 0,
370	  .maximum = SHRT_MAX,
371	  .default_num = 10
372	},
373
374	{ .name = "status-left-style",
375	  .type = OPTIONS_TABLE_STYLE,
376	  .default_str = "default"
377	},
378
379	{ .name = "status-position",
380	  .type = OPTIONS_TABLE_CHOICE,
381	  .choices = options_table_status_position_list,
382	  .default_num = 1
383	},
384
385	{ .name = "status-right",
386	  .type = OPTIONS_TABLE_STRING,
387	  .default_str = " \"#{=21:pane_title}\" %H:%M %d-%b-%y"
388	},
389
390	{ .name = "status-right-attr",
391	  .type = OPTIONS_TABLE_ATTRIBUTES,
392	  .default_num = 0,
393	  .style = "status-right-style"
394	},
395
396	{ .name = "status-right-bg",
397	  .type = OPTIONS_TABLE_COLOUR,
398	  .default_num = 8,
399	  .style = "status-right-style"
400	},
401
402	{ .name = "status-right-fg",
403	  .type = OPTIONS_TABLE_COLOUR,
404	  .default_num = 8,
405	  .style = "status-right-style"
406	},
407
408	{ .name = "status-right-length",
409	  .type = OPTIONS_TABLE_NUMBER,
410	  .minimum = 0,
411	  .maximum = SHRT_MAX,
412	  .default_num = 40
413	},
414
415	{ .name = "status-right-style",
416	  .type = OPTIONS_TABLE_STYLE,
417	  .default_str = "default"
418	},
419
420	{ .name = "status-style",
421	  .type = OPTIONS_TABLE_STYLE,
422	  .default_str = "bg=green,fg=black"
423	},
424
425	{ .name = "status-utf8",
426	  .type = OPTIONS_TABLE_FLAG,
427	  .default_num = 0 /* overridden in main() */
428	},
429
430	{ .name = "update-environment",
431	  .type = OPTIONS_TABLE_STRING,
432	  .default_str = "DISPLAY SSH_ASKPASS SSH_AUTH_SOCK SSH_AGENT_PID "
433	                 "SSH_CONNECTION WINDOWID XAUTHORITY"
434
435	},
436
437	{ .name = "visual-activity",
438	  .type = OPTIONS_TABLE_FLAG,
439	  .default_num = 0
440	},
441
442	{ .name = "visual-bell",
443	  .type = OPTIONS_TABLE_FLAG,
444	  .default_num = 0
445	},
446
447	{ .name = "visual-silence",
448	  .type = OPTIONS_TABLE_FLAG,
449	  .default_num = 0
450	},
451
452	{ .name = "word-separators",
453	  .type = OPTIONS_TABLE_STRING,
454	  .default_str = " -_@"
455	},
456
457	{ .name = NULL }
458};
459
460/* Window options. */
461const struct options_table_entry window_options_table[] = {
462	{ .name = "aggressive-resize",
463	  .type = OPTIONS_TABLE_FLAG,
464	  .default_num = 0
465	},
466
467	{ .name = "allow-rename",
468	  .type = OPTIONS_TABLE_FLAG,
469	  .default_num = 1
470	},
471
472	{ .name = "alternate-screen",
473	  .type = OPTIONS_TABLE_FLAG,
474	  .default_num = 1
475	},
476
477	{ .name = "automatic-rename",
478	  .type = OPTIONS_TABLE_FLAG,
479	  .default_num = 1
480	},
481
482	{ .name = "automatic-rename-format",
483	  .type = OPTIONS_TABLE_STRING,
484	  .default_str = "#{?pane_in_mode,[tmux],#{pane_current_command}}"
485	                 "#{?pane_dead,[dead],}"
486	},
487
488	{ .name = "clock-mode-colour",
489	  .type = OPTIONS_TABLE_COLOUR,
490	  .default_num = 4
491	},
492
493	{ .name = "clock-mode-style",
494	  .type = OPTIONS_TABLE_CHOICE,
495	  .choices = options_table_clock_mode_style_list,
496	  .default_num = 1
497	},
498
499	{ .name = "force-height",
500	  .type = OPTIONS_TABLE_NUMBER,
501	  .minimum = 0,
502	  .maximum = INT_MAX,
503	  .default_num = 0
504	},
505
506	{ .name = "force-width",
507	  .type = OPTIONS_TABLE_NUMBER,
508	  .minimum = 0,
509	  .maximum = INT_MAX,
510	  .default_num = 0
511	},
512
513	{ .name = "main-pane-height",
514	  .type = OPTIONS_TABLE_NUMBER,
515	  .minimum = 1,
516	  .maximum = INT_MAX,
517	  .default_num = 24
518	},
519
520	{ .name = "main-pane-width",
521	  .type = OPTIONS_TABLE_NUMBER,
522	  .minimum = 1,
523	  .maximum = INT_MAX,
524	  .default_num = 80
525	},
526
527	{ .name = "mode-attr",
528	  .type = OPTIONS_TABLE_ATTRIBUTES,
529	  .default_num = 0,
530	  .style = "mode-style"
531	},
532
533	{ .name = "mode-bg",
534	  .type = OPTIONS_TABLE_COLOUR,
535	  .default_num = 3,
536	  .style = "mode-style"
537	},
538
539	{ .name = "mode-fg",
540	  .type = OPTIONS_TABLE_COLOUR,
541	  .default_num = 0,
542	  .style = "mode-style"
543	},
544
545	{ .name = "mode-keys",
546	  .type = OPTIONS_TABLE_CHOICE,
547	  .choices = options_table_mode_keys_list,
548	  .default_num = MODEKEY_EMACS
549	},
550
551	{ .name = "mode-style",
552	  .type = OPTIONS_TABLE_STYLE,
553	  .default_str = "bg=yellow,fg=black"
554	},
555
556	{ .name = "monitor-activity",
557	  .type = OPTIONS_TABLE_FLAG,
558	  .default_num = 0
559	},
560
561	{ .name = "monitor-silence",
562	  .type = OPTIONS_TABLE_NUMBER,
563	  .minimum = 0,
564	  .maximum = INT_MAX,
565	  .default_num = 0
566	},
567
568	{ .name = "other-pane-height",
569	  .type = OPTIONS_TABLE_NUMBER,
570	  .minimum = 0,
571	  .maximum = INT_MAX,
572	  .default_num = 0
573	},
574
575	{ .name = "other-pane-width",
576	  .type = OPTIONS_TABLE_NUMBER,
577	  .minimum = 0,
578	  .maximum = INT_MAX,
579	  .default_num = 0
580	},
581
582	{ .name = "pane-active-border-bg",
583	  .type = OPTIONS_TABLE_COLOUR,
584	  .default_num = 8,
585	  .style = "pane-active-border-style"
586	},
587
588	{ .name = "pane-active-border-fg",
589	  .type = OPTIONS_TABLE_COLOUR,
590	  .default_num = 2,
591	  .style = "pane-active-border-style"
592	},
593
594	{ .name = "pane-active-border-style",
595	  .type = OPTIONS_TABLE_STYLE,
596	  .default_str = "fg=green"
597	},
598
599	{ .name = "pane-base-index",
600	  .type = OPTIONS_TABLE_NUMBER,
601	  .minimum = 0,
602	  .maximum = USHRT_MAX,
603	  .default_num = 0
604	},
605
606	{ .name = "pane-border-bg",
607	  .type = OPTIONS_TABLE_COLOUR,
608	  .default_num = 8,
609	  .style = "pane-border-style"
610	},
611
612	{ .name = "pane-border-fg",
613	  .type = OPTIONS_TABLE_COLOUR,
614	  .default_num = 8,
615	  .style = "pane-border-style"
616	},
617
618	{ .name = "pane-border-style",
619	  .type = OPTIONS_TABLE_STYLE,
620	  .default_str = "default"
621	},
622
623	{ .name = "remain-on-exit",
624	  .type = OPTIONS_TABLE_FLAG,
625	  .default_num = 0
626	},
627
628	{ .name = "synchronize-panes",
629	  .type = OPTIONS_TABLE_FLAG,
630	  .default_num = 0
631	},
632
633	{ .name = "utf8",
634	  .type = OPTIONS_TABLE_FLAG,
635	  .default_num = 0 /* overridden in main() */
636	},
637
638	{ .name = "window-active-style",
639	  .type = OPTIONS_TABLE_STYLE,
640	  .default_str = "default"
641	},
642
643	{ .name = "window-style",
644	  .type = OPTIONS_TABLE_STYLE,
645	  .default_str = "default"
646	},
647
648	{ .name = "window-status-activity-attr",
649	  .type = OPTIONS_TABLE_ATTRIBUTES,
650	  .default_num = GRID_ATTR_REVERSE,
651	  .style = "window-status-activity-style"
652	},
653
654	{ .name = "window-status-activity-bg",
655	  .type = OPTIONS_TABLE_COLOUR,
656	  .default_num = 8,
657	  .style = "window-status-activity-style"
658	},
659
660	{ .name = "window-status-activity-fg",
661	  .type = OPTIONS_TABLE_COLOUR,
662	  .default_num = 8,
663	  .style = "window-status-activity-style"
664	},
665
666	{ .name = "window-status-activity-style",
667	  .type = OPTIONS_TABLE_STYLE,
668	  .default_str = "reverse"
669	},
670
671	{ .name = "window-status-attr",
672	  .type = OPTIONS_TABLE_ATTRIBUTES,
673	  .default_num = 0,
674	  .style = "window-status-style"
675	},
676
677	{ .name = "window-status-bell-attr",
678	  .type = OPTIONS_TABLE_ATTRIBUTES,
679	  .default_num = GRID_ATTR_REVERSE,
680	  .style = "window-status-bell-style"
681	},
682
683	{ .name = "window-status-bell-bg",
684	  .type = OPTIONS_TABLE_COLOUR,
685	  .default_num = 8,
686	  .style = "window-status-bell-style"
687	},
688
689	{ .name = "window-status-bell-fg",
690	  .type = OPTIONS_TABLE_COLOUR,
691	  .default_num = 8,
692	  .style = "window-status-bell-style"
693	},
694
695	{ .name = "window-status-bell-style",
696	  .type = OPTIONS_TABLE_STYLE,
697	  .default_str = "reverse"
698	},
699
700	{ .name = "window-status-bg",
701	  .type = OPTIONS_TABLE_COLOUR,
702	  .default_num = 8,
703	  .style = "window-status-style"
704	},
705
706	{ .name = "window-status-current-attr",
707	  .type = OPTIONS_TABLE_ATTRIBUTES,
708	  .default_num = 0,
709	  .style = "window-status-current-style"
710	},
711
712	{ .name = "window-status-current-bg",
713	  .type = OPTIONS_TABLE_COLOUR,
714	  .default_num = 8,
715	  .style = "window-status-current-style"
716	},
717
718	{ .name = "window-status-current-fg",
719	  .type = OPTIONS_TABLE_COLOUR,
720	  .default_num = 8,
721	  .style = "window-status-current-style"
722	},
723
724	{ .name = "window-status-current-format",
725	  .type = OPTIONS_TABLE_STRING,
726	  .default_str = "#I:#W#{?window_flags,#{window_flags}, }"
727	},
728
729	{ .name = "window-status-current-style",
730	  .type = OPTIONS_TABLE_STYLE,
731	  .default_str = "default"
732	},
733
734	{ .name = "window-status-fg",
735	  .type = OPTIONS_TABLE_COLOUR,
736	  .default_num = 8,
737	  .style = "window-status-style"
738	},
739
740	{ .name = "window-status-format",
741	  .type = OPTIONS_TABLE_STRING,
742	  .default_str = "#I:#W#{?window_flags,#{window_flags}, }"
743	},
744
745	{ .name = "window-status-last-attr",
746	  .type = OPTIONS_TABLE_ATTRIBUTES,
747	  .default_num = 0,
748	  .style = "window-status-last-style"
749	},
750
751	{ .name = "window-status-last-bg",
752	  .type = OPTIONS_TABLE_COLOUR,
753	  .default_num = 8,
754	  .style = "window-status-last-style"
755	},
756
757	{ .name = "window-status-last-fg",
758	  .type = OPTIONS_TABLE_COLOUR,
759	  .default_num = 8,
760	  .style = "window-status-last-style"
761	},
762
763	{ .name = "window-status-last-style",
764	  .type = OPTIONS_TABLE_STYLE,
765	  .default_str = "default"
766	},
767
768	{ .name = "window-status-separator",
769	  .type = OPTIONS_TABLE_STRING,
770	  .default_str = " "
771	},
772
773	{ .name = "window-status-style",
774	  .type = OPTIONS_TABLE_STYLE,
775	  .default_str = "default"
776	},
777
778	{ .name = "wrap-search",
779	  .type = OPTIONS_TABLE_FLAG,
780	  .default_num = 1
781	},
782
783	{ .name = "xterm-keys",
784	  .type = OPTIONS_TABLE_FLAG,
785	  .default_num = 0
786	},
787
788	{ .name = NULL }
789};
790
791/* Populate an options tree from a table. */
792void
793options_table_populate_tree(
794    const struct options_table_entry *table, struct options *oo)
795{
796	const struct options_table_entry	*oe;
797
798	for (oe = table; oe->name != NULL; oe++) {
799		switch (oe->type) {
800		case OPTIONS_TABLE_STRING:
801			options_set_string(oo, oe->name, "%s", oe->default_str);
802			break;
803		case OPTIONS_TABLE_STYLE:
804			options_set_style(oo, oe->name, oe->default_str, 0);
805			break;
806		default:
807			options_set_number(oo, oe->name, oe->default_num);
808			break;
809		}
810	}
811}
812
813/* Print an option using its type from the table. */
814const char *
815options_table_print_entry(const struct options_table_entry *oe,
816    struct options_entry *o, int no_quotes)
817{
818	static char	 out[BUFSIZ];
819	const char	*s;
820
821	*out = '\0';
822	switch (oe->type) {
823	case OPTIONS_TABLE_STRING:
824		if (no_quotes)
825			xsnprintf(out, sizeof out, "%s", o->str);
826		else
827			xsnprintf(out, sizeof out, "\"%s\"", o->str);
828		break;
829	case OPTIONS_TABLE_NUMBER:
830		xsnprintf(out, sizeof out, "%lld", o->num);
831		break;
832	case OPTIONS_TABLE_KEY:
833		xsnprintf(out, sizeof out, "%s",
834		    key_string_lookup_key(o->num));
835		break;
836	case OPTIONS_TABLE_COLOUR:
837		s = colour_tostring(o->num);
838		xsnprintf(out, sizeof out, "%s", s);
839		break;
840	case OPTIONS_TABLE_ATTRIBUTES:
841		s = attributes_tostring(o->num);
842		xsnprintf(out, sizeof out, "%s", s);
843		break;
844	case OPTIONS_TABLE_FLAG:
845		if (o->num)
846			strlcpy(out, "on", sizeof out);
847		else
848			strlcpy(out, "off", sizeof out);
849		break;
850	case OPTIONS_TABLE_CHOICE:
851		s = oe->choices[o->num];
852		xsnprintf(out, sizeof out, "%s", s);
853		break;
854	case OPTIONS_TABLE_STYLE:
855		s = style_tostring(&o->style);
856		xsnprintf(out, sizeof out, "%s", s);
857		break;
858	}
859	return (out);
860}
861
862/* Find an option. */
863int
864options_table_find(
865    const char *optstr, const struct options_table_entry **table,
866    const struct options_table_entry **oe)
867{
868	static const struct options_table_entry	*tables[] = {
869		server_options_table,
870		window_options_table,
871		session_options_table
872	};
873	const struct options_table_entry	*oe_loop;
874	u_int					 i;
875
876	for (i = 0; i < nitems(tables); i++) {
877		for (oe_loop = tables[i]; oe_loop->name != NULL; oe_loop++) {
878			if (strncmp(oe_loop->name, optstr, strlen(optstr)) != 0)
879				continue;
880
881			/* If already found, ambiguous. */
882			if (*oe != NULL)
883				return (-1);
884			*oe = oe_loop;
885			*table = tables[i];
886
887			/* Bail now if an exact match. */
888			if (strcmp((*oe)->name, optstr) == 0)
889				break;
890		}
891	}
892	return (0);
893}
894