1*4c8945a0SNathan Whitehorn /* 2*4c8945a0SNathan Whitehorn * $Id: rc.c,v 1.45 2010/01/18 10:28:16 tom Exp $ 3*4c8945a0SNathan Whitehorn * 4*4c8945a0SNathan Whitehorn * rc.c -- routines for processing the configuration file 5*4c8945a0SNathan Whitehorn * 6*4c8945a0SNathan Whitehorn * Copyright 2000-2008,2010 Thomas E. Dickey 7*4c8945a0SNathan Whitehorn * 8*4c8945a0SNathan Whitehorn * This program is free software; you can redistribute it and/or modify 9*4c8945a0SNathan Whitehorn * it under the terms of the GNU Lesser General Public License, version 2.1 10*4c8945a0SNathan Whitehorn * as published by the Free Software Foundation. 11*4c8945a0SNathan Whitehorn * 12*4c8945a0SNathan Whitehorn * This program is distributed in the hope that it will be useful, but 13*4c8945a0SNathan Whitehorn * WITHOUT ANY WARRANTY; without even the implied warranty of 14*4c8945a0SNathan Whitehorn * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15*4c8945a0SNathan Whitehorn * Lesser General Public License for more details. 16*4c8945a0SNathan Whitehorn * 17*4c8945a0SNathan Whitehorn * You should have received a copy of the GNU Lesser General Public 18*4c8945a0SNathan Whitehorn * License along with this program; if not, write to 19*4c8945a0SNathan Whitehorn * Free Software Foundation, Inc. 20*4c8945a0SNathan Whitehorn * 51 Franklin St., Fifth Floor 21*4c8945a0SNathan Whitehorn * Boston, MA 02110, USA. 22*4c8945a0SNathan Whitehorn * 23*4c8945a0SNathan Whitehorn * An earlier version of this program lists as authors 24*4c8945a0SNathan Whitehorn * Savio Lam (lam836@cs.cuhk.hk) 25*4c8945a0SNathan Whitehorn */ 26*4c8945a0SNathan Whitehorn 27*4c8945a0SNathan Whitehorn #include <dialog.h> 28*4c8945a0SNathan Whitehorn 29*4c8945a0SNathan Whitehorn #include <dlg_keys.h> 30*4c8945a0SNathan Whitehorn 31*4c8945a0SNathan Whitehorn #ifdef HAVE_COLOR 32*4c8945a0SNathan Whitehorn #include <dlg_colors.h> 33*4c8945a0SNathan Whitehorn 34*4c8945a0SNathan Whitehorn /* 35*4c8945a0SNathan Whitehorn * For matching color names with color values 36*4c8945a0SNathan Whitehorn */ 37*4c8945a0SNathan Whitehorn static const color_names_st color_names[] = 38*4c8945a0SNathan Whitehorn { 39*4c8945a0SNathan Whitehorn #ifdef HAVE_USE_DEFAULT_COLORS 40*4c8945a0SNathan Whitehorn {"DEFAULT", -1}, 41*4c8945a0SNathan Whitehorn #endif 42*4c8945a0SNathan Whitehorn {"BLACK", COLOR_BLACK}, 43*4c8945a0SNathan Whitehorn {"RED", COLOR_RED}, 44*4c8945a0SNathan Whitehorn {"GREEN", COLOR_GREEN}, 45*4c8945a0SNathan Whitehorn {"YELLOW", COLOR_YELLOW}, 46*4c8945a0SNathan Whitehorn {"BLUE", COLOR_BLUE}, 47*4c8945a0SNathan Whitehorn {"MAGENTA", COLOR_MAGENTA}, 48*4c8945a0SNathan Whitehorn {"CYAN", COLOR_CYAN}, 49*4c8945a0SNathan Whitehorn {"WHITE", COLOR_WHITE}, 50*4c8945a0SNathan Whitehorn }; /* color names */ 51*4c8945a0SNathan Whitehorn #define COLOR_COUNT (sizeof(color_names) / sizeof(color_names[0])) 52*4c8945a0SNathan Whitehorn #endif /* HAVE_COLOR */ 53*4c8945a0SNathan Whitehorn 54*4c8945a0SNathan Whitehorn #define GLOBALRC "/etc/dialogrc" 55*4c8945a0SNathan Whitehorn #define DIALOGRC ".dialogrc" 56*4c8945a0SNathan Whitehorn 57*4c8945a0SNathan Whitehorn /* Types of values */ 58*4c8945a0SNathan Whitehorn #define VAL_INT 0 59*4c8945a0SNathan Whitehorn #define VAL_STR 1 60*4c8945a0SNathan Whitehorn #define VAL_BOOL 2 61*4c8945a0SNathan Whitehorn 62*4c8945a0SNathan Whitehorn /* Type of line in configuration file */ 63*4c8945a0SNathan Whitehorn typedef enum { 64*4c8945a0SNathan Whitehorn LINE_ERROR = -1, 65*4c8945a0SNathan Whitehorn LINE_EQUALS, 66*4c8945a0SNathan Whitehorn LINE_EMPTY 67*4c8945a0SNathan Whitehorn } PARSE_LINE; 68*4c8945a0SNathan Whitehorn 69*4c8945a0SNathan Whitehorn /* number of configuration variables */ 70*4c8945a0SNathan Whitehorn #define VAR_COUNT (sizeof(vars) / sizeof(vars_st)) 71*4c8945a0SNathan Whitehorn 72*4c8945a0SNathan Whitehorn /* check if character is white space */ 73*4c8945a0SNathan Whitehorn #define whitespace(c) (c == ' ' || c == TAB) 74*4c8945a0SNathan Whitehorn 75*4c8945a0SNathan Whitehorn /* check if character is string quoting characters */ 76*4c8945a0SNathan Whitehorn #define isquote(c) (c == '"' || c == '\'') 77*4c8945a0SNathan Whitehorn 78*4c8945a0SNathan Whitehorn /* get last character of string */ 79*4c8945a0SNathan Whitehorn #define lastch(str) str[strlen(str)-1] 80*4c8945a0SNathan Whitehorn 81*4c8945a0SNathan Whitehorn /* 82*4c8945a0SNathan Whitehorn * Configuration variables 83*4c8945a0SNathan Whitehorn */ 84*4c8945a0SNathan Whitehorn typedef struct { 85*4c8945a0SNathan Whitehorn const char *name; /* name of configuration variable as in DIALOGRC */ 86*4c8945a0SNathan Whitehorn void *var; /* address of actual variable to change */ 87*4c8945a0SNathan Whitehorn int type; /* type of value */ 88*4c8945a0SNathan Whitehorn const char *comment; /* comment to put in "rc" file */ 89*4c8945a0SNathan Whitehorn } vars_st; 90*4c8945a0SNathan Whitehorn 91*4c8945a0SNathan Whitehorn /* 92*4c8945a0SNathan Whitehorn * This table should contain only references to dialog_state, since dialog_vars 93*4c8945a0SNathan Whitehorn * is reset specially in dialog.c before each widget. 94*4c8945a0SNathan Whitehorn */ 95*4c8945a0SNathan Whitehorn static const vars_st vars[] = 96*4c8945a0SNathan Whitehorn { 97*4c8945a0SNathan Whitehorn {"aspect", 98*4c8945a0SNathan Whitehorn &dialog_state.aspect_ratio, 99*4c8945a0SNathan Whitehorn VAL_INT, 100*4c8945a0SNathan Whitehorn "Set aspect-ration."}, 101*4c8945a0SNathan Whitehorn 102*4c8945a0SNathan Whitehorn {"separate_widget", 103*4c8945a0SNathan Whitehorn &dialog_state.separate_str, 104*4c8945a0SNathan Whitehorn VAL_STR, 105*4c8945a0SNathan Whitehorn "Set separator (for multiple widgets output)."}, 106*4c8945a0SNathan Whitehorn 107*4c8945a0SNathan Whitehorn {"tab_len", 108*4c8945a0SNathan Whitehorn &dialog_state.tab_len, 109*4c8945a0SNathan Whitehorn VAL_INT, 110*4c8945a0SNathan Whitehorn "Set tab-length (for textbox tab-conversion)."}, 111*4c8945a0SNathan Whitehorn 112*4c8945a0SNathan Whitehorn {"visit_items", 113*4c8945a0SNathan Whitehorn &dialog_state.visit_items, 114*4c8945a0SNathan Whitehorn VAL_BOOL, 115*4c8945a0SNathan Whitehorn "Make tab-traversal for checklist, etc., include the list."}, 116*4c8945a0SNathan Whitehorn 117*4c8945a0SNathan Whitehorn #ifdef HAVE_COLOR 118*4c8945a0SNathan Whitehorn {"use_shadow", 119*4c8945a0SNathan Whitehorn &dialog_state.use_shadow, 120*4c8945a0SNathan Whitehorn VAL_BOOL, 121*4c8945a0SNathan Whitehorn "Shadow dialog boxes? This also turns on color."}, 122*4c8945a0SNathan Whitehorn 123*4c8945a0SNathan Whitehorn {"use_colors", 124*4c8945a0SNathan Whitehorn &dialog_state.use_colors, 125*4c8945a0SNathan Whitehorn VAL_BOOL, 126*4c8945a0SNathan Whitehorn "Turn color support ON or OFF"}, 127*4c8945a0SNathan Whitehorn #endif /* HAVE_COLOR */ 128*4c8945a0SNathan Whitehorn }; /* vars */ 129*4c8945a0SNathan Whitehorn 130*4c8945a0SNathan Whitehorn static int 131*4c8945a0SNathan Whitehorn skip_whitespace(char *str, int n) 132*4c8945a0SNathan Whitehorn { 133*4c8945a0SNathan Whitehorn while (whitespace(str[n]) && str[n] != '\0') 134*4c8945a0SNathan Whitehorn n++; 135*4c8945a0SNathan Whitehorn return n; 136*4c8945a0SNathan Whitehorn } 137*4c8945a0SNathan Whitehorn 138*4c8945a0SNathan Whitehorn static int 139*4c8945a0SNathan Whitehorn skip_keyword(char *str, int n) 140*4c8945a0SNathan Whitehorn { 141*4c8945a0SNathan Whitehorn while (isalnum(UCH(str[n])) && str[n] != '\0') 142*4c8945a0SNathan Whitehorn n++; 143*4c8945a0SNathan Whitehorn return n; 144*4c8945a0SNathan Whitehorn } 145*4c8945a0SNathan Whitehorn 146*4c8945a0SNathan Whitehorn static int 147*4c8945a0SNathan Whitehorn find_vars(char *name) 148*4c8945a0SNathan Whitehorn { 149*4c8945a0SNathan Whitehorn int result = -1; 150*4c8945a0SNathan Whitehorn unsigned i; 151*4c8945a0SNathan Whitehorn 152*4c8945a0SNathan Whitehorn for (i = 0; i < VAR_COUNT; i++) { 153*4c8945a0SNathan Whitehorn if (dlg_strcmp(vars[i].name, name) == 0) { 154*4c8945a0SNathan Whitehorn result = (int) i; 155*4c8945a0SNathan Whitehorn break; 156*4c8945a0SNathan Whitehorn } 157*4c8945a0SNathan Whitehorn } 158*4c8945a0SNathan Whitehorn return result; 159*4c8945a0SNathan Whitehorn } 160*4c8945a0SNathan Whitehorn 161*4c8945a0SNathan Whitehorn #ifdef HAVE_COLOR 162*4c8945a0SNathan Whitehorn static int 163*4c8945a0SNathan Whitehorn find_color(char *name) 164*4c8945a0SNathan Whitehorn { 165*4c8945a0SNathan Whitehorn int result = -1; 166*4c8945a0SNathan Whitehorn int i; 167*4c8945a0SNathan Whitehorn int limit = dlg_color_count(); 168*4c8945a0SNathan Whitehorn 169*4c8945a0SNathan Whitehorn for (i = 0; i < limit; i++) { 170*4c8945a0SNathan Whitehorn if (dlg_strcmp(dlg_color_table[i].name, name) == 0) { 171*4c8945a0SNathan Whitehorn result = i; 172*4c8945a0SNathan Whitehorn break; 173*4c8945a0SNathan Whitehorn } 174*4c8945a0SNathan Whitehorn } 175*4c8945a0SNathan Whitehorn return result; 176*4c8945a0SNathan Whitehorn } 177*4c8945a0SNathan Whitehorn 178*4c8945a0SNathan Whitehorn /* 179*4c8945a0SNathan Whitehorn * Convert an attribute to a string representation like this: 180*4c8945a0SNathan Whitehorn * 181*4c8945a0SNathan Whitehorn * "(foreground,background,highlight)" 182*4c8945a0SNathan Whitehorn */ 183*4c8945a0SNathan Whitehorn static char * 184*4c8945a0SNathan Whitehorn attr_to_str(char *str, int fg, int bg, int hl) 185*4c8945a0SNathan Whitehorn { 186*4c8945a0SNathan Whitehorn int i; 187*4c8945a0SNathan Whitehorn 188*4c8945a0SNathan Whitehorn strcpy(str, "("); 189*4c8945a0SNathan Whitehorn /* foreground */ 190*4c8945a0SNathan Whitehorn for (i = 0; fg != color_names[i].value; i++) ; 191*4c8945a0SNathan Whitehorn strcat(str, color_names[i].name); 192*4c8945a0SNathan Whitehorn strcat(str, ","); 193*4c8945a0SNathan Whitehorn 194*4c8945a0SNathan Whitehorn /* background */ 195*4c8945a0SNathan Whitehorn for (i = 0; bg != color_names[i].value; i++) ; 196*4c8945a0SNathan Whitehorn strcat(str, color_names[i].name); 197*4c8945a0SNathan Whitehorn 198*4c8945a0SNathan Whitehorn /* highlight */ 199*4c8945a0SNathan Whitehorn strcat(str, hl ? ",ON)" : ",OFF)"); 200*4c8945a0SNathan Whitehorn 201*4c8945a0SNathan Whitehorn return str; 202*4c8945a0SNathan Whitehorn } 203*4c8945a0SNathan Whitehorn 204*4c8945a0SNathan Whitehorn /* 205*4c8945a0SNathan Whitehorn * Extract the foreground, background and highlight values from an attribute 206*4c8945a0SNathan Whitehorn * represented as a string in this form: 207*4c8945a0SNathan Whitehorn * 208*4c8945a0SNathan Whitehorn * "(foreground,background,highlight)" 209*4c8945a0SNathan Whitehorn */ 210*4c8945a0SNathan Whitehorn static int 211*4c8945a0SNathan Whitehorn str_to_attr(char *str, int *fg, int *bg, int *hl) 212*4c8945a0SNathan Whitehorn { 213*4c8945a0SNathan Whitehorn int i = 0, get_fg = 1; 214*4c8945a0SNathan Whitehorn unsigned j; 215*4c8945a0SNathan Whitehorn char tempstr[MAX_LEN + 1], *part; 216*4c8945a0SNathan Whitehorn 217*4c8945a0SNathan Whitehorn if (str[0] != '(' || lastch(str) != ')') 218*4c8945a0SNathan Whitehorn return -1; /* invalid representation */ 219*4c8945a0SNathan Whitehorn 220*4c8945a0SNathan Whitehorn /* remove the parenthesis */ 221*4c8945a0SNathan Whitehorn strcpy(tempstr, str + 1); 222*4c8945a0SNathan Whitehorn lastch(tempstr) = '\0'; 223*4c8945a0SNathan Whitehorn 224*4c8945a0SNathan Whitehorn /* get foreground and background */ 225*4c8945a0SNathan Whitehorn 226*4c8945a0SNathan Whitehorn while (1) { 227*4c8945a0SNathan Whitehorn /* skip white space before fg/bg string */ 228*4c8945a0SNathan Whitehorn i = skip_whitespace(tempstr, i); 229*4c8945a0SNathan Whitehorn if (tempstr[i] == '\0') 230*4c8945a0SNathan Whitehorn return -1; /* invalid representation */ 231*4c8945a0SNathan Whitehorn part = tempstr + i; /* set 'part' to start of fg/bg string */ 232*4c8945a0SNathan Whitehorn 233*4c8945a0SNathan Whitehorn /* find end of fg/bg string */ 234*4c8945a0SNathan Whitehorn while (!whitespace(tempstr[i]) && tempstr[i] != ',' 235*4c8945a0SNathan Whitehorn && tempstr[i] != '\0') 236*4c8945a0SNathan Whitehorn i++; 237*4c8945a0SNathan Whitehorn 238*4c8945a0SNathan Whitehorn if (tempstr[i] == '\0') 239*4c8945a0SNathan Whitehorn return -1; /* invalid representation */ 240*4c8945a0SNathan Whitehorn else if (whitespace(tempstr[i])) { /* not yet ',' */ 241*4c8945a0SNathan Whitehorn tempstr[i++] = '\0'; 242*4c8945a0SNathan Whitehorn 243*4c8945a0SNathan Whitehorn /* skip white space before ',' */ 244*4c8945a0SNathan Whitehorn i = skip_whitespace(tempstr, i); 245*4c8945a0SNathan Whitehorn if (tempstr[i] != ',') 246*4c8945a0SNathan Whitehorn return -1; /* invalid representation */ 247*4c8945a0SNathan Whitehorn } 248*4c8945a0SNathan Whitehorn tempstr[i++] = '\0'; /* skip the ',' */ 249*4c8945a0SNathan Whitehorn for (j = 0; j < COLOR_COUNT && dlg_strcmp(part, color_names[j].name); 250*4c8945a0SNathan Whitehorn j++) ; 251*4c8945a0SNathan Whitehorn if (j == COLOR_COUNT) /* invalid color name */ 252*4c8945a0SNathan Whitehorn return -1; 253*4c8945a0SNathan Whitehorn if (get_fg) { 254*4c8945a0SNathan Whitehorn *fg = color_names[j].value; 255*4c8945a0SNathan Whitehorn get_fg = 0; /* next we have to get the background */ 256*4c8945a0SNathan Whitehorn } else { 257*4c8945a0SNathan Whitehorn *bg = color_names[j].value; 258*4c8945a0SNathan Whitehorn break; 259*4c8945a0SNathan Whitehorn } 260*4c8945a0SNathan Whitehorn } /* got foreground and background */ 261*4c8945a0SNathan Whitehorn 262*4c8945a0SNathan Whitehorn /* get highlight */ 263*4c8945a0SNathan Whitehorn 264*4c8945a0SNathan Whitehorn /* skip white space before highlight string */ 265*4c8945a0SNathan Whitehorn i = skip_whitespace(tempstr, i); 266*4c8945a0SNathan Whitehorn if (tempstr[i] == '\0') 267*4c8945a0SNathan Whitehorn return -1; /* invalid representation */ 268*4c8945a0SNathan Whitehorn part = tempstr + i; /* set 'part' to start of highlight string */ 269*4c8945a0SNathan Whitehorn 270*4c8945a0SNathan Whitehorn /* trim trailing white space from highlight string */ 271*4c8945a0SNathan Whitehorn i = (int) strlen(part) - 1; 272*4c8945a0SNathan Whitehorn while (whitespace(part[i]) && i > 0) 273*4c8945a0SNathan Whitehorn i--; 274*4c8945a0SNathan Whitehorn part[i + 1] = '\0'; 275*4c8945a0SNathan Whitehorn 276*4c8945a0SNathan Whitehorn if (!dlg_strcmp(part, "ON")) 277*4c8945a0SNathan Whitehorn *hl = TRUE; 278*4c8945a0SNathan Whitehorn else if (!dlg_strcmp(part, "OFF")) 279*4c8945a0SNathan Whitehorn *hl = FALSE; 280*4c8945a0SNathan Whitehorn else 281*4c8945a0SNathan Whitehorn return -1; /* invalid highlight value */ 282*4c8945a0SNathan Whitehorn 283*4c8945a0SNathan Whitehorn return 0; 284*4c8945a0SNathan Whitehorn } 285*4c8945a0SNathan Whitehorn #endif /* HAVE_COLOR */ 286*4c8945a0SNathan Whitehorn 287*4c8945a0SNathan Whitehorn /* 288*4c8945a0SNathan Whitehorn * Check if the line begins with a special keyword; if so, return true while 289*4c8945a0SNathan Whitehorn * pointing params to its parameters. 290*4c8945a0SNathan Whitehorn */ 291*4c8945a0SNathan Whitehorn static int 292*4c8945a0SNathan Whitehorn begins_with(char *line, const char *keyword, char **params) 293*4c8945a0SNathan Whitehorn { 294*4c8945a0SNathan Whitehorn int i = skip_whitespace(line, 0); 295*4c8945a0SNathan Whitehorn int j = skip_keyword(line, i); 296*4c8945a0SNathan Whitehorn 297*4c8945a0SNathan Whitehorn if ((j - i) == (int) strlen(keyword)) { 298*4c8945a0SNathan Whitehorn char save = line[j]; 299*4c8945a0SNathan Whitehorn line[j] = 0; 300*4c8945a0SNathan Whitehorn if (!dlg_strcmp(keyword, line + i)) { 301*4c8945a0SNathan Whitehorn *params = line + skip_whitespace(line, j + 1); 302*4c8945a0SNathan Whitehorn return 1; 303*4c8945a0SNathan Whitehorn } 304*4c8945a0SNathan Whitehorn line[j] = save; 305*4c8945a0SNathan Whitehorn } 306*4c8945a0SNathan Whitehorn 307*4c8945a0SNathan Whitehorn return 0; 308*4c8945a0SNathan Whitehorn } 309*4c8945a0SNathan Whitehorn 310*4c8945a0SNathan Whitehorn /* 311*4c8945a0SNathan Whitehorn * Parse a line in the configuration file 312*4c8945a0SNathan Whitehorn * 313*4c8945a0SNathan Whitehorn * Each line is of the form: "variable = value". On exit, 'var' will contain 314*4c8945a0SNathan Whitehorn * the variable name, and 'value' will contain the value string. 315*4c8945a0SNathan Whitehorn * 316*4c8945a0SNathan Whitehorn * Return values: 317*4c8945a0SNathan Whitehorn * 318*4c8945a0SNathan Whitehorn * LINE_EMPTY - line is blank or comment 319*4c8945a0SNathan Whitehorn * LINE_EQUALS - line contains "variable = value" 320*4c8945a0SNathan Whitehorn * LINE_ERROR - syntax error in line 321*4c8945a0SNathan Whitehorn */ 322*4c8945a0SNathan Whitehorn static PARSE_LINE 323*4c8945a0SNathan Whitehorn parse_line(char *line, char **var, char **value) 324*4c8945a0SNathan Whitehorn { 325*4c8945a0SNathan Whitehorn int i = 0; 326*4c8945a0SNathan Whitehorn 327*4c8945a0SNathan Whitehorn /* ignore white space at beginning of line */ 328*4c8945a0SNathan Whitehorn i = skip_whitespace(line, i); 329*4c8945a0SNathan Whitehorn 330*4c8945a0SNathan Whitehorn if (line[i] == '\0') /* line is blank */ 331*4c8945a0SNathan Whitehorn return LINE_EMPTY; 332*4c8945a0SNathan Whitehorn else if (line[i] == '#') /* line is comment */ 333*4c8945a0SNathan Whitehorn return LINE_EMPTY; 334*4c8945a0SNathan Whitehorn else if (line[i] == '=') /* variable names cannot start with a '=' */ 335*4c8945a0SNathan Whitehorn return LINE_ERROR; 336*4c8945a0SNathan Whitehorn 337*4c8945a0SNathan Whitehorn /* set 'var' to variable name */ 338*4c8945a0SNathan Whitehorn *var = line + i++; /* skip to next character */ 339*4c8945a0SNathan Whitehorn 340*4c8945a0SNathan Whitehorn /* find end of variable name */ 341*4c8945a0SNathan Whitehorn while (!whitespace(line[i]) && line[i] != '=' && line[i] != '\0') 342*4c8945a0SNathan Whitehorn i++; 343*4c8945a0SNathan Whitehorn 344*4c8945a0SNathan Whitehorn if (line[i] == '\0') /* syntax error */ 345*4c8945a0SNathan Whitehorn return LINE_ERROR; 346*4c8945a0SNathan Whitehorn else if (line[i] == '=') 347*4c8945a0SNathan Whitehorn line[i++] = '\0'; 348*4c8945a0SNathan Whitehorn else { 349*4c8945a0SNathan Whitehorn line[i++] = '\0'; 350*4c8945a0SNathan Whitehorn 351*4c8945a0SNathan Whitehorn /* skip white space before '=' */ 352*4c8945a0SNathan Whitehorn i = skip_whitespace(line, i); 353*4c8945a0SNathan Whitehorn 354*4c8945a0SNathan Whitehorn if (line[i] != '=') /* syntax error */ 355*4c8945a0SNathan Whitehorn return LINE_ERROR; 356*4c8945a0SNathan Whitehorn else 357*4c8945a0SNathan Whitehorn i++; /* skip the '=' */ 358*4c8945a0SNathan Whitehorn } 359*4c8945a0SNathan Whitehorn 360*4c8945a0SNathan Whitehorn /* skip white space after '=' */ 361*4c8945a0SNathan Whitehorn i = skip_whitespace(line, i); 362*4c8945a0SNathan Whitehorn 363*4c8945a0SNathan Whitehorn if (line[i] == '\0') 364*4c8945a0SNathan Whitehorn return LINE_ERROR; 365*4c8945a0SNathan Whitehorn else 366*4c8945a0SNathan Whitehorn *value = line + i; /* set 'value' to value string */ 367*4c8945a0SNathan Whitehorn 368*4c8945a0SNathan Whitehorn /* trim trailing white space from 'value' */ 369*4c8945a0SNathan Whitehorn i = (int) strlen(*value) - 1; 370*4c8945a0SNathan Whitehorn while (whitespace((*value)[i]) && i > 0) 371*4c8945a0SNathan Whitehorn i--; 372*4c8945a0SNathan Whitehorn (*value)[i + 1] = '\0'; 373*4c8945a0SNathan Whitehorn 374*4c8945a0SNathan Whitehorn return LINE_EQUALS; /* no syntax error in line */ 375*4c8945a0SNathan Whitehorn } 376*4c8945a0SNathan Whitehorn 377*4c8945a0SNathan Whitehorn /* 378*4c8945a0SNathan Whitehorn * Create the configuration file 379*4c8945a0SNathan Whitehorn */ 380*4c8945a0SNathan Whitehorn void 381*4c8945a0SNathan Whitehorn dlg_create_rc(const char *filename) 382*4c8945a0SNathan Whitehorn { 383*4c8945a0SNathan Whitehorn unsigned i; 384*4c8945a0SNathan Whitehorn FILE *rc_file; 385*4c8945a0SNathan Whitehorn 386*4c8945a0SNathan Whitehorn if ((rc_file = fopen(filename, "wt")) == NULL) 387*4c8945a0SNathan Whitehorn dlg_exiterr("Error opening file for writing in dlg_create_rc()."); 388*4c8945a0SNathan Whitehorn 389*4c8945a0SNathan Whitehorn fprintf(rc_file, "#\n\ 390*4c8945a0SNathan Whitehorn # Run-time configuration file for dialog\n\ 391*4c8945a0SNathan Whitehorn #\n\ 392*4c8945a0SNathan Whitehorn # Automatically generated by \"dialog --create-rc <file>\"\n\ 393*4c8945a0SNathan Whitehorn #\n\ 394*4c8945a0SNathan Whitehorn #\n\ 395*4c8945a0SNathan Whitehorn # Types of values:\n\ 396*4c8945a0SNathan Whitehorn #\n\ 397*4c8945a0SNathan Whitehorn # Number - <number>\n\ 398*4c8945a0SNathan Whitehorn # String - \"string\"\n\ 399*4c8945a0SNathan Whitehorn # Boolean - <ON|OFF>\n" 400*4c8945a0SNathan Whitehorn #ifdef HAVE_COLOR 401*4c8945a0SNathan Whitehorn "\ 402*4c8945a0SNathan Whitehorn # Attribute - (foreground,background,highlight?)\n" 403*4c8945a0SNathan Whitehorn #endif 404*4c8945a0SNathan Whitehorn ); 405*4c8945a0SNathan Whitehorn 406*4c8945a0SNathan Whitehorn /* Print an entry for each configuration variable */ 407*4c8945a0SNathan Whitehorn for (i = 0; i < VAR_COUNT; i++) { 408*4c8945a0SNathan Whitehorn fprintf(rc_file, "\n# %s\n", vars[i].comment); 409*4c8945a0SNathan Whitehorn switch (vars[i].type) { 410*4c8945a0SNathan Whitehorn case VAL_INT: 411*4c8945a0SNathan Whitehorn fprintf(rc_file, "%s = %d\n", vars[i].name, 412*4c8945a0SNathan Whitehorn *((int *) vars[i].var)); 413*4c8945a0SNathan Whitehorn break; 414*4c8945a0SNathan Whitehorn case VAL_STR: 415*4c8945a0SNathan Whitehorn fprintf(rc_file, "%s = \"%s\"\n", vars[i].name, 416*4c8945a0SNathan Whitehorn (char *) vars[i].var); 417*4c8945a0SNathan Whitehorn break; 418*4c8945a0SNathan Whitehorn case VAL_BOOL: 419*4c8945a0SNathan Whitehorn fprintf(rc_file, "%s = %s\n", vars[i].name, 420*4c8945a0SNathan Whitehorn *((bool *) vars[i].var) ? "ON" : "OFF"); 421*4c8945a0SNathan Whitehorn break; 422*4c8945a0SNathan Whitehorn } 423*4c8945a0SNathan Whitehorn } 424*4c8945a0SNathan Whitehorn #ifdef HAVE_COLOR 425*4c8945a0SNathan Whitehorn for (i = 0; i < (unsigned) dlg_color_count(); ++i) { 426*4c8945a0SNathan Whitehorn char buffer[MAX_LEN + 1]; 427*4c8945a0SNathan Whitehorn 428*4c8945a0SNathan Whitehorn fprintf(rc_file, "\n# %s\n", dlg_color_table[i].comment); 429*4c8945a0SNathan Whitehorn fprintf(rc_file, "%s = %s\n", dlg_color_table[i].name, 430*4c8945a0SNathan Whitehorn attr_to_str(buffer, 431*4c8945a0SNathan Whitehorn dlg_color_table[i].fg, 432*4c8945a0SNathan Whitehorn dlg_color_table[i].bg, 433*4c8945a0SNathan Whitehorn dlg_color_table[i].hilite)); 434*4c8945a0SNathan Whitehorn } 435*4c8945a0SNathan Whitehorn #endif /* HAVE_COLOR */ 436*4c8945a0SNathan Whitehorn #if 1 437*4c8945a0SNathan Whitehorn dlg_dump_keys(rc_file); 438*4c8945a0SNathan Whitehorn #endif 439*4c8945a0SNathan Whitehorn 440*4c8945a0SNathan Whitehorn (void) fclose(rc_file); 441*4c8945a0SNathan Whitehorn } 442*4c8945a0SNathan Whitehorn 443*4c8945a0SNathan Whitehorn /* 444*4c8945a0SNathan Whitehorn * Parse the configuration file and set up variables 445*4c8945a0SNathan Whitehorn */ 446*4c8945a0SNathan Whitehorn int 447*4c8945a0SNathan Whitehorn dlg_parse_rc(void) 448*4c8945a0SNathan Whitehorn { 449*4c8945a0SNathan Whitehorn int i; 450*4c8945a0SNathan Whitehorn int l = 1; 451*4c8945a0SNathan Whitehorn PARSE_LINE parse; 452*4c8945a0SNathan Whitehorn char str[MAX_LEN + 1]; 453*4c8945a0SNathan Whitehorn char *var; 454*4c8945a0SNathan Whitehorn char *value; 455*4c8945a0SNathan Whitehorn char *tempptr; 456*4c8945a0SNathan Whitehorn int result = 0; 457*4c8945a0SNathan Whitehorn FILE *rc_file = 0; 458*4c8945a0SNathan Whitehorn #if 1 459*4c8945a0SNathan Whitehorn char *params; 460*4c8945a0SNathan Whitehorn #endif 461*4c8945a0SNathan Whitehorn 462*4c8945a0SNathan Whitehorn /* 463*4c8945a0SNathan Whitehorn * At startup, dialog determines the settings to use as follows: 464*4c8945a0SNathan Whitehorn * 465*4c8945a0SNathan Whitehorn * a) if the environment variable $DIALOGRC is set, its value determines 466*4c8945a0SNathan Whitehorn * the name of the configuration file. 467*4c8945a0SNathan Whitehorn * 468*4c8945a0SNathan Whitehorn * b) if the file in (a) can't be found, use the file $HOME/.dialogrc 469*4c8945a0SNathan Whitehorn * as the configuration file. 470*4c8945a0SNathan Whitehorn * 471*4c8945a0SNathan Whitehorn * c) if the file in (b) can't be found, try using the GLOBALRC file. 472*4c8945a0SNathan Whitehorn * Usually this will be /etc/dialogrc. 473*4c8945a0SNathan Whitehorn * 474*4c8945a0SNathan Whitehorn * d) if the file in (c) cannot be found, use the compiled-in defaults. 475*4c8945a0SNathan Whitehorn */ 476*4c8945a0SNathan Whitehorn 477*4c8945a0SNathan Whitehorn /* try step (a) */ 478*4c8945a0SNathan Whitehorn if ((tempptr = getenv("DIALOGRC")) != NULL) 479*4c8945a0SNathan Whitehorn rc_file = fopen(tempptr, "rt"); 480*4c8945a0SNathan Whitehorn 481*4c8945a0SNathan Whitehorn if (rc_file == NULL) { /* step (a) failed? */ 482*4c8945a0SNathan Whitehorn /* try step (b) */ 483*4c8945a0SNathan Whitehorn if ((tempptr = getenv("HOME")) != NULL 484*4c8945a0SNathan Whitehorn && strlen(tempptr) < MAX_LEN - (sizeof(DIALOGRC) + 3)) { 485*4c8945a0SNathan Whitehorn if (tempptr[0] == '\0' || lastch(tempptr) == '/') 486*4c8945a0SNathan Whitehorn sprintf(str, "%s%s", tempptr, DIALOGRC); 487*4c8945a0SNathan Whitehorn else 488*4c8945a0SNathan Whitehorn sprintf(str, "%s/%s", tempptr, DIALOGRC); 489*4c8945a0SNathan Whitehorn rc_file = fopen(str, "rt"); 490*4c8945a0SNathan Whitehorn } 491*4c8945a0SNathan Whitehorn } 492*4c8945a0SNathan Whitehorn 493*4c8945a0SNathan Whitehorn if (rc_file == NULL) { /* step (b) failed? */ 494*4c8945a0SNathan Whitehorn /* try step (c) */ 495*4c8945a0SNathan Whitehorn strcpy(str, GLOBALRC); 496*4c8945a0SNathan Whitehorn if ((rc_file = fopen(str, "rt")) == NULL) 497*4c8945a0SNathan Whitehorn return 0; /* step (c) failed, use default values */ 498*4c8945a0SNathan Whitehorn } 499*4c8945a0SNathan Whitehorn 500*4c8945a0SNathan Whitehorn /* Scan each line and set variables */ 501*4c8945a0SNathan Whitehorn while ((result == 0) && (fgets(str, MAX_LEN, rc_file) != NULL)) { 502*4c8945a0SNathan Whitehorn dlg_trace_msg("rc:%s\n", str); 503*4c8945a0SNathan Whitehorn if (*str == '\0' || lastch(str) != '\n') { 504*4c8945a0SNathan Whitehorn /* ignore rest of file if line too long */ 505*4c8945a0SNathan Whitehorn fprintf(stderr, "\nParse error: line %d of configuration" 506*4c8945a0SNathan Whitehorn " file too long.\n", l); 507*4c8945a0SNathan Whitehorn result = -1; /* parse aborted */ 508*4c8945a0SNathan Whitehorn break; 509*4c8945a0SNathan Whitehorn } 510*4c8945a0SNathan Whitehorn 511*4c8945a0SNathan Whitehorn lastch(str) = '\0'; 512*4c8945a0SNathan Whitehorn if (begins_with(str, "bindkey", ¶ms)) { 513*4c8945a0SNathan Whitehorn dlg_parse_bindkey(params); 514*4c8945a0SNathan Whitehorn continue; 515*4c8945a0SNathan Whitehorn } 516*4c8945a0SNathan Whitehorn parse = parse_line(str, &var, &value); /* parse current line */ 517*4c8945a0SNathan Whitehorn 518*4c8945a0SNathan Whitehorn switch (parse) { 519*4c8945a0SNathan Whitehorn case LINE_EMPTY: /* ignore blank lines and comments */ 520*4c8945a0SNathan Whitehorn break; 521*4c8945a0SNathan Whitehorn case LINE_EQUALS: 522*4c8945a0SNathan Whitehorn /* search table for matching config variable name */ 523*4c8945a0SNathan Whitehorn if ((i = find_vars(var)) >= 0) { 524*4c8945a0SNathan Whitehorn switch (vars[i].type) { 525*4c8945a0SNathan Whitehorn case VAL_INT: 526*4c8945a0SNathan Whitehorn *((int *) vars[i].var) = atoi(value); 527*4c8945a0SNathan Whitehorn break; 528*4c8945a0SNathan Whitehorn case VAL_STR: 529*4c8945a0SNathan Whitehorn if (!isquote(value[0]) || !isquote(lastch(value)) 530*4c8945a0SNathan Whitehorn || strlen(value) < 2) { 531*4c8945a0SNathan Whitehorn fprintf(stderr, "\nParse error: string value " 532*4c8945a0SNathan Whitehorn "expected at line %d of configuration " 533*4c8945a0SNathan Whitehorn "file.\n", l); 534*4c8945a0SNathan Whitehorn result = -1; /* parse aborted */ 535*4c8945a0SNathan Whitehorn } else { 536*4c8945a0SNathan Whitehorn /* remove the (") quotes */ 537*4c8945a0SNathan Whitehorn value++; 538*4c8945a0SNathan Whitehorn lastch(value) = '\0'; 539*4c8945a0SNathan Whitehorn strcpy((char *) vars[i].var, value); 540*4c8945a0SNathan Whitehorn } 541*4c8945a0SNathan Whitehorn break; 542*4c8945a0SNathan Whitehorn case VAL_BOOL: 543*4c8945a0SNathan Whitehorn if (!dlg_strcmp(value, "ON")) 544*4c8945a0SNathan Whitehorn *((bool *) vars[i].var) = TRUE; 545*4c8945a0SNathan Whitehorn else if (!dlg_strcmp(value, "OFF")) 546*4c8945a0SNathan Whitehorn *((bool *) vars[i].var) = FALSE; 547*4c8945a0SNathan Whitehorn else { 548*4c8945a0SNathan Whitehorn fprintf(stderr, "\nParse error: boolean value " 549*4c8945a0SNathan Whitehorn "expected at line %d of configuration " 550*4c8945a0SNathan Whitehorn "file (found %s).\n", l, value); 551*4c8945a0SNathan Whitehorn result = -1; /* parse aborted */ 552*4c8945a0SNathan Whitehorn } 553*4c8945a0SNathan Whitehorn break; 554*4c8945a0SNathan Whitehorn } 555*4c8945a0SNathan Whitehorn #ifdef HAVE_COLOR 556*4c8945a0SNathan Whitehorn } else if ((i = find_color(var)) >= 0) { 557*4c8945a0SNathan Whitehorn int fg = 0; 558*4c8945a0SNathan Whitehorn int bg = 0; 559*4c8945a0SNathan Whitehorn int hl = 0; 560*4c8945a0SNathan Whitehorn if (str_to_attr(value, &fg, &bg, &hl) == -1) { 561*4c8945a0SNathan Whitehorn fprintf(stderr, "\nParse error: attribute " 562*4c8945a0SNathan Whitehorn "value expected at line %d of configuration " 563*4c8945a0SNathan Whitehorn "file.\n", l); 564*4c8945a0SNathan Whitehorn result = -1; /* parse aborted */ 565*4c8945a0SNathan Whitehorn } else { 566*4c8945a0SNathan Whitehorn dlg_color_table[i].fg = fg; 567*4c8945a0SNathan Whitehorn dlg_color_table[i].bg = bg; 568*4c8945a0SNathan Whitehorn dlg_color_table[i].hilite = hl; 569*4c8945a0SNathan Whitehorn } 570*4c8945a0SNathan Whitehorn } else { 571*4c8945a0SNathan Whitehorn #endif /* HAVE_COLOR */ 572*4c8945a0SNathan Whitehorn fprintf(stderr, "\nParse error: unknown variable " 573*4c8945a0SNathan Whitehorn "at line %d of configuration file:\n\t%s\n", l, var); 574*4c8945a0SNathan Whitehorn result = -1; /* parse aborted */ 575*4c8945a0SNathan Whitehorn } 576*4c8945a0SNathan Whitehorn break; 577*4c8945a0SNathan Whitehorn case LINE_ERROR: 578*4c8945a0SNathan Whitehorn fprintf(stderr, "\nParse error: syntax error at line %d of " 579*4c8945a0SNathan Whitehorn "configuration file.\n", l); 580*4c8945a0SNathan Whitehorn result = -1; /* parse aborted */ 581*4c8945a0SNathan Whitehorn break; 582*4c8945a0SNathan Whitehorn } 583*4c8945a0SNathan Whitehorn l++; /* next line */ 584*4c8945a0SNathan Whitehorn } 585*4c8945a0SNathan Whitehorn 586*4c8945a0SNathan Whitehorn (void) fclose(rc_file); 587*4c8945a0SNathan Whitehorn return result; 588*4c8945a0SNathan Whitehorn } 589