File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / rsync / popt / poptconfig.c
Revision 1.1.1.1 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Fri Feb 17 15:09:30 2012 UTC (12 years, 4 months ago) by misho
Branches: rsync, MAIN
CVS tags: v3_2_3, v3_1_2p5, rsync3_0_9p0, RSYNC3_1_0, RSYNC3_0_9, HEAD
rsync

    1: /** \ingroup popt
    2:  * \file popt/poptconfig.c
    3:  */
    4: 
    5: /* (C) 1998-2002 Red Hat, Inc. -- Licensing details are in the COPYING
    6:    file accompanying popt source distributions, available from 
    7:    ftp://ftp.rpm.org/pub/rpm/dist. */
    8: 
    9: #include "system.h"
   10: #include "poptint.h"
   11: /*@access poptContext @*/
   12: 
   13: /*@-compmempass@*/	/* FIX: item->option.longName kept, not dependent. */
   14: static void configLine(poptContext con, char * line)
   15: 	/*@modifies con @*/
   16: {
   17:     size_t nameLength;
   18:     const char * entryType;
   19:     const char * opt;
   20:     poptItem item = (poptItem) alloca(sizeof(*item));
   21:     int i, j;
   22: 
   23:     if (con->appName == NULL)
   24: 	return;
   25:     nameLength = strlen(con->appName);
   26:     
   27: /*@-boundswrite@*/
   28:     memset(item, 0, sizeof(*item));
   29: 
   30:     if (strncmp(line, con->appName, nameLength)) return;
   31: 
   32:     line += nameLength;
   33:     if (*line == '\0' || !isSpace(line)) return;
   34: 
   35:     while (*line != '\0' && isSpace(line)) line++;
   36:     entryType = line;
   37:     while (*line == '\0' || !isSpace(line)) line++;
   38:     *line++ = '\0';
   39: 
   40:     while (*line != '\0' && isSpace(line)) line++;
   41:     if (*line == '\0') return;
   42:     opt = line;
   43:     while (*line == '\0' || !isSpace(line)) line++;
   44:     *line++ = '\0';
   45: 
   46:     while (*line != '\0' && isSpace(line)) line++;
   47:     if (*line == '\0') return;
   48: 
   49:     /*@-temptrans@*/ /* FIX: line alias is saved */
   50:     if (opt[0] == '-' && opt[1] == '-')
   51: 	item->option.longName = opt + 2;
   52:     else if (opt[0] == '-' && opt[2] == '\0')
   53: 	item->option.shortName = opt[1];
   54:     /*@=temptrans@*/
   55: 
   56:     if (poptParseArgvString(line, &item->argc, &item->argv)) return;
   57: 
   58:     /*@-modobserver@*/
   59:     item->option.argInfo = POPT_ARGFLAG_DOC_HIDDEN;
   60:     for (i = 0, j = 0; i < item->argc; i++, j++) {
   61: 	const char * f;
   62: 	if (!strncmp(item->argv[i], "--POPTdesc=", sizeof("--POPTdesc=")-1)) {
   63: 	    f = item->argv[i] + sizeof("--POPTdesc=");
   64: 	    if (f[0] == '$' && f[1] == '"') f++;
   65: 	    item->option.descrip = f;
   66: 	    item->option.argInfo &= ~POPT_ARGFLAG_DOC_HIDDEN;
   67: 	    j--;
   68: 	} else
   69: 	if (!strncmp(item->argv[i], "--POPTargs=", sizeof("--POPTargs=")-1)) {
   70: 	    f = item->argv[i] + sizeof("--POPTargs=");
   71: 	    if (f[0] == '$' && f[1] == '"') f++;
   72: 	    item->option.argDescrip = f;
   73: 	    item->option.argInfo &= ~POPT_ARGFLAG_DOC_HIDDEN;
   74: 	    item->option.argInfo |= POPT_ARG_STRING;
   75: 	    j--;
   76: 	} else
   77: 	if (j != i)
   78: 	    item->argv[j] = item->argv[i];
   79:     }
   80:     if (j != i) {
   81: 	item->argv[j] = NULL;
   82: 	item->argc = j;
   83:     }
   84:     /*@=modobserver@*/
   85: /*@=boundswrite@*/
   86: 	
   87:     /*@-nullstate@*/ /* FIX: item->argv[] may be NULL */
   88:     if (!strcmp(entryType, "alias"))
   89: 	(void) poptAddItem(con, item, 0);
   90:     else if (!strcmp(entryType, "exec"))
   91: 	(void) poptAddItem(con, item, 1);
   92:     /*@=nullstate@*/
   93: }
   94: /*@=compmempass@*/
   95: 
   96: int poptReadConfigFile(poptContext con, const char * fn)
   97: {
   98:     const char * file, * chptr, * end;
   99:     char * buf;
  100: /*@dependent@*/ char * dst;
  101:     int fd, rc;
  102:     off_t fileLength;
  103: 
  104:     fd = open(fn, O_RDONLY);
  105:     if (fd < 0)
  106: 	return (errno == ENOENT ? 0 : POPT_ERROR_ERRNO);
  107: 
  108:     fileLength = lseek(fd, 0, SEEK_END);
  109:     if (fileLength == -1 || lseek(fd, 0, 0) == -1) {
  110: 	rc = errno;
  111: 	(void) close(fd);
  112: 	errno = rc;
  113: 	return POPT_ERROR_ERRNO;
  114:     }
  115: 
  116:     file = alloca(fileLength + 1);
  117:     if (read(fd, (char *)file, fileLength) != fileLength) {
  118: 	rc = errno;
  119: 	(void) close(fd);
  120: 	errno = rc;
  121: 	return POPT_ERROR_ERRNO;
  122:     }
  123:     if (close(fd) == -1)
  124: 	return POPT_ERROR_ERRNO;
  125: 
  126: /*@-boundswrite@*/
  127:     dst = buf = alloca(fileLength + 1);
  128: 
  129:     chptr = file;
  130:     end = (file + fileLength);
  131:     /*@-infloops@*/	/* LCL: can't detect chptr++ */
  132:     while (chptr < end) {
  133: 	switch (*chptr) {
  134: 	  case '\n':
  135: 	    *dst = '\0';
  136: 	    dst = buf;
  137: 	    while (*dst && isSpace(dst)) dst++;
  138: 	    if (*dst && *dst != '#')
  139: 		configLine(con, dst);
  140: 	    chptr++;
  141: 	    /*@switchbreak@*/ break;
  142: 	  case '\\':
  143: 	    *dst++ = *chptr++;
  144: 	    if (chptr < end) {
  145: 		if (*chptr == '\n') 
  146: 		    dst--, chptr++;	
  147: 		    /* \ at the end of a line does not insert a \n */
  148: 		else
  149: 		    *dst++ = *chptr++;
  150: 	    }
  151: 	    /*@switchbreak@*/ break;
  152: 	  default:
  153: 	    *dst++ = *chptr++;
  154: 	    /*@switchbreak@*/ break;
  155: 	}
  156:     }
  157:     /*@=infloops@*/
  158: /*@=boundswrite@*/
  159: 
  160:     return 0;
  161: }
  162: 
  163: int poptReadDefaultConfig(poptContext con, /*@unused@*/ UNUSED(int useEnv))
  164: {
  165:     char * fn, * home;
  166:     int rc;
  167: 
  168:     if (con->appName == NULL) return 0;
  169: 
  170:     rc = poptReadConfigFile(con, "/etc/popt");
  171:     if (rc) return rc;
  172: 
  173:     if ((home = getenv("HOME"))) {
  174: 	size_t bufsize = strlen(home) + 20;
  175: 	fn = alloca(bufsize);
  176: 	if (fn == NULL) return 0;
  177: 	snprintf(fn, bufsize, "%s/.popt", home);
  178: 	rc = poptReadConfigFile(con, fn);
  179: 	if (rc) return rc;
  180:     }
  181: 
  182:     return 0;
  183: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>