From a1de921567c0e45efa9cf1a8c9a947582a667796 Mon Sep 17 00:00:00 2001 From: Mikko Rasa Date: Sun, 22 Aug 2021 13:17:08 +0300 Subject: [PATCH] Use a persistent OVERLAPPED structure in EventReader --- source/io/windows/eventreader.cpp | 29 +++++++++++++---------------- 1 file changed, 13 insertions(+), 16 deletions(-) diff --git a/source/io/windows/eventreader.cpp b/source/io/windows/eventreader.cpp index 62c9763..8a4c862 100644 --- a/source/io/windows/eventreader.cpp +++ b/source/io/windows/eventreader.cpp @@ -11,12 +11,13 @@ namespace IO { struct EventReader::Private { - OVERLAPPED *overlapped; + OVERLAPPED overlapped; Handle event; unsigned buf_size; char *buffer; unsigned buf_avail; char *buf_next; + bool pending; }; @@ -24,18 +25,19 @@ EventReader::EventReader(Handle &h, unsigned size): handle(h), priv(new Private) { - priv->overlapped = 0; + memset(&priv->overlapped, 0, sizeof(OVERLAPPED)); *priv->event = CreateEvent(0, true, false, 0); + priv->overlapped.hEvent = *priv->event; priv->buf_size = size; priv->buffer = new char[priv->buf_size]; priv->buf_avail = 0; priv->buf_next = priv->buffer; + priv->pending = false; } EventReader::~EventReader() { CloseHandle(*priv->event); - delete priv->overlapped; delete[] priv->buffer; delete priv; } @@ -48,43 +50,38 @@ const Handle &EventReader::get_event() void EventReader::start() { - if(priv->buf_avail || priv->overlapped) + if(priv->buf_avail || priv->pending) return; - priv->overlapped = new OVERLAPPED; - memset(priv->overlapped, 0, sizeof(OVERLAPPED)); - priv->overlapped->hEvent = *priv->event; - DWORD ret; priv->buf_next = priv->buffer; - if(!ReadFile(*handle, priv->buffer, priv->buf_size, &ret, priv->overlapped)) + if(!ReadFile(*handle, priv->buffer, priv->buf_size, &ret, &priv->overlapped)) { unsigned err = GetLastError(); - if(err!=ERROR_IO_PENDING) + if(err==ERROR_IO_PENDING) + priv->pending = true; + else throw system_error("ReadFile"); } else { priv->buf_avail = ret; - delete priv->overlapped; - priv->overlapped = 0; SetEvent(*priv->event); } } void EventReader::wait() { - if(!priv->overlapped) + if(!priv->pending) return; DWORD ret; - if(!GetOverlappedResult(*handle, priv->overlapped, &ret, true)) + if(!GetOverlappedResult(*handle, &priv->overlapped, &ret, true)) throw system_error("GetOverlappedResult"); else { priv->buf_avail = ret; - delete priv->overlapped; - priv->overlapped = 0; + priv->pending = false; } } -- 2.43.0