Re: Data directory with trailing [back]slash

Bruce Momjian <[email protected]>
Newsgroups gmane.comp.db.postgresql.devel.win32,gmane.comp.db.postgresql.devel.patches
Message-ID <[email protected]>
Oops, path patch attached.

---------------------------------------------------------------------------

Bruce Momjian wrote:
> 
> I think this still is not fixed.  I think we need to add a call to
> trim_trailing_separator() in checkDataDir().  Magnus, can you confirm
> this will fix it?
> 
> ---------------------------------------------------------------------------
> 
> Bruce Momjian wrote:
> > 
> > I am now confused about the original report.  I don't see how my fix
> > would correct the reported problem.  trim_trailing_separator() would
> > have handled d:\pgdata\ and d:\pgdata just fine.  The fix only corrects
> > d:\.
> > 
> > Magnus, does current CVS fix the problem?
> > 
> > ---------------------------------------------------------------------------
> > 
> > Andrew Dunstan wrote:
> > > 
> > > 
> > > Tom Lane wrote:
> > > 
> > > >"Magnus Hagander" <[email protected]> writes:
> > > >  
> > > >
> > > >>It's not possible to start the postmaster on win32 with:
> > > >>postmaster -D d:\pgdata\
> > > >>or
> > > >>postmaster -D d:/pgdata/
> > > >>    
> > > >>
> > > >
> > > >Sounds like canonicalize_path() needs to be applied a bit sooner than
> > > >it is.
> > > >
> > > >BTW I think canonicalize_path() is a few bricks shy of a load yet:
> > > >I'm not sure it works well with Windows drive-letters, and it definitely
> > > >will strip significant slashes when given input like '/' or 'C:\'.
> > > >Feel free to fix those problems while at it...
> > > >  
> > > >
> > > 
> > > Or use the attached patch, which I think does it right.
> > > 
> > > cheers
> > > 
> > > andrew
> > 
> > 
> > > 
> > > ---------------------------(end of broadcast)---------------------------
> > > TIP 9: the planner will ignore your desire to choose an index scan if your
> > >       joining column's datatypes do not match
> > 
> > -- 
> >   Bruce Momjian                        |  http://candle.pha.pa.us
> >   [email protected]               |  (610) 359-1001
> >   +  If your life is a hard drive,     |  13 Roberts Road
> >   +  Christ can be your backup.        |  Newtown Square, Pennsylvania 19073
> > 
> > ---------------------------(end of broadcast)---------------------------
> > TIP 2: you can get off all lists at once with the unregister command
> >     (send "unregister YourEmailAddressHere" to [email protected])
> > 
> 
> -- 
>   Bruce Momjian                        |  http://candle.pha.pa.us
>   [email protected]               |  (610) 359-1001
>   +  If your life is a hard drive,     |  13 Roberts Road
>   +  Christ can be your backup.        |  Newtown Square, Pennsylvania 19073
> 
> ---------------------------(end of broadcast)---------------------------
> TIP 9: the planner will ignore your desire to choose an index scan if your
>       joining column's datatypes do not match
> 

-- 
  Bruce Momjian                        |  http://candle.pha.pa.us
  [email protected]               |  (610) 359-1001
  +  If your life is a hard drive,     |  13 Roberts Road
  +  Christ can be your backup.        |  Newtown Square, Pennsylvania 19073


---------------------------(end of broadcast)---------------------------
TIP 8: explain analyze is your friend
/bjm/diff (text/plain, 12.4 KB)
Index: src/backend/postmaster/postmaster.c
===================================================================
RCS file: /cvsroot/pgsql-server/src/backend/postmaster/postmaster.c,v
retrieving revision 1.407
diff -c -c -r1.407 postmaster.c
*** src/backend/postmaster/postmaster.c	11 Jul 2004 00:18:43 -0000	1.407
--- src/backend/postmaster/postmaster.c	11 Jul 2004 21:29:16 -0000
***************
*** 372,378 ****
  	InitializeGUCOptions();
  
  	userPGDATA = getenv("PGDATA");		/* default value */
! 
  	opterr = 1;
  
  	while ((opt = getopt(argc, argv, "A:a:B:b:c:D:d:Fh:ik:lm:MN:no:p:Ss-:")) != -1)
--- 372,379 ----
  	InitializeGUCOptions();
  
  	userPGDATA = getenv("PGDATA");		/* default value */
! 	canonicalize_path(userPGDATA);
! 	
  	opterr = 1;
  
  	while ((opt = getopt(argc, argv, "A:a:B:b:c:D:d:Fh:ik:lm:MN:no:p:Ss-:")) != -1)
Index: src/backend/utils/misc/guc.c
===================================================================
RCS file: /cvsroot/pgsql-server/src/backend/utils/misc/guc.c,v
retrieving revision 1.214
diff -c -c -r1.214 guc.c
*** src/backend/utils/misc/guc.c	11 Jul 2004 00:18:44 -0000	1.214
--- src/backend/utils/misc/guc.c	11 Jul 2004 21:29:19 -0000
***************
*** 113,118 ****
--- 113,119 ----
  static bool assign_stage_log_stats(bool newval, bool doit, GucSource source);
  static bool assign_log_stats(bool newval, bool doit, GucSource source);
  static bool assign_transaction_read_only(bool newval, bool doit, GucSource source);
+ static const char *assign_canonical_path(const char *newval, bool doit, GucSource source);
  
  static void ReadConfigFile(char *filename, GucContext context);
  
***************
*** 1470,1476 ****
  						 "the specified file.")
  		},
  		&Dynamic_library_path,
! 		"$libdir", NULL, NULL
  	},
  
  	{
--- 1471,1477 ----
  						 "the specified file.")
  		},
  		&Dynamic_library_path,
! 		"$libdir", assign_canonical_path, NULL
  	},
  
  	{
***************
*** 1556,1562 ****
  			GUC_LIST_INPUT | GUC_LIST_QUOTE
  		},
  		&preload_libraries_string,
! 		"", NULL, NULL
  	},
  
  	{
--- 1557,1563 ----
  			GUC_LIST_INPUT | GUC_LIST_QUOTE
  		},
  		&preload_libraries_string,
! 		"", assign_canonical_path, NULL
  	},
  
  	{
***************
*** 1678,1684 ****
  			NULL
  		},
  		&UnixSocketDir,
! 		"", NULL, NULL
  	},
  
  	{
--- 1679,1685 ----
  			NULL
  		},
  		&UnixSocketDir,
! 		"", assign_canonical_path, NULL
  	},
  
  	{
***************
*** 1712,1736 ****
  	{
  		{"pgdata", PGC_POSTMASTER, 0, gettext_noop("Sets the location of the data directory"), NULL}, 
  		&guc_pgdata,
! 		NULL, NULL, NULL
  	},
  
  	{
  		{"hba_conf", PGC_SIGHUP, 0, gettext_noop("Sets the location of the \"hba\" configuration file"), NULL}, 
  		&guc_hbafile,
! 		NULL, NULL, NULL
  	},
  
  	{
  		{"ident_conf", PGC_SIGHUP, 0, gettext_noop("Sets the location of the \"ident\" configuration file"), NULL}, 
  		&guc_identfile,
! 		NULL, NULL, NULL
  	},
  
  	{
  		{"external_pidfile", PGC_POSTMASTER, 0, gettext_noop("Writes the postmaster PID to the specified file"), NULL},
  		&external_pidfile,
! 		NULL, NULL, NULL
  	},
  
  	/* End-of-list marker */
--- 1713,1737 ----
  	{
  		{"pgdata", PGC_POSTMASTER, 0, gettext_noop("Sets the location of the data directory"), NULL}, 
  		&guc_pgdata,
! 		NULL, assign_canonical_path, NULL
  	},
  
  	{
  		{"hba_conf", PGC_SIGHUP, 0, gettext_noop("Sets the location of the \"hba\" configuration file"), NULL}, 
  		&guc_hbafile,
! 		NULL, assign_canonical_path, NULL
  	},
  
  	{
  		{"ident_conf", PGC_SIGHUP, 0, gettext_noop("Sets the location of the \"ident\" configuration file"), NULL}, 
  		&guc_identfile,
! 		NULL, assign_canonical_path, NULL
  	},
  
  	{
  		{"external_pidfile", PGC_POSTMASTER, 0, gettext_noop("Writes the postmaster PID to the specified file"), NULL},
  		&external_pidfile,
! 		NULL, assign_canonical_path, NULL
  	},
  
  	/* End-of-list marker */
***************
*** 5160,5167 ****
  }
  
  static const char *
! assign_client_min_messages(const char *newval,
! 						   bool doit, GucSource source)
  {
  	return (assign_msglvl(&client_min_messages, newval, doit, source));
  }
--- 5161,5167 ----
  }
  
  static const char *
! assign_client_min_messages(const char *newval, bool doit, GucSource source)
  {
  	return (assign_msglvl(&client_min_messages, newval, doit, source));
  }
***************
*** 5428,5433 ****
--- 5428,5448 ----
  				(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
  				 errmsg("cannot set transaction read only mode inside a subtransaction")));
  	return true;
+ }
+ 
+ static const char *
+ assign_canonical_path(const char *newval, bool doit, GucSource source)
+ {
+ 	
+ 	if (doit)
+ 	{
+ 		/* We have to create a new pointer to force the change */
+ 		char *canon_val = guc_strdup(FATAL, newval);
+ 		canonicalize_path(canon_val);
+ 		return canon_val;
+ 	}
+ 	else
+ 		return newval;
  }
  
  #include "guc-file.c"
Index: src/bin/psql/command.c
===================================================================
RCS file: /cvsroot/pgsql-server/src/bin/psql/command.c,v
retrieving revision 1.119
diff -c -c -r1.119 command.c
*** src/bin/psql/command.c	11 Jul 2004 13:29:15 -0000	1.119
--- src/bin/psql/command.c	11 Jul 2004 21:29:22 -0000
***************
*** 375,380 ****
--- 375,381 ----
  			fname = psql_scan_slash_option(scan_state,
  										   OT_NORMAL, NULL, true);
  			expand_tilde(&fname);
+ 			canonicalize_path(fname);
  			status = do_edit(fname, query_buf) ? CMD_NEWEDIT : CMD_ERROR;
  			free(fname);
  		}
***************
*** 777,784 ****
  					fd = popen(&fname[1], "w");
  				}
  				else
  					fd = fopen(fname, "w");
! 
  				if (!fd)
  				{
  					psql_error("%s: %s\n", fname, strerror(errno));
--- 778,787 ----
  					fd = popen(&fname[1], "w");
  				}
  				else
+ 				{
+ 					canonicalize_path(fname);
  					fd = fopen(fname, "w");
! 				}
  				if (!fd)
  				{
  					psql_error("%s: %s\n", fname, strerror(errno));
***************
*** 1122,1128 ****
  
  	if (filename_arg)
  		fname = filename_arg;
- 
  	else
  	{
  		/* make a temp file to edit */
--- 1125,1130 ----
***************
*** 1262,1267 ****
--- 1264,1270 ----
  	if (!filename)
  		return false;
  
+ 	canonicalize_path(filename);
  	fd = fopen(filename, PG_BINARY_R);
  
  	if (!fd)
Index: src/bin/psql/copy.c
===================================================================
RCS file: /cvsroot/pgsql-server/src/bin/psql/copy.c,v
retrieving revision 1.49
diff -c -c -r1.49 copy.c
*** src/bin/psql/copy.c	11 Jul 2004 13:29:15 -0000	1.49
--- src/bin/psql/copy.c	11 Jul 2004 21:29:22 -0000
***************
*** 513,518 ****
--- 513,520 ----
  		appendPQExpBuffer(&query, " FORCE NOT NULL %s", options->force_notnull_list);
  	}
  
+ 	canonicalize_path(options->file);
+ 
  	if (options->from)
  	{
  		if (options->file)
Index: src/port/path.c
===================================================================
RCS file: /cvsroot/pgsql-server/src/port/path.c,v
retrieving revision 1.22
diff -c -c -r1.22 path.c
*** src/port/path.c	11 Jul 2004 02:59:42 -0000	1.22
--- src/port/path.c	11 Jul 2004 21:29:23 -0000
***************
*** 33,38 ****
--- 33,39 ----
  #endif
  
  const static char *relative_path(const char *bin_path, const char *other_path);
+ static void make_relative(const char *my_exec_path, const char *p, char *ret_path);
  static void trim_directory(char *path);
  static void trim_trailing_separator(char *path);
  
***************
*** 43,57 ****
  		(p)++; \
  }
  
- /* Macro creates a relative path */
- #define MAKE_RELATIVE \
- do { \
- 		StrNCpy(path, my_exec_path, MAXPGPATH); \
- 		trim_directory(path); \
- 		trim_directory(path); \
- 		snprintf(ret_path, MAXPGPATH, "%s/%s", path, p); \
- } while (0)
- 
  /*
   *	first_dir_separator
   */
--- 44,49 ----
***************
*** 140,152 ****
  void
  get_share_path(const char *my_exec_path, char *ret_path)
  {
- 	char path[MAXPGPATH];
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, PGSHAREDIR)))
! 		MAKE_RELATIVE;
  	else
  		StrNCpy(ret_path, PGSHAREDIR, MAXPGPATH);
  }
  
  
--- 132,144 ----
  void
  get_share_path(const char *my_exec_path, char *ret_path)
  {
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, PGSHAREDIR)))
! 		make_relative(my_exec_path, p, ret_path);
  	else
  		StrNCpy(ret_path, PGSHAREDIR, MAXPGPATH);
+ 	canonicalize_path(ret_path);
  }
  
  
***************
*** 157,169 ****
  void
  get_etc_path(const char *my_exec_path, char *ret_path)
  {
- 	char path[MAXPGPATH];
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, SYSCONFDIR)))
! 		MAKE_RELATIVE;
  	else
  		StrNCpy(ret_path, SYSCONFDIR, MAXPGPATH);
  }
  
  
--- 149,161 ----
  void
  get_etc_path(const char *my_exec_path, char *ret_path)
  {
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, SYSCONFDIR)))
! 		make_relative(my_exec_path, p, ret_path);
  	else
  		StrNCpy(ret_path, SYSCONFDIR, MAXPGPATH);
+ 	canonicalize_path(ret_path);
  }
  
  
***************
*** 174,186 ****
  void
  get_include_path(const char *my_exec_path, char *ret_path)
  {
- 	char path[MAXPGPATH];
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, INCLUDEDIR)))
! 		MAKE_RELATIVE;
  	else
  		StrNCpy(ret_path, INCLUDEDIR, MAXPGPATH);
  }
  
  
--- 166,178 ----
  void
  get_include_path(const char *my_exec_path, char *ret_path)
  {
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, INCLUDEDIR)))
! 		make_relative(my_exec_path, p, ret_path);
  	else
  		StrNCpy(ret_path, INCLUDEDIR, MAXPGPATH);
+ 	canonicalize_path(ret_path);
  }
  
  
***************
*** 191,203 ****
  void
  get_pkginclude_path(const char *my_exec_path, char *ret_path)
  {
- 	char path[MAXPGPATH];
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, PKGINCLUDEDIR)))
! 		MAKE_RELATIVE;
  	else
  		StrNCpy(ret_path, PKGINCLUDEDIR, MAXPGPATH);
  }
  
  
--- 183,195 ----
  void
  get_pkginclude_path(const char *my_exec_path, char *ret_path)
  {
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, PKGINCLUDEDIR)))
! 		make_relative(my_exec_path, p, ret_path);
  	else
  		StrNCpy(ret_path, PKGINCLUDEDIR, MAXPGPATH);
+ 	canonicalize_path(ret_path);
  }
  
  
***************
*** 210,222 ****
  void
  get_pkglib_path(const char *my_exec_path, char *ret_path)
  {
- 	char path[MAXPGPATH];
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, PKGLIBDIR)))
! 		MAKE_RELATIVE;
  	else
  		StrNCpy(ret_path, PKGLIBDIR, MAXPGPATH);
  }
  
  
--- 202,214 ----
  void
  get_pkglib_path(const char *my_exec_path, char *ret_path)
  {
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, PKGLIBDIR)))
! 		make_relative(my_exec_path, p, ret_path);
  	else
  		StrNCpy(ret_path, PKGLIBDIR, MAXPGPATH);
+ 	canonicalize_path(ret_path);
  }
  
  
***************
*** 229,241 ****
  void
  get_locale_path(const char *my_exec_path, char *ret_path)
  {
- 	char path[MAXPGPATH];
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, LOCALEDIR)))
! 		MAKE_RELATIVE;
  	else
  		StrNCpy(ret_path, LOCALEDIR, MAXPGPATH);
  }
  
  
--- 221,233 ----
  void
  get_locale_path(const char *my_exec_path, char *ret_path)
  {
  	const char *p;
  	
  	if ((p = relative_path(PGBINDIR, LOCALEDIR)))
! 		make_relative(my_exec_path, p, ret_path);
  	else
  		StrNCpy(ret_path, LOCALEDIR, MAXPGPATH);
+ 	canonicalize_path(ret_path);
  }
  
  
***************
*** 270,275 ****
--- 262,268 ----
  	{
  		/* set for libpq to use */
  		snprintf(env_path, sizeof(env_path), "PGLOCALEDIR=%s", path);
+ 		canonicalize_path(env_path);
  		putenv(strdup(env_path));
  	}
  #endif
***************
*** 280,290 ****
--- 273,298 ----
  	
  		/* set for libpq to use */
  		snprintf(env_path, sizeof(env_path), "PGSYSCONFDIR=%s", path);
+ 		canonicalize_path(env_path);
  		putenv(strdup(env_path));
  	}
  }
  
  
+ /*
+  *	make_relative - adjust path to be relative to bin/
+  */
+ static void
+ make_relative(const char *my_exec_path, const char *p, char *ret_path)
+ {
+ 	char path[MAXPGPATH];
+ 
+ 	StrNCpy(path, my_exec_path, MAXPGPATH);
+ 	trim_directory(path);
+ 	trim_directory(path);
+ 	snprintf(ret_path, MAXPGPATH, "%s/%s", path, p);
+ }
+ 
  
  /*
   *	relative_path
***************
*** 391,397 ****
  	char *p = path + strlen(path);
  
  #ifdef WIN32
!     /* Skip over network and drive specifiers for win32 */
      if (strlen(path) >= 2)
      {
          if (IS_DIR_SEP(path[0]) && IS_DIR_SEP(path[1]))
--- 399,408 ----
  	char *p = path + strlen(path);
  
  #ifdef WIN32
! 	/*
! 	 *	Skip over network and drive specifiers for win32.
! 	 *	Set 'path' to point to the last character to keep.
! 	 */
      if (strlen(path) >= 2)
      {
          if (IS_DIR_SEP(path[0]) && IS_DIR_SEP(path[1]))
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.