Author: Armin Rigo <ar...@tunes.org> Branch: Changeset: r887:e0e14e5a9b5d Date: 2014-02-27 00:42 +0100 http://bitbucket.org/pypy/stmgc/changeset/e0e14e5a9b5d/
Log: Fix the big slowness that duhton's list_transaction sometimes shows. diff --git a/c7/stm/contention.c b/c7/stm/contention.c --- a/c7/stm/contention.c +++ b/c7/stm/contention.c @@ -82,7 +82,9 @@ /* wait, hopefully until the other thread broadcasts "I'm done aborting" (spurious wake-ups are ok). */ + dprintf(("contention: wait C_SAFE_POINT...\n")); cond_wait(C_SAFE_POINT); + dprintf(("contention: done\n")); cond_broadcast(C_RESUME); diff --git a/c7/stm/core.c b/c7/stm/core.c --- a/c7/stm/core.c +++ b/c7/stm/core.c @@ -171,7 +171,7 @@ #endif STM_PSEGMENT->shadowstack_at_start_of_transaction = tl->shadowstack; STM_PSEGMENT->threadlocal_at_start_of_transaction = tl->thread_local_obj; - STM_SEGMENT->nursery_end = NURSERY_END; + assert(STM_SEGMENT->nursery_end == NURSERY_END); dprintf(("start_transaction\n")); @@ -478,12 +478,28 @@ contention.c, we use a broadcast, to make sure that all threads are signalled, including the one that requested an abort, if any. Moreover, we wake up any thread waiting for this one to do a safe - point, if any. + point, if any (in _finish_transaction above). Finally, it's + possible that we reach this place from the middle of a piece of + code like wait_for_other_safe_points() which ends in broadcasting + C_RESUME; we must make sure to broadcast it. */ cond_broadcast(C_RELEASE_THREAD_SEGMENT); + cond_broadcast(C_RESUME); mutex_unlock(); + /* It seems to be a good idea, at least in some examples, to sleep + one microsecond here before retrying. Otherwise, what was + observed is that the transaction very often restarts too quickly + for contention.c to react, and before it can do anything, we have + again recreated in this thread a similar situation to the one + that caused contention. Anyway, usleep'ing in case of abort + doesn't seem like a very bad idea. If there are more threads + than segments, it should also make sure another thread gets the + segment next. + */ + usleep(1); + assert(jmpbuf_ptr != NULL); assert(jmpbuf_ptr != (stm_jmpbuf_t *)-1); /* for tests only */ __builtin_longjmp(*jmpbuf_ptr, 1); diff --git a/c7/stm/sync.c b/c7/stm/sync.c --- a/c7/stm/sync.c +++ b/c7/stm/sync.c @@ -323,6 +323,7 @@ assert(STM_PSEGMENT->safe_point == SP_RUNNING); while (STM_SEGMENT->nursery_end == NSE_SIGNAL) { + dprintf(("collectable_safe_point...\n")); STM_PSEGMENT->safe_point = SP_SAFE_POINT_CAN_COLLECT; STM_SEGMENT->nursery_end = NURSERY_END; @@ -334,4 +335,5 @@ STM_PSEGMENT->safe_point = SP_RUNNING; } + dprintf(("collectable_safe_point done\n")); } diff --git a/duhton/glob.c b/duhton/glob.c --- a/duhton/glob.c +++ b/duhton/glob.c @@ -705,9 +705,11 @@ int ms = DuInt_AsInt(obj); struct timeval t; + fprintf(stderr, "[sleeping %d ms]\n", ms); t.tv_sec = ms / 1000; t.tv_usec = (ms % 1000) * 1000; select(0, (fd_set *)0, (fd_set *)0, (fd_set *)0, &t); + fprintf(stderr, "[slept %d ms]\n", ms); return Du_None; } _______________________________________________ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit