This is intended to supplant the concept of deferred-warnings in ASDF by
imparting the ability to the FASLoader to issue warnings about unresolved
function linkage. At last, Lisp can use a more modern paradigm of
separately compiled translation units.
LOAD is totally unchanged if you don't hook into this mechanism in user code.
In fact, this hash function might be shorter. For example, according to the file,
the hash function for #(2 3 5 #xC #xE) performed a mask, two shifts, AREF,
and xor; while the quick function is merely + and LOGAND.
The call sequence needs only 1 add and 1 load where it used to need 3
loads for fdefn, fun, raw-fun. So while it is potentially faster, the
motivation was actually to remove support for untagged-fdefns which
strew #+/- all over the place.
The regression suite on ppc64 seems to be no more unstable than is typical.
I haven't observed a clean run in probably a year, and it may also be
getting some memory-ordering-related bugs due to the hash-table patches.
Solves the problem that if you're building in a tree of symlinks where files
aren't on the local machine, load-as-source made 10x too many OS calls.
Based on strace it looks like it still invokes unix-access and unix-open
at least 2x too many times, but there's definitely less lstat() now
for source files that produce no style-warnings or other noise.
This eliminates duplication between compiler/generic/core and compiler/dump.
And code-slots-per-simple-fun is mentioned in far fewer places.
The pristine core consumes 5% less code space, correspondingly more non-code,
but all other things being equal, the CPU's instruction cache will benefit.
This rectifies many awkward aspects of the immobile space fdefns
which it replaces.
All other architectures should be unaffected by the patch.
Tested with with +/- {immobile-space, sb-thread, mark-region}
on linux, and the default config on windows and macOS.
The launchpad complaint was that if we claim the spec permits us to disregard
some type constraints, surely it meant that no matter how spelled; but it would
be very incompatible to force users to put an (OR NULL) in their type,
so this does it for them only at evaluation of the DOLIST result form.
Since this change generally performs more analysis of which declarations are
bound or free, it also hoists the free ones outside the loop like they are
in CCL and CLISP which potentially remove type-checks from inside the loop
for free declarations on lexically visible vars with no SET.
e.g (DECLARE (FIXNUM LOOPVAR FOO)) where FOO is lexically known to be INTEGER,
it still checks for FIXNUM on each loop iteration which seems like a bug.
This hadn't been done ever since rev 790bca74 made SYMBOL-HASH less sensitive
to address-of-NIL. Consequently many of the lines are not needed now.
Additionally, add a small hack to avoid creating journal entries when
the static objects (symbols, fdefns) are changed.
Why not. It wasn't hard to find the problem, though I do not see how
this affected the number of perfect hashes needed during cross-compile.
Not sure if I should be worried.
Fixes lp#2060059
The COMPILED-DEBUG-FUN-VARS slot was designed to store a packed byte
vector where the names and packages of variables were dumped in a
packed representation with smarts to dump debug variables relative to
the current package or to flag them as uninterned, allowing the
omission of an explicit package name in the packed vector.
Due to bootstrapping reasons however, the initial SBCL commit changed
this to store symbols instead (as a necessity since package names were
dumped by xc like SB!C, not matching how they get loaded as SB!XC,
making the name+package strategy more difficult). The result was
significantly increasing the space usage of debug info relative to CMU
CL, since symbols needed to be loaded interned, taking up more space
to represent, even though most of the time interning is not even
needed outside of debugging contexts. Also space was wasted for
uninterned symbols. The vector for the slot was also no longer
dumpable as a byte vector, wasting a bunch of space. (later mitigated
by a hack on 64-bit where flags got packed together with scs).
Now that the bootstrap no longer involves package renaming and we have
a sane way of doing that, the original design using name+package and a
packed vector for COMPILED-DEBUG-FUN-VARS as in CMU CL can now be
brought back, saving ~400KB from a warm arm64 core. 32-bit targets
should benefit even more, since they didn't do the manual packing
mitigation.
So:
* We can get rid of the "large-fixnums" hack where scs got packed into
the flag, since now we just dump it all as a packed byte vector. In
particular 32-bit targets benefit now too from packing without having
to do manual packing.
* Symbols don't need to be needlessly interned before a debug fun even
gets parsed.
* A few FIXMEs are killed.
These are created by an ensuing commit, but it seems like commit emails
get lost when the diff exceeds a certain number of lines, and even if not,
this diff would cause clipping of the body of what is otherwise not
actually a very large change.
* Assume that non-minimal perfect hash calculation is faster than minimal.
The output value is bounded by pow2ceil(N) instead of N which avoids an
array bound check since the compiler knows that the final step was LOGAND
with a (2^N)-1 value exactly matching the key array.
* The ASSOC transform can use specialized vectors if the data are numeric.
* Run build-all-cores to generate new xperfecthash entries.
* Store symbols as well as symbol-hash. In doing this it should be possible
to alter CALC-SYMBOL-NAME-HASH without having to rebuild every target to
infer what entries the file was supposed to contain (since we can't easily
reverse-engineer symbols from their hashes). Using the symbols it is possible
to "upgrade" to a new SYMBOL-HASH algorithm via a one-time conversion of the
file, which might happen if we tack on a murmur3 final mix step or similar.
* Split the file into one per distinct value of N-FIXNUM-BITS so that a
given collection of symbols almost always identifies a file entry uniquely
(but not always, due to NIL having a hash that can vary)