1/*--------------------------------------------------------------------
4 * Utilities related to the handling of configuration files.
6 * This file contains some generic tools to work on configuration files
7 * used by PostgreSQL, be they related to GUCs or authentication.
10 * Portions Copyright (c) 1996-2025, PostgreSQL Global Development Group
11 * Portions Copyright (c) 1994, Regents of the University of California
14 * src/backend/utils/misc/conffiles.c
16 *--------------------------------------------------------------------
29 * AbsoluteConfigLocation
31 * Given a configuration file or directory location that may be a relative
32 * path, return an absolute one. We consider the location to be relative to
33 * the directory holding the calling file, or to DataDir if no calling file.
44 if (calling_file != NULL)
46 strlcpy(abs_path, calling_file,
sizeof(abs_path));
65 * Returns the list of config files located in a directory, in alphabetical
66 * order. On error, returns NULL with details about the error stored in
71 int elevel,
int *num_filenames,
char **err_msg)
76 char **filenames = NULL;
80 * Reject directory name that is all-blank (including empty), as that
81 * leads to confusion --- we'd read the containing directory, typically
82 * resulting in recursive inclusion of the same file(s).
84 if (strspn(includedir,
" \t\r\n") == strlen(includedir))
87 (
errcode(ERRCODE_INVALID_PARAMETER_VALUE),
88 errmsg(
"empty configuration directory name: \"%s\"",
90 *err_msg =
"empty configuration directory name";
100 errmsg(
"could not open configuration directory \"%s\": %m",
107 * Read the directory and put the filenames in an array, so we can sort
108 * them prior to caller processing the contents.
111 filenames = (
char **)
palloc(size_filenames *
sizeof(
char *));
120 * Only parse files with names ending in ".conf". Explicitly reject
121 * files starting with ".". This excludes things like "." and "..",
122 * as well as typical hidden files, backup files, and editor debris.
124 if (strlen(de->
d_name) < 6)
128 if (strcmp(de->
d_name + strlen(de->
d_name) - 5,
".conf") != 0)
143 /* Add file to array, increasing its size in blocks of 32 */
144 if (*num_filenames >= size_filenames)
146 size_filenames += 32;
147 filenames = (
char **)
repalloc(filenames,
148 size_filenames *
sizeof(
char *));
155 /* Sort the files by name before leaving */
156 if (*num_filenames > 0)
static void cleanup(void)
char * AbsoluteConfigLocation(const char *location, const char *calling_file)
char ** GetConfFilesInDir(const char *includedir, const char *calling_file, int elevel, int *num_filenames, char **err_msg)
int errcode_for_file_access(void)
int errcode(int sqlerrcode)
int errmsg(const char *fmt,...)
#define ereport(elevel,...)
DIR * AllocateDir(const char *dirname)
struct dirent * ReadDir(DIR *dir, const char *dirname)
PGFileType get_dirent_type(const char *path, const struct dirent *de, bool look_through_symlinks, int elevel)
Assert(PointerIsAligned(start, uint64))
char * pstrdup(const char *in)
void * repalloc(void *pointer, Size size)
void pfree(void *pointer)
void join_path_components(char *ret_path, const char *head, const char *tail)
#define is_absolute_path(filename)
void canonicalize_path(char *path)
int pg_qsort_strcmp(const void *a, const void *b)
void get_parent_directory(char *path)
#define qsort(a, b, c, d)
size_t strlcpy(char *dst, const char *src, size_t siz)
char * psprintf(const char *fmt,...)
static const char * directory