[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: Carbon Emacs won't start when installed in certain paths
From: |
YAMAMOTO Mitsuharu |
Subject: |
Re: Carbon Emacs won't start when installed in certain paths |
Date: |
Thu, 10 May 2007 18:20:21 +0900 |
User-agent: |
Wanderlust/2.14.0 (Africa) SEMI/1.14.6 (Maruoka) FLIM/1.14.8 (Shijō) APEL/10.6 Emacs/22.0.99 (sparc-sun-solaris2.8) MULE/5.0 (SAKAKI) |
>>>>> On Wed, 09 May 2007 17:36:37 +0900, YAMAMOTO Mitsuharu <address@hidden>
>>>>> said:
> Though the non-ASCII unibyte `default-directory' case seems to be
> sufficient for the originally reported problem, we should also handle
> the following cases in order to make Fexpand_file_name consistent and
> exhaustive with respect to non-ASCII unibyte file names:
> 1. Case that "~" or "~user" is expanded to a non-ASCII file name:
> This case is similar to the non-ASCII unibyte `default-directory'
> case.
> 2. Case that the argument `name' is in non-ASCII unibyte and
> `default-directory' is in multibyte:
> This case may return a wrong result either with or without my
> previous patch.
I tried handling these cases (with DECODE_FILE instead of
string_to_multibyte). What's pointed to by `newdir' previously is now
stored in a Lisp string `new_directory' until adjustments of
multibyteness has been completed.
YAMAMOTO Mitsuharu
address@hidden
Index: src/fileio.c
===================================================================
RCS file: /cvsroot/emacs/emacs/src/fileio.c,v
retrieving revision 1.580
diff -c -p -r1.580 fileio.c
*** src/fileio.c 22 Mar 2007 12:15:04 -0000 1.580
--- src/fileio.c 10 May 2007 09:09:53 -0000
*************** See also the function `substitute-in-fil
*** 1060,1067 ****
int collapse_newdir = 1;
int is_escaped = 0;
#endif /* DOS_NT */
! int length;
! Lisp_Object handler, result;
int multibyte;
CHECK_STRING (name);
--- 1060,1066 ----
int collapse_newdir = 1;
int is_escaped = 0;
#endif /* DOS_NT */
! Lisp_Object handler, new_directory, result;
int multibyte;
CHECK_STRING (name);
*************** See also the function `substitute-in-fil
*** 1345,1351 ****
default_directory if nm is not absolute, and finally collapse /./
and /foo/../ sequences.
! We set newdir to be the appropriate prefix if one is needed:
- the relevant user directory if nm starts with ~ or ~user
- the specified drive's working dir (DOS/NT only) if nm does not
start with /
--- 1344,1350 ----
default_directory if nm is not absolute, and finally collapse /./
and /foo/../ sequences.
! We set new_directory to be the appropriate prefix if one is needed:
- the relevant user directory if nm starts with ~ or ~user
- the specified drive's working dir (DOS/NT only) if nm does not
start with /
*************** See also the function `substitute-in-fil
*** 1356,1362 ****
return an absolute name, if the final prefix is not absolute we
append it to the current working directory. */
! newdir = 0;
if (nm[0] == '~') /* prefix ~ */
{
--- 1355,1361 ----
return an absolute name, if the final prefix is not absolute we
append it to the current working directory. */
! new_directory = Qnil;
if (nm[0] == '~') /* prefix ~ */
{
*************** See also the function `substitute-in-fil
*** 1366,1373 ****
#endif /* VMS */
|| nm[1] == 0) /* ~ by itself */
{
! if (!(newdir = (unsigned char *) egetenv ("HOME")))
! newdir = (unsigned char *) "";
nm++;
#ifdef DOS_NT
collapse_newdir = 0;
--- 1365,1376 ----
#endif /* VMS */
|| nm[1] == 0) /* ~ by itself */
{
! unsigned char *homedir = (unsigned char *) egetenv ("HOME");
!
! if (homedir)
! new_directory = make_unibyte_string (homedir, strlen (homedir));
! else
! new_directory = empty_string;
nm++;
#ifdef DOS_NT
collapse_newdir = 0;
*************** See also the function `substitute-in-fil
*** 1392,1398 ****
UNBLOCK_INPUT;
if (pw)
{
! newdir = (unsigned char *) pw -> pw_dir;
#ifdef VMS
nm = p + 1; /* skip the terminator */
#else
--- 1395,1403 ----
UNBLOCK_INPUT;
if (pw)
{
! unsigned char *homedir = (unsigned char *) pw -> pw_dir;
!
! new_directory = make_unibyte_string (homedir, strlen (homedir));
#ifdef VMS
nm = p + 1; /* skip the terminator */
#else
*************** See also the function `substitute-in-fil
*** 1411,1433 ****
#ifdef DOS_NT
/* On DOS and Windows, nm is absolute if a drive name was specified;
use the drive's current directory as the prefix if needed. */
! if (!newdir && drive)
{
/* Get default directory if needed to make nm absolute. */
if (!IS_DIRECTORY_SEP (nm[0]))
{
! newdir = alloca (MAXPATHLEN + 1);
! if (!getdefdir (toupper (drive) - 'A' + 1, newdir))
! newdir = NULL;
}
! if (!newdir)
{
/* Either nm starts with /, or drive isn't mounted. */
! newdir = alloca (4);
! newdir[0] = DRIVE_LETTER (drive);
! newdir[1] = ':';
! newdir[2] = '/';
! newdir[3] = 0;
}
}
#endif /* DOS_NT */
--- 1416,1438 ----
#ifdef DOS_NT
/* On DOS and Windows, nm is absolute if a drive name was specified;
use the drive's current directory as the prefix if needed. */
! if (NILP (new_directory) && drive)
{
/* Get default directory if needed to make nm absolute. */
if (!IS_DIRECTORY_SEP (nm[0]))
{
! unsigned char defdir[MAXPATHLEN + 1];
!
! if (getdefdir (toupper (drive) - 'A' + 1, defdir))
! new_directory = make_unibyte_string (defdir, strlen (defdir));
}
! if (NILP (new_directory))
{
/* Either nm starts with /, or drive isn't mounted. */
! new_directory = make_uninit_string (3);
! SSET (new_directory, 0, DRIVE_LETTER (drive));
! SSET (new_directory, 1, ':');
! SSET (new_directory, 2, '/');
}
}
#endif /* DOS_NT */
*************** See also the function `substitute-in-fil
*** 1446,1465 ****
#ifdef VMS
&& !index (nm, ':')
#endif
! && !newdir)
{
! newdir = SDATA (default_directory);
! multibyte |= STRING_MULTIBYTE (default_directory);
#ifdef DOS_NT
/* Note if special escape prefix is present, but remove for now. */
! if (newdir[0] == '/' && newdir[1] == ':')
{
is_escaped = 1;
! newdir += 2;
}
#endif
}
#ifdef DOS_NT
if (newdir)
{
--- 1451,1506 ----
#ifdef VMS
&& !index (nm, ':')
#endif
! && NILP (new_directory))
{
! new_directory = default_directory;
#ifdef DOS_NT
/* Note if special escape prefix is present, but remove for now. */
! if (SREF (new_directory, 0) == '/' && SREF (new_directory, 1) == ':')
{
is_escaped = 1;
! new_directory =
! make_specified_string (SDATA (new_directory) + 2, -1,
! SBYTES (new_directory) - 2,
! STRING_MULTIBYTE (new_directory));
}
#endif
}
+ if (NILP (new_directory))
+ newdir = 0;
+ else
+ {
+ /* If the multibyteness of `nm' (which is stored in `multibyte')
+ and that of 'new_directory' do not match, apply DECODE_FILE
+ to the unibyte side. Because DECODE_FILE may invoke GC and
+ string relocation, any pointers (`nm' in this case) that may
+ point to some string data must be adjusted after the
+ potential GC. */
+ if (multibyte != STRING_MULTIBYTE (new_directory))
+ {
+ struct gcpro gcpro1, gcpro2;
+
+ if (nm != SDATA (name))
+ name = make_specified_string (nm, -1, strlen (nm), multibyte);
+ if (multibyte)
+ {
+ GCPRO2 (name, default_directory);
+ new_directory = DECODE_FILE (new_directory);
+ UNGCPRO;
+ }
+ else
+ {
+ GCPRO2 (new_directory, default_directory);
+ name = DECODE_FILE (name);
+ UNGCPRO;
+ }
+ nm = SDATA (name);
+ multibyte = 1;
+ }
+ newdir = SDATA (new_directory);
+ }
+
#ifdef DOS_NT
if (newdir)
{
*************** See also the function `substitute-in-fil
*** 1532,1537 ****
--- 1573,1580 ----
if (newdir)
{
+ int length;
+
/* Get rid of any slash at the end of newdir, unless newdir is
just / or // (an incomplete UNC name). */
length = strlen (newdir);