Remove exponential backoff from chdir()

This issue probably only impacted the earliest releases of Windows 7 and
we only support Windows 10+ these days, so it's not worth adding 2000 ms
of startup latency to vim when ~/.vim doesn't exist.
This commit is contained in:
Justine Tunney 2024-09-10 21:21:52 -07:00
parent 4d05060aac
commit deb5e07b5a
No known key found for this signature in database
GPG key ID: BE714B4575D6E328
2 changed files with 23 additions and 46 deletions

View file

@ -16,70 +16,48 @@
TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
PERFORMANCE OF THIS SOFTWARE.
*/
#include "libc/calls/syscall-nt.internal.h"
#include "libc/calls/syscall_support-nt.internal.h"
#include "libc/errno.h"
#include "libc/macros.h"
#include "libc/nt/errors.h"
#include "libc/limits.h"
#include "libc/nt/files.h"
#include "libc/nt/process.h"
#include "libc/nt/runtime.h"
#include "libc/nt/synchronization.h"
#include "libc/sysv/errfuns.h"
textwindows int sys_chdir_nt_impl(char16_t path[hasatleast PATH_MAX],
uint32_t len) {
uint32_t n;
int e, ms, err;
char16_t var[4];
if (len && path[len - 1] != u'\\') {
if (len + 2 > PATH_MAX)
return enametoolong();
path[len + 0] = u'\\';
path[len + 1] = u'\0';
}
/*
* chdir() seems flaky on windows 7
* in a similar way to rmdir() sigh
*/
for (err = errno, ms = 1;; ms *= 2) {
if (SetCurrentDirectory(path)) {
/*
* Now we need to set a magic environment variable.
*/
if ((n = GetCurrentDirectory(PATH_MAX, path))) {
if (n < PATH_MAX) {
if (!((path[0] == '/' && path[1] == '/') ||
(path[0] == '\\' && path[1] == '\\'))) {
var[0] = '=';
var[1] = path[0];
var[2] = ':';
var[3] = 0;
if (!SetEnvironmentVariable(var, path)) {
return __winerr();
}
}
return 0;
} else {
return enametoolong();
if (SetCurrentDirectory(path)) {
/*
* Now we need to set a magic environment variable.
*/
if ((n = GetCurrentDirectory(PATH_MAX, path))) {
if (n < PATH_MAX) {
if (!((path[0] == '/' && path[1] == '/') ||
(path[0] == '\\' && path[1] == '\\'))) {
var[0] = '=';
var[1] = path[0];
var[2] = ':';
var[3] = 0;
if (!SetEnvironmentVariable(var, path))
return __winerr();
}
return 0;
} else {
return __winerr();
return enametoolong();
}
} else {
e = GetLastError();
if (ms <= 512 &&
(e == kNtErrorFileNotFound || e == kNtErrorAccessDenied)) {
Sleep(ms);
errno = err;
continue;
} else {
break;
}
return __winerr();
}
} else {
return __fix_enotdir(__winerr(), path);
}
return __fix_enotdir(-1, path);
}
textwindows int sys_chdir_nt(const char *path) {

View file

@ -57,15 +57,14 @@ static textwindows bool IsDirectorySymlink(const char16_t *path) {
static textwindows int sys_rmdir_nt(const char16_t *path) {
int ms;
for (ms = 1;; ms *= 2) {
if (RemoveDirectory(path)) {
if (RemoveDirectory(path))
return 0;
}
// Files can linger, for absolutely no reason.
// Possibly some Windows Defender bug on Win7.
// Sleep for up to one second w/ expo backoff.
// Alternative is use Microsoft internal APIs.
// Never could have imagined it'd be this bad.
if (GetLastError() == kNtErrorDirNotEmpty && ms <= 2048) {
if (GetLastError() == kNtErrorDirNotEmpty && ms <= 1024) {
Sleep(ms);
continue;
} else {