*** a/src/backend/utils/init/miscinit.c --- b/src/backend/utils/init/miscinit.c *************** *** 93,98 **** SetDataDir(const char *dir) --- 93,100 ---- /* If presented path is relative, convert to absolute */ new = make_absolute_path(dir); + if (new == NULL) + elog(FATAL, "could not get absolute path :%s : %m", dir); if (DataDir) free(DataDir); *************** *** 117,194 **** ChangeToDataDir(void) DataDir))); } - /* - * If the given pathname isn't already absolute, make it so, interpreting - * it relative to the current working directory. - * - * Also canonicalizes the path. The result is always a malloc'd copy. - * - * Note: interpretation of relative-path arguments during postmaster startup - * should happen before doing ChangeToDataDir(), else the user will probably - * not like the results. - */ - char * - make_absolute_path(const char *path) - { - char *new; - - /* Returning null for null input is convenient for some callers */ - if (path == NULL) - return NULL; - - if (!is_absolute_path(path)) - { - char *buf; - size_t buflen; - - buflen = MAXPGPATH; - for (;;) - { - buf = malloc(buflen); - if (!buf) - ereport(FATAL, - (errcode(ERRCODE_OUT_OF_MEMORY), - errmsg("out of memory"))); - - if (getcwd(buf, buflen)) - break; - else if (errno == ERANGE) - { - free(buf); - buflen *= 2; - continue; - } - else - { - free(buf); - elog(FATAL, "could not get current working directory: %m"); - } - } - - new = malloc(strlen(buf) + strlen(path) + 2); - if (!new) - ereport(FATAL, - (errcode(ERRCODE_OUT_OF_MEMORY), - errmsg("out of memory"))); - sprintf(new, "%s/%s", buf, path); - free(buf); - } - else - { - new = strdup(path); - if (!new) - ereport(FATAL, - (errcode(ERRCODE_OUT_OF_MEMORY), - errmsg("out of memory"))); - } - - /* Make sure punctuation is canonical, too */ - canonicalize_path(new); - - return new; - } - - /* ---------------------------------------------------------------- * User ID state * --- 119,124 ---- *** a/src/backend/utils/misc/guc.c --- b/src/backend/utils/misc/guc.c *************** *** 4166,4171 **** SelectConfigFiles(const char *userDoption, const char *progname) --- 4166,4174 ---- else configdir = make_absolute_path(getenv("PGDATA")); + if (configdir == NULL) + return false; + /* * Find the configuration file: if config_file was specified on the * command line, use it, else use configdir/postgresql.conf. In any case *************** *** 4173,4179 **** SelectConfigFiles(const char *userDoption, const char *progname) --- 4176,4186 ---- * the same way by future backends. */ if (ConfigFileName) + { fname = make_absolute_path(ConfigFileName); + if (fname == NULL) + return false; + } else if (configdir) { fname = guc_malloc(FATAL, *************** *** 4255,4261 **** SelectConfigFiles(const char *userDoption, const char *progname) --- 4262,4272 ---- * Figure out where pg_hba.conf is, and make sure the path is absolute. */ if (HbaFileName) + { fname = make_absolute_path(HbaFileName); + if (fname == NULL) + return false; + } else if (configdir) { fname = guc_malloc(FATAL, *************** *** 4278,4284 **** SelectConfigFiles(const char *userDoption, const char *progname) --- 4289,4299 ---- * Likewise for pg_ident.conf. */ if (IdentFileName) + { fname = make_absolute_path(IdentFileName); + if (fname == NULL) + return false; + } else if (configdir) { fname = guc_malloc(FATAL, *** a/src/include/miscadmin.h --- b/src/include/miscadmin.h *************** *** 296,302 **** extern void SetCurrentRoleId(Oid roleid, bool is_superuser); extern void SetDataDir(const char *dir); extern void ChangeToDataDir(void); - extern char *make_absolute_path(const char *path); /* in utils/misc/superuser.c */ extern bool superuser(void); /* current user is superuser */ --- 296,301 ---- *** a/src/include/port.h --- b/src/include/port.h *************** *** 59,64 **** extern void get_html_path(const char *my_exec_path, char *ret_path); --- 59,65 ---- extern void get_man_path(const char *my_exec_path, char *ret_path); extern bool get_home_path(char *ret_path); extern void get_parent_directory(char *path); + extern char *make_absolute_path(const char *path); /* port/dirmod.c */ extern char **pgfnames(const char *path); *** a/src/port/path.c --- b/src/port/path.c *************** *** 757,759 **** trim_trailing_separator(char *path) --- 757,833 ---- for (p--; p > path && IS_DIR_SEP(*p); p--) *p = '\0'; } + + /* + * If the given pathname isn't already absolute, make it so, interpreting + * it relative to the current working directory. + * + * Also canonicalizes the path. The result is always a malloc'd copy. + * incase of error returns NULL. + */ + char * + make_absolute_path(const char *path) + { + char *result; + + /* Returning null for null input is convenient for some callers */ + if (path == NULL) + return NULL; + + if (!is_absolute_path(path)) + { + char *buf; + size_t buflen; + + buflen = MAXPGPATH; + for (;;) + { + buf = malloc(buflen); + if (!buf) + { + fprintf(stderr, "out of memory\n"); + return NULL; + } + + if (getcwd(buf, buflen)) + break; + else if (errno == ERANGE) + { + free(buf); + buflen *= 2; + continue; + } + else + { + free(buf); + fprintf(stderr, "could not get current working directory :%s\n", strerror(errno)); + return NULL; + } + } + + result = malloc(strlen(buf) + strlen(path) + 2); + if (!result) + { + free(buf); + fprintf(stderr, "out of memory\n"); + return NULL; + } + + sprintf(result, "%s/%s", buf, path); + free(buf); + } + else + { + result = strdup(path); + if (!result) + { + fprintf(stderr, "out of memory\n"); + return NULL; + } + } + + /* Make sure punctuation is canonical, too */ + canonicalize_path(result); + + return result; + } *** a/src/test/regress/pg_regress.c --- b/src/test/regress/pg_regress.c *************** *** 1832,1864 **** create_role(const char *rolename, const _stringlist * granted_dbs) } } - static char * - make_absolute_path(const char *in) - { - char *result; - - if (is_absolute_path(in)) - result = strdup(in); - else - { - static char cwdbuf[MAXPGPATH]; - - if (!cwdbuf[0]) - { - if (!getcwd(cwdbuf, sizeof(cwdbuf))) - { - fprintf(stderr, _("could not get current working directory: %s\n"), strerror(errno)); - exit(2); - } - } - - result = psprintf("%s/%s", cwdbuf, in); - } - - canonicalize_path(result); - return result; - } - static void help(void) { --- 1832,1837 ---- *************** *** 2004,2009 **** regression_main(int argc, char *argv[], init_function ifunc, test_function tfunc --- 1977,1984 ---- break; case 9: temp_install = make_absolute_path(optarg); + if (temp_install == NULL) + exit(2); break; case 10: nolocale = true; *************** *** 2074,2081 **** regression_main(int argc, char *argv[], init_function ifunc, test_function tfunc --- 2049,2065 ---- port = 0xC000 | (PG_VERSION_NUM & 0x3FFF); inputdir = make_absolute_path(inputdir); + if (inputdir == NULL) + exit(2); + outputdir = make_absolute_path(outputdir); + if (outputdir == NULL) + exit(2); + dlpath = make_absolute_path(dlpath); + if (dlpath == NULL) + exit(2); + /* * Initialization