# HG changeset patch # User Adrian Aichner # Date 1259279501 -3600 # Node ID 6e6f7b79c1fcef251427bb28ec82021fb1965688 # Parent 217abcf015c44f8bdc53700122b3f52a684043f7 xemacs: fix issue 634 -------------------- ChangeLog entries follow: -------------------- src/ChangeLog addition: 2009-11-27 Adrian Aichner * nt.c (mswindows_getdcwd): Check first whether drive is valid with _getdrives() to avoid crash in _wgetdcwd(...) when linking against msvcrt8. This fix was taken from the Mozilla project which experienced the same problem. diff -r 217abcf015c4 -r 6e6f7b79c1fc src/ChangeLog --- a/src/ChangeLog Thu Nov 19 18:21:06 2009 -0500 +++ b/src/ChangeLog Fri Nov 27 00:51:41 2009 +0100 @@ -1,3 +1,10 @@ +2009-11-27 Adrian Aichner + + * nt.c (mswindows_getdcwd): Check first whether drive is valid + with _getdrives() to avoid crash in _wgetdcwd(...) when linking + against msvcrt8. This fix was taken from the Mozilla project + which experienced the same problem. + 2009-11-19 Vin Shelton * sysdep.c (sys_subshell): Restore sys_subshell(); it's necessary diff -r 217abcf015c4 -r 6e6f7b79c1fc src/nt.c --- a/src/nt.c Thu Nov 19 18:21:06 2009 -0500 +++ b/src/nt.c Fri Nov 27 00:51:41 2009 +0100 @@ -1815,7 +1815,27 @@ { Extbyte *cwdext; Ibyte *cwd; - + /* Following comment and two-liner fix comes from + https://bugzilla.mozilla.org/show_bug.cgi?id=419326 which + apparently fell prey to this feature of msvcrt8 as well. */ + /* We need to worry about IPH, for details read bug 419326. + * _getdrives - http://msdn2.microsoft.com/en-us/library/xdhk0xd2.aspx + * uses a bitmask, bit 0 is 'a:' + * _chdrive - http://msdn2.microsoft.com/en-us/library/0d1409hb.aspx + * _getdcwd - http://msdn2.microsoft.com/en-us/library/7t2zk3s4.aspx + * take an int, 1 is 'a:'. + * + * Because of this, we need to do some math. Subtract 1 to convert from + * _chdrive/_getdcwd format to _getdrives drive numbering. + * Shift left x bits to convert from integer indexing to bitfield indexing. + * And of course, we need to find out if the drive is in the bitmask. + * + * If we're really unlucky, we can still lose, but only if the user + * manages to eject the drive between our call to _getdrives() and + * our *calls* to _wgetdcwd. + */ + if (!((1 << (drivelet - 1)) & _getdrives())) + return NULL; if (XEUNICODE_P) cwdext = (Extbyte *) _wgetdcwd (drivelet, NULL, 0); else