diff options
author | Gerald Combs <gerald@wireshark.org> | 2017-02-16 15:31:56 -0800 |
---|---|---|
committer | Gerald Combs <gerald@wireshark.org> | 2017-02-17 17:19:06 +0000 |
commit | 560a6c3823cf560b883e29db0a403517def86639 (patch) | |
tree | 9bdc7d4bc914cb4698af10b329bbe31d4a2e0a82 /rawshark.c | |
parent | 48eff6a36bac1526756bbb42a8c9841641792938 (diff) |
Rawshark: Try to avoid a VC runtime crash.
The MSDN documentation for _read says
"If fd is invalid, the file is not open for reading, or the file is
locked, the invalid parameter handler is invoked, as described in
Parameter Validation."
This means that on Windows, if our parent has closed stdin when we call
_read we'll crash. Add a check to bail out early if that's happened.
Fix a sign cast while we're here.
Change-Id: I8afb75f6e56c6a6c2b62103ba7e2fb635dc85702
Reviewed-on: https://code.wireshark.org/review/20153
Reviewed-by: Gerald Combs <gerald@wireshark.org>
Diffstat (limited to 'rawshark.c')
-rw-r--r-- | rawshark.c | 27 |
1 files changed, 22 insertions, 5 deletions
diff --git a/rawshark.c b/rawshark.c index bc6e783630..e319acd01c 100644 --- a/rawshark.c +++ b/rawshark.c @@ -875,10 +875,10 @@ main(int argc, char *argv[]) /* Do we need to PCAP header and magic? */ if (skip_pcap_header) { - size_t bytes_left = sizeof(struct pcap_hdr) + sizeof(guint32); + unsigned int bytes_left = (unsigned int) sizeof(struct pcap_hdr) + sizeof(guint32); gchar buf[sizeof(struct pcap_hdr) + sizeof(guint32)]; while (bytes_left != 0) { - ssize_t bytes = ws_read(fd, buf, (int)bytes_left); + ssize_t bytes = ws_read(fd, buf, bytes_left); if (bytes <= 0) { cmdarg_err("Not enough bytes for pcap header."); ret = FORMAT_ERROR; @@ -926,7 +926,7 @@ raw_pipe_read(struct wtap_pkthdr *phdr, guchar * pd, int *err, gchar **err_info, struct pcap_pkthdr mem_hdr; struct pcaprec_hdr disk_hdr; ssize_t bytes_read = 0; - size_t bytes_needed = sizeof(disk_hdr); + unsigned int bytes_needed = (unsigned int) sizeof(disk_hdr); guchar *ptr = (guchar*) &disk_hdr; *err = 0; @@ -936,9 +936,26 @@ raw_pipe_read(struct wtap_pkthdr *phdr, guchar * pd, int *err, gchar **err_info, ptr = (guchar*) &mem_hdr; } + /* + * Newer versions of the VC runtime do parameter validation. If stdin + * has been closed, calls to _read, _get_osfhandle, et al will trigger + * the invalid parameter handler and crash. + * We could alternatively use ReadFile or set an invalid parameter + * handler. + * We could also tell callers not to close stdin prematurely. + */ +#ifdef _WIN32 + DWORD ghi_flags; + if (fd == 0 && GetHandleInformation(GetStdHandle(STD_INPUT_HANDLE), &ghi_flags) == 0) { + *err = 0; + *err_info = NULL; + return FALSE; + } +#endif + /* Copied from capture_loop.c */ while (bytes_needed > 0) { - bytes_read = ws_read(fd, ptr, (int)bytes_needed); + bytes_read = ws_read(fd, ptr, bytes_needed); if (bytes_read == 0) { *err = 0; *err_info = NULL; @@ -984,7 +1001,7 @@ raw_pipe_read(struct wtap_pkthdr *phdr, guchar * pd, int *err, gchar **err_info, ptr = pd; while (bytes_needed > 0) { - bytes_read = ws_read(fd, ptr, (int)bytes_needed); + bytes_read = ws_read(fd, ptr, bytes_needed); if (bytes_read == 0) { *err = WTAP_ERR_SHORT_READ; *err_info = NULL; |