summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJames Ross-Gowan <rossymiles@gmail.com>2014-11-18 13:18:22 +1100
committerwm4 <wm4@nowhere>2014-11-18 13:34:00 +0100
commit9e77ba8003240f69ac95f0cad16ea0d424c46c18 (patch)
tree51a751c1054b93865292e4b3408ff74514aad94e
parent67132750a65946a936b0f8fea2099d0a9f7ca889 (diff)
downloadmpv-9e77ba8003240f69ac95f0cad16ea0d424c46c18.tar.bz2
mpv-9e77ba8003240f69ac95f0cad16ea0d424c46c18.tar.xz
stream: signal a Windows event object on cancel
This will be used in the following commit to cancel subprocesses started by Lua.
-rw-r--r--stream/stream.c31
-rw-r--r--stream/stream.h4
2 files changed, 35 insertions, 0 deletions
diff --git a/stream/stream.c b/stream/stream.c
index e51a1666f0..e87e5cab07 100644
--- a/stream/stream.c
+++ b/stream/stream.c
@@ -45,6 +45,10 @@
#include "options/m_option.h"
#include "options/m_config.h"
+#ifdef __MINGW32__
+#include <windows.h>
+#endif
+
// Includes additional padding in case sizes get rounded up by sector size.
#define TOTAL_BUFFER_SIZE (STREAM_MAX_BUFFER_SIZE + STREAM_MAX_SECTOR_SIZE)
@@ -986,14 +990,22 @@ struct bstr stream_read_complete(struct stream *s, void *talloc_ctx,
struct mp_cancel {
atomic_bool triggered;
+#ifdef __MINGW32__
+ HANDLE event;
+#else
int wakeup_pipe[2];
+#endif
};
static void cancel_destroy(void *p)
{
struct mp_cancel *c = p;
+#ifdef __MINGW32__
+ CloseHandle(c->event);
+#else
close(c->wakeup_pipe[0]);
close(c->wakeup_pipe[1]);
+#endif
}
struct mp_cancel *mp_cancel_new(void *talloc_ctx)
@@ -1001,7 +1013,11 @@ struct mp_cancel *mp_cancel_new(void *talloc_ctx)
struct mp_cancel *c = talloc_ptrtype(talloc_ctx, c);
talloc_set_destructor(c, cancel_destroy);
*c = (struct mp_cancel){.triggered = ATOMIC_VAR_INIT(false)};
+#ifdef __MINGW32__
+ c->event = CreateEventW(NULL, TRUE, FALSE, NULL);
+#else
mp_make_wakeup_pipe(c->wakeup_pipe);
+#endif
return c;
}
@@ -1009,13 +1025,20 @@ struct mp_cancel *mp_cancel_new(void *talloc_ctx)
void mp_cancel_trigger(struct mp_cancel *c)
{
atomic_store(&c->triggered, true);
+#ifdef __MINGW32__
+ SetEvent(c->event);
+#else
write(c->wakeup_pipe[1], &(char){0}, 1);
+#endif
}
// Restore original state. (Allows reusing a mp_cancel.)
void mp_cancel_reset(struct mp_cancel *c)
{
atomic_store(&c->triggered, false);
+#ifdef __MINGW32__
+ ResetEvent(c->event);
+#else
// Flush it fully.
while (1) {
int r = read(c->wakeup_pipe[0], &(char[256]){0}, 256);
@@ -1024,6 +1047,7 @@ void mp_cancel_reset(struct mp_cancel *c)
if (r <= 0)
break;
}
+#endif
}
// Return whether the caller should abort.
@@ -1033,12 +1057,19 @@ bool mp_cancel_test(struct mp_cancel *c)
return c ? atomic_load(&c->triggered) : false;
}
+#ifdef __MINGW32__
+void *mp_cancel_get_event(struct mp_cancel *c)
+{
+ return c->event;
+}
+#else
// The FD becomes readable if mp_cancel_test() would return true.
// Don't actually read from it, just use it for poll().
int mp_cancel_get_fd(struct mp_cancel *c)
{
return c->wakeup_pipe[0];
}
+#endif
void stream_print_proto_list(struct mp_log *log)
{
diff --git a/stream/stream.h b/stream/stream.h
index 5cf3487462..e017eef1fd 100644
--- a/stream/stream.h
+++ b/stream/stream.h
@@ -264,7 +264,11 @@ struct mp_cancel *mp_cancel_new(void *talloc_ctx);
void mp_cancel_trigger(struct mp_cancel *c);
bool mp_cancel_test(struct mp_cancel *c);
void mp_cancel_reset(struct mp_cancel *c);
+#ifdef __MINGW32__
+void *mp_cancel_get_event(struct mp_cancel *c);
+#else
int mp_cancel_get_fd(struct mp_cancel *c);
+#endif
// stream_file.c
char *mp_file_url_to_filename(void *talloc_ctx, bstr url);