diff --git a/lib/libspl/include/os/windows/unistd.h b/lib/libspl/include/os/windows/unistd.h index 868e2e071ac9..4e96d0b5c3ad 100644 --- a/lib/libspl/include/os/windows/unistd.h +++ b/lib/libspl/include/os/windows/unistd.h @@ -63,6 +63,8 @@ extern size_t strlcpy(register char *s, register const char *t, extern size_t strlcat(register char *s, register const char *t, register size_t n); +extern ssize_t getline_impl(char **linep, size_t *linecapp, FILE *stream, + boolean_t internal); extern ssize_t getline(char **linep, size_t *linecapp, FILE *stream); // int pread_win(HANDLE h, void *buf, size_t nbyte, off_t offset); diff --git a/lib/libspl/include/os/windows/wfunopen.h b/lib/libspl/include/os/windows/wfunopen.h index c58cf6b62ea7..f26d59f16848 100644 --- a/lib/libspl/include/os/windows/wfunopen.h +++ b/lib/libspl/include/os/windows/wfunopen.h @@ -122,10 +122,12 @@ static inline ssize_t wosix_getline(char **linep, size_t *linecap, FILE *f) fakeFILE *fFILE = (fakeFILE *)f; int result; - if (fFILE->realFILE) + if (f == stdin) + result = getline_impl(linep, linecap, f, FALSE); + else if (fFILE->realFILE) result = getline(linep, linecap, fFILE->realFILE); else - result = fFILE->readfn(fFILE->cookie, *linep, *linecap); + result = getline_impl(linep, linecap, (FILE *)fFILE, TRUE); return (result); } diff --git a/lib/libspl/os/windows/posix.c b/lib/libspl/os/windows/posix.c index 63f42a197eac..98ba4bd54722 100644 --- a/lib/libspl/os/windows/posix.c +++ b/lib/libspl/os/windows/posix.c @@ -40,6 +40,7 @@ #include #include #include +#include /* Magic instruction to compiler to add library */ #pragma comment(lib, "ws2_32.lib") @@ -796,10 +797,10 @@ strlcpy(register char *s, register const char *t, register size_t n) break; } } while ((*s++ = *t++)); - if (!n) - while (*t++) - ; - return (t - o - 1); + if (!n) + while (*t++) + ; + return (t - o - 1); } extern size_t @@ -889,17 +890,21 @@ console_echo(boolean_t willecho) // Not really getline, just used for password input in libzfs_crypto.c #define MAX_GETLINE 128 ssize_t -getline(char **linep, size_t *linecapp, - FILE *stream) +getline_impl(char **linep, size_t *linecapp, + FILE *stream, boolean_t internal) { static char getpassbuf[MAX_GETLINE + 1]; size_t i = 0; + fakeFILE *fFILE = (fakeFILE *)stream; console_echo(FALSE); int c; for (;;) { - c = getc(stream); + if (internal) + fFILE->readfn(fFILE->cookie, (char *)&c, 1); + else + c = getc(stream); if ((c == '\r') || (c == '\n')) { getpassbuf[i] = '\0'; break; @@ -920,6 +925,14 @@ getline(char **linep, size_t *linecapp, return (i); } +#undef getline +ssize_t +getline(char **linep, size_t *linecapp, FILE *stream) +{ + return (getline_impl(linep, linecapp, + stream, FALSE)); +} + /* Windows POSIX wrappers */