Author: Armin Rigo <[email protected]>
Branch: 
Changeset: r75:d8c52869d637
Date: 2013-06-05 20:48 +0200
http://bitbucket.org/pypy/stmgc/changeset/d8c52869d637/

Log:    Introduce "handles" as written down in doc-objects.txt

diff --git a/c3/et.c b/c3/et.c
--- a/c3/et.c
+++ b/c3/et.c
@@ -296,6 +296,7 @@
 
 static gcptr LocalizePublic(struct tx_descriptor *d, gcptr R)
 {
+  assert(R->h_tid & GCFLAG_PUBLIC);
   if (R->h_tid & GCFLAG_PUBLIC_TO_PRIVATE)
     {
       wlog_t *entry;
@@ -726,13 +727,22 @@
       assert(!is_young(R));
       assert(R->h_revision != localrev);
 
+      /* XXX compactify and don't leak! */
+      revision_t *handle_block = stm_malloc(3 * WORD);
+      handle_block = (revision_t *)
+        ((((intptr_t)handle_block) + HANDLE_BLOCK_SIZE-1)
+         & ~(HANDLE_BLOCK_SIZE-1));
+      handle_block[0] = d->my_lock;
+      handle_block[1] = v;
+
+      revision_t w = ((revision_t)(handle_block + 1)) + 2;
+
 #ifdef DUMP_EXTRA
-      fprintf(stderr, "%p->h_revision = %p | 2 (UpdateChainHeads2)\n",
-              R, (gcptr)v);
+      fprintf(stderr, "%p->h_revision = %p (UpdateChainHeads2)\n",
+              R, (gcptr)w);
       /*mark*/
 #endif
-      assert(!(v & 3));
-      ACCESS_ONCE(R->h_revision) = v | 2;
+      ACCESS_ONCE(R->h_revision) = w;
 
       if (R->h_tid & GCFLAG_PREBUILT_ORIGINAL)
         {
diff --git a/c3/et.h b/c3/et.h
--- a/c3/et.h
+++ b/c3/et.h
@@ -13,6 +13,8 @@
 
 #define LOCKED  ((INTPTR_MAX - 0xffff) | 1)
 
+#define HANDLE_BLOCK_SIZE   (2 * WORD)
+
 /* Description of the flags
  * ------------------------
  *
diff --git a/c3/test/support.py b/c3/test/support.py
--- a/c3/test/support.py
+++ b/c3/test/support.py
@@ -84,6 +84,7 @@
     gcptr pseudoprebuilt(size_t size, int tid);
     revision_t get_private_rev_num(void);
     revision_t get_start_time(void);
+    revision_t get_my_lock(void);
 
     gcptr *addr_of_thread_local(void);
     int in_nursery(gcptr);
@@ -92,6 +93,8 @@
     /* some constants normally private that are useful in the tests */
     #define WORD                     ...
     #define GC_PAGE_SIZE             ...
+    #define LOCKED                   ...
+    #define HANDLE_BLOCK_SIZE        ...
     #define GCFLAG_OLD               ...
     #define GCFLAG_VISITED           ...
     #define GCFLAG_PUBLIC            ...
@@ -118,6 +121,7 @@
     extern void stmgcpage_add_prebuilt_root(gcptr);
     extern void stm_clear_between_tests(void);
     extern revision_t get_private_rev_num(void);
+    extern local_gcpages_t *stm_local_gcpages(void);
 
     int gettid(gcptr obj)
     {
@@ -205,6 +209,11 @@
         return thread_descriptor->start_time;
     }
 
+    revision_t get_my_lock(void)
+    {
+        return thread_descriptor->my_lock;
+    }
+
     gcptr *addr_of_thread_local(void)
     {
         return &stm_thread_local_obj;
@@ -540,3 +549,11 @@
         result.append(p)
         index += 1
     return result
+
+def decode_handle(r):
+    assert (r & 3) == 2
+    p = r & ~(lib.HANDLE_BLOCK_SIZE-1)
+    my_lock = ffi.cast("revision_t *", p)[0]
+    assert my_lock >= lib.LOCKED
+    ptr = ffi.cast("gcptr *", r - 2)[0]
+    return ptr, my_lock
diff --git a/c3/test/test_et.py b/c3/test/test_et.py
--- a/c3/test/test_et.py
+++ b/c3/test/test_et.py
@@ -138,7 +138,7 @@
     lib.stm_begin_inevitable_transaction()
     assert classify(p) == "public"
     assert classify(p2) == "protected"
-    assert p.h_revision == int(ffi.cast("revision_t", p2)) + 2
+    assert decode_handle(p.h_revision) == (p2, lib.get_my_lock())
     assert lib.rawgetlong(p, 0) == 28971289
     assert lib.rawgetlong(p2, 0) == 1289222
 
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to