]> granicus.if.org Git - gc/commitdiff
2011-04-23 Ivan Maidanski <ivmai@mail.ru>
authorivmai <ivmai>
Sat, 23 Apr 2011 08:51:53 +0000 (08:51 +0000)
committerIvan Maidanski <ivmai@mail.ru>
Tue, 26 Jul 2011 17:06:58 +0000 (21:06 +0400)
* mark.c (GC_clear_hdr_marks): Don't test USE_MARK_BYTES.
* extra/setjmp_t.c (main): Don't test USE_MARK_BITS.
* include/private/gc_pmark.h (SET_MARK_BIT_EXIT_IF_SET): Ditto.
* include/private/gc_pmark.h (SET_MARK_BIT_EXIT_IF_SET): Remove
"mark_byte" local variable.
* include/private/gc_pmark.h (OR_WORD_EXIT_IF_SET): Add a comment
about that AO_or() is not used by GC unless USE_MARK_BITS
explicitly set.
* include/private/gc_priv.h (OR_WORD): Ditto.
* include/private/gc_pmark.h (INCR_MARKS): Remove trailing ';',
add parentheses.
* include/private/gc_priv.h (ONES): Define before use by
MAKE_COOLER.
* include/private/gc_priv.h (MARK_BITS_SZ): Define where used.
* include/private/gc_priv.h (OR_WORD): Don't define if
USE_MARK_BYTES.
* include/private/gcconfig.h (USE_MARK_BYTES); Remove duplicate
definition; simplify expression.

ChangeLog
extra/setjmp_t.c
include/private/gc_pmark.h
include/private/gc_priv.h
include/private/gcconfig.h
mark.c

index a61a85ff28ce11e9b538cb3de0dcfe0b7f518adc..8fa4db2c416b3dc160d44ffb13492085a06b4f2d 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,24 @@
+2011-04-23  Ivan Maidanski  <ivmai@mail.ru>
+
+       * mark.c (GC_clear_hdr_marks): Don't test USE_MARK_BYTES.
+       * extra/setjmp_t.c (main): Don't test USE_MARK_BITS.
+       * include/private/gc_pmark.h (SET_MARK_BIT_EXIT_IF_SET): Ditto.
+       * include/private/gc_pmark.h (SET_MARK_BIT_EXIT_IF_SET): Remove
+       "mark_byte" local variable.
+       * include/private/gc_pmark.h (OR_WORD_EXIT_IF_SET): Add a comment
+       about that AO_or() is not used by GC unless USE_MARK_BITS
+       explicitly set.
+       * include/private/gc_priv.h (OR_WORD): Ditto.
+       * include/private/gc_pmark.h (INCR_MARKS): Remove trailing ';',
+       add parentheses.
+       * include/private/gc_priv.h (ONES): Define before use by
+       MAKE_COOLER.
+       * include/private/gc_priv.h (MARK_BITS_SZ): Define where used.
+       * include/private/gc_priv.h (OR_WORD): Don't define if
+       USE_MARK_BYTES.
+       * include/private/gcconfig.h (USE_MARK_BYTES); Remove duplicate
+       definition; simplify expression.
+
 2011-04-22  Ivan Maidanski  <ivmai@mail.ru>
 
        * os_dep.c (GC_get_maps): Always close the file.
index 5f4519b29f6802ee38aa1ac09f70a1395728e67e..0952fb03971b7d1314bb0331a6700b2ac928399e 100644 (file)
@@ -112,7 +112,7 @@ int main(void)
     printf("\tUsing one mark ");
 #   if defined(USE_MARK_BYTES)
       printf("byte");
-#   elif defined(USE_MARK_BITS)
+#   else
       printf("bit");
 #   endif
     printf(" per ");
index 05b082b4f65162a461c9ad89f9e2499caacf9b1f..d99e0b7f6dfa75ae8084b56e450cfcb4428f68c7 100644 (file)
@@ -164,9 +164,19 @@ exit_label: ; \
 }
 
 /* Set mark bit, exit if it was already set.    */
-
-#ifdef USE_MARK_BITS
+#ifdef USE_MARK_BYTES
+  /* There is a race here, and we may set                               */
+  /* the bit twice in the concurrent case.  This can result in the      */
+  /* object being pushed twice.  But that's only a performance issue.   */
+# define SET_MARK_BIT_EXIT_IF_SET(hhdr,bit_no,exit_label) \
+    { \
+        char * mark_byte_addr = (char *)hhdr -> hb_marks + (bit_no); \
+        if (*mark_byte_addr) goto exit_label; \
+        *mark_byte_addr = 1;  \
+    }
+#else
 # ifdef PARALLEL_MARK
+    /* This is used only if we explicitly set USE_MARK_BITS.            */
     /* The following may fail to exit even if the bit was already set.  */
     /* For our uses, that's benign:                                     */
 #   define OR_WORD_EXIT_IF_SET(addr, bits, exit_label) \
@@ -192,40 +202,13 @@ exit_label: ; \
         OR_WORD_EXIT_IF_SET(mark_word_addr, (word)1 << modWORDSZ(bit_no), \
                             exit_label); \
     }
-#endif /* USE_MARK_BITS */
-
-#if defined(I386) && defined(__GNUC__)
-# define LONG_MULT(hprod, lprod, x, y) { \
-        __asm__ __volatile__("mull %2" : "=a"(lprod), "=d"(hprod) \
-                             : "g"(y), "0"(x)); \
-  }
-#else /* No in-line X86 assembly code */
-# define LONG_MULT(hprod, lprod, x, y) { \
-        unsigned long long prod = (unsigned long long)(x) \
-                                  * (unsigned long long)(y); \
-        hprod = prod >> 32;  \
-        lprod = (unsigned32)prod;  \
-  }
-#endif
-
-#ifdef USE_MARK_BYTES
-  /* There is a race here, and we may set                               */
-  /* the bit twice in the concurrent case.  This can result in the      */
-  /* object being pushed twice.  But that's only a performance issue.   */
-# define SET_MARK_BIT_EXIT_IF_SET(hhdr,bit_no,exit_label) \
-    { \
-        char * mark_byte_addr = (char *)hhdr -> hb_marks + (bit_no); \
-        char mark_byte = *mark_byte_addr; \
-        if (mark_byte) goto exit_label; \
-        *mark_byte_addr = 1;  \
-    }
-#endif /* USE_MARK_BYTES */
+#endif /* !USE_MARK_BYTES */
 
 #ifdef PARALLEL_MARK
 # define INCR_MARKS(hhdr) \
-        AO_store(&(hhdr -> hb_n_marks), AO_load(&(hhdr -> hb_n_marks))+1);
+                AO_store(&hhdr->hb_n_marks, AO_load(&hhdr->hb_n_marks) + 1)
 #else
-# define INCR_MARKS(hhdr) ++(hhdr -> hb_n_marks)
+# define INCR_MARKS(hhdr) (void)(++hhdr->hb_n_marks)
 #endif
 
 #ifdef ENABLE_TRACE
@@ -238,6 +221,20 @@ exit_label: ; \
 # define TRACE_TARGET(source, cmd)
 #endif
 
+#if defined(I386) && defined(__GNUC__)
+# define LONG_MULT(hprod, lprod, x, y) { \
+        __asm__ __volatile__("mull %2" : "=a"(lprod), "=d"(hprod) \
+                             : "g"(y), "0"(x)); \
+  }
+#else
+# define LONG_MULT(hprod, lprod, x, y) { \
+        unsigned long long prod = (unsigned long long)(x) \
+                                  * (unsigned long long)(y); \
+        hprod = prod >> 32;  \
+        lprod = (unsigned32)prod;  \
+  }
+#endif /* !I386 */
+
 /* If the mark bit corresponding to current is not set, set it, and     */
 /* push the contents of the object on the mark stack.  Current points   */
 /* to the beginning of the object.  We rely on the fact that the        */
index 7168c14783f894c22092982ac97ca4feaa1aa15d..ad6699e9d5172d99ddad21e8b283a15f395459f3 100644 (file)
@@ -172,6 +172,8 @@ typedef char * ptr_t;   /* A generic pointer to which we can add        */
 # include "gc_locks.h"
 #endif
 
+#define ONES ((word)(signed_word)(-1))
+
 # ifdef STACK_GROWS_DOWN
 #   define COOLER_THAN >
 #   define HOTTER_THAN <
@@ -579,7 +581,6 @@ GC_EXTERN GC_warn_proc GC_current_warn_proc;
 #define WORDSZ ((word)CPP_WORDSZ)
 #define SIGNB  ((word)1 << (WORDSZ-1))
 #define BYTES_PER_WORD      ((word)(sizeof (word)))
-#define ONES                ((word)(signed_word)(-1))
 #define divWORDSZ(n) ((n) >> LOGWL)     /* divide n by size of word */
 
 #if GRANULE_BYTES == 8
@@ -768,17 +769,6 @@ typedef word page_hash_table[PHT_SIZE];
            /* initial group of mark bits, and it is safe     */
            /* to allocate smaller header for large objects.  */
 
-# ifdef USE_MARK_BYTES
-#   define MARK_BITS_SZ (MARK_BITS_PER_HBLK + 1)
-        /* Unlike the other case, this is in units of bytes.            */
-        /* Since we force doubleword alignment, we need at most one     */
-        /* mark bit per 2 words.  But we do allocate and set one        */
-        /* extra mark bit to avoid an explicit check for the            */
-        /* partial object at the end of each block.                     */
-# else
-#   define MARK_BITS_SZ (MARK_BITS_PER_HBLK/CPP_WORDSZ + 1)
-# endif
-
 #ifdef PARALLEL_MARK
 # include "atomic_ops.h"
   typedef AO_t counter_t;
@@ -860,6 +850,12 @@ struct hblkhdr {
                                 /* Without parallel marking, the count  */
                                 /* is accurate.                         */
 #   ifdef USE_MARK_BYTES
+#     define MARK_BITS_SZ (MARK_BITS_PER_HBLK + 1)
+        /* Unlike the other case, this is in units of bytes.            */
+        /* Since we force doubleword alignment, we need at most one     */
+        /* mark bit per 2 words.  But we do allocate and set one        */
+        /* extra mark bit to avoid an explicit check for the            */
+        /* partial object at the end of each block.                     */
       union {
         char _hb_marks[MARK_BITS_SZ];
                             /* The i'th byte is 1 if the object         */
@@ -872,6 +868,7 @@ struct hblkhdr {
       } _mark_byte_union;
 #     define hb_marks _mark_byte_union._hb_marks
 #   else
+#     define MARK_BITS_SZ (MARK_BITS_PER_HBLK/CPP_WORDSZ + 1)
       word hb_marks[MARK_BITS_SZ];
 #   endif /* !USE_MARK_BYTES */
 };
@@ -1335,14 +1332,6 @@ struct GC_traced_stack_sect_s {
 /*  with it. Only those corresponding to the beginning of an */
 /*  object are used.                                         */
 
-/* Set mark bit correctly, even if mark bits may be concurrently        */
-/* accessed.                                                            */
-#ifdef PARALLEL_MARK
-# define OR_WORD(addr, bits) AO_or((volatile AO_t *)(addr), (AO_t)(bits))
-#else
-# define OR_WORD(addr, bits) (void)(*(addr) |= (bits))
-#endif
-
 /* Mark bit operations */
 
 /*
@@ -1357,6 +1346,14 @@ struct GC_traced_stack_sect_s {
 # define set_mark_bit_from_hdr(hhdr,n) ((hhdr)->hb_marks[n] = 1)
 # define clear_mark_bit_from_hdr(hhdr,n) ((hhdr)->hb_marks[n] = 0)
 #else
+/* Set mark bit correctly, even if mark bits may be concurrently        */
+/* accessed.                                                            */
+# ifdef PARALLEL_MARK
+    /* This is used only if we explicitly set USE_MARK_BITS.    */
+#   define OR_WORD(addr, bits) AO_or((volatile AO_t *)(addr), (AO_t)(bits))
+# else
+#   define OR_WORD(addr, bits) (void)(*(addr) |= (bits))
+# endif
 # define mark_bit_from_hdr(hhdr,n) \
               (((hhdr)->hb_marks[divWORDSZ(n)] >> modWORDSZ(n)) & (word)1)
 # define set_mark_bit_from_hdr(hhdr,n) \
index ec5e96ed36fec6381738641a4ea400683631f738..894f31d6a164d0ace71c152c2be717954e12f889 100644 (file)
 #     define ALIGNMENT 4
 #   endif
 #   if !defined(GC_HPUX_THREADS) && !defined(GC_LINUX_THREADS) \
-       && !defined(OPENBSD)
-#     ifndef LINUX /* For now. */
-#       define MPROTECT_VDB
-#     endif
-#   else
-#     ifdef PARALLEL_MARK
-#       define USE_MARK_BYTES
-                /* Minimize compare-and-swap usage.             */
-#     endif
+       && !defined(OPENBSD) && !defined(LINUX) /* For now. */
+#     define MPROTECT_VDB
 #   endif
 #   define STACK_GROWS_UP
 #   ifdef HPUX
 # define IF_CANCEL(x) /* empty */
 #endif
 
-#if !defined(USE_MARK_BITS) && !defined(USE_MARK_BYTES)
-# if defined(THREADS) && defined(PARALLEL_MARK)
-#   define USE_MARK_BYTES
-# else
-#   define USE_MARK_BITS
-# endif
+#if !defined(USE_MARK_BITS) && !defined(USE_MARK_BYTES) \
+    && defined(PARALLEL_MARK)
+   /* Minimize compare-and-swap usage.  */
+#  define USE_MARK_BYTES
 #endif
 
 #if defined(MSWINCE) && !defined(__CEGCC__) && !defined(NO_GETENV)
diff --git a/mark.c b/mark.c
index deb3cdf7433b698828630605110977df06ef099b..99fa43274da961f8fb2ab032e853c5cbae5b90dd 100644 (file)
--- a/mark.c
+++ b/mark.c
@@ -144,14 +144,8 @@ GC_INNER GC_bool GC_collection_in_progress(void)
 GC_INNER void GC_clear_hdr_marks(hdr *hhdr)
 {
     size_t last_bit = FINAL_MARK_BIT(hhdr -> hb_sz);
-
-#   ifdef USE_MARK_BYTES
-      BZERO(hhdr -> hb_marks, MARK_BITS_SZ);
-      hhdr -> hb_marks[last_bit] = 1;
-#   else
-      BZERO(hhdr -> hb_marks, MARK_BITS_SZ*sizeof(word));
-      set_mark_bit_from_hdr(hhdr, last_bit);
-#   endif
+    BZERO(hhdr -> hb_marks, sizeof(hhdr->hb_marks));
+    set_mark_bit_from_hdr(hhdr, last_bit);
     hhdr -> hb_n_marks = 0;
 }
 
@@ -1570,7 +1564,7 @@ GC_INNER void GC_push_all_stack(ptr_t bottom, ptr_t top)
                   qcontents = (q)[3]; \
                   GC_PUSH_ONE_HEAP(qcontents, (q)+3); }
 # endif
-#endif
+#endif /* !USE_MARK_BYTES && MARK_BIT_PER_GRANULE */
 
 #ifdef USE_PUSH_MARKED_ACCELERATORS
 /* Push all objects reachable from marked objects in the given block */