* configure.ac (ALIGNOF_INT, ALIGNOF_LONG, ALIGNOF_LONG_LONG):
New variables.
(emacs_cv_alignas_unavailable): Define if alignas and structure
alignment primitives are unavailable. In such an environment,
the MSB tagging scheme must be enabled, as must the GNU malloc.
* msdos/sed2v2.inp: Adjust correspondingly.
* src/alloc.c (union emacs_align_type): Remove types which
contain flexible array members. The address of a field
subsequent to an aggregate with flexible array members cannot
validly be taken.
(mark_memory) [!USE_LSB_TAG && !WIDE_EMACS_INT]: Strip type bits
before scanning memory.
* src/emacs.c (main):
* src/eval.c (Fautoload_do_load):
* src/fns.c (Frequire): Rename a number of illogically named
fields.
* src/lisp.h (ALIGNOF_EMACS_INT): Define to the natural
alignment of EMACS_INT.
(IDEAL_GCALIGNMENT): New macro.
(USE_LSB_TAG): Disable if no alignment specifiers are available,
WIDE_EMACS_INT is undefined, and the natural alignment of
EMACS_INT falls short of LSB tagging's requirements.
(gflags): Rename illogically named fields and don't define them
as bitfields, which runs afoul of certain compiler issues.
(will_dump_p, will_bootstrap_p, will_dump_with_pdumper_p)
(dumped_with_pdumper_p): Adjust accordingly.
* src/pdumper.c (VM_SUPPORTED): Define to 0 when !USE_LSB_TAG.
It is better to read dump files into the heap by hand than to be
supplied with an address that is not representable.
(_dump_object_start_pseudovector): Rename to
dump_object_start_pseudovector, to avoid encroaching on reserved
names.
(START_DUMP_PVEC): Adjust correspondingly.
(dump_mmap_contiguous_vm): Preserve errno around failure
cleanup.
(dump_bitset_bit_set_p): Work around certain compiler issues.
(pdumper_load) [!USE_LSB_TAG]: Reject dump file allocations
that are not representable as Lisp_Objects.
Tested on i386-unknown-solaris2.10, sparc-sun-solaris2.10.
From a suggestion by Pip Cet.
* src/alloc.c (make_formatted_string): Omit first argument,
to simplify the calling convention. All callers changed.
* src/doprnt.c (doprnt): Also support %u. Update doc.
The case_Lisp_Int macro was originally introduced with different
definitions depending on USE_2_TAGS_FOR_INTS. However, since commit
2b57012478, we have assumed that USE_2_TAGS_FOR_INTS is always
defined, and the macro has only a single definition. As a result, the
macro is now unnecessary, and replacing it with standard C case labels
improves readability and understanding.
* src/lisp.h (case_Lisp_Int): Delete macro.
* src/alloc.c (process_mark_stack, survives_gc_p):
* src/data.c (Fcl_type_of):
* src/fns.c (value_cmp, sxhash_obj):
* src/pdumper.c (dump_object):
* src/print.c (print_object):
* src/xfaces.c (face_attr_equal_p): Remove uses of above macro.
Since the introduction of the 'calln' macro, the 'call1', 'call2', ...,
'call8' macros are just aliases for the former. This is slightly
misleading and potentially unhelpful. The number of arguments N can
also easily go out-of-synch with the used alias callN. There is no
reason not to replace these aliases with using 'calln' directly.
To reduce the risk for mistakes, the tool Coccinelle was used to make
these changes. See <https://coccinelle.gitlabpages.inria.fr/website/>.
* src/alloc.c, src/androidvfs.c, src/androidfns.c, src/buffer.c:
* src/callint.c, src/callproc.c, src/casefiddle.c, src/charset.c:
* src/chartab.c, src/cmds.c, src/coding.c, src/composite.c:
* src/data.c, src/dbusbind.c, src/dired.c, src/doc.c:
* src/emacs.c, src/eval.c, src/fileio.c, src/filelock.c:
* src/fns.c, src/frame.c, src/gtkutil.c, src/haikufns.c:
* src/haikumenu.c, src/image.c, src/insdel.c, src/intervals.c:
* src/keyboard.c, src/keymap.c, src/lisp.h, src/lread.c:
* src/minibuf.c, src/nsfns.m, src/nsselect.m, src/pgtkfns.c:
* src/pgtkselect.c, src/print.c, src/process.c, src/sort.c:
* src/syntax.c, src/textconv.c, src/textprop.c, src/undo.c:
* src/w32fns.c, src/window.c, src/xfaces.c, src/xfns.c:
* src/xmenu.c, src/xselect.c, src/xterm.c:
Replace all uses of 'call1', 'call2', ..., 'call8' with 'calln'.
Problem reported by Hong Xu <https://bugs.gnu.org/75551#14>.
* src/alloc.c (MALLOC_IS_LISP_ALIGNED): static_assert it,
since it is true on all current Emacs platforms.
All uses simplified to assume it is true.
(xmalloc, xzalloc, xrealloc, lisp_malloc): Just use
malloc/calloc/realloc. Since we are using the malloc-gnu
and realloc-posix modules, we need not worry about whether
these functions return a null pointer for zero-size requests.
(xrealloc): Stop worrying about no-longer-existing platforms
where realloc (nullptr, ...) did not work.
(laligned, lmalloc, lrealloc): Remove. All uses removed.
This check was added to 'malloc_initialize_hook' in order to "insulate
Emacs better from configuration screwups" (commit b4788b9394). With
unexec gone, we no longer use 'malloc_set_state', and thus don't need
this check.
Note that this patch removes the last uses of the deprecated glibc
functions 'malloc_set_state' and 'malloc_get_state' from our code.
* src/alloc.c (malloc_initialize_hook) [DOUG_LEA_MALLOC]:
Remove check for working 'malloc_set_state'.
(alloc_unexec_pre) [DOUG_LEA_MALLOC]: Delete unused function.
(alloc_unexec_post) [DOUG_LEA_MALLOC]: Delete function.
(malloc_state_ptr) [DOUG_LEA_MALLOC]: Delete variable.
* configure.ac (emacs_cv_var_doug_lea_malloc): Don't check for
malloc_set_state and malloc_get_state.
As pure storage is now gone, it no longer needs to be documented.
* doc/lispref/elisp.texi (Top):
* doc/lispref/internals.texi (GNU Emacs Internals): Remove "Pure
Storage" section.
(Building Emacs, Garbage Collection, Writing Emacs Primitives):
* doc/lispref/symbols.texi (Standard Properties): Remove references to
pure storage.
* src/alloc.c (Fgarbage_collect): Remove docstring text referring to
pure storage.
This is based on a diff from 2024-10-15 which still applied.
Since then, I've inadvertantly modified the igc branch so that
it is no longer possible to get a clean diff of what has changed
since I created the branch.
Enable GC_REMEMBER_LAST_MARKED by default (it was disabled in Emacs 29)
to make it easier to debug difficult-to-reproduce GC problems
encountered by users. This increases GC costs by about 5 %, which can
be avoided by turning the mark trace buffer back off using the new
--disable-gc-mark-trace option.
See discussion at
https://lists.gnu.org/archive/html/emacs-devel/2024-09/msg00240.html
* configure.ac (--disable-gc-mark-trace): New config option.
* etc/NEWS: Mention it.
* src/alloc.c: Enable it by default and avoid a compiler warning.
This fixes the problem whereby attaching GDB to a running Emacs
on MS-Windows would slow down keyboard input, because the
low-level keyboard hook installed by Emacs at startup was still
installed, but with Emacs stopped, the hook code couldn't run,
and therefore the OS would time-out waiting for the hook to
return. Now when GDB is attached to Emacs, it will remove the
hook right away.
* src/.gdbinit: Call 'remove_w32_kbdhook' if the keyboard hook is
already installed.
* src/alloc.c (defined_WINDOWSNT): New enum.
(gdb_make_enums_visible): Add 'defined_WINDOWSNT'.
The purpose of these changes is to improve the code handling the
display of buffers in windows, switching to previous and next
buffers in windows and restoring a previous state after quitting
or killing buffers. In particular it does:
- Add a new window parameter 'quit-restore-prev' so a window can
keep its initial 'quit-restore' parameter and undoing a sequence
of quit window operations becomes more reliable (Bug#59862).
- Optionally have 'kill-buffer' call 'quit-restore-window' for
all windows showing the argument buffer (Bug#59862).
- Add a new hook so it's possible to avoid that a window gets
deleted implicitly by functions like 'kill-buffer' (Bug#71386).
- Add a new option to make 'quit-restore-window' delete windows
more aggressively (Bug#59862).
- Immediately remove killed buffers from all windows' previous
and next buffers. For windows that are already dead, use a weak
hash table to be used by 'kill-buffer'. This avoids any special
handling of such windows by the garbage collector.
- Immediately remove 'quit-restore' and 'quit-restore-prev'
window parameters that reference killed buffers. These
parameters have no more use once their buffers got killed.
- Make sure that internal windows do not have any previous and
next buffers. This fixes a silly memory leak.
- Make sure that after set_window_buffer and some wset_buffer
calls the buffer now shown in the window does not appear in the
lists of that window's previous and next buffers. The old
behavior could make functions investigating these lists
erroneously believe that there still existed some other buffer
to switch to.
* src/alloc.c (mark_discard_killed_buffers): Remove function.
(mark_window): No more filter previous and next buffer lists.
* src/window.h (struct window): Move up prev_buffers and
next-buffers in structure; they are now treated by the collector
as usual.
* src/window.c (window_discard_buffer_from_alist)
(window_discard_buffer_from_list)
(window_discard_buffer_from_window)
(window_discard_buffer_from_dead_windows)
(Fwindow_discard_buffer): New functions.
(set_window_buffer): Discard BUFFER from WINDOW's previous and
next buffers.
(make_parent_window): Make sure internal windows have no previous
and next buffers.
(make_window): Don't initialize window's previous and next
buffers, they are handled by allocate_window now.
(Fdelete_window_internal): Add WINDOW to window_dead_windows_table.
(Fset_window_configuration): Remove resurrected window from
window_dead_windows_table. Make sure buffers set by wset_buffer
calls are not recorded in window's previous and next buffers.
(delete_all_child_windows): Add deleted windows to
window_dead_windows_table.
(window_dead_windows_table): New weak hash table to record dead
windows that are stored in saved window configurations.
* src/buffer.c (Fkill_buffer): Call new function
'window_discard_buffer_from_dead_windows'.
* lisp/window.el (window-deletable-functions): New hook.
(window-deletable-p): Update doc-string. Run
'window-deletable-functions' (Bug#71386).
(unrecord-window-buffer): New argument ALL. Move body to
'window-discard-buffer-from-window' so that if ALL is non-nil,
WINDOW's 'quit-restore' and 'quit-restore-prev' parameters get
removed too.
(switch-to-prev-buffer): Don't care about killed buffers here;
'replace-buffer-in-windows' should have done that already. Use
'unrecord-window-buffer'.
(switch-to-next-buffer): Don't care about killed buffers here;
'replace-buffer-in-windows' should do that now.
(kill-buffer-quit-windows): New option.
(delete-windows-on): Update doc-string. Handle new option
'kill-buffer-quit-windows'. Update 'unrecord-window-buffer'
calls.
(replace-buffer-in-windows): Update doc-string. Handle new
option 'kill-buffer-quit-windows' (Bug#59862). Update call to
'unrecord-window-buffer'.
(quit-restore-window-no-switch): New option.
(quit-restore-window): Update doc-string. Handle additional
values of BURY-OR-KILL so to not kill a buffer about to be
killed by the caller. Handle 'quit-restore-prev' parameter
(Bug#59862). Handle new option 'quit-restore-window-no-switch'
(Bug#59862).
(quit-windows-on): Update doc-string. Call 'quit-window-hook'
and call 'quit-restore-window' directly so that the buffer does
not get buried or killed by the latter. Update
'unrecord-window-buffer' call.
(display-buffer-record-window): Update doc-string. Handle new
`quit-restore-prev' parameter (Bug#59862).
(switch-to-buffer): Call 'display-buffer-record-window' so a
latter 'quit-restore-window' can use its parameters.
* doc/lispref/windows.texi (Deleting Windows): Describe implicit
deletion of windows and new hook 'window-deletable-functions'.
(Buffers and Windows): Update description of
'replace-buffer-in-windows'. Describe new option
'kill-buffer-quit-windows'.
(Quitting Windows): Describe 'quit-restore-prev' parameter and
new option 'quit-restore-window-no-switch'. Update description
of 'quit-restore-window'.
(Window Parameters): Mention 'quit-restore-prev' parameter.
* etc/NEWS: Add entries for 'window-deletable-functions',
'kill-buffer-quit-windows', 'quit-restore-window-no-switch'.
mention new parameter 'quit-restore-prev' and new argument
values for 'quit-restore-window'.
* src/alloc.c (make_clear_bool_vector): It’s now the caller’s
responsibility to make sure the bool vector length is in range.
Add an eassert to double-check this. This lets some locals be
ptrdiff_t not EMACS_INT.
(Fmake_bool_vector, Fbool_vector):
Check that bool vector lengths are in range.
* src/lisp.h (BOOL_VECTOR_LENGTH_MAX): New macro.
(bool_vector_words, bool_vector_bytes): Avoid undefined
behavior if size == EMACS_INT_MAX - (BITS_PER_BITS_WORD - 1).
This is mostly theoretical but it’s easy to do it right.
* src/lread.c (read_bool_vector): Use EMACS_INT, not just ptrdiff_t.
Check that length doesn’t exceed BOOL_VECTOR_LENGTH_MAX.
This fixes an unlikely integer overflow where the calculated size
went negative.
Although loading uninitialized works from memory and then ignoring
the result works fine on conventional architectures, it
technically has undefined behavior in C, so redo bool_vector
allocation so that the code never does that. This can improve
performance when allocating large vectors of nil, since calloc can
clear the memory lazily.
* src/alloc.c (make_clear_bool_vector): New function,
a generalization of make_uninit_bool_vector.
(make_uninit_bool_vector): Use it.
(Fmake_bool_vector): If !INIT, rely on make_clear_bool_vector.
* src/alloc.c (Fbool_vector):
* src/fns.c (Freverse): Don’t access uninitialized bool_vector words.
* src/alloc.c (mark_frame): Mark this frame's image cache, if it
exist.
(mark_terminals): Cease marking T->image_cache.
* src/androidfns.c (unwind_create_frame, Fx_create_frame)
(android_create_tip_frame):
* src/haikufns.c (unwind_create_frame, haiku_create_frame)
(haiku_create_tip_frame):
* src/nsfns.m (unwind_create_frame):
* src/pgtkfns.c (unwind_create_frame, Fx_create_frame)
(x_create_tip_frame):
* src/xfns.c (unwind_create_frame, Fx_create_frame)
(x_create_tip_frame):
* src/w32fns.c (unwind_create_frame, Fx_create_frame)
(w32_create_tip_frame): Remove adjustments of the frame image
cache's reference count rendered redundant by the assignment of
image caches to individual frames rather than terminals.
* src/dispextern.h (struct image_cache) <scaling_col_width>: New
field.
* src/frame.c (gui_set_font): In lieu of clearing F's image
cache unconditionally, establish whether the column width as
considered by compute_image_size has changed, and if so, adjust
or reassign the frame's image cache.
(make_frame): Clear F->image_cache.
* src/frame.h (struct frame) <image_cache>: New field.
(FRAME_IMAGE_CACHE): Return F->image_cache.
* src/image.c (make_image_cache): Clear C->scaling_col_width.
(cache_image): Adjust to new means of assigning image caches to
frames.
* src/termhooks.h (struct terminal) <image_cache>: Delete field.
* src/xfaces.c (init_frame_faces): Do image cache assignment
with all new frames.
This is a new warning diagnostic in GCC 14.
* lib-src/etags.c (mercury_heuristics_ratio):
* src/pgtkselect.c, src/xselect.c (selection_request_stack):
* src/xselect.c (outstanding_transfers):
* src/xterm.c (pending_selection_requests)
(x_dnd_waiting_for_motif_finish_display):
Now static.
* lib-src/make-docfile.c (close_emacs_globals):
Arrange for lispsym to be declared with extern first,
when compiling lread.c.
* src/alloc.c (gdb_make_enums_visible) [__GNUC__]:
* src/emacs.c (RCS_Id):
* src/keyboard.c (stop_character):
* src/print.c (print_output_debug_flag):
Now declared with extern first.
* src/lisp.h (DEFINE_GDB_SYMBOL_BEGIN) [MAIN_PROGRAM]:
Arrange for ID to be declared extern first.
* src/lisp.h (garbage_collection_inhibited):
* src/xterm.h (x_frame_parm_handlers):
Declare here, so that its interface is properly checked. Other decls
removed.
* lisp/cus-edit.el (Custom-mode): Enable text conversion, now
that fields are correctly treated.
* src/alloc.c (mark_frame): Mark f->conversion.field.
* src/androidterm.c (android_update_selection): Adjust
conversion region and selection position by the field start and
end.
* src/editfns.c (find_field): Export function.
* src/frame.c (make_frame): Clear f->conversion.field.
* src/frame.h (struct text_conversion_state) <field>: New field.
* src/lisp.h (find_fields, reset_frame_conversion): Export
functions.
* src/minibuf.c (Fread_from_minibuffer): Reset frame conversion
if Voverriding_text_conversion_style is set.
* src/textconv.c (textconv_query): Narrow to field.
(reset_frame_conversion): New function.
(reset_frame_state): Clear conversion field.
(really_delete_surrounding_text): Narrow to field.
(locate_and_save_position_in_field): New function.
(really_request_point_update, really_set_point_and_mark)
(complete_edit_check, handle_pending_conversion_events_1)
(handle_pending_conversion_events, get_conversion_field)
(set_composing_region, textconv_set_point_and_mark, replace_text)
(get_extracted_text, get_surrounding_text, report_point_change):
Compute, narrow to and offset by the currently active field
whenever point is updated or a command is received.
(syms_of_textconv): Revise doc strings.
* src/textconv.h (get_conversion_field): Export function.
In preparation for the use of `PVEC_COMPILED` objects for
interpreted functions, rename them to use a more neutral name.
* src/lisp.h (enum pvec_type): Rename `PVEC_COMPILED` to `PVEC_CLOSURE`.
(enum Lisp_Compiled): Use `CLOSURE_` prefix i.s.o `COMPILED_`.
Also use `CODE` rather than `BYTECODE`.
(CLOSUREP): Rename from `COMPILEDP`.
(enum Lisp_Closure): Rename from `Lisp_Compiled`.
* src/alloc.c, src/bytecode.c, src/comp.c, src/data.c, src/eval.c,
* src/fns.c, src/lisp.h, src/lread.c, src/pdumper.c, src/print.c,
* src/profiler.c: Rename all uses accordingly.
* src/.gdbinit (xclosure): Rename from `xcompiled`.
(xcompiled): New obsolete alias.
(xpr): Adjust accordingly. Also adjust to new PVEC_CLOSURE tag name.
This reverts commit de6b1e1efb.
While it did simplify code, there aren't much in the way of technical
benefits the change at this time, and there were protest against the
unwarranted style change.
The new opaque type replaces the previous use of vectors for obarrays.
`obarray-make` now returns objects of this type. Functions that take
obarrays continue to accept vectors for compatibility, now just using
their first slot to store an actual obarray object.
obarray-size and obarray-default-size now obsolete.
* lisp/obarray.el (obarray-default-size, obarray-size):
Declare obsolete.
(obarray-make, obarrayp, obarray-clear): Remove from here.
* src/fns.c (reduce_emacs_uint_to_hash_hash): Remove from here.
* src/lisp.h (struct Lisp_Obarray, OBARRAYP, XOBARRAY, CHECK_OBARRAY)
(make_lisp_obarray, obarray_size, check_obarray)
(obarray_iter_t, make_obarray_iter, obarray_iter_at_end)
(obarray_iter_step, obarray_iter_symbol, DOOBARRAY, knuth_hash): New.
(reduce_emacs_uint_to_hash_hash): Moved here.
* src/lread.c (check_obarray): Renamed and reworked as...
(checked_obarray_slow): ...this.
(intern_sym, Funintern, oblookup, map_obarray)
(Finternal__obarray_buckets): Adapt to new type.
(obarray_index, allocate_obarray, make_obarray, grow_obarray)
(obarray_default_bits, Fobarray_make, Fobarrayp, Fobarray_clear): New.
* etc/emacs_lldb.py (Lisp_Object):
* lisp/emacs-lisp/cl-macs.el (`(,type . ,pred)):
* lisp/emacs-lisp/cl-preloaded.el (cl--typeof-types):
* lisp/emacs-lisp/comp-common.el (comp-known-type-specifiers):
* lisp/emacs-lisp/comp.el (comp-known-predicates):
* src/alloc.c (cleanup_vector, process_mark_stack):
* src/data.c (Ftype_of, syms_of_data):
* src/minibuf.c (Ftry_completion, Fall_completions, Ftest_completion):
* src/pdumper.c (dump_obarray_buckets, dump_obarray, dump_vectorlike):
* src/print.c (print_vectorlike_unreadable):
* test/lisp/abbrev-tests.el (abbrev-make-abbrev-table-test):
* test/lisp/obarray-tests.el (obarrayp-test)
(obarrayp-unchecked-content-test, obarray-make-default-test)
(obarray-make-with-size-test):
Adapt to new type.
This makes both lookups and rehashing cheaper. The index vector size
is now always a power of 2. The first table size is reduced to
6 (from 8), because index vectors would become excessively big
otherwise.
* src/lisp.h (struct Lisp_Hash_Table): Replace index_size with
index_bits. All references adapted.
(hash_table_index_size): New accessor; use it where applicable.
* src/fns.c (hash_index_size): Replace with...
(compute_hash_index_bits): ...this new function, returning the log2 of the
index size. All callers adapted.
(hash_index_index): Knuth multiplicative hashing instead of remainder.
(maybe_resize_hash_table): Reduce first table size from 8 to 6.
* src/lisp.h (TAG_PTR_INITIALLY): Rename from TAG_PTR, since calls
can be used only as initializers, and the convention elsewhere in
lisp.c is to give these macros names ending in ‘_INITIALLY’.
This should help avoid confusion such as we recently experienced
in make_lisp_symbol_internal. All uses changed.
`struct composition` kept an index into the internal `key_and_value` array
of hash tables, which only worked because of details of how
hash-tables are handled. Replace it with a reference to the
key stored at that location in the hash-table, which saves us an
indirection while at it.
* src/composite.h (struct composition): Replace `hash_index` with
the actual `key`.
(COMPOSITION_KEY): Simplify accordingly.
(mark_composite): Declare.
* src/composite.c (get_composition_id): Adjust accordingly.
(mark_composite): New function.
* src/charset.c (mark_charset): Uncomment.
* src/lisp.h (mark_charset): Declare.
* src/alloc.c (garbage_collect): Call `mark_charset` and `mark_composite`.
* src/pdumper.c (hash_table_contents): Remove invalid comment, since
compositions aren't dumped.
This removes hacks from code that had to be careful not to use
Qunbound as a hash table key, at the cost of a minor hack in
the GC marker.
* src/lisp.h (INVALID_LISP_VALUE, HASH_UNUSED_ENTRY_KEY):
Define as a null-pointer float.
* src/alloc.c (process_mark_stack): Add hack to ignore that value.
* src/pdumper.c (dump_object_needs_dumping_p)
(pdumper_init_symbol_unbound, pdumper_load):
* src/print.c (PRINT_CIRCLE_CANDIDATE_P): Remove hacks for Qunbound.
Be more systematic about putting space before paren in calls,
and in avoiding unnecessary parentheses in macros.
This was partly inspired by my wading through gcc -E output
while debugging something else, and seeing too many parens.
This patch does not change the generated .o files on my platform.
This saves several words in the hash table object at the cost of an
indirection at runtime. This seems to be a gain in overall
performance.
FIXME: We cache hash test objects in a rather clumsy way. A better
solution is sought.
* src/lisp.h (struct Lisp_Hash_Table): Use a pointer to the test
struct. All references adapted.
* src/alloc.c (garbage_collect):
* src/fns.c (struct hash_table_user_test, hash_table_user_tests)
(mark_fns, get_hash_table_user_test): New state for caching test
structs, and functions managing it.