wine-staging/patches/vcomp-Functions/0001-vcomp-Split-team-data-and-task-data.patch

193 lines
6.7 KiB
Diff

From 52ef17d8550f05778f548cc01fce2a0eaa3b223b Mon Sep 17 00:00:00 2001
From: Sebastian Lackner <sebastian@fds-team.de>
Date: Sat, 18 Jul 2015 17:22:01 +0200
Subject: vcomp: Split team data and task data.
---
dlls/vcomp/main.c | 47 ++++++++++++++++++++++++++++++++++-------------
dlls/vcomp/tests/vcomp.c | 20 ++++++++++++++++++++
2 files changed, 54 insertions(+), 13 deletions(-)
diff --git a/dlls/vcomp/main.c b/dlls/vcomp/main.c
index 0f8a272..8866b15 100644
--- a/dlls/vcomp/main.c
+++ b/dlls/vcomp/main.c
@@ -52,6 +52,7 @@ static RTL_CRITICAL_SECTION vcomp_section = { &critsect_debug, -1, 0, 0, 0, 0 };
struct vcomp_thread_data
{
struct vcomp_team_data *team;
+ struct vcomp_task_data *task;
int thread_num;
int fork_threads;
@@ -77,7 +78,10 @@ struct vcomp_team_data
/* barrier */
unsigned int barrier;
int barrier_count;
+};
+struct vcomp_task_data
+{
/* section */
unsigned int section;
int num_sections;
@@ -177,20 +181,32 @@ static inline void vcomp_set_thread_data(struct vcomp_thread_data *thread_data)
TlsSetValue(vcomp_context_tls, thread_data);
}
+struct vcomp_thread_and_task_data
+{
+ struct vcomp_thread_data thread;
+ struct vcomp_task_data task;
+};
+
static struct vcomp_thread_data *vcomp_init_thread_data(void)
{
struct vcomp_thread_data *thread_data = vcomp_get_thread_data();
+ struct vcomp_task_data *task_data;
if (thread_data) return thread_data;
- if (!(thread_data = HeapAlloc(GetProcessHeap(), 0, sizeof(*thread_data))))
+ if (!(thread_data = HeapAlloc(GetProcessHeap(), 0, sizeof(struct vcomp_thread_and_task_data))))
{
ERR("could not create thread data\n");
ExitProcess(1);
}
+ task_data = &((struct vcomp_thread_and_task_data *)thread_data)->task;
+ task_data->section = 0;
+
thread_data->team = NULL;
+ thread_data->task = task_data;
thread_data->thread_num = 0;
thread_data->fork_threads = 0;
+ thread_data->section = 1;
vcomp_set_thread_data(thread_data);
return thread_data;
@@ -311,35 +327,35 @@ void CDECL _vcomp_single_end(void)
void CDECL _vcomp_sections_init(int n)
{
- struct vcomp_thread_data *thread_data = vcomp_get_thread_data();
- struct vcomp_team_data *team_data = thread_data->team;
+ struct vcomp_thread_data *thread_data = vcomp_init_thread_data();
+ struct vcomp_task_data *task_data = thread_data->task;
TRACE("(%d)\n", n);
EnterCriticalSection(&vcomp_section);
thread_data->section++;
- if ((int)(thread_data->section - team_data->section) > 0)
+ if ((int)(thread_data->section - task_data->section) > 0)
{
- team_data->section = thread_data->section;
- team_data->num_sections = n;
- team_data->section_index = 0;
+ task_data->section = thread_data->section;
+ task_data->num_sections = n;
+ task_data->section_index = 0;
}
LeaveCriticalSection(&vcomp_section);
}
int CDECL _vcomp_sections_next(void)
{
- struct vcomp_thread_data *thread_data = vcomp_get_thread_data();
- struct vcomp_team_data *team_data = thread_data->team;
+ struct vcomp_thread_data *thread_data = vcomp_init_thread_data();
+ struct vcomp_task_data *task_data = thread_data->task;
int i = -1;
TRACE("()\n");
EnterCriticalSection(&vcomp_section);
- if (thread_data->section == team_data->section &&
- team_data->section_index != team_data->num_sections)
+ if (thread_data->section == task_data->section &&
+ task_data->section_index != task_data->num_sections)
{
- i = team_data->section_index++;
+ i = task_data->section_index++;
}
LeaveCriticalSection(&vcomp_section);
return i;
@@ -391,6 +407,7 @@ void WINAPIV _vcomp_fork(BOOL ifval, int nargs, void *wrapper, ...)
struct vcomp_thread_data *prev_thread_data = vcomp_init_thread_data();
struct vcomp_thread_data thread_data;
struct vcomp_team_data team_data;
+ struct vcomp_task_data task_data;
int num_threads;
TRACE("(%d, %d, %p, ...)\n", ifval, nargs, wrapper);
@@ -412,9 +429,11 @@ void WINAPIV _vcomp_fork(BOOL ifval, int nargs, void *wrapper, ...)
__ms_va_start(team_data.valist, wrapper);
team_data.barrier = 0;
team_data.barrier_count = 0;
- team_data.section = 0;
+
+ task_data.section = 0;
thread_data.team = &team_data;
+ thread_data.task = &task_data;
thread_data.thread_num = 0;
thread_data.fork_threads = 0;
thread_data.section = 1;
@@ -431,6 +450,7 @@ void WINAPIV _vcomp_fork(BOOL ifval, int nargs, void *wrapper, ...)
{
struct vcomp_thread_data *data = LIST_ENTRY(ptr, struct vcomp_thread_data, entry);
data->team = &team_data;
+ data->task = &task_data;
data->thread_num = team_data.num_threads++;
data->fork_threads = 0;
data->section = 1;
@@ -450,6 +470,7 @@ void WINAPIV _vcomp_fork(BOOL ifval, int nargs, void *wrapper, ...)
if (!data) break;
data->team = &team_data;
+ data->task = &task_data;
data->thread_num = team_data.num_threads;
data->fork_threads = 0;
data->section = 1;
diff --git a/dlls/vcomp/tests/vcomp.c b/dlls/vcomp/tests/vcomp.c
index c433991..a933a4e 100644
--- a/dlls/vcomp/tests/vcomp.c
+++ b/dlls/vcomp/tests/vcomp.c
@@ -378,6 +378,20 @@ static void test_vcomp_sections_init(void)
int max_threads = pomp_get_max_threads();
int i;
+if (0)
+{
+ /* calling _vcomp_sections_next without prior _vcomp_sections_init
+ * returns uninitialized memory on Windows. */
+ i = p_vcomp_sections_next();
+ ok(i == -1, "expected -1, got %d\n", i);
+}
+
+ a = b = c = 0;
+ section_cb(&a, &b, &c);
+ ok(a == 20, "expected a = 20, got %d\n", a);
+ ok(b == 30, "expected b = 30, got %d\n", b);
+ ok(c == 40, "expected c = 40, got %d\n", c);
+
for (i = 1; i <= 4; i++)
{
pomp_set_num_threads(i);
@@ -387,6 +401,12 @@ static void test_vcomp_sections_init(void)
ok(a == 20, "expected a = 20, got %d\n", a);
ok(b == 30, "expected b = 30, got %d\n", b);
ok(c == 40, "expected c = 40, got %d\n", c);
+
+ a = b = c = 0;
+ p_vcomp_fork(FALSE, 3, section_cb, &a, &b, &c);
+ ok(a == 20, "expected a = 20, got %d\n", a);
+ ok(b == 30, "expected b = 30, got %d\n", b);
+ ok(c == 40, "expected c = 40, got %d\n", c);
}
pomp_set_num_threads(max_threads);
--
2.4.5