mirror of
https://git.savannah.gnu.org/git/emacs.git
synced 2024-11-21 06:55:39 +00:00
(DOHASH): Change calling convention
This leads to simpler code in the users, and more efficient machine code because we don't repeatedly need to fetch the `table_size` and `key_and_value` fields of the hash table object. * src/lisp.h (DOHASH): Rewrite. * src/composite.c (composition_gstring_lookup_cache): Simplify. (composition_gstring_cache_clear_font): * src/print.c (print): * src/pdumper.c (hash_table_contents): * src/minibuf.c (Ftest_completion): * src/json.c (lisp_to_json_nonscalar_1): * src/emacs-module.c (module_global_reference_p): * src/comp.c (compile_function, Fcomp__compile_ctxt_to_file): * src/fns.c (Fmaphash): Adjust to new calling convention.
This commit is contained in:
parent
802821b81a
commit
3018c6e7ba
19
src/comp.c
19
src/comp.c
@ -4330,12 +4330,9 @@ compile_function (Lisp_Object func)
|
||||
declare_block (Qentry);
|
||||
Lisp_Object blocks = CALL1I (comp-func-blocks, func);
|
||||
struct Lisp_Hash_Table *ht = XHASH_TABLE (blocks);
|
||||
DOHASH (ht, i)
|
||||
{
|
||||
Lisp_Object block_name = HASH_KEY (ht, i);
|
||||
if (!EQ (block_name, Qentry))
|
||||
declare_block (block_name);
|
||||
}
|
||||
DOHASH (ht, block_name, block)
|
||||
if (!EQ (block_name, Qentry))
|
||||
declare_block (block_name);
|
||||
|
||||
gcc_jit_block_add_assignment (retrive_block (Qentry),
|
||||
NULL,
|
||||
@ -4343,10 +4340,8 @@ compile_function (Lisp_Object func)
|
||||
gcc_jit_lvalue_as_rvalue (comp.func_relocs));
|
||||
|
||||
|
||||
DOHASH (ht, i)
|
||||
DOHASH (ht, block_name, block)
|
||||
{
|
||||
Lisp_Object block_name = HASH_KEY (ht, i);
|
||||
Lisp_Object block = HASH_VALUE (ht, i);
|
||||
Lisp_Object insns = CALL1I (comp-block-insns, block);
|
||||
if (NILP (block) || NILP (insns))
|
||||
xsignal1 (Qnative_ice,
|
||||
@ -4961,10 +4956,12 @@ DEFUN ("comp--compile-ctxt-to-file", Fcomp__compile_ctxt_to_file,
|
||||
|
||||
struct Lisp_Hash_Table *func_h =
|
||||
XHASH_TABLE (CALL1I (comp-ctxt-funcs-h, Vcomp_ctxt));
|
||||
DOHASH (func_h, i) declare_function (HASH_VALUE (func_h, i));
|
||||
DOHASH (func_h, k, v)
|
||||
declare_function (v);
|
||||
/* Compile all functions. Can't be done before because the
|
||||
relocation structs has to be already defined. */
|
||||
DOHASH (func_h, i) compile_function (HASH_VALUE (func_h, i));
|
||||
DOHASH (func_h, k, v)
|
||||
compile_function (v);
|
||||
|
||||
/* Work around bug#46495 (GCC PR99126). */
|
||||
#if defined (WIDE_EMACS_INT) \
|
||||
|
@ -643,10 +643,7 @@ static Lisp_Object gstring_hash_table;
|
||||
Lisp_Object
|
||||
composition_gstring_lookup_cache (Lisp_Object header)
|
||||
{
|
||||
struct Lisp_Hash_Table *h = XHASH_TABLE (gstring_hash_table);
|
||||
ptrdiff_t i = hash_lookup (h, header);
|
||||
|
||||
return (i >= 0 ? HASH_VALUE (h, i) : Qnil);
|
||||
return Fgethash (header, gstring_hash_table, Qnil);
|
||||
}
|
||||
|
||||
Lisp_Object
|
||||
@ -687,14 +684,9 @@ composition_gstring_cache_clear_font (Lisp_Object font_object)
|
||||
{
|
||||
struct Lisp_Hash_Table *h = XHASH_TABLE (gstring_hash_table);
|
||||
|
||||
DOHASH (h, i)
|
||||
{
|
||||
Lisp_Object k = HASH_KEY (h, i);
|
||||
Lisp_Object gstring = HASH_VALUE (h, i);
|
||||
|
||||
if (EQ (LGSTRING_FONT (gstring), font_object))
|
||||
hash_remove_from_table (h, k);
|
||||
}
|
||||
DOHASH (h, k, gstring)
|
||||
if (EQ (LGSTRING_FONT (gstring), font_object))
|
||||
hash_remove_from_table (h, k);
|
||||
}
|
||||
|
||||
DEFUN ("clear-composition-cache", Fclear_composition_cache,
|
||||
|
@ -410,8 +410,8 @@ module_global_reference_p (emacs_value v, ptrdiff_t *n)
|
||||
struct Lisp_Hash_Table *h = XHASH_TABLE (Vmodule_refs_hash);
|
||||
/* Note that we can't use `hash_lookup' because V might be a local
|
||||
reference that's identical to some global reference. */
|
||||
DOHASH (h, i)
|
||||
if (&XMODULE_GLOBAL_REFERENCE (HASH_VALUE (h, i))->value == v)
|
||||
DOHASH (h, k, val)
|
||||
if (&XMODULE_GLOBAL_REFERENCE (val)->value == v)
|
||||
return true;
|
||||
/* Only used for debugging, so we don't care about overflow, just
|
||||
make sure the operation is defined. */
|
||||
|
@ -5617,7 +5617,7 @@ If KEY is not found, return DFLT which defaults to nil. */)
|
||||
(Lisp_Object key, Lisp_Object table, Lisp_Object dflt)
|
||||
{
|
||||
struct Lisp_Hash_Table *h = check_hash_table (table);
|
||||
ptrdiff_t i = hash_lookup_with_hash (h, key, hash_from_key (h, key));
|
||||
ptrdiff_t i = hash_lookup (h, key);
|
||||
return i >= 0 ? HASH_VALUE (h, i) : dflt;
|
||||
}
|
||||
|
||||
@ -5662,7 +5662,8 @@ set a new value for KEY, or `remhash' to remove KEY.
|
||||
(Lisp_Object function, Lisp_Object table)
|
||||
{
|
||||
struct Lisp_Hash_Table *h = check_hash_table (table);
|
||||
DOHASH (h, i) call2 (function, HASH_KEY (h, i), HASH_VALUE (h, i));
|
||||
DOHASH (h, k, v)
|
||||
call2 (function, k, v);
|
||||
return Qnil;
|
||||
}
|
||||
|
||||
|
@ -361,9 +361,8 @@ lisp_to_json_nonscalar_1 (Lisp_Object lisp,
|
||||
json = json_check (json_object ());
|
||||
count = SPECPDL_INDEX ();
|
||||
record_unwind_protect_ptr (json_release_object, json);
|
||||
DOHASH (h, i)
|
||||
DOHASH (h, key, v)
|
||||
{
|
||||
Lisp_Object key = HASH_KEY (h, i);
|
||||
CHECK_STRING (key);
|
||||
Lisp_Object ekey = json_encode (key);
|
||||
/* We can't specify the length, so the string must be
|
||||
@ -376,7 +375,7 @@ lisp_to_json_nonscalar_1 (Lisp_Object lisp,
|
||||
wrong_type_argument (Qjson_value_p, lisp);
|
||||
int status
|
||||
= json_object_set_new (json, key_str,
|
||||
lisp_to_json (HASH_VALUE (h, i), conf));
|
||||
lisp_to_json (v, conf));
|
||||
if (status == -1)
|
||||
{
|
||||
/* A failure can be caused either by an invalid key or
|
||||
|
20
src/lisp.h
20
src/lisp.h
@ -2598,16 +2598,24 @@ hash_from_key (struct Lisp_Hash_Table *h, Lisp_Object key)
|
||||
return h->test->hashfn (key, h);
|
||||
}
|
||||
|
||||
/* Hash table iteration construct (roughly an inlined maphash):
|
||||
Iterate IDXVAR as index over valid entries of TABLE.
|
||||
/* Iterate K and V as key and value of valid entries in hash table H.
|
||||
The body may remove the current entry or alter its value slot, but not
|
||||
mutate TABLE in any other way. */
|
||||
#define DOHASH(TABLE, IDXVAR) \
|
||||
for (ptrdiff_t IDXVAR = 0; IDXVAR < (TABLE)->table_size; IDXVAR++) \
|
||||
if (hash_unused_entry_key_p (HASH_KEY (TABLE, IDXVAR))) \
|
||||
; \
|
||||
#define DOHASH(h, k, v) \
|
||||
for (Lisp_Object *dohash_##k##_##v##_kv = (h)->key_and_value, \
|
||||
*dohash_##k##_##v##_end = dohash_##k##_##v##_kv \
|
||||
+ 2 * HASH_TABLE_SIZE (h), \
|
||||
k, v; \
|
||||
dohash_##k##_##v##_kv < dohash_##k##_##v##_end \
|
||||
&& (k = dohash_##k##_##v##_kv[0], \
|
||||
v = dohash_##k##_##v##_kv[1], /*maybe unsed*/ (void)v, \
|
||||
true); \
|
||||
dohash_##k##_##v##_kv += 2) \
|
||||
if (hash_unused_entry_key_p (k)) \
|
||||
; \
|
||||
else
|
||||
|
||||
|
||||
void hash_table_thaw (Lisp_Object hash_table);
|
||||
|
||||
/* Default size for hash tables if not specified. */
|
||||
|
@ -2059,8 +2059,7 @@ If COLLECTION is a function, it is called with three arguments:
|
||||
the values STRING, PREDICATE and `lambda'. */)
|
||||
(Lisp_Object string, Lisp_Object collection, Lisp_Object predicate)
|
||||
{
|
||||
Lisp_Object tail, tem = Qnil;
|
||||
ptrdiff_t i = 0;
|
||||
Lisp_Object tail, tem = Qnil, arg = Qnil;
|
||||
|
||||
CHECK_STRING (string);
|
||||
|
||||
@ -2079,7 +2078,7 @@ the values STRING, PREDICATE and `lambda'. */)
|
||||
SBYTES (string));
|
||||
if (completion_ignore_case && !SYMBOLP (tem))
|
||||
{
|
||||
for (i = ASIZE (collection) - 1; i >= 0; i--)
|
||||
for (ptrdiff_t i = ASIZE (collection) - 1; i >= 0; i--)
|
||||
{
|
||||
tail = AREF (collection, i);
|
||||
if (SYMBOLP (tail))
|
||||
@ -2107,24 +2106,27 @@ the values STRING, PREDICATE and `lambda'. */)
|
||||
else if (HASH_TABLE_P (collection))
|
||||
{
|
||||
struct Lisp_Hash_Table *h = XHASH_TABLE (collection);
|
||||
i = hash_lookup (h, string);
|
||||
ptrdiff_t i = hash_lookup (h, string);
|
||||
if (i >= 0)
|
||||
{
|
||||
tem = HASH_KEY (h, i);
|
||||
arg = HASH_VALUE (h, i);
|
||||
goto found_matching_key;
|
||||
}
|
||||
else
|
||||
DOHASH (h, j)
|
||||
DOHASH (h, k, v)
|
||||
{
|
||||
i = j;
|
||||
tem = HASH_KEY (h, i);
|
||||
tem = k;
|
||||
Lisp_Object strkey = (SYMBOLP (tem) ? Fsymbol_name (tem) : tem);
|
||||
if (!STRINGP (strkey)) continue;
|
||||
if (BASE_EQ (Fcompare_strings (string, Qnil, Qnil,
|
||||
strkey, Qnil, Qnil,
|
||||
completion_ignore_case ? Qt : Qnil),
|
||||
Qt))
|
||||
goto found_matching_key;
|
||||
Qt))
|
||||
{
|
||||
arg = v;
|
||||
goto found_matching_key;
|
||||
}
|
||||
}
|
||||
return Qnil;
|
||||
found_matching_key: ;
|
||||
@ -2141,7 +2143,7 @@ the values STRING, PREDICATE and `lambda'. */)
|
||||
if (!NILP (predicate))
|
||||
{
|
||||
return HASH_TABLE_P (collection)
|
||||
? call2 (predicate, tem, HASH_VALUE (XHASH_TABLE (collection), i))
|
||||
? call2 (predicate, tem, arg)
|
||||
: call1 (predicate, tem);
|
||||
}
|
||||
else
|
||||
|
@ -2655,10 +2655,10 @@ hash_table_contents (struct Lisp_Hash_Table *h)
|
||||
indices to stay constant across the dump.
|
||||
FIXME: Remove such dependency on hash table internals (there might
|
||||
be another one in `composition_gstring_from_id`). */
|
||||
DOHASH (h, i)
|
||||
DOHASH (h, k, v)
|
||||
{
|
||||
key_and_value[n++] = HASH_KEY (h, i);
|
||||
key_and_value[n++] = HASH_VALUE (h, i);
|
||||
key_and_value[n++] = k;
|
||||
key_and_value[n++] = v;
|
||||
}
|
||||
|
||||
return key_and_value;
|
||||
|
@ -1285,9 +1285,9 @@ print (Lisp_Object obj, Lisp_Object printcharfun, bool escapeflag)
|
||||
{ /* Remove unnecessary objects, which appear only once in OBJ;
|
||||
that is, whose status is Qt. */
|
||||
struct Lisp_Hash_Table *h = XHASH_TABLE (Vprint_number_table);
|
||||
DOHASH (h, i)
|
||||
if (EQ (HASH_VALUE (h, i), Qt))
|
||||
Fremhash (HASH_KEY (h, i), Vprint_number_table);
|
||||
DOHASH (h, k, v)
|
||||
if (EQ (v, Qt))
|
||||
Fremhash (k, Vprint_number_table);
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user