GnuCOBOL  2.0
A free COBOL compiler
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros
config.c File Reference
#include "config.h"
#include "defaults.h"
#include <stdio.h>
#include <stdlib.h>
#include <stddef.h>
#include <string.h>
#include <ctype.h>
#include "cobc.h"
#include "config.def"
Include dependency graph for config.c:

Data Structures

struct  config_struct
 

Macros

#define CB_CONFIG_ANY(type, var, name)   type var = (type)0;
 
#define CB_CONFIG_INT(var, name)   int var = 0;
 
#define CB_CONFIG_STRING(var, name)   const char *var = NULL;
 
#define CB_CONFIG_BOOLEAN(var, name)   int var = 0;
 
#define CB_CONFIG_SUPPORT(var, name)   enum cb_support var = CB_OK;
 
#define CB_CONFIG_ANY(type, var, name)   , {CB_ANY, name, (void *)&var, NULL}
 
#define CB_CONFIG_INT(var, name)   , {CB_INT, name, (void *)&var, NULL}
 
#define CB_CONFIG_STRING(var, name)   , {CB_STRING, name, (void *)&var, NULL}
 
#define CB_CONFIG_BOOLEAN(var, name)   , {CB_BOOLEAN, name, (void *)&var, NULL}
 
#define CB_CONFIG_SUPPORT(var, name)   , {CB_SUPPORT, name, (void *)&var, NULL}
 
#define CB_CONFIG_SIZE   sizeof(config_table) / sizeof(struct config_struct)
 

Enumerations

enum  cb_config_type {
  CB_ANY = 0, CB_INT, CB_STRING, CB_BOOLEAN,
  CB_SUPPORT
}
 

Functions

static char * read_string (const char *text)
 
static void invalid_value (const char *fname, const int line, const char *name, const char *val)
 
static void unsupported_value (const char *fname, const int line, const char *name, const char *val)
 
int cb_load_std (const char *name)
 
int cb_config_entry (char *buff, const char *fname, const int line)
 
int cb_load_conf (const char *fname, const int check_nodef, const int prefix_dir)
 

Variables

static struct config_struct config_table []
 

Macro Definition Documentation

#define CB_CONFIG_ANY (   type,
  var,
  name 
)    type var = (type)0;
#define CB_CONFIG_ANY (   type,
  var,
  name 
)    , {CB_ANY, name, (void *)&var, NULL}
#define CB_CONFIG_BOOLEAN (   var,
  name 
)    int var = 0;
#define CB_CONFIG_BOOLEAN (   var,
  name 
)    , {CB_BOOLEAN, name, (void *)&var, NULL}
#define CB_CONFIG_INT (   var,
  name 
)    int var = 0;
#define CB_CONFIG_INT (   var,
  name 
)    , {CB_INT, name, (void *)&var, NULL}
#define CB_CONFIG_SIZE   sizeof(config_table) / sizeof(struct config_struct)

Referenced by cb_config_entry(), and cb_load_conf().

#define CB_CONFIG_STRING (   var,
  name 
)    const char *var = NULL;
#define CB_CONFIG_STRING (   var,
  name 
)    , {CB_STRING, name, (void *)&var, NULL}
#define CB_CONFIG_SUPPORT (   var,
  name 
)    enum cb_support var = CB_OK;
#define CB_CONFIG_SUPPORT (   var,
  name 
)    , {CB_SUPPORT, name, (void *)&var, NULL}

Enumeration Type Documentation

Enumerator
CB_ANY 
CB_INT 
CB_STRING 
CB_BOOLEAN 
CB_SUPPORT 
34  {
35  CB_ANY = 0,
36  CB_INT, /* integer */
37  CB_STRING, /* "..." */
38  CB_BOOLEAN, /* 'yes', 'no' */
39  CB_SUPPORT /* 'ok', 'archaic', 'obsolete',
40  'skip', 'ignore', 'unconformable' */
41 };

Function Documentation

int cb_config_entry ( char *  buff,
const char *  fname,
const int  line 
)

References _, CB_ANY, CB_ARCHAIC, CB_ASSIGN_IBM, CB_ASSIGN_MF, CB_BINARY_SIZE_1_2_4_8, CB_BINARY_SIZE_1__8, CB_BINARY_SIZE_2_4_8, CB_BOOLEAN, CB_BYTEORDER_BIG_ENDIAN, CB_BYTEORDER_NATIVE, CB_CONFIG_SIZE, CB_ERROR, CB_IGNORE, CB_INT, CB_OBSOLETE, CB_OK, CB_SKIP, CB_STRING, CB_SUPPORT, CB_UNCONFORMABLE, CB_WARNING, cobc_main_malloc(), cobc_nores_base, config_table, configuration_error(), invalid_value(), config_struct::name, noreserve::next, noreserve::noresword, NULL, read_string(), unsupported_value(), config_struct::val, and config_struct::var.

Referenced by cb_load_conf(), and process_command_line().

136 {
137  char *s;
138  const char *name;
139  char *e;
140  struct noreserve *noresptr;
141  size_t size;
142  const char *val;
143  void *var;
144  size_t i;
145  size_t j;
146 
147  /* Get tag */
148  s = strpbrk (buff, " \t:=");
149  if (!s) {
150  configuration_error (fname, line,
151  _("Invalid configuration '%s'"), buff);
152  return -1;
153  }
154  *s = 0;
155 
156  /* Find entry */
157  for (i = 0; i < CB_CONFIG_SIZE; i++) {
158  if (strcmp (buff, config_table[i].name) == 0) {
159  break;
160  }
161  }
162  if (i == CB_CONFIG_SIZE) {
163  configuration_error (fname, line, _("Unknown configuration tag '%s'"), buff);
164  return -1;
165  }
166 
167  /* Get value */
168  /* Move pointer to beginning of value */
169  for (s++; *s && strchr (" \t:=", *s); s++) {
170  ;
171  }
172  /* Set end pointer to first # (comment) or end of value */
173  for (e = s + 1; *e && !strchr ("#", *e); e++) {
174  ;
175  }
176  /* Remove trailing white-spaces */
177  for (--e; e >= s && strchr (" \t\r\n", *e); e--) {
178  ;
179  }
180  e[1] = 0;
181  config_table[i].val = s;
182 
183  /* Set value */
184  name = config_table[i].name;
185  var = config_table[i].var;
186  val = config_table[i].val;
187  switch (config_table[i].type) {
188  case CB_ANY:
189  if (strcmp (name, "assign-clause") == 0) {
190  if (strcmp (val, "cobol2002") == 0) {
191  unsupported_value (fname, line, name, val);
192  return -1;
193  } else if (strcmp (val, "mf") == 0) {
194  cb_assign_clause = CB_ASSIGN_MF;
195  } else if (strcmp (val, "ibm") == 0) {
196  cb_assign_clause = CB_ASSIGN_IBM;
197  } else {
198  invalid_value (fname, line, name, val);
199  return -1;
200  }
201  } else if (strcmp (name, "binary-size") == 0) {
202  if (strcmp (val, "2-4-8") == 0) {
203  cb_binary_size = CB_BINARY_SIZE_2_4_8;
204  } else if (strcmp (val, "1-2-4-8") == 0) {
205  cb_binary_size = CB_BINARY_SIZE_1_2_4_8;
206  } else if (strcmp (val, "1--8") == 0) {
207  cb_binary_size = CB_BINARY_SIZE_1__8;
208  } else {
209  invalid_value (fname, line, name, val);
210  return -1;
211  }
212  } else if (strcmp (name, "binary-byteorder") == 0) {
213  if (strcmp (val, "native") == 0) {
214  cb_binary_byteorder = CB_BYTEORDER_NATIVE;
215  } else if (strcmp (val, "big-endian") == 0) {
216  cb_binary_byteorder = CB_BYTEORDER_BIG_ENDIAN;
217  } else {
218  invalid_value (fname, line, name, val);
219  return -1;
220  }
221  }
222  break;
223  case CB_INT:
224  for (j = 0; val[j]; j++) {
225  if (val[j] < '0' || val[j] > '9') {
226  invalid_value (fname, line, name, val);
227  return -1;
228  break;
229  }
230  }
231  *((int *)var) = atoi (val);
232  break;
233  case CB_STRING:
234  val = read_string (val);
235 
236  if (strcmp (name, "include") == 0) {
237  if (fname) {
238  /* Include another conf file */
239  return 1;
240  } else {
242  _("'%s' not supported with -cb_conf"), name);
243  return -1;
244  }
245  } else if (strcmp (name, "not-reserved") == 0) {
246  size = strlen (val);
247  noresptr = cobc_main_malloc (sizeof (struct noreserve)
248  + size + 1U);
249  noresptr->noresword = (char *)noresptr
250  + sizeof (struct noreserve);
251  memcpy (noresptr->noresword, val, size);
252  noresptr->next = cobc_nores_base;
253  cobc_nores_base = noresptr;
254  } else {
255  *((const char **)var) = val;
256  }
257  break;
258  case CB_BOOLEAN:
259  if (strcmp (val, "yes") == 0) {
260  *((int *)var) = 1;
261  } else if (strcmp (val, "no") == 0) {
262  *((int *)var) = 0;
263  } else {
264  invalid_value (fname, line, name, val);
265  return -1;
266  }
267  break;
268  case CB_SUPPORT:
269  if (strcmp (val, "ok") == 0) {
270  *((enum cb_support *)var) = CB_OK;
271  } else if (strcmp (val, "warning") == 0) {
272  *((enum cb_support *)var) = CB_WARNING;
273  } else if (strcmp (val, "archaic") == 0) {
274  *((enum cb_support *)var) = CB_ARCHAIC;
275  } else if (strcmp (val, "obsolete") == 0) {
276  *((enum cb_support *)var) = CB_OBSOLETE;
277  } else if (strcmp (val, "skip") == 0) {
278  *((enum cb_support *)var) = CB_SKIP;
279  } else if (strcmp (val, "ignore") == 0) {
280  *((enum cb_support *)var) = CB_IGNORE;
281  } else if (strcmp (val, "error") == 0) {
282  *((enum cb_support *)var) = CB_ERROR;
283  } else if (strcmp (val, "unconformable") == 0) {
284  *((enum cb_support *)var) = CB_UNCONFORMABLE;
285  } else {
286  invalid_value (fname, line, name, val);
287  return -1;
288  }
289  break;
290  default:
291  configuration_error (fname, line, _("Invalid type for '%s'"), name);
292  return -1;
293  }
294  return 0;
295 }
int cb_load_conf ( const char *  fname,
const int  check_nodef,
const int  prefix_dir 
)

References _, cb_config_entry(), CB_CONFIG_SIZE, cb_load_conf(), cob_config_dir, COB_SMALL_BUFF, COB_SMALL_MAX, config_table, configuration_error(), line, NULL, read_string(), SLASH_STR, and config_struct::val.

Referenced by cb_load_conf(), cb_load_std(), and process_command_line().

299 {
300  const unsigned char *x;
301  const char *name;
302  FILE *fp;
303  size_t i;
304  int sub_ret, ret;
305  int line;
306  char buff[COB_SMALL_BUFF];
307 
308  /* Initialize the configuration table */
309  if (check_nodef) {
310  for (i = 0; i < CB_CONFIG_SIZE; i++) {
311  config_table[i].val = NULL;
312  }
313  }
314 
315  if (prefix_dir) {
316  snprintf (buff, (size_t)COB_SMALL_MAX,
317  "%s%s%s", cob_config_dir, SLASH_STR, fname);
318  name = buff;
319  } else {
320  name = fname;
321  }
322  /* Open the configuration file */
323  fp = fopen (name, "r");
324  if (fp == NULL) {
325  fflush (stderr);
326  configuration_error (name, 0, _("No such file or directory"));
327  return -1;
328  }
329 
330  /* Read the configuration file */
331  ret = 0;
332  line = 0;
333  while (fgets (buff, COB_SMALL_BUFF, fp)) {
334  line++;
335 
336  /* Skip line comments, empty lines */
337  if (buff[0] == '#' || buff[0] == '\n') {
338  continue;
339  }
340 
341  /* Skip blank lines */
342  for (x = (const unsigned char *)buff; *x; x++) {
343  if (isgraph (*x)) {
344  break;
345  }
346  }
347  if (!*x) {
348  continue;
349  }
350 
351  sub_ret = cb_config_entry (buff, fname, line);
352  if (sub_ret == 1) {
353  /* Include another configuration file */
354  /* Find entry for getting include value */
355  for (i = 0; i < CB_CONFIG_SIZE; i++) {
356  if (strcmp (buff, config_table[i].name) == 0) {
357  break;
358  }
359  }
360  sub_ret = cb_load_conf (read_string(config_table[i].val), 0, 1);
361  if (sub_ret != 0) {
362  fclose (fp);
363  /* Only 1 include allowed */
364  if (sub_ret == 1) {
366  _("Only one include in configuration files allowed"));
367  sub_ret = -1;
368  }
369  }
370  }
371  if (sub_ret != 0) ret = sub_ret;
372  }
373  fclose (fp);
374 
375  /* Checks for missing definitions */
376  if (check_nodef) {
377  for (i = 2U; i < CB_CONFIG_SIZE; i++) {
378  if (config_table[i].val == NULL) {
379  configuration_error (fname, 0, _("No definition of '%s'"),
380  config_table[i].name);
381  ret = -1;
382  }
383  }
384  }
385 
386  return ret;
387 }
int cb_load_std ( const char *  name)

References cb_load_conf().

Referenced by process_command_line().

130 {
131  return cb_load_conf (name, 1, 1);
132 }
static void invalid_value ( const char *  fname,
const int  line,
const char *  name,
const char *  val 
)
static

References _, and configuration_error().

Referenced by cb_config_entry().

114 {
115  configuration_error (fname, line,
116  _("Invalid value '%s' for configuration tag '%s'"), val, name);
117 }
static char* read_string ( const char *  text)
static

References cobc_main_strdup(), and p.

Referenced by cb_config_entry(), and cb_load_conf().

96 {
97  char *p;
98  char *s;
99 
100  s = cobc_main_strdup (text);
101  if (*s == '\"') {
102  s++;
103  }
104  for (p = s; *p; p++) {
105  if (*p == '\"') {
106  *p = '\0';
107  }
108  }
109  return s;
110 }
static void unsupported_value ( const char *  fname,
const int  line,
const char *  name,
const char *  val 
)
static

References _, and configuration_error().

Referenced by cb_config_entry().

121 {
122  configuration_error (fname, line,
123  _("Unsupported value '%s' for configuration tag '%s'"), val, name);
124 }

Variable Documentation

struct config_struct config_table[]
static

Referenced by cb_config_entry(), and cb_load_conf().