Beispiel #1
0
_nc_set_writedir(char *dir)
/* set the write directory for compiled entries */
{
    const char *destination;
    char actual[PATH_MAX];

    if (dir == 0
	&& use_terminfo_vars())
	dir = getenv("TERMINFO");

    if (dir != 0)
	(void) _nc_tic_dir(dir);

    destination = _nc_tic_dir(0);
    if (make_directory(destination) < 0) {
	char *home = _nc_home_terminfo();

	if (home != 0) {
	    destination = home;
	    if (make_directory(destination) < 0)
		_nc_err_abort("%s: permission denied (errno %d)",
			      destination, errno);
	}
    }

    /*
     * Note: because of this code, this logic should be exercised
     * *once only* per run.
     */
    if (chdir(_nc_tic_dir(destination)) < 0
	|| getcwd(actual, sizeof(actual)) == 0)
	_nc_err_abort("%s: not a directory", destination);
    _nc_keep_tic_dir(strdup(actual));
}
Beispiel #2
0
_nc_tic_dir(const char *path)
{
    if (!KeepTicDirectory) {
	if (path != 0) {
	    TicDirectory = path;
	    HaveTicDirectory = TRUE;
	} else if (!HaveTicDirectory && use_terminfo_vars()) {
	    char *envp;
	    if ((envp = getenv("TERMINFO")) != 0)
		return _nc_tic_dir(envp);
	}
    }
    return TicDirectory;
}
Beispiel #3
0
_nc_tic_dir(const char *path)
{
    T(("_nc_tic_dir %s", NonNull(path)));
    if (!KeepTicDirectory) {
	if (path != 0) {
	    TicDirectory = path;
	    HaveTicDirectory = TRUE;
	} else if (HaveTicDirectory == 0) {
	    if (use_terminfo_vars()) {
		char *envp;
		if ((envp = getenv("TERMINFO")) != 0)
		    return _nc_tic_dir(envp);
	    }
	}
    }
    return TicDirectory ? TicDirectory : TERMINFO;
}
Beispiel #4
0
_nc_home_terminfo(void)
{
    char *result = 0;
#if USE_HOME_TERMINFO
    char *home;

    if (use_terminfo_vars()) {
	if (MyBuffer == 0) {
	    if ((home = getenv("HOME")) != 0) {
		size_t want = (strlen(home) + sizeof(PRIVATE_INFO));
		TYPE_MALLOC(char, want, MyBuffer);
		_nc_SPRINTF(MyBuffer, _nc_SLIMIT(want) PRIVATE_INFO, home);
	    }
	}
	result = MyBuffer;
    }
#endif
    return result;
}
Beispiel #5
0
_nc_set_writedir(char *dir)
{
    const char *destination;
    char actual[PATH_MAX];

    if (dir == 0
#ifndef USE_ROOT_ENVIRON
	&& use_terminfo_vars()
#endif
	)
	dir = getenv("TERMINFO");

    if (dir != 0)
	(void) _nc_tic_dir(dir);

    destination = _nc_tic_dir(0);
    if (make_db_root(destination) < 0) {
	char *home = _nc_home_terminfo();

	if (home != 0) {
	    destination = home;
	    if (make_db_root(destination) < 0)
		_nc_err_abort("%s: permission denied (errno %d)",
			      destination, errno);
	}
    }

    /*
     * Note: because of this code, this logic should be exercised
     * *once only* per run.
     */
#if USE_HASHED_DB
    make_db_path(actual, destination, sizeof(actual));
#else
    if (chdir(_nc_tic_dir(destination)) < 0
	|| getcwd(actual, sizeof(actual)) == 0)
	_nc_err_abort("%s: not a directory", destination);
#endif
    _nc_keep_tic_dir(strdup(actual));
}
Beispiel #6
0
_nc_first_db(DBDIRS * state, int *offset)
{
    bool cache_has_expired = FALSE;
    *state = dbdTIC;
    *offset = 0;

    T(("_nc_first_db"));

    /* build a blob containing all of the strings we will use for a lookup
     * table.
     */
    if (my_blob == 0 || (cache_has_expired = cache_expired())) {
	size_t blobsize = 0;
	const char *values[dbdLAST];
	struct stat *my_stat;
	int j, k;

	if (cache_has_expired)
	    free_cache();

	for (j = 0; j < dbdLAST; ++j)
	    values[j] = 0;

	/*
	 * This is the first item in the list, and is used only when tic is
	 * writing to the database, as a performance improvement.
	 */
	values[dbdTIC] = TicDirectory;

#if NCURSES_USE_DATABASE
#ifdef TERMINFO_DIRS
	values[dbdCfgList] = TERMINFO_DIRS;
#endif
#ifdef TERMINFO
	values[dbdCfgOnce] = TERMINFO;
#endif
#endif

#if NCURSES_USE_TERMCAP
	values[dbdCfgList2] = TERMPATH;
#endif

	if (use_terminfo_vars()) {
#if NCURSES_USE_DATABASE
	    values[dbdEnvOnce] = cache_getenv("TERMINFO", dbdEnvOnce);
	    values[dbdHome] = _nc_home_terminfo();
	    (void) cache_getenv("HOME", dbdHome);
	    values[dbdEnvList] = cache_getenv("TERMINFO_DIRS", dbdEnvList);

#endif
#if NCURSES_USE_TERMCAP
	    values[dbdEnvOnce2] = cache_getenv("TERMCAP", dbdEnvOnce2);
	    /* only use $TERMCAP if it is an absolute path */
	    if (values[dbdEnvOnce2] != 0
		&& *values[dbdEnvOnce2] != '/') {
		values[dbdEnvOnce2] = 0;
	    }
	    values[dbdEnvList2] = cache_getenv("TERMPATH", dbdEnvList2);
#endif /* NCURSES_USE_TERMCAP */
	}

	for (j = 0; j < dbdLAST; ++j) {
	    if (values[j] == 0)
		values[j] = "";
	    blobsize += 2 + strlen(values[j]);
	}

	my_blob = malloc(blobsize);
	if (my_blob != 0) {
	    *my_blob = '\0';
	    for (j = 0; j < dbdLAST; ++j) {
		add_to_blob(values[j], blobsize);
	    }

	    /* Now, build an array which will be pointers to the distinct
	     * strings in the blob.
	     */
	    blobsize = 2;
	    for (j = 0; my_blob[j] != '\0'; ++j) {
		if (my_blob[j] == NCURSES_PATHSEP)
		    ++blobsize;
	    }
	    my_list = typeCalloc(char *, blobsize);
	    my_stat = typeCalloc(struct stat, blobsize);
	    if (my_list != 0 && my_stat != 0) {
		k = 0;
		my_list[k++] = my_blob;
		for (j = 0; my_blob[j] != '\0'; ++j) {
		    if (my_blob[j] == NCURSES_PATHSEP) {
			my_blob[j] = '\0';
			my_list[k++] = &my_blob[j + 1];
		    }
		}

		/*
		 * Eliminate duplicates from the list.
		 */
		for (j = 0; my_list[j] != 0; ++j) {
#ifdef TERMINFO
		    if (*my_list[j] == '\0')
			my_list[j] = strdup(TERMINFO);
#endif
		    for (k = 0; k < j; ++k) {
			if (!strcmp(my_list[j], my_list[k])) {
			    k = j - 1;
			    while ((my_list[j] = my_list[j + 1]) != 0) {
				++j;
			    }
			    j = k;
			    break;
			}
		    }
		}

		/*
		 * Eliminate non-existent databases, and those that happen to
		 * be symlinked to another location.
		 */
		for (j = 0; my_list[j] != 0; ++j) {
		    bool found = check_existence(my_list[j], &my_stat[j]);
#if HAVE_LINK
		    if (found) {
			for (k = 0; k < j; ++k) {
			    if (my_stat[j].st_dev == my_stat[k].st_dev
				&& my_stat[j].st_ino == my_stat[k].st_ino) {
				found = FALSE;
				break;
			    }
			}
		    }
#endif
		    if (!found) {
			k = j;
			while ((my_list[k] = my_list[k + 1]) != 0) {
			    ++k;
			}
			--j;
		    }
		}
		my_size = j;
		my_time = time((time_t *) 0);
	    } else {
		FreeAndNull(my_blob);
	    }
	    free(my_stat);
	}
Beispiel #7
0
_nc_next_db(DBDIRS * state, int *offset)
{
    const char *result;
    char *envp;

    while (*state < dbdLAST) {
	DBDIRS next = (DBDIRS) ((int) (*state) + 1);

	result = 0;

	switch (*state) {
	case dbdTIC:
	    if (HaveTicDirectory)
		result = _nc_tic_dir(0);
	    break;
#if USE_DATABASE
	case dbdEnvOnce:
	    if (use_terminfo_vars()) {
		if ((envp = getenv("TERMINFO")) != 0)
		    result = _nc_tic_dir(envp);
	    }
	    break;
	case dbdHome:
	    if (use_terminfo_vars()) {
		result = _nc_home_terminfo();
	    }
	    break;
	case dbdEnvList:
	    if (use_terminfo_vars()) {
		if ((result = NEXT_DBD(getenv("TERMINFO_DIRS"), offset)) != 0)
		    next = *state;
	    }
	    break;
	case dbdCfgList:
#ifdef TERMINFO_DIRS
	    if ((result = NEXT_DBD(TERMINFO_DIRS, offset)) != 0)
		next = *state;
#endif
	    break;
	case dbdCfgOnce:
#ifndef TERMINFO_DIRS
	    result = TERMINFO;
#endif
	    break;
#endif /* USE_DATABASE */
#if USE_TERMCAP
	case dbdEnvOnce2:
	    if (use_terminfo_vars()) {
		if ((envp = getenv("TERMCAP")) != 0)
		    result = _nc_tic_dir(envp);
	    }
	    break;
	case dbdEnvList2:
	    if (use_terminfo_vars()) {
		if ((result = NEXT_DBD(getenv("TERMPATH"), offset)) != 0)
		    next = *state;
	    }
	    break;
	case dbdCfgList2:
	    if ((result = NEXT_DBD(TERMPATH, offset)) != 0)
		next = *state;
	    break;
#endif /* USE_TERMCAP */
	case dbdLAST:
	    break;
	}
	if (*state != next) {
	    *state = next;
	    *offset = 0;
	    _nc_last_db();
	}
	if (result != 0) {
	    return result;
	}
    }
    return 0;
}