[prev in list] [next in list] [prev in thread] [next in thread] 

List:       sbcl-commits
Subject:    [Sbcl-commits] master: Assert self-containedness of all but 1 autogenerated header
From:       snuglas via Sbcl-commits <sbcl-commits () lists ! sourceforge ! net>
Date:       2023-06-29 16:48:55
Message-ID: 1688057335.454862.6664 () sfp-scm-3 ! v30 ! lw ! sourceforge ! com
[Download RAW message or body]

The branch "master" has been updated in SBCL:
       via  b3ab2dcf41501a6045013ef00d2317175a2dcbf2 (commit)
      from  4e15055ee77065e87df331daeae28387f1c061df (commit)

- Log -----------------------------------------------------------------
commit b3ab2dcf41501a6045013ef00d2317175a2dcbf2
Author: Douglas Katzman <dougk@google.com>
Date:   Thu Jun 29 12:45:20 2023 -0400

    Assert self-containedness of all but 1 autogenerated header
    
    Good layering makes logic clearer when designing new C algorithms that
    manipulate object representations, without needing to deal with the insanity
    of the 16 inclusions of src/runtime/thread.h just to include the
    primitive thread.h structure for example.
---
 src/compiler/generic/genesis.lisp | 55 +++++++++++++++++++++++++++++++++++----
 src/runtime/gencgc-alloc-region.h | 10 -------
 src/runtime/gencgc-internal.h     |  1 +
 src/runtime/gencgc.c              | 13 ++-------
 src/runtime/thread.h              | 23 +---------------
 tests/genheaders.test.sh          | 29 ++++++++++++++++-----
 6 files changed, 77 insertions(+), 54 deletions(-)

diff --git a/src/compiler/generic/genesis.lisp b/src/compiler/generic/genesis.lisp
index 8602ba0da..76bc55931 100644
--- a/src/compiler/generic/genesis.lisp
+++ b/src/compiler/generic/genesis.lisp
@@ -3328,6 +3328,32 @@ lispobj symbol_package(struct symbol*);~%" (genesis-header-prefix))
       "length_"
       (c-name (string-downcase slot-name))))
 
+(defun write-genesis-thread-h-requisites ()
+  (format t "
+#include \"genesis/config.h\"
+#ifndef LISP_FEATURE_WIN32
+#include <pthread.h>
+#endif
+#include \"gencgc-alloc-region.h\"
+
+#define N_HISTOGRAM_BINS_LARGE 32
+#define N_HISTOGRAM_BINS_SMALL 32
+typedef lispobj size_histogram[2*N_HISTOGRAM_BINS_LARGE+N_HISTOGRAM_BINS_SMALL];
+
+struct thread_state_word {
+  // - control_stack_guard_page_protected is referenced from
+  //   hand-written assembly code. (grep 'THREAD_STATE_WORD_OFFSET')
+  // - sprof_enable is referenced with SAPs.
+  //   (grep 'sb-vm:thread-state-word-slot')
+  char control_stack_guard_page_protected;
+  char sprof_enable; // statistical CPU profiler switch
+  char state;
+  char user_thread_p; // opposite of lisp's ephemeral-p
+#ifdef LISP_FEATURE_64_BIT
+  char padding[4];
+#endif
+};~%"))
+
 (defun write-weak-pointer-manipulators ()
   #+64-bit
   (format t "static inline void set_weak_pointer_next(struct weak_pointer *wp, void *next) {
@@ -3355,6 +3381,7 @@ static inline struct weak_pointer *get_weak_pointer_next(struct weak_pointer *wp
                (format t "#define CODE_SLOTS_PER_SIMPLE_FUN ~d~2%"
                        sb-vm:code-slots-per-simple-fun))
              (when (eq name 'sb-vm::thread)
+               (write-genesis-thread-h-requisites)
                (format t "#define INIT_THREAD_REGIONS(x) \\~%")
                (let ((tlabs (map 'list
                                  (lambda (x) (c-name (string-downcase (second x))))
@@ -4075,16 +4102,35 @@ III. initially undefined function references (alphabetically):
 
 #+gencgc
 (defun write-mark-array-operators (stream &optional (ncards sb-vm::cards-per-page))
+  (format stream "#include ~S
+extern unsigned char *gc_card_mark;~%" (lispobj-dot-h))
+
   #-soft-card-marks
   (progn
     (aver (= ncards 1))
-    (format stream "static inline int cardseq_all_marked_nonsticky(long card) {
+    #+nil ; we take these from gc-private.h. Is that right?
+    (progn
+      (format stream "static inline int cardseq_all_marked_nonsticky(long card) {
     return gc_card_mark[card] == CARD_MARKED;~%}~%")
-    (format stream "static inline int cardseq_any_marked(long card) {
+      (format stream "static inline int cardseq_any_marked(long card) {
     return gc_card_mark[card] != CARD_UNMARKED;~%}~%")
-    (format stream "static inline int cardseq_any_sticky_mark(long card) {
+      (format stream "static inline int cardseq_any_sticky_mark(long card) {
     return gc_card_mark[card] == STICKY_MARK;~%}~%"))
-  #+soft-card-marks
+    (return-from write-mark-array-operators))
+
+  ;; This string has a ~s and ~w so don't use FORMAT on it
+  (write-string "
+/* SIMD-within-a-register algorithms
+ *
+ * from https://graphics.stanford.edu/~seander/bithacks.html
+ */
+static inline uword_t word_haszero(uword_t word) {
+  return ((word - 0x0101010101010101LL) & ~word & 0x8080808080808080LL) != 0;
+}
+static inline uword_t word_has_stickymark(uword_t word) {
+  return word_haszero(word ^ 0x0202020202020202LL);
+}
+" stream)
   ;; In general we have to be wary of wraparound of the card index bits
   ;; - see example in comment above the definition of addr_to_card_index() -
   ;; but it's OK to treat marks as linearly addressable within a page.
@@ -4146,7 +4192,6 @@ III. initially undefined function references (alphabetically):
         (out-to "regnames" (write-regnames-h stream))
         (out-to "errnames" (write-errnames-h stream))
         (out-to "gc-tables" (sb-vm::write-gc-tables stream))
-        #+soft-card-marks
         (out-to "cardmarks" (write-mark-array-operators stream))
         (out-to "tagnames" (write-tagnames-h stream))
         (out-to "print.inc" (write-c-print-dispatch stream))
diff --git a/src/runtime/gencgc-alloc-region.h b/src/runtime/gencgc-alloc-region.h
index a9cd1d643..7c707a8c7 100644
--- a/src/runtime/gencgc-alloc-region.h
+++ b/src/runtime/gencgc-alloc-region.h
@@ -1,12 +1,6 @@
 #ifndef _GENCGC_ALLOC_REGION_H_
 #define _GENCGC_ALLOC_REGION_H_
 
-#include "gc.h"
-
-#ifndef LISP_FEATURE_GENCGC
-#error "gencgc-alloc-region.h included, but LISP_FEATURE_GENCGC not defined"
-#endif
-
 /* Abstract out the data for an allocation region allowing a single
  * routine to be used for allocation and closing. */
 /* Caution: if you change this, you may have to change compiler/generic/objdef
@@ -27,9 +21,6 @@ typedef struct {
     uword_t token;
 } arena_state;
 
-// Macro to statically initialize instead of using set_region_empty()
-#define ALLOC_REGION_INITIALIZER {(void*)0x1000, (void*)1000, 0}
-
 // One region for each of page type.
 // These indices have no correlation to PAGE_TYPE constants.
 // MIXED has to always be at array index 0 because lisp accesses
@@ -49,7 +40,6 @@ extern struct alloc_region  gc_alloc_region[6];
                |(uintptr_t)gc_alloc_region[4].start_addr \
                |(uintptr_t)gc_alloc_region[5].start_addr))
 
-extern generation_index_t from_space, new_space;
 extern int gencgc_alloc_profiler;
 
 #endif /*  _GENCGC_ALLOC_REGION_H_ */
diff --git a/src/runtime/gencgc-internal.h b/src/runtime/gencgc-internal.h
index e24434146..c4dc2fd3c 100644
--- a/src/runtime/gencgc-internal.h
+++ b/src/runtime/gencgc-internal.h
@@ -323,6 +323,7 @@ static inline boolean pinned_p(lispobj obj, page_index_t page)
     return (pins & (1<<subpage)) && hopscotch_containsp(&pinned_objects, obj);
 }
 
+extern generation_index_t from_space, new_space;
 // Return true only if 'obj' must be *physically* transported to survive gc.
 // Return false if obj is in the immobile space regardless of its generation.
 // Pretend pinned objects are not in oldspace so that they don't get moved.
diff --git a/src/runtime/gencgc.c b/src/runtime/gencgc.c
index 12e1203a9..d7c6a4951 100644
--- a/src/runtime/gencgc.c
+++ b/src/runtime/gencgc.c
@@ -226,18 +226,9 @@ static inline void reset_page_flags(page_index_t page) {
     assign_page_card_marks(page, CARD_MARKED);
 }
 
-/* SIMD-within-a-register algorithms
- *
- * from https://graphics.stanford.edu/~seander/bithacks.html
- */
-#ifdef LISP_FEATURE_SOFT_CARD_MARKS
-static inline uword_t word_haszero(uword_t word) {
-  return ((word - 0x0101010101010101LL) & ~word & 0x8080808080808080LL) != 0;
-}
-static inline uword_t word_has_stickymark(uword_t word) {
-  return word_haszero(word ^ 0x0202020202020202LL);
-}
 #include "genesis/cardmarks.h"
+#ifdef LISP_FEATURE_SOFT_CARD_MARKS
+// This is a macro from gc-private.h otherwise
 int page_cards_all_marked_nonsticky(page_index_t page) {
     return cardseq_all_marked_nonsticky(page_to_card_index(page));
 }
diff --git a/src/runtime/thread.h b/src/runtime/thread.h
index 5d8e45d00..c66a56450 100644
--- a/src/runtime/thread.h
+++ b/src/runtime/thread.h
@@ -8,36 +8,15 @@
 #include "globals.h"
 #include "runtime.h"
 #include "os.h"
-#ifdef LISP_FEATURE_GENCGC
-#include "gencgc-alloc-region.h"
-#endif
 #include "genesis/symbol.h"
 #include "genesis/static-symbols.h"
-
-struct thread_state_word {
-  // - control_stack_guard_page_protected is referenced from
-  //   hand-written assembly code. (grep "THREAD_STATE_WORD_OFFSET")
-  // - sprof_enable is referenced with SAPs.
-  //   (grep "sb-vm:thread-state-word-slot")
-  char control_stack_guard_page_protected;
-  char sprof_enable; // statistical CPU profiler switch
-  char state;
-  char user_thread_p; // opposite of lisp's ephemeral-p
-#ifdef LISP_FEATURE_64_BIT
-  char padding[4];
-#endif
-};
-
-#define N_HISTOGRAM_BINS_LARGE 32
-#define N_HISTOGRAM_BINS_SMALL 32
-typedef lispobj size_histogram[2*N_HISTOGRAM_BINS_LARGE+N_HISTOGRAM_BINS_SMALL];
-
 #include "genesis/thread.h"
 #include "genesis/thread-instance.h"
 #include "genesis/fdefn.h"
 #include "genesis/vector.h"
 #include "interrupt.h"
 #include "validate.h"           /* for BINDING_STACK_SIZE etc */
+#include "gc.h" // for page_index_t
 
 enum threadstate {STATE_RUNNING=1, STATE_STOPPED, STATE_DEAD};
 
diff --git a/tests/genheaders.test.sh b/tests/genheaders.test.sh
index b4dcc4210..8003c3b3d 100755
--- a/tests/genheaders.test.sh
+++ b/tests/genheaders.test.sh
@@ -7,10 +7,10 @@ create_test_subdirectory
 run_sbcl <<EOF
 ;; technically this is "skipped" if not fasteval, but we don't have "skipped"
 ;; as a status code from shell tests.
-(unless (and (find-package "SB-INTERPRETER")
-             ;; host with #+sb-devel hangs, not sure why
-             (not (member :sb-devel *features*)))
- ;; exit normally so that the shell doesn't exit abnormally (as per "set -e")
+(when (member :sb-devel *features*)
+  ;; host with #+sb-devel hangs
+  ;; exit normally so that the shell doesn't exit abnormally (as per "set -e")
+ (format t "~&Skipping test due to sb-devel~%")
  (exit))
 (setq *evaluator-mode* :interpret)
 (defvar *sbcl-local-target-features-file* "../local-target-features.lisp-expr")
@@ -20,7 +20,8 @@ run_sbcl <<EOF
 (in-package "SB-COLD")
 (defvar *target-sbcl-version* (read-from-file "../version.lisp-expr"))
 (in-host-compilation-mode
- (lambda (&aux (sb-xc:*features* (cons :c-headers-only sb-xc:*features*)))
+ (lambda (&aux (sb-xc:*features* (cons :c-headers-only sb-xc:*features*))
+               (*load-verbose* t))
    (do-stems-and-flags (stem flags 1)
      (when (member :c-headers flags)
        (handler-bind ((style-warning (function muffle-warning)))
@@ -29,7 +30,23 @@ run_sbcl <<EOF
    (load "../src/compiler/generic/genesis.lisp")))
 (genesis :c-header-dir-name "$TEST_DIRECTORY/" :verbose t)
 (assert (probe-file "$TEST_DIRECTORY/gc-tables.h"))
-(dolist (pathname (directory "$TEST_DIRECTORY/*.*")) (delete-file pathname))
 EOF
 
+src=$TEST_DIRECTORY/test.c
+obj=$TEST_DIRECTORY/test.o
+# no files exist if the generator test was entirely skipped
+if [ -r $TEST_DIRECTORY/array.h ]
+then
+    for i in $TEST_DIRECTORY/*.h
+    do
+        case $i in
+        */gc-tables.h) ;; # fails to compile by itself (FIXME)
+        *)
+          echo "#include \"$i\"" > ${src}
+          ./run-compiler.sh -I../src/runtime -c -o ${obj} ${src}
+          ;;
+        esac
+    done
+fi
+
 exit $EXIT_TEST_WIN

-----------------------------------------------------------------------


hooks/post-receive
-- 
SBCL


_______________________________________________
Sbcl-commits mailing list
Sbcl-commits@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/sbcl-commits
[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic