📄 monet_options.mx
字号:
@' The contents of this file are subject to the MonetDB Public License@' Version 1.1 (the "License"); you may not use this file except in@' compliance with the License. You may obtain a copy of the License at@' http://monetdb.cwi.nl/Legal/MonetDBLicense-1.1.html@'@' Software distributed under the License is distributed on an "AS IS"@' basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the@' License for the specific language governing rights and limitations@' under the License.@'@' The Original Code is the MonetDB Database System.@'@' The Initial Developer of the Original Code is CWI.@' Portions created by CWI are Copyright (C) 1997-2007 CWI.@' All Rights Reserved.@f monet_options@a N.J. Nes@* A simple option handling library@TThe monet server and clients make use of command line options and a (possibly)shared config file. With this library a set (represented by set,setlen) ofoptions is created. An option is stored as name and value strings with aspecial flag indicating the origin of the options, (builtin, system configfile, special config file or command line option). @h#ifndef _MO_H_#define _MO_H_#include "monet_utils.h"#ifndef HAVE_GETOPT_LONG# include "monet_getopt.h"#else# ifdef HAVE_GETOPT_H# include "getopt.h"# endif#endiftypedef enum opt_kind { opt_builtin = 0, opt_config = 1, opt_cmdline = 2} opt_kind;typedef struct opt { opt_kind kind; char *name; char *value;} opt;#ifdef __cplusplusextern "C" {#endif/* mo_print_options will print the option set on stderr */mutils_export void mo_print_options(opt *set, int setlen);/* mo_find_option, finds the option with the given name in the option set (set,setlen). */mutils_export char *mo_find_option(opt *set, int setlen, const char *name);/* the option values can contain ${prefix} and ${exec_prefix}, these will be substituted using the mo_substitute function. The return value is a newly allocated buffer, it is the caller's responsibility to free the buffer. */mutils_export char *mo_substitute(opt *set, int setlen, char *name);/* mo_system_config will add the options from the system config file (returns the new setlen) */mutils_export int mo_system_config(opt **Set, int setlen);/* mo_builtin_settings, will place the builtin settings into a new option set (returns the length of this set). */mutils_export int mo_builtin_settings(opt **Set);/* mo_add_option will add a single option to the option set (returns new length) */mutils_export int mo_add_option(opt **Set, int setlen, opt_kind kind, const char *name, const char *value);/* mo_free_options will free the resouces take by the options set */mutils_export void mo_free_options(opt *set, int setlen);#ifdef __cplusplus}#endif#endif@c#include "monetdb_config.h"#include "monet_options.h"#include <stdio.h>#include <string.h>#include <ctype.h>#if HAVE_UNISTD_H#include <unistd.h>#endif#ifndef HAVE_GETOPT_LONG# include "getopt.c"# include "getopt1.c"#endif#if !HAVE_DECL_STRDUP#ifdef HAVE_STRDUPextern char *strdup(const char *);#else#define strdup(s) strcpy(malloc(strlen(s)+1),(s))#endif#endif#ifdef NATIVE_WIN32#define strdup _strdup#define getpid _getpid#endif/* these two are used of the set parameter passed into functions is NULL */static int default_setlen = 0;static opt *default_set = NULL;static intmo_default_set(opt **Set, int setlen){ if (*Set == NULL) { if (default_set == NULL) { default_setlen = mo_builtin_settings(&default_set); default_setlen = mo_system_config(&default_set, default_setlen); } *Set = default_set; setlen = default_setlen; } return setlen;}voidmo_print_options(opt *set, int setlen){ int i = 0; setlen = mo_default_set(&set, setlen); for (i = 0; i < setlen; i++) { if (set[i].kind == opt_builtin) { fprintf(stderr, "# builtin opt \t%s = %s\n", set[i].name, set[i].value); } } for (i = 0; i < setlen; i++) { if (set[i].kind == opt_config) { fprintf(stderr, "# config opt \t%s = %s\n", set[i].name, set[i].value); } } for (i = 0; i < setlen; i++) { if (set[i].kind == opt_cmdline) { fprintf(stderr, "# cmdline opt \t%s = %s\n", set[i].name, set[i].value); } }}char *mo_find_option(opt *set, int setlen, const char *name){ opt *o = NULL; int i; setlen = mo_default_set(&set, setlen); for (i = 0; i < setlen; i++) { if (strcmp(set[i].name, name) == 0) if (!o || o->kind < set[i].kind) o = set + i; } if (o) return o->value; return NULL;}char *mo_substitute(opt *set, int setlen, char *val){ char *q; size_t n = strlen(val) + 1; char *s = strdup(val); setlen = mo_default_set(&set, setlen); q = s; while ((q = strchr(q, '$')) != NULL) { if (strncmp(q, "${exec_prefix}", 14) == 0) { char *p = mo_find_option(set, setlen, "exec_prefix"); char *t; if (!p) return s; t = malloc((n = n - 14 + strlen(p))); *q = 0; snprintf(t, n, "%s%s%s", s, p, q + 14); free(s); q = t + (q-s); s = t; } else if (strncmp(q, "${prefix}", 9) == 0) { char *p = mo_find_option(set, setlen, "prefix"); char *t; if (!p) return s; t = malloc((n = n - 9 + strlen(p))); *q = 0; snprintf(t, n, "%s%s%s", s, p, q + 9); free(s); q = t + (q-s); s = t; } else q++; } return s;}static intmo_config_file(opt **Set, int setlen, char *file){ char buf[BUFSIZ]; FILE *fd = NULL; opt *set; if (Set == NULL) { if (default_set == NULL) { set = NULL; setlen = mo_default_set(&set, 0); } Set = &default_set; setlen = default_setlen; } set = *Set; fd = fopen(file, "r"); if (fd == NULL) { fprintf(stderr, "Could not open file %s\n", file); return setlen; } while (fgets(buf, BUFSIZ, fd) != NULL) { char *s, *t, *val; int quote; for (s = buf; *s && isspace((int) (*s)); s++) ; if (*s == '#') continue; /* commentary */ if (*s == 0) continue; /* empty line */ val = strchr(s, '='); if (val == NULL) { fprintf(stderr, "mo_config_file: syntax error in %s at %s\n", file, s); fclose(fd); exit(1); } *val = 0; for (t = s; *t && !isspace((int) (*t)); t++) ; *t = 0; /* skip any leading blanks in the value part */ for (val++; *val && isspace((int) (*val)); val++) ; /* search to unquoted # */ quote = 0; for (t = val; *t; t++) { if (*t == '"') quote = !quote; else if (!quote && *t == '#') break; } if (quote) { fprintf(stderr, "mo_config_file: wrong number of quotes in %s at %s\n", file, val); fclose(fd); exit(1); } /* remove trailing white space */ while (isspace((int) (t[-1]))) t--; *t++ = 0; /* treat value as empty if it consists only of white space */ if (t <= val) val = t - 1; set = (opt *) realloc(set, (setlen + 1) * sizeof(opt)); set[setlen].kind = opt_config; set[setlen].name = strdup(s); set[setlen].value = malloc((size_t) (t - val)); for (t = val, s = set[setlen].value; *t; t++) if (*t != '"') *s++ = *t; *s = 0; setlen++; } (void) fclose(fd); *Set = set; return setlen;}intmo_system_config(opt **Set, int setlen){ char *cfg; if (Set == NULL) { if (default_set == NULL) { opt *set = NULL; setlen = mo_default_set(&set, 0); } Set = &default_set; setlen = default_setlen; } cfg = mo_find_option(*Set, setlen, "config"); if (!cfg) return setlen; cfg = mo_substitute(*Set, setlen, cfg); setlen = mo_config_file(Set, setlen, cfg); free(cfg); return setlen;}intmo_builtin_settings(opt **Set){ int i = 0; opt *set; char buf[BUFSIZ]; if (Set == NULL) return 0;#define N_OPTIONS 28 /*MUST MATCH # OPTIONS BELOW */ set = malloc(sizeof(opt) * N_OPTIONS); if (set == NULL) return 0; set[i].kind = opt_builtin; set[i].name = strdup("gdk_arch"); snprintf(buf, BUFSIZ, "%dbit%s", (int) sizeof(char *) * 8, HOST); set[i].value = strdup(buf); i++; set[i].kind = opt_builtin; set[i].name = strdup("gdk_version"); set[i].value = strdup(VERSION); i++; set[i].kind = opt_builtin; set[i].name = strdup("monet_pid"); snprintf(buf, BUFSIZ, "%d", (int) getpid()); set[i].value = strdup(buf); i++; set[i].kind = opt_builtin; set[i].name = strdup("prefix"); set[i].value = strdup(MONETDB_PREFIX); i++; set[i].kind = opt_builtin; set[i].name = strdup("exec_prefix"); set[i].value = strdup(MONETDB_EXEC_PREFIX); i++; set[i].kind = opt_builtin; set[i].name = strdup("gdk_dbname"); set[i].value = strdup("tst"); i++; set[i].kind = opt_builtin; set[i].name = strdup("gdk_dbfarm"); snprintf(buf, BUFSIZ, "%s%c%s", MONETDB_LOCALSTATEDIR, DIR_SEP, PACKAGE); set[i].value = strdup(buf); i++; set[i].kind = opt_builtin; set[i].name = strdup("gdk_debug"); set[i].value = strdup("8"); i++; set[i].kind = opt_builtin; set[i].name = strdup("gdk_mem_bigsize"); set[i].value = strdup("262144"); i++; /* * gdk_vm_minsize will be set/limited to * 1/8 of the physically available amount of main-memory * during start-up in src/tools/Mserver.mx */ set[i].kind = opt_builtin; set[i].name = strdup("gdk_vm_minsize"); set[i].value = strdup("137438953472"); i++; set[i].kind = opt_builtin; set[i].name = strdup("gdk_alloc_map"); set[i].value = strdup("yes"); i++; set[i].kind = opt_builtin; set[i].name = strdup("gdk_mem_pagebits");#ifdef WIN32 set[i].value = strdup("16");#else set[i].value = strdup("14");#endif i++; set[i].kind = opt_builtin; set[i].name = strdup("monet_admin"); set[i].value = strdup("adm"); i++; set[i].kind = opt_builtin; set[i].name = strdup("monet_prompt"); set[i].value = strdup(">"); i++; set[i].kind = opt_builtin; set[i].name = strdup("monet_welcome"); set[i].value = strdup("yes"); i++; set[i].kind = opt_builtin; set[i].name = strdup("monet_mod_path"); /* on most platforms, we only need libdir/PACKAGE, but with * MinGW, we also need libdir/bin */ snprintf(buf, BUFSIZ, "%s%c%s%c%s%cbin", MONETDB_LIBDIR, DIR_SEP, PACKAGE, PATH_SEP, MONETDB_LIBDIR, DIR_SEP); set[i].value = strdup(buf); i++; set[i].kind = opt_builtin; set[i].name = strdup("monet_daemon"); set[i].value = strdup("yes"); i++; set[i].kind = opt_builtin; set[i].name = strdup("host"); set[i].value = strdup("localhost"); i++; set[i].kind = opt_builtin; set[i].name = strdup("mapi_port"); set[i].value = strdup("50000"); i++; set[i].kind = opt_builtin; set[i].name = strdup("mapi_noheaders"); set[i].value = strdup("no"); i++; set[i].kind = opt_builtin; set[i].name = strdup("mapi_debug"); set[i].value = strdup("0"); i++; set[i].kind = opt_builtin; set[i].name = strdup("mapi_clients"); set[i].value = strdup("2"); i++; set[i].kind = opt_builtin; set[i].name = strdup("sql_debug"); set[i].value = strdup("0"); i++; set[i].kind = opt_builtin; set[i].name = strdup("sql_logdir"); snprintf(buf, BUFSIZ, "%s%c%s%csql_logs", MONETDB_LOCALSTATEDIR, DIR_SEP, PACKAGE, DIR_SEP); set[i].value = strdup(buf); i++; set[i].kind = opt_builtin; set[i].name = strdup("xquery_logdir"); snprintf(buf, BUFSIZ, "%s%c%s%cxquery_logs", MONETDB_LOCALSTATEDIR, DIR_SEP, PACKAGE, DIR_SEP); set[i].value = strdup(buf); i++; set[i].kind = opt_builtin; set[i].name = strdup("standoff_ns"); set[i].value = strdup("http://monetdb.cwi.nl/standoff"); i++; set[i].kind = opt_builtin; set[i].name = strdup("standoff_start"); set[i].value = strdup("start"); i++; set[i].kind = opt_builtin; set[i].name = strdup("standoff_end"); set[i].value = strdup("end"); i++; assert(i == N_OPTIONS); *Set = set; return i;}intmo_add_option(opt **Set, int setlen, opt_kind kind, const char *name, const char *value){ opt *set; if (Set == NULL) { if (default_set == NULL) { set = NULL; setlen = mo_default_set(&set, 0); } Set = &default_set; setlen = default_setlen; } set = (opt *) realloc(*Set, (setlen + 1) * sizeof(opt)); set[setlen].kind = kind; set[setlen].name = strdup(name); set[setlen].value = strdup(value); *Set = set; return setlen + 1;}voidmo_free_options(opt *set, int setlen){ int i; if (set == NULL) { set = default_set; setlen = default_setlen; default_set = NULL; default_setlen = 0; } for (i = 0; i < setlen; i++) { if (set[i].name) free(set[i].name); if (set[i].value) free(set[i].value); } free(set);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -