Example #1
0
/**
 *  scan the command line for immediate action options.
 *  This is only called the first time through.
 */
LOCAL tSuccess
doImmediateOpts(tOptions* pOpts)
{
    pOpts->curOptIdx = 1;     /* start by skipping program name */
    pOpts->pzCurOpt  = NULL;

    /*
     *  Examine all the options from the start.  We process any options that
     *  are marked for immediate processing.
     */
    for (;;) {
        tOptState optState = OPTSTATE_INITIALIZER(PRESET);

        switch (nextOption(pOpts, &optState)) {
        case FAILURE: goto   failed_option;
        case PROBLEM: return SUCCESS; /* no more args */
        case SUCCESS: break;
        }

        /*
         *  IF this is an immediate-attribute option, then do it.
         */
        if (! DO_IMMEDIATELY(optState.flags))
            continue;

        if (! SUCCESSFUL(handle_opt(pOpts, &optState)))
            break;
    } failed_option:;

    if ((pOpts->fOptSet & OPTPROC_ERRSTOP) != 0)
        (*pOpts->pUsageProc)(pOpts, EXIT_FAILURE);

    return FAILURE;
}
Example #2
0
/**
 * Process all the options from our current position onward.  (This allows
 * interspersed options and arguments for the few non-standard programs that
 * require it.)  Thus, do not rewind option indexes because some programs
 * choose to re-invoke after a non-option.
 */
LOCAL tSuccess
doRegularOpts(tOptions* pOpts)
{
    for (;;) {
        tOptState optState = OPTSTATE_INITIALIZER(DEFINED);

        switch (nextOption(pOpts, &optState)) {
        case FAILURE: goto   failed_option;
        case PROBLEM: return SUCCESS; /* no more args */
        case SUCCESS: break;
        }

        /*
         *  IF this is an immediate action option,
         *  THEN skip it (unless we are supposed to do it a second time).
         */
        if (! DO_NORMALLY(optState.flags)) {
            if (! DO_SECOND_TIME(optState.flags))
                continue;
            optState.pOD->optOccCt--; /* don't count this repetition */
        }

        if (! SUCCESSFUL(handle_opt(pOpts, &optState)))
            break;
    } failed_option:;

    if ((pOpts->fOptSet & OPTPROC_ERRSTOP) != 0)
        (*pOpts->pUsageProc)(pOpts, EXIT_FAILURE);

    return FAILURE;
}
Example #3
0
/*=export_func  optionVendorOption
 * private:
 *
 * what:  Process a vendor option
 * arg:   + tOptions * + pOpts    + program options descriptor +
 * arg:   + tOptDesc * + pOptDesc + the descriptor for this arg +
 *
 * doc:
 *  For POSIX specified utilities, the options are constrained to the options,
 *  @xref{config attributes, Program Configuration}.  AutoOpts clients should
 *  never specify this directly.  It gets referenced when the option
 *  definitions contain a "vendor-opt" attribute.
=*/
void
optionVendorOption(tOptions * pOpts, tOptDesc * pOD)
{
    tOptState     opt_st   = OPTSTATE_INITIALIZER(PRESET);
    char const *  vopt_str = pOD->optArg.argString;

    if (pOpts <= OPTPROC_EMIT_LIMIT)
        return;

    if ((pOD->fOptState & OPTST_RESET) != 0)
        return;

    if ((pOD->fOptState & OPTPROC_IMMEDIATE) == 0)
        opt_st.flags = OPTST_DEFINED;

    if (  ((pOpts->fOptSet & OPTPROC_VENDOR_OPT) == 0)
       || ! SUCCESSFUL(opt_find_long(pOpts, vopt_str, &opt_st))
       || ! SUCCESSFUL(get_opt_arg(pOpts, &opt_st)) )
    {
        fprintf(stderr, zIllVendOptStr, pOpts->pzProgName, vopt_str);
        (*pOpts->pUsageProc)(pOpts, EXIT_FAILURE);
        /* NOTREACHED */
        _exit(EXIT_FAILURE); /* to be certain */
    }

    /*
     *  See if we are in immediate handling state.
     */
    if (pOpts->fOptSet & OPTPROC_IMMEDIATE) {
        /*
         *  See if the enclosed option is okay with that state.
         */
        if (DO_IMMEDIATELY(opt_st.flags))
            (void)handle_opt(pOpts, &opt_st);

    } else {
        /*
         *  non-immediate direction.
         *  See if the enclosed option is okay with that state.
         */
        if (DO_NORMALLY(opt_st.flags) || DO_SECOND_TIME(opt_st.flags))
            (void)handle_opt(pOpts, &opt_st);
    }
}
Example #4
0
File: ducrc.c Project: Solertis/duc
int ducrc_getopt(struct ducrc *ducrc, int *argc, char **argv[])
{
	struct option longopts[MAX_OPTIONS + 1] = { { NULL } };
	char optstr[MAX_OPTIONS*2] = "";
	int n = 0;
	int l = 0;

	/* Prepare a list of options for getopt_long() */

	struct ducrc_option **os = ducrc->option_list;

	int i;
	for(i=0; i<ducrc->noptions; i++) {
		struct ducrc_option *o = *os;
		
		longopts[n].name = o->longopt;
		if(o->shortopt) {
			l += sprintf(optstr+l, "%c", o->shortopt);
			longopts[n].val = o->shortopt;
		}

		if(o->type == DUCRC_TYPE_BOOL) {
			longopts[n].has_arg = no_argument;
		} else {
			longopts[n].has_arg = required_argument;
			if(o->shortopt) l += sprintf(optstr+l, ":");
		}

		n++;
		os++;
	}

	/* Rely on libc to do the hard work */

	int c;
	int idx;

	if(*argc > 1) optind = 2;

	while( ( c = getopt_long(*argc, *argv, optstr, longopts, &idx)) != -1) {
		if(c == '?') return -1;
		handle_opt(ducrc, c, c ? 0 : longopts[idx].name, optarg);
	}
	
	*argc -= optind;
	*argv += optind;

	return 0;
}
Example #5
0
/**
 *  scan the command line for immediate action options.
 *  This is only called the first time through.
 *  While this procedure is active, the OPTPROC_IMMEDIATE is true.
 *
 *  @param pOpts   program options descriptor
 *  @returns SUCCESS or FAILURE
 */
LOCAL tSuccess
immediate_opts(tOptions * opts)
{
    tSuccess  res;

    opts->fOptSet  |= OPTPROC_IMMEDIATE;
    opts->curOptIdx = 1;     /* start by skipping program name */
    opts->pzCurOpt  = NULL;

    /*
     *  Examine all the options from the start.  We process any options that
     *  are marked for immediate processing.
     */
    for (;;) {
        tOptState opt_st = OPTSTATE_INITIALIZER(PRESET);

        res = next_opt(opts, &opt_st);
        switch (res) {
        case FAILURE: goto   failed_option;
        case PROBLEM: res = SUCCESS; goto leave;
        case SUCCESS: break;
        }

        /*
         *  IF this is an immediate-attribute option, then do it.
         */
        if (! DO_IMMEDIATELY(opt_st.flags))
            continue;

        if (! SUCCESSFUL(handle_opt(opts, &opt_st)))
            break;
    } failed_option:;

    if ((opts->fOptSet & OPTPROC_ERRSTOP) != 0)
        (*opts->pUsageProc)(opts, EXIT_FAILURE);

 leave:

    opts->fOptSet &= ~OPTPROC_IMMEDIATE;
    return res;
}
Example #6
0
/*
 *  Load an option from a block of text.  The text must start with the
 *  configurable/option name and be followed by its associated value.
 *  That value may be processed in any of several ways.  See "tOptionLoadMode"
 *  in autoopts.h.
 */
LOCAL void
loadOptionLine(
    tOptions*   pOpts,
    tOptState*  pOS,
    char*       pzLine,
    tDirection  direction,
    tOptionLoadMode   load_mode )
{
    while (IS_WHITESPACE_CHAR(*pzLine))  pzLine++;

    {
        char* pzArg = assembleArgValue(pzLine, load_mode);

        if (! SUCCESSFUL(opt_find_long(pOpts, pzLine, pOS)))
            return;
        if (pOS->flags & OPTST_NO_INIT)
            return;
        pOS->pzOptArg = pzArg;
    }

    switch (pOS->flags & (OPTST_IMM|OPTST_DISABLE_IMM)) {
    case 0:
        /*
         *  The selected option has no immediate action.
         *  THEREFORE, if the direction is PRESETTING
         *  THEN we skip this option.
         */
        if (PRESETTING(direction))
            return;
        break;

    case OPTST_IMM:
        if (PRESETTING(direction)) {
            /*
             *  We are in the presetting direction with an option we handle
             *  immediately for enablement, but normally for disablement.
             *  Therefore, skip if disabled.
             */
            if ((pOS->flags & OPTST_DISABLED) == 0)
                return;
        } else {
            /*
             *  We are in the processing direction with an option we handle
             *  immediately for enablement, but normally for disablement.
             *  Therefore, skip if NOT disabled.
             */
            if ((pOS->flags & OPTST_DISABLED) != 0)
                return;
        }
        break;

    case OPTST_DISABLE_IMM:
        if (PRESETTING(direction)) {
            /*
             *  We are in the presetting direction with an option we handle
             *  immediately for disablement, but normally for disablement.
             *  Therefore, skip if NOT disabled.
             */
            if ((pOS->flags & OPTST_DISABLED) != 0)
                return;
        } else {
            /*
             *  We are in the processing direction with an option we handle
             *  immediately for disablement, but normally for disablement.
             *  Therefore, skip if disabled.
             */
            if ((pOS->flags & OPTST_DISABLED) == 0)
                return;
        }
        break;

    case OPTST_IMM|OPTST_DISABLE_IMM:
        /*
         *  The selected option is always for immediate action.
         *  THEREFORE, if the direction is PROCESSING
         *  THEN we skip this option.
         */
        if (PROCESSING(direction))
            return;
        break;
    }

    /*
     *  Fix up the args.
     */
    if (OPTST_GET_ARGTYPE(pOS->pOD->fOptState) == OPARG_TYPE_NONE) {
        if (*pOS->pzOptArg != NUL)
            return;
        pOS->pzOptArg = NULL;

    } else if (pOS->pOD->fOptState & OPTST_ARG_OPTIONAL) {
        if (*pOS->pzOptArg == NUL)
             pOS->pzOptArg = NULL;
        else {
            AGDUPSTR(pOS->pzOptArg, pOS->pzOptArg, "option argument");
            pOS->flags |= OPTST_ALLOC_ARG;
        }

    } else {
        if (*pOS->pzOptArg == NUL)
             pOS->pzOptArg = zNil;
        else {
            AGDUPSTR(pOS->pzOptArg, pOS->pzOptArg, "option argument");
            pOS->flags |= OPTST_ALLOC_ARG;
        }
    }

    {
        tOptionLoadMode sv = option_load_mode;
        option_load_mode = load_mode;
        handle_opt(pOpts, pOS);
        option_load_mode = sv;
    }
}
Example #7
0
/**
 *  Load an option from a block of text.  The text must start with the
 *  configurable/option name and be followed by its associated value.
 *  That value may be processed in any of several ways.  See "tOptionLoadMode"
 *  in autoopts.h.
 *
 * @param[in,out] opts       program options descriptor
 * @param[in,out] opt_state  option processing state
 * @param[in,out] line       source line with long option name in it
 * @param[in]     direction  current processing direction (preset or not)
 * @param[in]     load_mode  option loading mode (OPTION_LOAD_*)
 */
LOCAL void
loadOptionLine(
    tOptions *  opts,
    tOptState * opt_state,
    char *      line,
    tDirection  direction,
    tOptionLoadMode   load_mode )
{
    line = SPN_LOAD_LINE_SKIP_CHARS(line);

    {
        char * arg = assemble_arg_val(line, load_mode);

        if (! SUCCESSFUL(opt_find_long(opts, line, opt_state)))
            return;

        if (opt_state->flags & OPTST_NO_INIT)
            return;

        opt_state->pzOptArg = arg;
    }

    switch (opt_state->flags & (OPTST_IMM|OPTST_DISABLE_IMM)) {
    case 0:
        /*
         *  The selected option has no immediate action.
         *  THEREFORE, if the direction is PRESETTING
         *  THEN we skip this option.
         */
        if (PRESETTING(direction))
            return;
        break;

    case OPTST_IMM:
        if (PRESETTING(direction)) {
            /*
             *  We are in the presetting direction with an option we handle
             *  immediately for enablement, but normally for disablement.
             *  Therefore, skip if disabled.
             */
            if ((opt_state->flags & OPTST_DISABLED) == 0)
                return;
        } else {
            /*
             *  We are in the processing direction with an option we handle
             *  immediately for enablement, but normally for disablement.
             *  Therefore, skip if NOT disabled.
             */
            if ((opt_state->flags & OPTST_DISABLED) != 0)
                return;
        }
        break;

    case OPTST_DISABLE_IMM:
        if (PRESETTING(direction)) {
            /*
             *  We are in the presetting direction with an option we handle
             *  immediately for disablement, but normally for disablement.
             *  Therefore, skip if NOT disabled.
             */
            if ((opt_state->flags & OPTST_DISABLED) != 0)
                return;
        } else {
            /*
             *  We are in the processing direction with an option we handle
             *  immediately for disablement, but normally for disablement.
             *  Therefore, skip if disabled.
             */
            if ((opt_state->flags & OPTST_DISABLED) == 0)
                return;
        }
        break;

    case OPTST_IMM|OPTST_DISABLE_IMM:
        /*
         *  The selected option is always for immediate action.
         *  THEREFORE, if the direction is PROCESSING
         *  THEN we skip this option.
         */
        if (PROCESSING(direction))
            return;
        break;
    }

    /*
     *  Fix up the args.
     */
    if (OPTST_GET_ARGTYPE(opt_state->pOD->fOptState) == OPARG_TYPE_NONE) {
        if (*opt_state->pzOptArg != NUL)
            return;
        opt_state->pzOptArg = NULL;

    } else if (opt_state->pOD->fOptState & OPTST_ARG_OPTIONAL) {
        if (*opt_state->pzOptArg == NUL)
             opt_state->pzOptArg = NULL;
        else {
            AGDUPSTR(opt_state->pzOptArg, opt_state->pzOptArg, "opt arg");
            opt_state->flags |= OPTST_ALLOC_ARG;
        }

    } else {
        if (*opt_state->pzOptArg == NUL)
             opt_state->pzOptArg = zNil;
        else {
            AGDUPSTR(opt_state->pzOptArg, opt_state->pzOptArg, "opt arg");
            opt_state->flags |= OPTST_ALLOC_ARG;
        }
    }

    {
        tOptionLoadMode sv = option_load_mode;
        option_load_mode = load_mode;
        handle_opt(opts, opt_state);
        option_load_mode = sv;
    }
}
Example #8
0
static void
do_env_opt(tOptState * os, char * env_name,
            tOptions * pOpts, teEnvPresetType type)
{
    os->pzOptArg = getenv(env_name);
    if (os->pzOptArg == NULL)
        return;

    os->flags   = OPTST_PRESET | OPTST_ALLOC_ARG | os->pOD->fOptState;
    os->optType = TOPT_UNDEFINED;

    if (  (os->pOD->pz_DisablePfx != NULL)
       && (streqvcmp(os->pzOptArg, os->pOD->pz_DisablePfx) == 0)) {
        os->flags |= OPTST_DISABLED;
        os->pzOptArg = NULL;
    }

    switch (type) {
    case ENV_IMM:
        /*
         *  Process only immediate actions
         */
        if (DO_IMMEDIATELY(os->flags))
            break;
        return;

    case ENV_NON_IMM:
        /*
         *  Process only NON immediate actions
         */
        if (DO_NORMALLY(os->flags) || DO_SECOND_TIME(os->flags))
            break;
        return;

    default: /* process everything */
        break;
    }

    /*
     *  Make sure the option value string is persistent and consistent.
     *
     *  The interpretation of the option value depends
     *  on the type of value argument the option takes
     */
    if (OPTST_GET_ARGTYPE(os->pOD->fOptState) == OPARG_TYPE_NONE) {
        /*
         *  Ignore any value.
         */
        os->pzOptArg = NULL;

    } else if (os->pzOptArg[0] == NUL) {
        /*
         * If the argument is the empty string and the argument is
         * optional, then treat it as if the option was not specified.
         */
        if ((os->pOD->fOptState & OPTST_ARG_OPTIONAL) == 0)
            return;
        os->pzOptArg = NULL;

    } else {
        AGDUPSTR(os->pzOptArg, os->pzOptArg, "option argument");
        os->flags |= OPTST_ALLOC_ARG;
    }

    handle_opt(pOpts, os);
}
Example #9
0
File: ducrc.c Project: Solertis/duc
int ducrc_read(struct ducrc *ducrc, const char *path)
{

	FILE *f = fopen(path, "r");
	if(f == NULL) {
		//duc_log(NULL, DUC_LOG_DBG, "Not reading configuration from '%s': %s", path, strerror(errno));
		return -1;
	}

	char section[256] = "";
	char buf[256];

	while(fgets(buf, sizeof buf, f) != NULL) {

		char *l = trim(buf);
		char *p;

		/* Strip newlines and comments */

		p = strchr(l, '#'); if(p) *p = '\0';
		p = strchr(l, '\n'); if(p) *p = '\0';
		p = strchr(l, '\r'); if(p) *p = '\0';

		/* section? */

		if(l[0] == '[') {
			p = strchr(l, ']');
			if(p) {
				*p = 0;
				strncpy(section, l+1, sizeof(section));
			}
			continue;
		}

		if(strlen(section) == 0 || 
				strcmp(section, "global") == 0 || 
				strcmp(section, ducrc->section) == 0) {

			/* key + value ? */

			p = strchr(l, ' ');

			if(p) {
				*p = '\0';
				char *longopt = trim(l);
				char *val = trim(p + 1);
				handle_opt(ducrc, 0, longopt,  val);
				continue;
			}

			/* longopt only */

			char *longopt = trim(l);
			if(strlen(longopt) > 0) {
				handle_opt(ducrc, 0, longopt, NULL);
			}
		}
	}
		

	fclose(f);

	return 0;
}
Example #10
0
/**
 *  Load an option from a block of text.  The text must start with the
 *  configurable/option name and be followed by its associated value.
 *  That value may be processed in any of several ways.  See "tOptionLoadMode"
 *  in autoopts.h.
 *
 * @param[in,out] opts       program options descriptor
 * @param[in,out] opt_state  option processing state
 * @param[in,out] line       source line with long option name in it
 * @param[in]     direction  current processing direction (preset or not)
 * @param[in]     load_mode  option loading mode (OPTION_LOAD_*)
 */
LOCAL void
load_opt_line(tOptions * opts, tOptState * opt_state, char * line,
              tDirection direction, tOptionLoadMode load_mode )
{
    /*
     * When parsing a stored line, we only look at the characters after
     * a hyphen.  Long names must always be at least two characters and
     * short options are always exactly one character long.
     */
    line = SPN_LOAD_LINE_SKIP_CHARS(line);

    {
        char * arg = assemble_arg_val(line, load_mode);

        if (IS_OPTION_NAME_CHAR(line[1])) {

            if (! SUCCESSFUL(opt_find_long(opts, line, opt_state)))
                return;

        } else if (! SUCCESSFUL(opt_find_short(opts, *line, opt_state)))
            return;

        if ((! CALLED(direction)) && (opt_state->flags & OPTST_NO_INIT))
            return;

        opt_state->pzOptArg = trim_quotes(arg);
    }

    if (! direction_ok(opt_state->flags, direction))
        return;

    /*
     *  Fix up the args.
     */
    if (OPTST_GET_ARGTYPE(opt_state->pOD->fOptState) == OPARG_TYPE_NONE) {
        if (*opt_state->pzOptArg != NUL)
            return;
        opt_state->pzOptArg = NULL;

    } else if (opt_state->pOD->fOptState & OPTST_ARG_OPTIONAL) {
        if (*opt_state->pzOptArg == NUL)
             opt_state->pzOptArg = NULL;
        else {
            AGDUPSTR(opt_state->pzOptArg, opt_state->pzOptArg, "opt arg");
            opt_state->flags |= OPTST_ALLOC_ARG;
        }

    } else {
        if (*opt_state->pzOptArg == NUL)
             opt_state->pzOptArg = zNil;
        else {
            AGDUPSTR(opt_state->pzOptArg, opt_state->pzOptArg, "opt arg");
            opt_state->flags |= OPTST_ALLOC_ARG;
        }
    }

    {
        tOptionLoadMode sv = option_load_mode;
        option_load_mode = load_mode;
        handle_opt(opts, opt_state);
        option_load_mode = sv;
    }
}