Function is rewritten in C in compiler.d to remove a dependency
between the bytecodes compiler and the clos module. It may be more
performant thanks to more precise type handing, however we use a list
instead of a hashtable, so it may be slower with lookup. To assess
that we should run some benchmarks against real code -- rewriting C
code to work with a hash table should be trivial.
clos::need-to-make-load-form-p is now si::need-to-make-load-form-p and
may be called from C code as si_need_to_make_load_form_p.
We've reinitialized the class even when it was already finalized and
none of its parents has changed with the recomputed information.
That leads to replacing the class slots with a result of COMPUTE-SLOTS
and in effect changing the INSTANCE-SIG (see src/clos/change.lsp).
Next time when ENSURE-UP-TO-DATE-INSTANCE is called (i.e from the
STANDARD-INSTANCE-ACCESS), then the instance is reinitalized.
Behavior was the most notable when we had tried to re-finalize the
STANDARD-EFFECTIVE-SLOT-DEFINITION class, because then /its new/ slots
were by definition obsolete after calling setf on this class and
unbound, what leads to an infinite recursion when we try to signal
unbound-slot condition.
Fixes#568.
Now instead of a default printer #<a foo> we have the identity
information #<a foo 0x56123571d240>. That is certainly useful for
printing when we have lists of instances of the same class.
@"foo" will expand to ecl_make_constant_base_string("foo", -1) now.
That saves some typing during testing when we want to feed a string to
the cl_format and other CL functions opearting on strings.
Now:
cl_format(3, @"~a: ~s", obj1, obj2);
Then:
cl_object str = ecl_make_constant_base_string("~a: ~s", -1);
cl_format(3, str, obj1, obj2);
Init forms are deferred when possible. This change solves two problems:
- init forms using uninitialized constant boxes
- make forms not signaling an error when circular
Partial fix for #562 (we need to fix bytecodes compiler too).
When a local function calls a closure it has to be a closure too. Thus
when updating the closure type for a function f, we have to possibly
update also all functions referencing f.
Fixes#545.
According to the C99 standard, compilers are supposed to automatically
choose the correct type. However, for the C89 standard explicit suffixes
are needed for long longs. Guess what standard msvc follows...
Bug was introduced by the recent race condition fixes of commit
cc7c0d4386. ecl_list_process needs to be
able to allocate memory and bind special variables, which wasn't possible
previously, because the environment was not yet initialized. Since we can't
initialize the environment before calling ecl_list_process (that was the
reason for the race condition in the first place), we use the fake environment
allocated on the stack (where the gc can find its contents) until we can
safely call ecl_list_process and switch over to the real environment.
Fixes#564.
This reverts commit bd9c590810.
Apparently, _fpreset is not just equivalent to feclearexcept and really
needed when doing a longjmp out of a signal handler. On top of that, with
MSVC 2019, I now observe segmentation faults without _fpreset, but not with
_fpreset in si_trap_fpe!
This lead to problems in code that defined validate-superclass methods
for custom metaclasses. Such methods are not installed at compile
time, giving errors when we called validate-superclass from
ensure-class during compilation.
The C standard allows compilers to ignore side effects of floating
point operations unless the STDC FENV_ACCESS pragma is in effect. This
could lead to spurious floating point exceptions being signaled
because the C compiler optimized a calculation that would ordinarily
not set fpe bits to one that did (observed with clang for a cast
double to cl_fixnum).
To solve this, we resurrect the ECL_MATHERR macro which was removed in
commit cb03494a6d. We handle fpe bits
only around calculations which are known to be "unsafe" in the sense
that they can produce floating point exceptions. Before the
calculation, all bits are unset and afterwards, we test for
exceptions.
The disadvantage of this method is that optimizations by the C
compiler resulting in unboxed float arithmetic might lead to
missing exceptions, because our native C compiler does not insert
ECL_MATHERR statements around these calculations.
Due to the fact that the thread local environment is allocated with
mmap, the garbage collector is only aware of it after the thread is
listed in cl_core.processes. Therefore, we have to list the thread
before we allocate any memory in its environment. We were doing this
previously, however a bit earlier than needed which had the
unfortunate side effect that not all threads listed in
cl_core.processes had valid environment associated to them. Now, we
delay the listing until immediately before allocating the contents of
environment, ensuring that all listed threads have valid environments.