summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authornormal <normal@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2014-09-11 19:25:32 +0000
committernormal <normal@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>2014-09-11 19:25:32 +0000
commitf0c968a778ee35f483a05c6d206eb815b1da177b (patch)
treec3e3672ef1ef7d24d825e926a1912597abda8d34
parent1d0de2a513cf84a4b74d1cada2b05c2dce49042f (diff)
iseq_inline_storage_entry: 24=>16 bytes on 64-bit
We may tag the running_thread pointer to avoid making the "once" struct bigger than "struct iseq_inline_cache_entry". This only saves a small amount with "valgrind ruby -e exit" before: total heap usage: 48,122 allocs, 19,248 frees, 8,110,149 bytes allocated after: total heap usage: 48,122 allocs, 19,253 frees, 8,099,197 bytes allocated * insns.def (once): define and use fake RUNNING_THREAD_ONCE_DONE pointer to indicate is->once.running_thread is done. * vm_core.h (iseq_inline_storage_entry): remove done field, allowing the union to be reduced from 24=>16 bytes on 64-bit git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@47542 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
-rw-r--r--ChangeLog9
-rw-r--r--insns.def37
-rw-r--r--vm_core.h1
3 files changed, 27 insertions, 20 deletions
diff --git a/ChangeLog b/ChangeLog
index 4b58a4ef34..11bc8f9833 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,12 @@
+Fri Sep 12 04:24:03 2014 Eric Wong <e@80x24.org>
+
+ * insns.def (once): define and use fake RUNNING_THREAD_ONCE_DONE
+ pointer to indicate is->once.running_thread is done.
+
+ * vm_core.h (iseq_inline_storage_entry): remove done field,
+ allowing the union to be reduced from 24=>16 bytes on 64-bit
+ [Feature #10187]
+
Thu Sep 11 20:10:00 2014 Koichi Sasada <ko1@atdot.net>
* vm.c (rb_thread_mark): use rb_gc_mark_values() to mark VM stack.
diff --git a/insns.def b/insns.def
index 679927b4e9..bfa11a9b8d 100644
--- a/insns.def
+++ b/insns.def
@@ -1239,28 +1239,27 @@ once
{
union iseq_inline_storage_entry *is = (union iseq_inline_storage_entry *)ic;
+#define RUNNING_THREAD_ONCE_DONE ((rb_thread_t *)(0x1))
retry:
- if (is->once.done == Qfalse) {
- if (is->once.running_thread == NULL) {
- is->once.running_thread = th;
- val = is->once.value = rb_ensure(vm_once_exec, (VALUE)iseq, vm_once_clear, (VALUE)is);
- /* is->once.running_thread is cleared by vm_once_clear() */
- is->once.done = Qtrue;
- rb_iseq_add_mark_object(GET_ISEQ(), val);
- }
- else if (is->once.running_thread == th) {
- /* recursive once */
- val = vm_once_exec((VALUE)iseq);
- }
- else {
- /* waiting for finish */
- RUBY_VM_CHECK_INTS(th);
- rb_thread_schedule();
- goto retry;
- }
+ if (is->once.running_thread == RUNNING_THREAD_ONCE_DONE) {
+ val = is->once.value;
+ }
+ else if (is->once.running_thread == NULL) {
+ is->once.running_thread = th;
+ val = is->once.value = rb_ensure(vm_once_exec, (VALUE)iseq, vm_once_clear, (VALUE)is);
+ /* is->once.running_thread is cleared by vm_once_clear() */
+ is->once.running_thread = RUNNING_THREAD_ONCE_DONE; /* success */
+ rb_iseq_add_mark_object(GET_ISEQ(), val);
+ }
+ else if (is->once.running_thread == th) {
+ /* recursive once */
+ val = vm_once_exec((VALUE)iseq);
}
else {
- val = is->once.value;
+ /* waiting for finish */
+ RUBY_VM_CHECK_INTS(th);
+ rb_thread_schedule();
+ goto retry;
}
}
diff --git a/vm_core.h b/vm_core.h
index 78396d12fb..1c3d0cc548 100644
--- a/vm_core.h
+++ b/vm_core.h
@@ -127,7 +127,6 @@ union iseq_inline_storage_entry {
struct {
struct rb_thread_struct *running_thread;
VALUE value;
- VALUE done;
} once;
struct iseq_inline_cache_entry cache;
};