ChangeLog fix
[bpt/emacs.git] / src / fns.c
CommitLineData
7b863bd5 1/* Random utility Lisp functions.
f0ddbf7b 2
ba318903
PE
3Copyright (C) 1985-1987, 1993-1995, 1997-2014 Free Software Foundation,
4Inc.
7b863bd5
JB
5
6This file is part of GNU Emacs.
7
9ec0b715 8GNU Emacs is free software: you can redistribute it and/or modify
7b863bd5 9it under the terms of the GNU General Public License as published by
9ec0b715
GM
10the Free Software Foundation, either version 3 of the License, or
11(at your option) any later version.
7b863bd5
JB
12
13GNU Emacs is distributed in the hope that it will be useful,
14but WITHOUT ANY WARRANTY; without even the implied warranty of
15MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16GNU General Public License for more details.
17
18You should have received a copy of the GNU General Public License
9ec0b715 19along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
7b863bd5 20
18160b98 21#include <config.h>
7b863bd5 22
dfcf069d 23#include <unistd.h>
58edb572 24#include <time.h>
dfcf069d 25
f03dc6ef
PE
26#include <intprops.h>
27
7b863bd5
JB
28#include "lisp.h"
29#include "commands.h"
38583a69 30#include "character.h"
dec002ca 31#include "coding.h"
7b863bd5 32#include "buffer.h"
f812877e 33#include "keyboard.h"
8feddab4 34#include "keymap.h"
ac811a55 35#include "intervals.h"
2d8e7e1f
RS
36#include "frame.h"
37#include "window.h"
91b11d9d 38#include "blockinput.h"
3df07ecd 39#if defined (HAVE_X_WINDOWS)
dfcf069d
AS
40#include "xterm.h"
41#endif
7b863bd5 42
955cbe7b
PE
43Lisp_Object Qstring_lessp;
44static Lisp_Object Qprovide, Qrequire;
45static Lisp_Object Qyes_or_no_p_history;
eb4ffa4e 46Lisp_Object Qcursor_in_echo_area;
955cbe7b
PE
47static Lisp_Object Qwidget_type;
48static Lisp_Object Qcodeset, Qdays, Qmonths, Qpaper;
7b863bd5 49
7f3f739f
LL
50static Lisp_Object Qmd5, Qsha1, Qsha224, Qsha256, Qsha384, Qsha512;
51
9f4ffeee 52static bool internal_equal (Lisp_Object, Lisp_Object, int, bool, Lisp_Object);
e0f5cf5a 53\f
a7ca3326 54DEFUN ("identity", Fidentity, Sidentity, 1, 1, 0,
ddb67bdc 55 doc: /* Return the argument unchanged. */)
5842a27b 56 (Lisp_Object arg)
7b863bd5
JB
57{
58 return arg;
59}
60
61DEFUN ("random", Frandom, Srandom, 0, 1, 0,
e9d8ddc9 62 doc: /* Return a pseudo-random number.
48de8b12
CY
63All integers representable in Lisp, i.e. between `most-negative-fixnum'
64and `most-positive-fixnum', inclusive, are equally likely.
65
13d62fad
JB
66With positive integer LIMIT, return random number in interval [0,LIMIT).
67With argument t, set the random number seed from the current time and pid.
085d34c4
GM
68With a string argument, set the seed based on the string's contents.
69Other values of LIMIT are ignored.
70
71See Info node `(elisp)Random Numbers' for more details. */)
5842a27b 72 (Lisp_Object limit)
7b863bd5 73{
e2d6972a 74 EMACS_INT val;
7b863bd5 75
13d62fad 76 if (EQ (limit, Qt))
0e23ef9d
PE
77 init_random ();
78 else if (STRINGP (limit))
79 seed_random (SSDATA (limit), SBYTES (limit));
d8ed26bd 80
0e23ef9d 81 val = get_random ();
d16ae622
PE
82 if (INTEGERP (limit) && 0 < XINT (limit))
83 while (true)
84 {
85 /* Return the remainder, except reject the rare case where
86 get_random returns a number so close to INTMASK that the
87 remainder isn't random. */
88 EMACS_INT remainder = val % XINT (limit);
89 if (val - remainder <= INTMASK - XINT (limit) + 1)
90 return make_number (remainder);
91 val = get_random ();
92 }
0e23ef9d 93 return make_number (val);
7b863bd5
JB
94}
95\f
e6966cd6
PE
96/* Heuristic on how many iterations of a tight loop can be safely done
97 before it's time to do a QUIT. This must be a power of 2. */
98enum { QUIT_COUNT_HEURISTIC = 1 << 16 };
99
4a74c818 100/* Random data-structure functions. */
7b863bd5 101
84575e67
PE
102static void
103CHECK_LIST_END (Lisp_Object x, Lisp_Object y)
104{
105 CHECK_TYPE (NILP (x), Qlistp, y);
106}
107
a7ca3326 108DEFUN ("length", Flength, Slength, 1, 1, 0,
e9d8ddc9 109 doc: /* Return the length of vector, list or string SEQUENCE.
47cebab1 110A byte-code function object is also allowed.
f5965ada 111If the string contains multibyte characters, this is not necessarily
47cebab1 112the number of bytes in the string; it is the number of characters.
adf2c803 113To get the number of bytes, use `string-bytes'. */)
5842a27b 114 (register Lisp_Object sequence)
7b863bd5 115{
504f24f1 116 register Lisp_Object val;
7b863bd5 117
88fe8140 118 if (STRINGP (sequence))
d5db4077 119 XSETFASTINT (val, SCHARS (sequence));
88fe8140 120 else if (VECTORP (sequence))
7edbb0da 121 XSETFASTINT (val, ASIZE (sequence));
88fe8140 122 else if (CHAR_TABLE_P (sequence))
64a5094a 123 XSETFASTINT (val, MAX_CHAR);
88fe8140 124 else if (BOOL_VECTOR_P (sequence))
1c0a7493 125 XSETFASTINT (val, bool_vector_size (sequence));
876c194c
SM
126 else if (COMPILEDP (sequence))
127 XSETFASTINT (val, ASIZE (sequence) & PSEUDOVECTOR_SIZE_MASK);
88fe8140 128 else if (CONSP (sequence))
7b863bd5 129 {
00c604f2
PE
130 EMACS_INT i = 0;
131
132 do
7b863bd5 133 {
7843e09c 134 ++i;
e6966cd6 135 if ((i & (QUIT_COUNT_HEURISTIC - 1)) == 0)
00c604f2
PE
136 {
137 if (MOST_POSITIVE_FIXNUM < i)
138 error ("List too long");
139 QUIT;
140 }
7843e09c 141 sequence = XCDR (sequence);
7b863bd5 142 }
00c604f2 143 while (CONSP (sequence));
7b863bd5 144
89662fc3 145 CHECK_LIST_END (sequence, sequence);
f2be3671
GM
146
147 val = make_number (i);
7b863bd5 148 }
88fe8140 149 else if (NILP (sequence))
a2ad3e19 150 XSETFASTINT (val, 0);
7b863bd5 151 else
692ae65c 152 wrong_type_argument (Qsequencep, sequence);
89662fc3 153
a2ad3e19 154 return val;
7b863bd5
JB
155}
156
5a30fab8 157DEFUN ("safe-length", Fsafe_length, Ssafe_length, 1, 1, 0,
e9d8ddc9 158 doc: /* Return the length of a list, but avoid error or infinite loop.
47cebab1
GM
159This function never gets an error. If LIST is not really a list,
160it returns 0. If LIST is circular, it returns a finite value
adf2c803 161which is at least the number of distinct elements. */)
5842a27b 162 (Lisp_Object list)
5a30fab8 163{
e6966cd6
PE
164 Lisp_Object tail, halftail;
165 double hilen = 0;
166 uintmax_t lolen = 1;
167
168 if (! CONSP (list))
ff2bc410 169 return make_number (0);
5a30fab8
RS
170
171 /* halftail is used to detect circular lists. */
e6966cd6 172 for (tail = halftail = list; ; )
5a30fab8 173 {
e6966cd6
PE
174 tail = XCDR (tail);
175 if (! CONSP (tail))
cb3d1a0a 176 break;
e6966cd6
PE
177 if (EQ (tail, halftail))
178 break;
179 lolen++;
180 if ((lolen & 1) == 0)
181 {
182 halftail = XCDR (halftail);
183 if ((lolen & (QUIT_COUNT_HEURISTIC - 1)) == 0)
184 {
185 QUIT;
186 if (lolen == 0)
187 hilen += UINTMAX_MAX + 1.0;
188 }
189 }
5a30fab8
RS
190 }
191
e6966cd6
PE
192 /* If the length does not fit into a fixnum, return a float.
193 On all known practical machines this returns an upper bound on
194 the true length. */
195 return hilen ? make_float (hilen + lolen) : make_fixnum_or_float (lolen);
5a30fab8
RS
196}
197
91f78c99 198DEFUN ("string-bytes", Fstring_bytes, Sstring_bytes, 1, 1, 0,
e9d8ddc9 199 doc: /* Return the number of bytes in STRING.
eeb7eaa8 200If STRING is multibyte, this may be greater than the length of STRING. */)
5842a27b 201 (Lisp_Object string)
026f59ce 202{
b7826503 203 CHECK_STRING (string);
d5db4077 204 return make_number (SBYTES (string));
026f59ce
RS
205}
206
a7ca3326 207DEFUN ("string-equal", Fstring_equal, Sstring_equal, 2, 2, 0,
e9d8ddc9 208 doc: /* Return t if two strings have identical contents.
47cebab1 209Case is significant, but text properties are ignored.
adf2c803 210Symbols are also allowed; their print names are used instead. */)
5842a27b 211 (register Lisp_Object s1, Lisp_Object s2)
7b863bd5 212{
7650760e 213 if (SYMBOLP (s1))
c06583e1 214 s1 = SYMBOL_NAME (s1);
7650760e 215 if (SYMBOLP (s2))
c06583e1 216 s2 = SYMBOL_NAME (s2);
b7826503
PJ
217 CHECK_STRING (s1);
218 CHECK_STRING (s2);
7b863bd5 219
d5db4077
KR
220 if (SCHARS (s1) != SCHARS (s2)
221 || SBYTES (s1) != SBYTES (s2)
72af86bd 222 || memcmp (SDATA (s1), SDATA (s2), SBYTES (s1)))
7b863bd5
JB
223 return Qnil;
224 return Qt;
225}
226
a7ca3326 227DEFUN ("compare-strings", Fcompare_strings, Scompare_strings, 6, 7, 0,
b756c005 228 doc: /* Compare the contents of two strings, converting to multibyte if needed.
5bec25eb
CY
229The arguments START1, END1, START2, and END2, if non-nil, are
230positions specifying which parts of STR1 or STR2 to compare. In
231string STR1, compare the part between START1 (inclusive) and END1
232\(exclusive). If START1 is nil, it defaults to 0, the beginning of
233the string; if END1 is nil, it defaults to the length of the string.
234Likewise, in string STR2, compare the part between START2 and END2.
235
236The strings are compared by the numeric values of their characters.
237For instance, STR1 is "less than" STR2 if its first differing
238character has a smaller numeric value. If IGNORE-CASE is non-nil,
239characters are converted to lower-case before comparing them. Unibyte
240strings are converted to multibyte for comparison.
47cebab1
GM
241
242The value is t if the strings (or specified portions) match.
243If string STR1 is less, the value is a negative number N;
244 - 1 - N is the number of characters that match at the beginning.
245If string STR1 is greater, the value is a positive number N;
adf2c803 246 N - 1 is the number of characters that match at the beginning. */)
5842a27b 247 (Lisp_Object str1, Lisp_Object start1, Lisp_Object end1, Lisp_Object str2, Lisp_Object start2, Lisp_Object end2, Lisp_Object ignore_case)
0e1e9f8d 248{
d311d28c
PE
249 register ptrdiff_t end1_char, end2_char;
250 register ptrdiff_t i1, i1_byte, i2, i2_byte;
0e1e9f8d 251
b7826503
PJ
252 CHECK_STRING (str1);
253 CHECK_STRING (str2);
0e1e9f8d
RS
254 if (NILP (start1))
255 start1 = make_number (0);
256 if (NILP (start2))
257 start2 = make_number (0);
b7826503
PJ
258 CHECK_NATNUM (start1);
259 CHECK_NATNUM (start2);
0e1e9f8d 260 if (! NILP (end1))
b7826503 261 CHECK_NATNUM (end1);
0e1e9f8d 262 if (! NILP (end2))
b7826503 263 CHECK_NATNUM (end2);
0e1e9f8d 264
d5db4077 265 end1_char = SCHARS (str1);
0e1e9f8d
RS
266 if (! NILP (end1) && end1_char > XINT (end1))
267 end1_char = XINT (end1);
d311d28c
PE
268 if (end1_char < XINT (start1))
269 args_out_of_range (str1, start1);
0e1e9f8d 270
d5db4077 271 end2_char = SCHARS (str2);
0e1e9f8d
RS
272 if (! NILP (end2) && end2_char > XINT (end2))
273 end2_char = XINT (end2);
d311d28c
PE
274 if (end2_char < XINT (start2))
275 args_out_of_range (str2, start2);
276
277 i1 = XINT (start1);
278 i2 = XINT (start2);
279
280 i1_byte = string_char_to_byte (str1, i1);
281 i2_byte = string_char_to_byte (str2, i2);
0e1e9f8d
RS
282
283 while (i1 < end1_char && i2 < end2_char)
284 {
285 /* When we find a mismatch, we must compare the
286 characters, not just the bytes. */
287 int c1, c2;
288
289 if (STRING_MULTIBYTE (str1))
2efdd1b9 290 FETCH_STRING_CHAR_ADVANCE_NO_CHECK (c1, str1, i1, i1_byte);
0e1e9f8d
RS
291 else
292 {
d5db4077 293 c1 = SREF (str1, i1++);
4c0354d7 294 MAKE_CHAR_MULTIBYTE (c1);
0e1e9f8d
RS
295 }
296
297 if (STRING_MULTIBYTE (str2))
2efdd1b9 298 FETCH_STRING_CHAR_ADVANCE_NO_CHECK (c2, str2, i2, i2_byte);
0e1e9f8d
RS
299 else
300 {
d5db4077 301 c2 = SREF (str2, i2++);
4c0354d7 302 MAKE_CHAR_MULTIBYTE (c2);
0e1e9f8d
RS
303 }
304
305 if (c1 == c2)
306 continue;
307
308 if (! NILP (ignore_case))
309 {
310 Lisp_Object tem;
311
312 tem = Fupcase (make_number (c1));
313 c1 = XINT (tem);
314 tem = Fupcase (make_number (c2));
315 c2 = XINT (tem);
316 }
317
318 if (c1 == c2)
319 continue;
320
321 /* Note that I1 has already been incremented
322 past the character that we are comparing;
323 hence we don't add or subtract 1 here. */
324 if (c1 < c2)
60f8d735 325 return make_number (- i1 + XINT (start1));
0e1e9f8d 326 else
60f8d735 327 return make_number (i1 - XINT (start1));
0e1e9f8d
RS
328 }
329
330 if (i1 < end1_char)
331 return make_number (i1 - XINT (start1) + 1);
332 if (i2 < end2_char)
333 return make_number (- i1 + XINT (start1) - 1);
334
335 return Qt;
336}
337
a7ca3326 338DEFUN ("string-lessp", Fstring_lessp, Sstring_lessp, 2, 2, 0,
e9d8ddc9 339 doc: /* Return t if first arg string is less than second in lexicographic order.
47cebab1 340Case is significant.
adf2c803 341Symbols are also allowed; their print names are used instead. */)
5842a27b 342 (register Lisp_Object s1, Lisp_Object s2)
7b863bd5 343{
d311d28c
PE
344 register ptrdiff_t end;
345 register ptrdiff_t i1, i1_byte, i2, i2_byte;
7b863bd5 346
7650760e 347 if (SYMBOLP (s1))
c06583e1 348 s1 = SYMBOL_NAME (s1);
7650760e 349 if (SYMBOLP (s2))
c06583e1 350 s2 = SYMBOL_NAME (s2);
b7826503
PJ
351 CHECK_STRING (s1);
352 CHECK_STRING (s2);
7b863bd5 353
09ab3c3b
KH
354 i1 = i1_byte = i2 = i2_byte = 0;
355
d5db4077
KR
356 end = SCHARS (s1);
357 if (end > SCHARS (s2))
358 end = SCHARS (s2);
7b863bd5 359
09ab3c3b 360 while (i1 < end)
7b863bd5 361 {
09ab3c3b
KH
362 /* When we find a mismatch, we must compare the
363 characters, not just the bytes. */
364 int c1, c2;
365
2efdd1b9
KH
366 FETCH_STRING_CHAR_ADVANCE (c1, s1, i1, i1_byte);
367 FETCH_STRING_CHAR_ADVANCE (c2, s2, i2, i2_byte);
09ab3c3b
KH
368
369 if (c1 != c2)
370 return c1 < c2 ? Qt : Qnil;
7b863bd5 371 }
d5db4077 372 return i1 < SCHARS (s2) ? Qt : Qnil;
7b863bd5
JB
373}
374\f
f66c7cf8 375static Lisp_Object concat (ptrdiff_t nargs, Lisp_Object *args,
f75d7a91 376 enum Lisp_Type target_type, bool last_special);
7b863bd5
JB
377
378/* ARGSUSED */
379Lisp_Object
971de7fb 380concat2 (Lisp_Object s1, Lisp_Object s2)
7b863bd5 381{
7b863bd5
JB
382 Lisp_Object args[2];
383 args[0] = s1;
384 args[1] = s2;
385 return concat (2, args, Lisp_String, 0);
7b863bd5
JB
386}
387
d4af3687
RS
388/* ARGSUSED */
389Lisp_Object
971de7fb 390concat3 (Lisp_Object s1, Lisp_Object s2, Lisp_Object s3)
d4af3687 391{
d4af3687
RS
392 Lisp_Object args[3];
393 args[0] = s1;
394 args[1] = s2;
395 args[2] = s3;
396 return concat (3, args, Lisp_String, 0);
d4af3687
RS
397}
398
a7ca3326 399DEFUN ("append", Fappend, Sappend, 0, MANY, 0,
e9d8ddc9 400 doc: /* Concatenate all the arguments and make the result a list.
47cebab1
GM
401The result is a list whose elements are the elements of all the arguments.
402Each argument may be a list, vector or string.
4bf8e2a3
MB
403The last argument is not copied, just used as the tail of the new list.
404usage: (append &rest SEQUENCES) */)
f66c7cf8 405 (ptrdiff_t nargs, Lisp_Object *args)
7b863bd5
JB
406{
407 return concat (nargs, args, Lisp_Cons, 1);
408}
409
a7ca3326 410DEFUN ("concat", Fconcat, Sconcat, 0, MANY, 0,
e9d8ddc9 411 doc: /* Concatenate all the arguments and make the result a string.
47cebab1 412The result is a string whose elements are the elements of all the arguments.
4bf8e2a3
MB
413Each argument may be a string or a list or vector of characters (integers).
414usage: (concat &rest SEQUENCES) */)
f66c7cf8 415 (ptrdiff_t nargs, Lisp_Object *args)
7b863bd5
JB
416{
417 return concat (nargs, args, Lisp_String, 0);
418}
419
a7ca3326 420DEFUN ("vconcat", Fvconcat, Svconcat, 0, MANY, 0,
e9d8ddc9 421 doc: /* Concatenate all the arguments and make the result a vector.
47cebab1 422The result is a vector whose elements are the elements of all the arguments.
4bf8e2a3
MB
423Each argument may be a list, vector or string.
424usage: (vconcat &rest SEQUENCES) */)
f66c7cf8 425 (ptrdiff_t nargs, Lisp_Object *args)
7b863bd5 426{
3e7383eb 427 return concat (nargs, args, Lisp_Vectorlike, 0);
7b863bd5
JB
428}
429
3720677d 430
a7ca3326 431DEFUN ("copy-sequence", Fcopy_sequence, Scopy_sequence, 1, 1, 0,
7652ade0 432 doc: /* Return a copy of a list, vector, string or char-table.
47cebab1 433The elements of a list or vector are not copied; they are shared
adf2c803 434with the original. */)
5842a27b 435 (Lisp_Object arg)
7b863bd5 436{
265a9e55 437 if (NILP (arg)) return arg;
e03f7933
RS
438
439 if (CHAR_TABLE_P (arg))
440 {
38583a69 441 return copy_char_table (arg);
e03f7933
RS
442 }
443
444 if (BOOL_VECTOR_P (arg))
445 {
2cf00efc
PE
446 EMACS_INT nbits = bool_vector_size (arg);
447 ptrdiff_t nbytes = bool_vector_bytes (nbits);
448 Lisp_Object val = make_uninit_bool_vector (nbits);
449 memcpy (bool_vector_data (val), bool_vector_data (arg), nbytes);
e03f7933
RS
450 return val;
451 }
452
7650760e 453 if (!CONSP (arg) && !VECTORP (arg) && !STRINGP (arg))
89662fc3
KS
454 wrong_type_argument (Qsequencep, arg);
455
210272ce 456 return concat (1, &arg, XTYPE (arg), 0);
7b863bd5
JB
457}
458
2d6115c8
KH
459/* This structure holds information of an argument of `concat' that is
460 a string and has text properties to be copied. */
87f0532f 461struct textprop_rec
2d6115c8 462{
f66c7cf8 463 ptrdiff_t argnum; /* refer to ARGS (arguments of `concat') */
d311d28c
PE
464 ptrdiff_t from; /* refer to ARGS[argnum] (argument string) */
465 ptrdiff_t to; /* refer to VAL (the target string) */
2d6115c8
KH
466};
467
7b863bd5 468static Lisp_Object
f66c7cf8 469concat (ptrdiff_t nargs, Lisp_Object *args,
f75d7a91 470 enum Lisp_Type target_type, bool last_special)
7b863bd5
JB
471{
472 Lisp_Object val;
f75d7a91
PE
473 Lisp_Object tail;
474 Lisp_Object this;
d311d28c
PE
475 ptrdiff_t toindex;
476 ptrdiff_t toindex_byte = 0;
f75d7a91
PE
477 EMACS_INT result_len;
478 EMACS_INT result_len_byte;
f66c7cf8 479 ptrdiff_t argnum;
7b863bd5
JB
480 Lisp_Object last_tail;
481 Lisp_Object prev;
f75d7a91 482 bool some_multibyte;
2d6115c8 483 /* When we make a multibyte string, we can't copy text properties
66699ad3
PE
484 while concatenating each string because the length of resulting
485 string can't be decided until we finish the whole concatenation.
2d6115c8 486 So, we record strings that have text properties to be copied
66699ad3 487 here, and copy the text properties after the concatenation. */
093386ca 488 struct textprop_rec *textprops = NULL;
78edd3b7 489 /* Number of elements in textprops. */
f66c7cf8 490 ptrdiff_t num_textprops = 0;
2ec7f67a 491 USE_SAFE_ALLOCA;
7b863bd5 492
093386ca
GM
493 tail = Qnil;
494
7b863bd5
JB
495 /* In append, the last arg isn't treated like the others */
496 if (last_special && nargs > 0)
497 {
498 nargs--;
499 last_tail = args[nargs];
500 }
501 else
502 last_tail = Qnil;
503
89662fc3 504 /* Check each argument. */
7b863bd5
JB
505 for (argnum = 0; argnum < nargs; argnum++)
506 {
507 this = args[argnum];
7650760e 508 if (!(CONSP (this) || NILP (this) || VECTORP (this) || STRINGP (this)
876c194c 509 || COMPILEDP (this) || BOOL_VECTOR_P (this)))
89662fc3 510 wrong_type_argument (Qsequencep, this);
7b863bd5
JB
511 }
512
ea35ce3d
RS
513 /* Compute total length in chars of arguments in RESULT_LEN.
514 If desired output is a string, also compute length in bytes
515 in RESULT_LEN_BYTE, and determine in SOME_MULTIBYTE
516 whether the result should be a multibyte string. */
517 result_len_byte = 0;
518 result_len = 0;
519 some_multibyte = 0;
520 for (argnum = 0; argnum < nargs; argnum++)
7b863bd5 521 {
e6d4aefa 522 EMACS_INT len;
7b863bd5 523 this = args[argnum];
ea35ce3d
RS
524 len = XFASTINT (Flength (this));
525 if (target_type == Lisp_String)
5b6dddaa 526 {
09ab3c3b
KH
527 /* We must count the number of bytes needed in the string
528 as well as the number of characters. */
d311d28c 529 ptrdiff_t i;
5b6dddaa 530 Lisp_Object ch;
c1f134b5 531 int c;
d311d28c 532 ptrdiff_t this_len_byte;
5b6dddaa 533
876c194c 534 if (VECTORP (this) || COMPILEDP (this))
ea35ce3d 535 for (i = 0; i < len; i++)
dec58e65 536 {
7edbb0da 537 ch = AREF (this, i);
63db3c1b 538 CHECK_CHARACTER (ch);
c1f134b5
PE
539 c = XFASTINT (ch);
540 this_len_byte = CHAR_BYTES (c);
d311d28c
PE
541 if (STRING_BYTES_BOUND - result_len_byte < this_len_byte)
542 string_overflow ();
ea35ce3d 543 result_len_byte += this_len_byte;
c1f134b5 544 if (! ASCII_CHAR_P (c) && ! CHAR_BYTE8_P (c))
ea35ce3d 545 some_multibyte = 1;
dec58e65 546 }
1c0a7493 547 else if (BOOL_VECTOR_P (this) && bool_vector_size (this) > 0)
6d475204 548 wrong_type_argument (Qintegerp, Faref (this, make_number (0)));
ea35ce3d 549 else if (CONSP (this))
70949dac 550 for (; CONSP (this); this = XCDR (this))
dec58e65 551 {
70949dac 552 ch = XCAR (this);
63db3c1b 553 CHECK_CHARACTER (ch);
c1f134b5
PE
554 c = XFASTINT (ch);
555 this_len_byte = CHAR_BYTES (c);
d311d28c
PE
556 if (STRING_BYTES_BOUND - result_len_byte < this_len_byte)
557 string_overflow ();
ea35ce3d 558 result_len_byte += this_len_byte;
c1f134b5 559 if (! ASCII_CHAR_P (c) && ! CHAR_BYTE8_P (c))
ea35ce3d 560 some_multibyte = 1;
dec58e65 561 }
470730a8 562 else if (STRINGP (this))
ea35ce3d 563 {
06f57aa7 564 if (STRING_MULTIBYTE (this))
09ab3c3b
KH
565 {
566 some_multibyte = 1;
d311d28c 567 this_len_byte = SBYTES (this);
09ab3c3b
KH
568 }
569 else
d311d28c
PE
570 this_len_byte = count_size_as_multibyte (SDATA (this),
571 SCHARS (this));
572 if (STRING_BYTES_BOUND - result_len_byte < this_len_byte)
573 string_overflow ();
574 result_len_byte += this_len_byte;
ea35ce3d 575 }
5b6dddaa 576 }
ea35ce3d
RS
577
578 result_len += len;
d311d28c
PE
579 if (MOST_POSITIVE_FIXNUM < result_len)
580 memory_full (SIZE_MAX);
7b863bd5
JB
581 }
582
09ab3c3b
KH
583 if (! some_multibyte)
584 result_len_byte = result_len;
7b863bd5 585
ea35ce3d 586 /* Create the output object. */
7b863bd5 587 if (target_type == Lisp_Cons)
ea35ce3d 588 val = Fmake_list (make_number (result_len), Qnil);
3e7383eb 589 else if (target_type == Lisp_Vectorlike)
ea35ce3d 590 val = Fmake_vector (make_number (result_len), Qnil);
b10b2daa 591 else if (some_multibyte)
ea35ce3d 592 val = make_uninit_multibyte_string (result_len, result_len_byte);
b10b2daa
RS
593 else
594 val = make_uninit_string (result_len);
7b863bd5 595
09ab3c3b
KH
596 /* In `append', if all but last arg are nil, return last arg. */
597 if (target_type == Lisp_Cons && EQ (val, Qnil))
598 return last_tail;
7b863bd5 599
ea35ce3d 600 /* Copy the contents of the args into the result. */
7b863bd5 601 if (CONSP (val))
2d6115c8 602 tail = val, toindex = -1; /* -1 in toindex is flag we are making a list */
7b863bd5 603 else
ea35ce3d 604 toindex = 0, toindex_byte = 0;
7b863bd5
JB
605
606 prev = Qnil;
2d6115c8 607 if (STRINGP (val))
0065d054 608 SAFE_NALLOCA (textprops, 1, nargs);
7b863bd5
JB
609
610 for (argnum = 0; argnum < nargs; argnum++)
611 {
612 Lisp_Object thislen;
d311d28c
PE
613 ptrdiff_t thisleni = 0;
614 register ptrdiff_t thisindex = 0;
615 register ptrdiff_t thisindex_byte = 0;
7b863bd5
JB
616
617 this = args[argnum];
618 if (!CONSP (this))
619 thislen = Flength (this), thisleni = XINT (thislen);
620
ea35ce3d
RS
621 /* Between strings of the same kind, copy fast. */
622 if (STRINGP (this) && STRINGP (val)
623 && STRING_MULTIBYTE (this) == some_multibyte)
7b863bd5 624 {
d311d28c 625 ptrdiff_t thislen_byte = SBYTES (this);
2d6115c8 626
72af86bd 627 memcpy (SDATA (val) + toindex_byte, SDATA (this), SBYTES (this));
0c94c8d6 628 if (string_intervals (this))
2d6115c8 629 {
87f0532f 630 textprops[num_textprops].argnum = argnum;
38583a69 631 textprops[num_textprops].from = 0;
87f0532f 632 textprops[num_textprops++].to = toindex;
2d6115c8 633 }
ea35ce3d 634 toindex_byte += thislen_byte;
38583a69 635 toindex += thisleni;
ea35ce3d 636 }
09ab3c3b
KH
637 /* Copy a single-byte string to a multibyte string. */
638 else if (STRINGP (this) && STRINGP (val))
639 {
0c94c8d6 640 if (string_intervals (this))
2d6115c8 641 {
87f0532f
KH
642 textprops[num_textprops].argnum = argnum;
643 textprops[num_textprops].from = 0;
644 textprops[num_textprops++].to = toindex;
2d6115c8 645 }
d5db4077
KR
646 toindex_byte += copy_text (SDATA (this),
647 SDATA (val) + toindex_byte,
648 SCHARS (this), 0, 1);
09ab3c3b
KH
649 toindex += thisleni;
650 }
ea35ce3d
RS
651 else
652 /* Copy element by element. */
653 while (1)
654 {
655 register Lisp_Object elt;
656
657 /* Fetch next element of `this' arg into `elt', or break if
658 `this' is exhausted. */
659 if (NILP (this)) break;
660 if (CONSP (this))
70949dac 661 elt = XCAR (this), this = XCDR (this);
6a7df83b
RS
662 else if (thisindex >= thisleni)
663 break;
664 else if (STRINGP (this))
ea35ce3d 665 {
2cef5737 666 int c;
6a7df83b 667 if (STRING_MULTIBYTE (this))
c1f134b5
PE
668 FETCH_STRING_CHAR_ADVANCE_NO_CHECK (c, this,
669 thisindex,
670 thisindex_byte);
6a7df83b 671 else
ea35ce3d 672 {
c1f134b5
PE
673 c = SREF (this, thisindex); thisindex++;
674 if (some_multibyte && !ASCII_CHAR_P (c))
675 c = BYTE8_TO_CHAR (c);
ea35ce3d 676 }
c1f134b5 677 XSETFASTINT (elt, c);
6a7df83b
RS
678 }
679 else if (BOOL_VECTOR_P (this))
680 {
df5b4930 681 elt = bool_vector_ref (this, thisindex);
6a7df83b 682 thisindex++;
ea35ce3d 683 }
6a7df83b 684 else
68b587a6
SM
685 {
686 elt = AREF (this, thisindex);
687 thisindex++;
688 }
7b863bd5 689
ea35ce3d
RS
690 /* Store this element into the result. */
691 if (toindex < 0)
7b863bd5 692 {
f3fbd155 693 XSETCAR (tail, elt);
ea35ce3d 694 prev = tail;
70949dac 695 tail = XCDR (tail);
7b863bd5 696 }
ea35ce3d 697 else if (VECTORP (val))
68b587a6
SM
698 {
699 ASET (val, toindex, elt);
700 toindex++;
701 }
ea35ce3d
RS
702 else
703 {
13bdea59
PE
704 int c;
705 CHECK_CHARACTER (elt);
706 c = XFASTINT (elt);
38583a69 707 if (some_multibyte)
13bdea59 708 toindex_byte += CHAR_STRING (c, SDATA (val) + toindex_byte);
ea35ce3d 709 else
13bdea59 710 SSET (val, toindex_byte++, c);
38583a69 711 toindex++;
ea35ce3d
RS
712 }
713 }
7b863bd5 714 }
265a9e55 715 if (!NILP (prev))
f3fbd155 716 XSETCDR (prev, last_tail);
7b863bd5 717
87f0532f 718 if (num_textprops > 0)
2d6115c8 719 {
33f37824 720 Lisp_Object props;
d311d28c 721 ptrdiff_t last_to_end = -1;
33f37824 722
87f0532f 723 for (argnum = 0; argnum < num_textprops; argnum++)
2d6115c8 724 {
87f0532f 725 this = args[textprops[argnum].argnum];
33f37824
KH
726 props = text_property_list (this,
727 make_number (0),
d5db4077 728 make_number (SCHARS (this)),
33f37824 729 Qnil);
66699ad3 730 /* If successive arguments have properties, be sure that the
33f37824 731 value of `composition' property be the copy. */
3bd00f3b 732 if (last_to_end == textprops[argnum].to)
33f37824
KH
733 make_composition_value_copy (props);
734 add_text_properties_from_list (val, props,
735 make_number (textprops[argnum].to));
d5db4077 736 last_to_end = textprops[argnum].to + SCHARS (this);
2d6115c8
KH
737 }
738 }
2ec7f67a
KS
739
740 SAFE_FREE ();
b4f334f7 741 return val;
7b863bd5
JB
742}
743\f
09ab3c3b 744static Lisp_Object string_char_byte_cache_string;
d311d28c
PE
745static ptrdiff_t string_char_byte_cache_charpos;
746static ptrdiff_t string_char_byte_cache_bytepos;
09ab3c3b 747
57247650 748void
971de7fb 749clear_string_char_byte_cache (void)
57247650
KH
750{
751 string_char_byte_cache_string = Qnil;
752}
753
13818c30 754/* Return the byte index corresponding to CHAR_INDEX in STRING. */
ea35ce3d 755
d311d28c
PE
756ptrdiff_t
757string_char_to_byte (Lisp_Object string, ptrdiff_t char_index)
ea35ce3d 758{
d311d28c
PE
759 ptrdiff_t i_byte;
760 ptrdiff_t best_below, best_below_byte;
761 ptrdiff_t best_above, best_above_byte;
ea35ce3d 762
09ab3c3b 763 best_below = best_below_byte = 0;
d5db4077
KR
764 best_above = SCHARS (string);
765 best_above_byte = SBYTES (string);
95ac7579
KH
766 if (best_above == best_above_byte)
767 return char_index;
09ab3c3b
KH
768
769 if (EQ (string, string_char_byte_cache_string))
770 {
771 if (string_char_byte_cache_charpos < char_index)
772 {
773 best_below = string_char_byte_cache_charpos;
774 best_below_byte = string_char_byte_cache_bytepos;
775 }
776 else
777 {
778 best_above = string_char_byte_cache_charpos;
779 best_above_byte = string_char_byte_cache_bytepos;
780 }
781 }
782
783 if (char_index - best_below < best_above - char_index)
784 {
8f924df7 785 unsigned char *p = SDATA (string) + best_below_byte;
38583a69 786
09ab3c3b
KH
787 while (best_below < char_index)
788 {
38583a69
KH
789 p += BYTES_BY_CHAR_HEAD (*p);
790 best_below++;
09ab3c3b 791 }
8f924df7 792 i_byte = p - SDATA (string);
09ab3c3b
KH
793 }
794 else
ea35ce3d 795 {
8f924df7 796 unsigned char *p = SDATA (string) + best_above_byte;
38583a69 797
09ab3c3b
KH
798 while (best_above > char_index)
799 {
38583a69
KH
800 p--;
801 while (!CHAR_HEAD_P (*p)) p--;
09ab3c3b
KH
802 best_above--;
803 }
8f924df7 804 i_byte = p - SDATA (string);
ea35ce3d
RS
805 }
806
09ab3c3b 807 string_char_byte_cache_bytepos = i_byte;
38583a69 808 string_char_byte_cache_charpos = char_index;
09ab3c3b
KH
809 string_char_byte_cache_string = string;
810
ea35ce3d
RS
811 return i_byte;
812}
09ab3c3b 813\f
ea35ce3d
RS
814/* Return the character index corresponding to BYTE_INDEX in STRING. */
815
d311d28c
PE
816ptrdiff_t
817string_byte_to_char (Lisp_Object string, ptrdiff_t byte_index)
ea35ce3d 818{
d311d28c
PE
819 ptrdiff_t i, i_byte;
820 ptrdiff_t best_below, best_below_byte;
821 ptrdiff_t best_above, best_above_byte;
ea35ce3d 822
09ab3c3b 823 best_below = best_below_byte = 0;
d5db4077
KR
824 best_above = SCHARS (string);
825 best_above_byte = SBYTES (string);
95ac7579
KH
826 if (best_above == best_above_byte)
827 return byte_index;
09ab3c3b
KH
828
829 if (EQ (string, string_char_byte_cache_string))
830 {
831 if (string_char_byte_cache_bytepos < byte_index)
832 {
833 best_below = string_char_byte_cache_charpos;
834 best_below_byte = string_char_byte_cache_bytepos;
835 }
836 else
837 {
838 best_above = string_char_byte_cache_charpos;
839 best_above_byte = string_char_byte_cache_bytepos;
840 }
841 }
842
843 if (byte_index - best_below_byte < best_above_byte - byte_index)
844 {
8f924df7
KH
845 unsigned char *p = SDATA (string) + best_below_byte;
846 unsigned char *pend = SDATA (string) + byte_index;
38583a69
KH
847
848 while (p < pend)
09ab3c3b 849 {
38583a69
KH
850 p += BYTES_BY_CHAR_HEAD (*p);
851 best_below++;
09ab3c3b
KH
852 }
853 i = best_below;
8f924df7 854 i_byte = p - SDATA (string);
09ab3c3b
KH
855 }
856 else
ea35ce3d 857 {
8f924df7
KH
858 unsigned char *p = SDATA (string) + best_above_byte;
859 unsigned char *pbeg = SDATA (string) + byte_index;
38583a69
KH
860
861 while (p > pbeg)
09ab3c3b 862 {
38583a69
KH
863 p--;
864 while (!CHAR_HEAD_P (*p)) p--;
09ab3c3b
KH
865 best_above--;
866 }
867 i = best_above;
8f924df7 868 i_byte = p - SDATA (string);
ea35ce3d
RS
869 }
870
09ab3c3b
KH
871 string_char_byte_cache_bytepos = i_byte;
872 string_char_byte_cache_charpos = i;
873 string_char_byte_cache_string = string;
874
ea35ce3d
RS
875 return i;
876}
09ab3c3b 877\f
9d6d303b 878/* Convert STRING to a multibyte string. */
ea35ce3d 879
2f7c71a1 880static Lisp_Object
971de7fb 881string_make_multibyte (Lisp_Object string)
ea35ce3d
RS
882{
883 unsigned char *buf;
d311d28c 884 ptrdiff_t nbytes;
e76ca790
MB
885 Lisp_Object ret;
886 USE_SAFE_ALLOCA;
ea35ce3d
RS
887
888 if (STRING_MULTIBYTE (string))
889 return string;
890
d5db4077
KR
891 nbytes = count_size_as_multibyte (SDATA (string),
892 SCHARS (string));
6d475204
RS
893 /* If all the chars are ASCII, they won't need any more bytes
894 once converted. In that case, we can return STRING itself. */
d5db4077 895 if (nbytes == SBYTES (string))
6d475204
RS
896 return string;
897
98c6f1e3 898 buf = SAFE_ALLOCA (nbytes);
d5db4077 899 copy_text (SDATA (string), buf, SBYTES (string),
ea35ce3d
RS
900 0, 1);
901
f1e59824 902 ret = make_multibyte_string ((char *) buf, SCHARS (string), nbytes);
233f3db6 903 SAFE_FREE ();
799c08ac
KS
904
905 return ret;
ea35ce3d
RS
906}
907
2df18cdb 908
8f924df7
KH
909/* Convert STRING (if unibyte) to a multibyte string without changing
910 the number of characters. Characters 0200 trough 0237 are
911 converted to eight-bit characters. */
2df18cdb
KH
912
913Lisp_Object
971de7fb 914string_to_multibyte (Lisp_Object string)
2df18cdb
KH
915{
916 unsigned char *buf;
d311d28c 917 ptrdiff_t nbytes;
799c08ac
KS
918 Lisp_Object ret;
919 USE_SAFE_ALLOCA;
2df18cdb
KH
920
921 if (STRING_MULTIBYTE (string))
922 return string;
923
de883a70 924 nbytes = count_size_as_multibyte (SDATA (string), SBYTES (string));
8f924df7
KH
925 /* If all the chars are ASCII, they won't need any more bytes once
926 converted. */
2df18cdb 927 if (nbytes == SBYTES (string))
42a5b22f 928 return make_multibyte_string (SSDATA (string), nbytes, nbytes);
2df18cdb 929
98c6f1e3 930 buf = SAFE_ALLOCA (nbytes);
72af86bd 931 memcpy (buf, SDATA (string), SBYTES (string));
2df18cdb
KH
932 str_to_multibyte (buf, nbytes, SBYTES (string));
933
f1e59824 934 ret = make_multibyte_string ((char *) buf, SCHARS (string), nbytes);
233f3db6 935 SAFE_FREE ();
799c08ac
KS
936
937 return ret;
2df18cdb
KH
938}
939
940
ea35ce3d
RS
941/* Convert STRING to a single-byte string. */
942
943Lisp_Object
971de7fb 944string_make_unibyte (Lisp_Object string)
ea35ce3d 945{
d311d28c 946 ptrdiff_t nchars;
ea35ce3d 947 unsigned char *buf;
a6cb6b78 948 Lisp_Object ret;
799c08ac 949 USE_SAFE_ALLOCA;
ea35ce3d
RS
950
951 if (! STRING_MULTIBYTE (string))
952 return string;
953
799c08ac 954 nchars = SCHARS (string);
ea35ce3d 955
98c6f1e3 956 buf = SAFE_ALLOCA (nchars);
d5db4077 957 copy_text (SDATA (string), buf, SBYTES (string),
ea35ce3d
RS
958 1, 0);
959
f1e59824 960 ret = make_unibyte_string ((char *) buf, nchars);
233f3db6 961 SAFE_FREE ();
a6cb6b78
JD
962
963 return ret;
ea35ce3d 964}
09ab3c3b 965
a7ca3326 966DEFUN ("string-make-multibyte", Fstring_make_multibyte, Sstring_make_multibyte,
09ab3c3b 967 1, 1, 0,
e9d8ddc9 968 doc: /* Return the multibyte equivalent of STRING.
6b61353c
KH
969If STRING is unibyte and contains non-ASCII characters, the function
970`unibyte-char-to-multibyte' is used to convert each unibyte character
971to a multibyte character. In this case, the returned string is a
972newly created string with no text properties. If STRING is multibyte
973or entirely ASCII, it is returned unchanged. In particular, when
974STRING is unibyte and entirely ASCII, the returned string is unibyte.
975\(When the characters are all ASCII, Emacs primitives will treat the
976string the same way whether it is unibyte or multibyte.) */)
5842a27b 977 (Lisp_Object string)
09ab3c3b 978{
b7826503 979 CHECK_STRING (string);
aabd38ec 980
09ab3c3b
KH
981 return string_make_multibyte (string);
982}
983
a7ca3326 984DEFUN ("string-make-unibyte", Fstring_make_unibyte, Sstring_make_unibyte,
09ab3c3b 985 1, 1, 0,
e9d8ddc9 986 doc: /* Return the unibyte equivalent of STRING.
f8f2fbf9
EZ
987Multibyte character codes are converted to unibyte according to
988`nonascii-translation-table' or, if that is nil, `nonascii-insert-offset'.
989If the lookup in the translation table fails, this function takes just
adf2c803 990the low 8 bits of each character. */)
5842a27b 991 (Lisp_Object string)
09ab3c3b 992{
b7826503 993 CHECK_STRING (string);
aabd38ec 994
09ab3c3b
KH
995 return string_make_unibyte (string);
996}
6d475204 997
a7ca3326 998DEFUN ("string-as-unibyte", Fstring_as_unibyte, Sstring_as_unibyte,
6d475204 999 1, 1, 0,
e9d8ddc9 1000 doc: /* Return a unibyte string with the same individual bytes as STRING.
47cebab1
GM
1001If STRING is unibyte, the result is STRING itself.
1002Otherwise it is a newly created string, with no text properties.
1003If STRING is multibyte and contains a character of charset
6b61353c 1004`eight-bit', it is converted to the corresponding single byte. */)
5842a27b 1005 (Lisp_Object string)
6d475204 1006{
b7826503 1007 CHECK_STRING (string);
aabd38ec 1008
6d475204
RS
1009 if (STRING_MULTIBYTE (string))
1010 {
17b9dc45 1011 unsigned char *str = (unsigned char *) xlispstrdup (string);
04d47595 1012 ptrdiff_t bytes = str_as_unibyte (str, SBYTES (string));
2efdd1b9 1013
f1e59824 1014 string = make_unibyte_string ((char *) str, bytes);
2efdd1b9 1015 xfree (str);
6d475204
RS
1016 }
1017 return string;
1018}
1019
a7ca3326 1020DEFUN ("string-as-multibyte", Fstring_as_multibyte, Sstring_as_multibyte,
6d475204 1021 1, 1, 0,
e9d8ddc9 1022 doc: /* Return a multibyte string with the same individual bytes as STRING.
47cebab1
GM
1023If STRING is multibyte, the result is STRING itself.
1024Otherwise it is a newly created string, with no text properties.
2d5cc537 1025
47cebab1 1026If STRING is unibyte and contains an individual 8-bit byte (i.e. not
2d5cc537
DL
1027part of a correct utf-8 sequence), it is converted to the corresponding
1028multibyte character of charset `eight-bit'.
3100d59f
KH
1029See also `string-to-multibyte'.
1030
1031Beware, this often doesn't really do what you think it does.
1032It is similar to (decode-coding-string STRING 'utf-8-emacs).
1033If you're not sure, whether to use `string-as-multibyte' or
1034`string-to-multibyte', use `string-to-multibyte'. */)
5842a27b 1035 (Lisp_Object string)
6d475204 1036{
b7826503 1037 CHECK_STRING (string);
aabd38ec 1038
6d475204
RS
1039 if (! STRING_MULTIBYTE (string))
1040 {
2efdd1b9 1041 Lisp_Object new_string;
d311d28c 1042 ptrdiff_t nchars, nbytes;
2efdd1b9 1043
d5db4077
KR
1044 parse_str_as_multibyte (SDATA (string),
1045 SBYTES (string),
2efdd1b9
KH
1046 &nchars, &nbytes);
1047 new_string = make_uninit_multibyte_string (nchars, nbytes);
72af86bd 1048 memcpy (SDATA (new_string), SDATA (string), SBYTES (string));
d5db4077
KR
1049 if (nbytes != SBYTES (string))
1050 str_as_multibyte (SDATA (new_string), nbytes,
1051 SBYTES (string), NULL);
2efdd1b9 1052 string = new_string;
0c94c8d6 1053 set_string_intervals (string, NULL);
6d475204
RS
1054 }
1055 return string;
1056}
2df18cdb 1057
a7ca3326 1058DEFUN ("string-to-multibyte", Fstring_to_multibyte, Sstring_to_multibyte,
2df18cdb
KH
1059 1, 1, 0,
1060 doc: /* Return a multibyte string with the same individual chars as STRING.
9c7a329a 1061If STRING is multibyte, the result is STRING itself.
2df18cdb 1062Otherwise it is a newly created string, with no text properties.
88dad6e7
KH
1063
1064If STRING is unibyte and contains an 8-bit byte, it is converted to
2d5cc537
DL
1065the corresponding multibyte character of charset `eight-bit'.
1066
1067This differs from `string-as-multibyte' by converting each byte of a correct
1068utf-8 sequence to an eight-bit character, not just bytes that don't form a
1069correct sequence. */)
5842a27b 1070 (Lisp_Object string)
2df18cdb
KH
1071{
1072 CHECK_STRING (string);
1073
1074 return string_to_multibyte (string);
1075}
1076
b4480f16 1077DEFUN ("string-to-unibyte", Fstring_to_unibyte, Sstring_to_unibyte,
6e8b42de 1078 1, 1, 0,
b4480f16
KH
1079 doc: /* Return a unibyte string with the same individual chars as STRING.
1080If STRING is unibyte, the result is STRING itself.
1081Otherwise it is a newly created string, with no text properties,
1082where each `eight-bit' character is converted to the corresponding byte.
1083If STRING contains a non-ASCII, non-`eight-bit' character,
6e8b42de 1084an error is signaled. */)
5842a27b 1085 (Lisp_Object string)
b4480f16
KH
1086{
1087 CHECK_STRING (string);
1088
1089 if (STRING_MULTIBYTE (string))
1090 {
d311d28c 1091 ptrdiff_t chars = SCHARS (string);
23f86fce 1092 unsigned char *str = xmalloc (chars);
67dbec33 1093 ptrdiff_t converted = str_to_unibyte (SDATA (string), str, chars);
6e8b42de 1094
b4480f16 1095 if (converted < chars)
7c85f529 1096 error ("Can't convert the %"pD"dth character to unibyte", converted);
f1e59824 1097 string = make_unibyte_string ((char *) str, chars);
b4480f16
KH
1098 xfree (str);
1099 }
1100 return string;
1101}
1102
ea35ce3d 1103\f
a7ca3326 1104DEFUN ("copy-alist", Fcopy_alist, Scopy_alist, 1, 1, 0,
e9d8ddc9 1105 doc: /* Return a copy of ALIST.
47cebab1
GM
1106This is an alist which represents the same mapping from objects to objects,
1107but does not share the alist structure with ALIST.
1108The objects mapped (cars and cdrs of elements of the alist)
1109are shared, however.
e9d8ddc9 1110Elements of ALIST that are not conses are also shared. */)
5842a27b 1111 (Lisp_Object alist)
7b863bd5
JB
1112{
1113 register Lisp_Object tem;
1114
b7826503 1115 CHECK_LIST (alist);
265a9e55 1116 if (NILP (alist))
7b863bd5
JB
1117 return alist;
1118 alist = concat (1, &alist, Lisp_Cons, 0);
70949dac 1119 for (tem = alist; CONSP (tem); tem = XCDR (tem))
7b863bd5
JB
1120 {
1121 register Lisp_Object car;
70949dac 1122 car = XCAR (tem);
7b863bd5
JB
1123
1124 if (CONSP (car))
f3fbd155 1125 XSETCAR (tem, Fcons (XCAR (car), XCDR (car)));
7b863bd5
JB
1126 }
1127 return alist;
1128}
1129
8ec49c53
PE
1130/* Check that ARRAY can have a valid subarray [FROM..TO),
1131 given that its size is SIZE.
1132 If FROM is nil, use 0; if TO is nil, use SIZE.
1133 Count negative values backwards from the end.
1134 Set *IFROM and *ITO to the two indexes used. */
fbc87aea 1135
8ec49c53
PE
1136static void
1137validate_subarray (Lisp_Object array, Lisp_Object from, Lisp_Object to,
1138 ptrdiff_t size, EMACS_INT *ifrom, EMACS_INT *ito)
fbc87aea 1139{
8ec49c53
PE
1140 EMACS_INT f, t;
1141
1142 if (INTEGERP (from))
fbc87aea 1143 {
8ec49c53
PE
1144 f = XINT (from);
1145 if (f < 0)
1146 f += size;
fbc87aea 1147 }
8ec49c53
PE
1148 else if (NILP (from))
1149 f = 0;
fbc87aea 1150 else
8ec49c53
PE
1151 wrong_type_argument (Qintegerp, from);
1152
1153 if (INTEGERP (to))
fbc87aea 1154 {
8ec49c53
PE
1155 t = XINT (to);
1156 if (t < 0)
1157 t += size;
fbc87aea 1158 }
8ec49c53
PE
1159 else if (NILP (to))
1160 t = size;
1161 else
1162 wrong_type_argument (Qintegerp, to);
1163
1164 if (! (0 <= f && f <= t && t <= size))
1165 args_out_of_range_3 (array, from, to);
fbc87aea 1166
8ec49c53
PE
1167 *ifrom = f;
1168 *ito = t;
fbc87aea
DA
1169}
1170
1171DEFUN ("substring", Fsubstring, Ssubstring, 1, 3, 0,
753169bd
CY
1172 doc: /* Return a new string whose contents are a substring of STRING.
1173The returned string consists of the characters between index FROM
1174\(inclusive) and index TO (exclusive) of STRING. FROM and TO are
1175zero-indexed: 0 means the first character of STRING. Negative values
1176are counted from the end of STRING. If TO is nil, the substring runs
1177to the end of STRING.
1178
1179The STRING argument may also be a vector. In that case, the return
1180value is a new vector that contains the elements between index FROM
fbc87aea
DA
1181\(inclusive) and index TO (exclusive) of that vector argument.
1182
1183With one argument, just copy STRING (with properties, if any). */)
1184 (Lisp_Object string, Lisp_Object from, Lisp_Object to)
7b863bd5 1185{
ac811a55 1186 Lisp_Object res;
d311d28c 1187 ptrdiff_t size;
8ec49c53 1188 EMACS_INT ifrom, ito;
21fbc8e5 1189
21fbc8e5 1190 if (STRINGP (string))
d311d28c 1191 size = SCHARS (string);
fbc87aea 1192 else if (VECTORP (string))
7edbb0da 1193 size = ASIZE (string);
7b863bd5 1194 else
fbc87aea 1195 wrong_type_argument (Qarrayp, string);
8ec49c53
PE
1196
1197 validate_subarray (string, from, to, size, &ifrom, &ito);
8c172e82 1198
21fbc8e5
RS
1199 if (STRINGP (string))
1200 {
8ec49c53
PE
1201 ptrdiff_t from_byte
1202 = !ifrom ? 0 : string_char_to_byte (string, ifrom);
1203 ptrdiff_t to_byte
1204 = ito == size ? SBYTES (string) : string_char_to_byte (string, ito);
42a5b22f 1205 res = make_specified_string (SSDATA (string) + from_byte,
8ec49c53 1206 ito - ifrom, to_byte - from_byte,
b10b2daa 1207 STRING_MULTIBYTE (string));
8ec49c53 1208 copy_text_properties (make_number (ifrom), make_number (ito),
21ab867f 1209 string, make_number (0), res, Qnil);
ea35ce3d
RS
1210 }
1211 else
8ec49c53 1212 res = Fvector (ito - ifrom, aref_addr (string, ifrom));
ea35ce3d
RS
1213
1214 return res;
1215}
1216
aebf4d42
RS
1217
1218DEFUN ("substring-no-properties", Fsubstring_no_properties, Ssubstring_no_properties, 1, 3, 0,
1219 doc: /* Return a substring of STRING, without text properties.
b756c005 1220It starts at index FROM and ends before TO.
aebf4d42
RS
1221TO may be nil or omitted; then the substring runs to the end of STRING.
1222If FROM is nil or omitted, the substring starts at the beginning of STRING.
1223If FROM or TO is negative, it counts from the end.
1224
1225With one argument, just copy STRING without its properties. */)
5842a27b 1226 (Lisp_Object string, register Lisp_Object from, Lisp_Object to)
aebf4d42 1227{
d311d28c 1228 ptrdiff_t size;
e6d4aefa 1229 EMACS_INT from_char, to_char;
d311d28c 1230 ptrdiff_t from_byte, to_byte;
aebf4d42
RS
1231
1232 CHECK_STRING (string);
1233
d5db4077 1234 size = SCHARS (string);
8ec49c53 1235 validate_subarray (string, from, to, size, &from_char, &to_char);
aebf4d42 1236
8ec49c53 1237 from_byte = !from_char ? 0 : string_char_to_byte (string, from_char);
d311d28c 1238 to_byte =
8ec49c53 1239 to_char == size ? SBYTES (string) : string_char_to_byte (string, to_char);
42a5b22f 1240 return make_specified_string (SSDATA (string) + from_byte,
aebf4d42
RS
1241 to_char - from_char, to_byte - from_byte,
1242 STRING_MULTIBYTE (string));
1243}
1244
ea35ce3d
RS
1245/* Extract a substring of STRING, giving start and end positions
1246 both in characters and in bytes. */
1247
1248Lisp_Object
d311d28c
PE
1249substring_both (Lisp_Object string, ptrdiff_t from, ptrdiff_t from_byte,
1250 ptrdiff_t to, ptrdiff_t to_byte)
ea35ce3d
RS
1251{
1252 Lisp_Object res;
d311d28c 1253 ptrdiff_t size;
ea35ce3d 1254
89662fc3 1255 CHECK_VECTOR_OR_STRING (string);
ea35ce3d 1256
0bc0b309 1257 size = STRINGP (string) ? SCHARS (string) : ASIZE (string);
ea35ce3d
RS
1258
1259 if (!(0 <= from && from <= to && to <= size))
1260 args_out_of_range_3 (string, make_number (from), make_number (to));
1261
1262 if (STRINGP (string))
1263 {
42a5b22f 1264 res = make_specified_string (SSDATA (string) + from_byte,
b10b2daa
RS
1265 to - from, to_byte - from_byte,
1266 STRING_MULTIBYTE (string));
21ab867f
AS
1267 copy_text_properties (make_number (from), make_number (to),
1268 string, make_number (0), res, Qnil);
21fbc8e5
RS
1269 }
1270 else
4939150c 1271 res = Fvector (to - from, aref_addr (string, from));
b4f334f7 1272
ac811a55 1273 return res;
7b863bd5
JB
1274}
1275\f
a7ca3326 1276DEFUN ("nthcdr", Fnthcdr, Snthcdr, 2, 2, 0,
b756c005 1277 doc: /* Take cdr N times on LIST, return the result. */)
5842a27b 1278 (Lisp_Object n, Lisp_Object list)
7b863bd5 1279{
6346d301 1280 EMACS_INT i, num;
b7826503 1281 CHECK_NUMBER (n);
7b863bd5 1282 num = XINT (n);
265a9e55 1283 for (i = 0; i < num && !NILP (list); i++)
7b863bd5
JB
1284 {
1285 QUIT;
89662fc3 1286 CHECK_LIST_CONS (list, list);
71a8e74b 1287 list = XCDR (list);
7b863bd5
JB
1288 }
1289 return list;
1290}
1291
a7ca3326 1292DEFUN ("nth", Fnth, Snth, 2, 2, 0,
e9d8ddc9
MB
1293 doc: /* Return the Nth element of LIST.
1294N counts from zero. If LIST is not that long, nil is returned. */)
5842a27b 1295 (Lisp_Object n, Lisp_Object list)
7b863bd5
JB
1296{
1297 return Fcar (Fnthcdr (n, list));
1298}
1299
a7ca3326 1300DEFUN ("elt", Felt, Selt, 2, 2, 0,
e9d8ddc9 1301 doc: /* Return element of SEQUENCE at index N. */)
5842a27b 1302 (register Lisp_Object sequence, Lisp_Object n)
7b863bd5 1303{
b7826503 1304 CHECK_NUMBER (n);
89662fc3
KS
1305 if (CONSP (sequence) || NILP (sequence))
1306 return Fcar (Fnthcdr (n, sequence));
1307
1308 /* Faref signals a "not array" error, so check here. */
876c194c 1309 CHECK_ARRAY (sequence, Qsequencep);
89662fc3 1310 return Faref (sequence, n);
7b863bd5
JB
1311}
1312
a7ca3326 1313DEFUN ("member", Fmember, Smember, 2, 2, 0,
b756c005 1314 doc: /* Return non-nil if ELT is an element of LIST. Comparison done with `equal'.
e9d8ddc9 1315The value is actually the tail of LIST whose car is ELT. */)
5842a27b 1316 (register Lisp_Object elt, Lisp_Object list)
7b863bd5
JB
1317{
1318 register Lisp_Object tail;
9beb8baa 1319 for (tail = list; CONSP (tail); tail = XCDR (tail))
7b863bd5
JB
1320 {
1321 register Lisp_Object tem;
89662fc3 1322 CHECK_LIST_CONS (tail, list);
71a8e74b 1323 tem = XCAR (tail);
265a9e55 1324 if (! NILP (Fequal (elt, tem)))
7b863bd5
JB
1325 return tail;
1326 QUIT;
1327 }
1328 return Qnil;
1329}
1330
a7ca3326 1331DEFUN ("memq", Fmemq, Smemq, 2, 2, 0,
b756c005 1332 doc: /* Return non-nil if ELT is an element of LIST. Comparison done with `eq'.
008ef0ef 1333The value is actually the tail of LIST whose car is ELT. */)
5842a27b 1334 (register Lisp_Object elt, Lisp_Object list)
7b863bd5 1335{
f2be3671 1336 while (1)
7b863bd5 1337 {
f2be3671
GM
1338 if (!CONSP (list) || EQ (XCAR (list), elt))
1339 break;
59f953a2 1340
f2be3671
GM
1341 list = XCDR (list);
1342 if (!CONSP (list) || EQ (XCAR (list), elt))
1343 break;
1344
1345 list = XCDR (list);
1346 if (!CONSP (list) || EQ (XCAR (list), elt))
1347 break;
1348
1349 list = XCDR (list);
7b863bd5
JB
1350 QUIT;
1351 }
f2be3671 1352
89662fc3 1353 CHECK_LIST (list);
f2be3671 1354 return list;
7b863bd5
JB
1355}
1356
008ef0ef 1357DEFUN ("memql", Fmemql, Smemql, 2, 2, 0,
b756c005 1358 doc: /* Return non-nil if ELT is an element of LIST. Comparison done with `eql'.
008ef0ef 1359The value is actually the tail of LIST whose car is ELT. */)
5842a27b 1360 (register Lisp_Object elt, Lisp_Object list)
008ef0ef
KS
1361{
1362 register Lisp_Object tail;
1363
1364 if (!FLOATP (elt))
1365 return Fmemq (elt, list);
1366
9beb8baa 1367 for (tail = list; CONSP (tail); tail = XCDR (tail))
008ef0ef
KS
1368 {
1369 register Lisp_Object tem;
1370 CHECK_LIST_CONS (tail, list);
1371 tem = XCAR (tail);
9f4ffeee 1372 if (FLOATP (tem) && internal_equal (elt, tem, 0, 0, Qnil))
008ef0ef
KS
1373 return tail;
1374 QUIT;
1375 }
1376 return Qnil;
1377}
1378
a7ca3326 1379DEFUN ("assq", Fassq, Sassq, 2, 2, 0,
e9d8ddc9 1380 doc: /* Return non-nil if KEY is `eq' to the car of an element of LIST.
6b61353c 1381The value is actually the first element of LIST whose car is KEY.
e9d8ddc9 1382Elements of LIST that are not conses are ignored. */)
5842a27b 1383 (Lisp_Object key, Lisp_Object list)
7b863bd5 1384{
f2be3671 1385 while (1)
7b863bd5 1386 {
f2be3671
GM
1387 if (!CONSP (list)
1388 || (CONSP (XCAR (list))
1389 && EQ (XCAR (XCAR (list)), key)))
1390 break;
59f953a2 1391
f2be3671
GM
1392 list = XCDR (list);
1393 if (!CONSP (list)
1394 || (CONSP (XCAR (list))
1395 && EQ (XCAR (XCAR (list)), key)))
1396 break;
59f953a2 1397
f2be3671
GM
1398 list = XCDR (list);
1399 if (!CONSP (list)
1400 || (CONSP (XCAR (list))
1401 && EQ (XCAR (XCAR (list)), key)))
1402 break;
59f953a2 1403
f2be3671 1404 list = XCDR (list);
7b863bd5
JB
1405 QUIT;
1406 }
f2be3671 1407
89662fc3 1408 return CAR (list);
7b863bd5
JB
1409}
1410
1411/* Like Fassq but never report an error and do not allow quits.
1412 Use only on lists known never to be circular. */
1413
1414Lisp_Object
971de7fb 1415assq_no_quit (Lisp_Object key, Lisp_Object list)
7b863bd5 1416{
f2be3671
GM
1417 while (CONSP (list)
1418 && (!CONSP (XCAR (list))
1419 || !EQ (XCAR (XCAR (list)), key)))
1420 list = XCDR (list);
1421
89662fc3 1422 return CAR_SAFE (list);
7b863bd5
JB
1423}
1424
a7ca3326 1425DEFUN ("assoc", Fassoc, Sassoc, 2, 2, 0,
e9d8ddc9 1426 doc: /* Return non-nil if KEY is `equal' to the car of an element of LIST.
6b61353c 1427The value is actually the first element of LIST whose car equals KEY. */)
5842a27b 1428 (Lisp_Object key, Lisp_Object list)
7b863bd5 1429{
89662fc3 1430 Lisp_Object car;
f2be3671
GM
1431
1432 while (1)
7b863bd5 1433 {
f2be3671
GM
1434 if (!CONSP (list)
1435 || (CONSP (XCAR (list))
1436 && (car = XCAR (XCAR (list)),
1437 EQ (car, key) || !NILP (Fequal (car, key)))))
1438 break;
59f953a2 1439
f2be3671
GM
1440 list = XCDR (list);
1441 if (!CONSP (list)
1442 || (CONSP (XCAR (list))
1443 && (car = XCAR (XCAR (list)),
1444 EQ (car, key) || !NILP (Fequal (car, key)))))
1445 break;
59f953a2 1446
f2be3671
GM
1447 list = XCDR (list);
1448 if (!CONSP (list)
1449 || (CONSP (XCAR (list))
1450 && (car = XCAR (XCAR (list)),
1451 EQ (car, key) || !NILP (Fequal (car, key)))))
1452 break;
59f953a2 1453
f2be3671 1454 list = XCDR (list);
7b863bd5
JB
1455 QUIT;
1456 }
f2be3671 1457
89662fc3 1458 return CAR (list);
7b863bd5
JB
1459}
1460
86840809
KH
1461/* Like Fassoc but never report an error and do not allow quits.
1462 Use only on lists known never to be circular. */
1463
1464Lisp_Object
971de7fb 1465assoc_no_quit (Lisp_Object key, Lisp_Object list)
86840809
KH
1466{
1467 while (CONSP (list)
1468 && (!CONSP (XCAR (list))
1469 || (!EQ (XCAR (XCAR (list)), key)
1470 && NILP (Fequal (XCAR (XCAR (list)), key)))))
1471 list = XCDR (list);
1472
1473 return CONSP (list) ? XCAR (list) : Qnil;
1474}
1475
a7ca3326 1476DEFUN ("rassq", Frassq, Srassq, 2, 2, 0,
e9d8ddc9 1477 doc: /* Return non-nil if KEY is `eq' to the cdr of an element of LIST.
6b61353c 1478The value is actually the first element of LIST whose cdr is KEY. */)
5842a27b 1479 (register Lisp_Object key, Lisp_Object list)
7b863bd5 1480{
f2be3671 1481 while (1)
7b863bd5 1482 {
f2be3671
GM
1483 if (!CONSP (list)
1484 || (CONSP (XCAR (list))
1485 && EQ (XCDR (XCAR (list)), key)))
1486 break;
59f953a2 1487
f2be3671
GM
1488 list = XCDR (list);
1489 if (!CONSP (list)
1490 || (CONSP (XCAR (list))
1491 && EQ (XCDR (XCAR (list)), key)))
1492 break;
59f953a2 1493
f2be3671
GM
1494 list = XCDR (list);
1495 if (!CONSP (list)
1496 || (CONSP (XCAR (list))
1497 && EQ (XCDR (XCAR (list)), key)))
1498 break;
59f953a2 1499
f2be3671 1500 list = XCDR (list);
7b863bd5
JB
1501 QUIT;
1502 }
f2be3671 1503
89662fc3 1504 return CAR (list);
7b863bd5 1505}
0fb5a19c 1506
a7ca3326 1507DEFUN ("rassoc", Frassoc, Srassoc, 2, 2, 0,
e9d8ddc9 1508 doc: /* Return non-nil if KEY is `equal' to the cdr of an element of LIST.
6b61353c 1509The value is actually the first element of LIST whose cdr equals KEY. */)
5842a27b 1510 (Lisp_Object key, Lisp_Object list)
0fb5a19c 1511{
89662fc3 1512 Lisp_Object cdr;
f2be3671
GM
1513
1514 while (1)
0fb5a19c 1515 {
f2be3671
GM
1516 if (!CONSP (list)
1517 || (CONSP (XCAR (list))
1518 && (cdr = XCDR (XCAR (list)),
1519 EQ (cdr, key) || !NILP (Fequal (cdr, key)))))
1520 break;
59f953a2 1521
f2be3671
GM
1522 list = XCDR (list);
1523 if (!CONSP (list)
1524 || (CONSP (XCAR (list))
1525 && (cdr = XCDR (XCAR (list)),
1526 EQ (cdr, key) || !NILP (Fequal (cdr, key)))))
1527 break;
59f953a2 1528
f2be3671
GM
1529 list = XCDR (list);
1530 if (!CONSP (list)
1531 || (CONSP (XCAR (list))
1532 && (cdr = XCDR (XCAR (list)),
1533 EQ (cdr, key) || !NILP (Fequal (cdr, key)))))
1534 break;
59f953a2 1535
f2be3671 1536 list = XCDR (list);
0fb5a19c
RS
1537 QUIT;
1538 }
f2be3671 1539
89662fc3 1540 return CAR (list);
0fb5a19c 1541}
7b863bd5 1542\f
a7ca3326 1543DEFUN ("delq", Fdelq, Sdelq, 2, 2, 0,
d105a573
CY
1544 doc: /* Delete members of LIST which are `eq' to ELT, and return the result.
1545More precisely, this function skips any members `eq' to ELT at the
1546front of LIST, then removes members `eq' to ELT from the remaining
1547sublist by modifying its list structure, then returns the resulting
1548list.
1549
1550Write `(setq foo (delq element foo))' to be sure of correctly changing
1551the value of a list `foo'. */)
5842a27b 1552 (register Lisp_Object elt, Lisp_Object list)
7b863bd5 1553{
105324ce
SM
1554 Lisp_Object tail, tortoise, prev = Qnil;
1555 bool skip;
7b863bd5 1556
105324ce 1557 FOR_EACH_TAIL (tail, list, tortoise, skip)
7b863bd5 1558 {
105324ce 1559 Lisp_Object tem = XCAR (tail);
7b863bd5
JB
1560 if (EQ (elt, tem))
1561 {
265a9e55 1562 if (NILP (prev))
70949dac 1563 list = XCDR (tail);
7b863bd5 1564 else
70949dac 1565 Fsetcdr (prev, XCDR (tail));
7b863bd5
JB
1566 }
1567 else
1568 prev = tail;
7b863bd5
JB
1569 }
1570 return list;
1571}
1572
a7ca3326 1573DEFUN ("delete", Fdelete, Sdelete, 2, 2, 0,
d105a573
CY
1574 doc: /* Delete members of SEQ which are `equal' to ELT, and return the result.
1575SEQ must be a sequence (i.e. a list, a vector, or a string).
1576The return value is a sequence of the same type.
1577
1578If SEQ is a list, this behaves like `delq', except that it compares
1579with `equal' instead of `eq'. In particular, it may remove elements
1580by altering the list structure.
1581
1582If SEQ is not a list, deletion is never performed destructively;
1583instead this function creates and returns a new vector or string.
1584
1585Write `(setq foo (delete element foo))' to be sure of correctly
1586changing the value of a sequence `foo'. */)
5842a27b 1587 (Lisp_Object elt, Lisp_Object seq)
1e134a5f 1588{
e517f19d
GM
1589 if (VECTORP (seq))
1590 {
d311d28c 1591 ptrdiff_t i, n;
1e134a5f 1592
e517f19d
GM
1593 for (i = n = 0; i < ASIZE (seq); ++i)
1594 if (NILP (Fequal (AREF (seq, i), elt)))
1595 ++n;
1596
1597 if (n != ASIZE (seq))
1598 {
b3660ef6 1599 struct Lisp_Vector *p = allocate_vector (n);
59f953a2 1600
e517f19d
GM
1601 for (i = n = 0; i < ASIZE (seq); ++i)
1602 if (NILP (Fequal (AREF (seq, i), elt)))
91f2d272 1603 p->contents[n++] = AREF (seq, i);
e517f19d 1604
e517f19d
GM
1605 XSETVECTOR (seq, p);
1606 }
1607 }
1608 else if (STRINGP (seq))
1e134a5f 1609 {
d311d28c 1610 ptrdiff_t i, ibyte, nchars, nbytes, cbytes;
e517f19d
GM
1611 int c;
1612
1613 for (i = nchars = nbytes = ibyte = 0;
d5db4077 1614 i < SCHARS (seq);
e517f19d 1615 ++i, ibyte += cbytes)
1e134a5f 1616 {
e517f19d
GM
1617 if (STRING_MULTIBYTE (seq))
1618 {
62a6e103 1619 c = STRING_CHAR (SDATA (seq) + ibyte);
e517f19d
GM
1620 cbytes = CHAR_BYTES (c);
1621 }
1e134a5f 1622 else
e517f19d 1623 {
d5db4077 1624 c = SREF (seq, i);
e517f19d
GM
1625 cbytes = 1;
1626 }
59f953a2 1627
e517f19d
GM
1628 if (!INTEGERP (elt) || c != XINT (elt))
1629 {
1630 ++nchars;
1631 nbytes += cbytes;
1632 }
1633 }
1634
d5db4077 1635 if (nchars != SCHARS (seq))
e517f19d
GM
1636 {
1637 Lisp_Object tem;
1638
1639 tem = make_uninit_multibyte_string (nchars, nbytes);
1640 if (!STRING_MULTIBYTE (seq))
d5db4077 1641 STRING_SET_UNIBYTE (tem);
59f953a2 1642
e517f19d 1643 for (i = nchars = nbytes = ibyte = 0;
d5db4077 1644 i < SCHARS (seq);
e517f19d
GM
1645 ++i, ibyte += cbytes)
1646 {
1647 if (STRING_MULTIBYTE (seq))
1648 {
62a6e103 1649 c = STRING_CHAR (SDATA (seq) + ibyte);
e517f19d
GM
1650 cbytes = CHAR_BYTES (c);
1651 }
1652 else
1653 {
d5db4077 1654 c = SREF (seq, i);
e517f19d
GM
1655 cbytes = 1;
1656 }
59f953a2 1657
e517f19d
GM
1658 if (!INTEGERP (elt) || c != XINT (elt))
1659 {
08663750
KR
1660 unsigned char *from = SDATA (seq) + ibyte;
1661 unsigned char *to = SDATA (tem) + nbytes;
d311d28c 1662 ptrdiff_t n;
59f953a2 1663
e517f19d
GM
1664 ++nchars;
1665 nbytes += cbytes;
59f953a2 1666
e517f19d
GM
1667 for (n = cbytes; n--; )
1668 *to++ = *from++;
1669 }
1670 }
1671
1672 seq = tem;
1e134a5f 1673 }
1e134a5f 1674 }
e517f19d
GM
1675 else
1676 {
1677 Lisp_Object tail, prev;
1678
9beb8baa 1679 for (tail = seq, prev = Qnil; CONSP (tail); tail = XCDR (tail))
e517f19d 1680 {
89662fc3 1681 CHECK_LIST_CONS (tail, seq);
59f953a2 1682
e517f19d
GM
1683 if (!NILP (Fequal (elt, XCAR (tail))))
1684 {
1685 if (NILP (prev))
1686 seq = XCDR (tail);
1687 else
1688 Fsetcdr (prev, XCDR (tail));
1689 }
1690 else
1691 prev = tail;
1692 QUIT;
1693 }
1694 }
59f953a2 1695
e517f19d 1696 return seq;
1e134a5f
RM
1697}
1698
a7ca3326 1699DEFUN ("nreverse", Fnreverse, Snreverse, 1, 1, 0,
254b7645
LL
1700 doc: /* Reverse order of items in a list, vector or string SEQ.
1701If SEQ is a list, it should be nil-terminated.
1702This function may destructively modify SEQ to produce the value. */)
ddc30c99 1703 (Lisp_Object seq)
7b863bd5 1704{
ddc30c99
DA
1705 if (NILP (seq))
1706 return seq;
254b7645
LL
1707 else if (STRINGP (seq))
1708 return Freverse (seq);
ddc30c99
DA
1709 else if (CONSP (seq))
1710 {
1711 Lisp_Object prev, tail, next;
7b863bd5 1712
ddc30c99
DA
1713 for (prev = Qnil, tail = seq; !NILP (tail); tail = next)
1714 {
1715 QUIT;
1716 CHECK_LIST_CONS (tail, tail);
1717 next = XCDR (tail);
1718 Fsetcdr (tail, prev);
1719 prev = tail;
1720 }
1721 seq = prev;
1722 }
1723 else if (VECTORP (seq))
7b863bd5 1724 {
ddc30c99
DA
1725 ptrdiff_t i, size = ASIZE (seq);
1726
1727 for (i = 0; i < size / 2; i++)
1728 {
1729 Lisp_Object tem = AREF (seq, i);
1730 ASET (seq, i, AREF (seq, size - i - 1));
1731 ASET (seq, size - i - 1, tem);
1732 }
7b863bd5 1733 }
ddc30c99
DA
1734 else if (BOOL_VECTOR_P (seq))
1735 {
1736 ptrdiff_t i, size = bool_vector_size (seq);
1737
1738 for (i = 0; i < size / 2; i++)
1739 {
1740 bool tem = bool_vector_bitref (seq, i);
1741 bool_vector_set (seq, i, bool_vector_bitref (seq, size - i - 1));
1742 bool_vector_set (seq, size - i - 1, tem);
1743 }
1744 }
1745 else
1746 wrong_type_argument (Qarrayp, seq);
1747 return seq;
7b863bd5
JB
1748}
1749
a7ca3326 1750DEFUN ("reverse", Freverse, Sreverse, 1, 1, 0,
c269148b 1751 doc: /* Return the reversed copy of list, vector, or string SEQ.
e9d8ddc9 1752See also the function `nreverse', which is used more often. */)
c269148b 1753 (Lisp_Object seq)
7b863bd5 1754{
9d14ae76 1755 Lisp_Object new;
7b863bd5 1756
c269148b
DA
1757 if (NILP (seq))
1758 return Qnil;
1759 else if (CONSP (seq))
5c3ea973 1760 {
c269148b
DA
1761 for (new = Qnil; CONSP (seq); seq = XCDR (seq))
1762 {
1763 QUIT;
1764 new = Fcons (XCAR (seq), new);
1765 }
1766 CHECK_LIST_END (seq, seq);
5c3ea973 1767 }
c269148b
DA
1768 else if (VECTORP (seq))
1769 {
1770 ptrdiff_t i, size = ASIZE (seq);
1771
1772 new = make_uninit_vector (size);
1773 for (i = 0; i < size; i++)
1774 ASET (new, i, AREF (seq, size - i - 1));
1775 }
1776 else if (BOOL_VECTOR_P (seq))
1777 {
1778 ptrdiff_t i;
1779 EMACS_INT nbits = bool_vector_size (seq);
1780
1781 new = make_uninit_bool_vector (nbits);
1782 for (i = 0; i < nbits; i++)
1783 bool_vector_set (new, i, bool_vector_bitref (seq, nbits - i - 1));
1784 }
1785 else if (STRINGP (seq))
1786 {
1787 ptrdiff_t size = SCHARS (seq), bytes = SBYTES (seq);
1788
1789 if (size == bytes)
1790 {
1791 ptrdiff_t i;
1792
1793 new = make_uninit_string (size);
1794 for (i = 0; i < size; i++)
1795 SSET (new, i, SREF (seq, size - i - 1));
1796 }
1797 else
1798 {
1799 unsigned char *p, *q;
1800
1801 new = make_uninit_multibyte_string (size, bytes);
1802 p = SDATA (seq), q = SDATA (new) + bytes;
1803 while (q > SDATA (new))
1804 {
1805 int ch, len;
1806
1807 ch = STRING_CHAR_AND_LENGTH (p, len);
1808 p += len, q -= len;
1809 CHAR_STRING (ch, q);
1810 }
1811 }
1812 }
1813 else
1814 wrong_type_argument (Qsequencep, seq);
9d14ae76 1815 return new;
7b863bd5
JB
1816}
1817\f
a7ca3326 1818DEFUN ("sort", Fsort, Ssort, 2, 2, 0,
e9d8ddc9 1819 doc: /* Sort LIST, stably, comparing elements using PREDICATE.
47cebab1 1820Returns the sorted list. LIST is modified by side effects.
5c796e80 1821PREDICATE is called with two elements of LIST, and should return non-nil
71f6424d 1822if the first element should sort before the second. */)
5842a27b 1823 (Lisp_Object list, Lisp_Object predicate)
7b863bd5
JB
1824{
1825 Lisp_Object front, back;
1826 register Lisp_Object len, tem;
1827 struct gcpro gcpro1, gcpro2;
6346d301 1828 EMACS_INT length;
7b863bd5
JB
1829
1830 front = list;
1831 len = Flength (list);
1832 length = XINT (len);
1833 if (length < 2)
1834 return list;
1835
1836 XSETINT (len, (length / 2) - 1);
1837 tem = Fnthcdr (len, list);
1838 back = Fcdr (tem);
1839 Fsetcdr (tem, Qnil);
1840
1841 GCPRO2 (front, back);
88fe8140
EN
1842 front = Fsort (front, predicate);
1843 back = Fsort (back, predicate);
7b863bd5 1844 UNGCPRO;
88fe8140 1845 return merge (front, back, predicate);
7b863bd5
JB
1846}
1847
1848Lisp_Object
971de7fb 1849merge (Lisp_Object org_l1, Lisp_Object org_l2, Lisp_Object pred)
7b863bd5
JB
1850{
1851 Lisp_Object value;
1852 register Lisp_Object tail;
1853 Lisp_Object tem;
1854 register Lisp_Object l1, l2;
1855 struct gcpro gcpro1, gcpro2, gcpro3, gcpro4;
1856
1857 l1 = org_l1;
1858 l2 = org_l2;
1859 tail = Qnil;
1860 value = Qnil;
1861
1862 /* It is sufficient to protect org_l1 and org_l2.
1863 When l1 and l2 are updated, we copy the new values
1864 back into the org_ vars. */
1865 GCPRO4 (org_l1, org_l2, pred, value);
1866
1867 while (1)
1868 {
265a9e55 1869 if (NILP (l1))
7b863bd5
JB
1870 {
1871 UNGCPRO;
265a9e55 1872 if (NILP (tail))
7b863bd5
JB
1873 return l2;
1874 Fsetcdr (tail, l2);
1875 return value;
1876 }
265a9e55 1877 if (NILP (l2))
7b863bd5
JB
1878 {
1879 UNGCPRO;
265a9e55 1880 if (NILP (tail))
7b863bd5
JB
1881 return l1;
1882 Fsetcdr (tail, l1);
1883 return value;
1884 }
1885 tem = call2 (pred, Fcar (l2), Fcar (l1));
265a9e55 1886 if (NILP (tem))
7b863bd5
JB
1887 {
1888 tem = l1;
1889 l1 = Fcdr (l1);
1890 org_l1 = l1;
1891 }
1892 else
1893 {
1894 tem = l2;
1895 l2 = Fcdr (l2);
1896 org_l2 = l2;
1897 }
265a9e55 1898 if (NILP (tail))
7b863bd5
JB
1899 value = tem;
1900 else
1901 Fsetcdr (tail, tem);
1902 tail = tem;
1903 }
1904}
be9d483d 1905
2d6fabfc 1906\f
12ae7fc6 1907/* This does not check for quits. That is safe since it must terminate. */
7b863bd5 1908
a7ca3326 1909DEFUN ("plist-get", Fplist_get, Splist_get, 2, 2, 0,
27f604dd
KS
1910 doc: /* Extract a value from a property list.
1911PLIST is a property list, which is a list of the form
1912\(PROP1 VALUE1 PROP2 VALUE2...). This function returns the value
12ae7fc6
KS
1913corresponding to the given PROP, or nil if PROP is not one of the
1914properties on the list. This function never signals an error. */)
5842a27b 1915 (Lisp_Object plist, Lisp_Object prop)
27f604dd
KS
1916{
1917 Lisp_Object tail, halftail;
1918
1919 /* halftail is used to detect circular lists. */
1920 tail = halftail = plist;
1921 while (CONSP (tail) && CONSP (XCDR (tail)))
1922 {
1923 if (EQ (prop, XCAR (tail)))
1924 return XCAR (XCDR (tail));
1925
1926 tail = XCDR (XCDR (tail));
1927 halftail = XCDR (halftail);
1928 if (EQ (tail, halftail))
1929 break;
1930 }
1931
1932 return Qnil;
1933}
1934
a7ca3326 1935DEFUN ("get", Fget, Sget, 2, 2, 0,
e9d8ddc9
MB
1936 doc: /* Return the value of SYMBOL's PROPNAME property.
1937This is the last value stored with `(put SYMBOL PROPNAME VALUE)'. */)
5842a27b 1938 (Lisp_Object symbol, Lisp_Object propname)
be9d483d 1939{
b7826503 1940 CHECK_SYMBOL (symbol);
c644523b 1941 return Fplist_get (XSYMBOL (symbol)->plist, propname);
be9d483d
BG
1942}
1943
a7ca3326 1944DEFUN ("plist-put", Fplist_put, Splist_put, 3, 3, 0,
e9d8ddc9 1945 doc: /* Change value in PLIST of PROP to VAL.
47cebab1
GM
1946PLIST is a property list, which is a list of the form
1947\(PROP1 VALUE1 PROP2 VALUE2 ...). PROP is a symbol and VAL is any object.
1948If PROP is already a property on the list, its value is set to VAL,
1949otherwise the new PROP VAL pair is added. The new plist is returned;
1950use `(setq x (plist-put x prop val))' to be sure to use the new value.
e9d8ddc9 1951The PLIST is modified by side effects. */)
5842a27b 1952 (Lisp_Object plist, register Lisp_Object prop, Lisp_Object val)
7b863bd5
JB
1953{
1954 register Lisp_Object tail, prev;
1955 Lisp_Object newcell;
1956 prev = Qnil;
70949dac
KR
1957 for (tail = plist; CONSP (tail) && CONSP (XCDR (tail));
1958 tail = XCDR (XCDR (tail)))
7b863bd5 1959 {
70949dac 1960 if (EQ (prop, XCAR (tail)))
be9d483d 1961 {
70949dac 1962 Fsetcar (XCDR (tail), val);
be9d483d
BG
1963 return plist;
1964 }
91f78c99 1965
7b863bd5 1966 prev = tail;
2d6fabfc 1967 QUIT;
7b863bd5 1968 }
088c8c37 1969 newcell = Fcons (prop, Fcons (val, NILP (prev) ? plist : XCDR (XCDR (prev))));
265a9e55 1970 if (NILP (prev))
be9d483d 1971 return newcell;
7b863bd5 1972 else
70949dac 1973 Fsetcdr (XCDR (prev), newcell);
be9d483d
BG
1974 return plist;
1975}
1976
a7ca3326 1977DEFUN ("put", Fput, Sput, 3, 3, 0,
e9d8ddc9
MB
1978 doc: /* Store SYMBOL's PROPNAME property with value VALUE.
1979It can be retrieved with `(get SYMBOL PROPNAME)'. */)
5842a27b 1980 (Lisp_Object symbol, Lisp_Object propname, Lisp_Object value)
be9d483d 1981{
b7826503 1982 CHECK_SYMBOL (symbol);
c644523b
DA
1983 set_symbol_plist
1984 (symbol, Fplist_put (XSYMBOL (symbol)->plist, propname, value));
c07289e0 1985 return value;
7b863bd5 1986}
aebf4d42
RS
1987\f
1988DEFUN ("lax-plist-get", Flax_plist_get, Slax_plist_get, 2, 2, 0,
1989 doc: /* Extract a value from a property list, comparing with `equal'.
1990PLIST is a property list, which is a list of the form
1991\(PROP1 VALUE1 PROP2 VALUE2...). This function returns the value
1992corresponding to the given PROP, or nil if PROP is not
1993one of the properties on the list. */)
5842a27b 1994 (Lisp_Object plist, Lisp_Object prop)
aebf4d42
RS
1995{
1996 Lisp_Object tail;
91f78c99 1997
aebf4d42
RS
1998 for (tail = plist;
1999 CONSP (tail) && CONSP (XCDR (tail));
2000 tail = XCDR (XCDR (tail)))
2001 {
2002 if (! NILP (Fequal (prop, XCAR (tail))))
2003 return XCAR (XCDR (tail));
2004
2005 QUIT;
2006 }
2007
89662fc3 2008 CHECK_LIST_END (tail, prop);
91f78c99 2009
aebf4d42
RS
2010 return Qnil;
2011}
7b863bd5 2012
aebf4d42
RS
2013DEFUN ("lax-plist-put", Flax_plist_put, Slax_plist_put, 3, 3, 0,
2014 doc: /* Change value in PLIST of PROP to VAL, comparing with `equal'.
2015PLIST is a property list, which is a list of the form
9e76ae05 2016\(PROP1 VALUE1 PROP2 VALUE2 ...). PROP and VAL are any objects.
aebf4d42
RS
2017If PROP is already a property on the list, its value is set to VAL,
2018otherwise the new PROP VAL pair is added. The new plist is returned;
2019use `(setq x (lax-plist-put x prop val))' to be sure to use the new value.
2020The PLIST is modified by side effects. */)
5842a27b 2021 (Lisp_Object plist, register Lisp_Object prop, Lisp_Object val)
aebf4d42
RS
2022{
2023 register Lisp_Object tail, prev;
2024 Lisp_Object newcell;
2025 prev = Qnil;
2026 for (tail = plist; CONSP (tail) && CONSP (XCDR (tail));
2027 tail = XCDR (XCDR (tail)))
2028 {
2029 if (! NILP (Fequal (prop, XCAR (tail))))
2030 {
2031 Fsetcar (XCDR (tail), val);
2032 return plist;
2033 }
91f78c99 2034
aebf4d42
RS
2035 prev = tail;
2036 QUIT;
2037 }
6c6f1994 2038 newcell = list2 (prop, val);
aebf4d42
RS
2039 if (NILP (prev))
2040 return newcell;
2041 else
2042 Fsetcdr (XCDR (prev), newcell);
2043 return plist;
2044}
2045\f
95f8c3b9
JPW
2046DEFUN ("eql", Feql, Seql, 2, 2, 0,
2047 doc: /* Return t if the two args are the same Lisp object.
2048Floating-point numbers of equal value are `eql', but they may not be `eq'. */)
5842a27b 2049 (Lisp_Object obj1, Lisp_Object obj2)
95f8c3b9
JPW
2050{
2051 if (FLOATP (obj1))
9f4ffeee 2052 return internal_equal (obj1, obj2, 0, 0, Qnil) ? Qt : Qnil;
95f8c3b9
JPW
2053 else
2054 return EQ (obj1, obj2) ? Qt : Qnil;
2055}
2056
a7ca3326 2057DEFUN ("equal", Fequal, Sequal, 2, 2, 0,
e9d8ddc9 2058 doc: /* Return t if two Lisp objects have similar structure and contents.
47cebab1
GM
2059They must have the same data type.
2060Conses are compared by comparing the cars and the cdrs.
2061Vectors and strings are compared element by element.
2062Numbers are compared by value, but integers cannot equal floats.
2063 (Use `=' if you want integers and floats to be able to be equal.)
e9d8ddc9 2064Symbols must match exactly. */)
5842a27b 2065 (register Lisp_Object o1, Lisp_Object o2)
7b863bd5 2066{
9f4ffeee 2067 return internal_equal (o1, o2, 0, 0, Qnil) ? Qt : Qnil;
6b61353c
KH
2068}
2069
2070DEFUN ("equal-including-properties", Fequal_including_properties, Sequal_including_properties, 2, 2, 0,
2071 doc: /* Return t if two Lisp objects have similar structure and contents.
2072This is like `equal' except that it compares the text properties
2073of strings. (`equal' ignores text properties.) */)
5842a27b 2074 (register Lisp_Object o1, Lisp_Object o2)
6b61353c 2075{
9f4ffeee 2076 return internal_equal (o1, o2, 0, 1, Qnil) ? Qt : Qnil;
e0f5cf5a
RS
2077}
2078
6b61353c
KH
2079/* DEPTH is current depth of recursion. Signal an error if it
2080 gets too deep.
f75d7a91 2081 PROPS means compare string text properties too. */
6b61353c 2082
f75d7a91 2083static bool
9f4ffeee
SM
2084internal_equal (Lisp_Object o1, Lisp_Object o2, int depth, bool props,
2085 Lisp_Object ht)
e0f5cf5a 2086{
9f4ffeee
SM
2087 if (depth > 10)
2088 {
2089 if (depth > 200)
2090 error ("Stack overflow in equal");
2091 if (NILP (ht))
2092 {
56a0e352
PE
2093 Lisp_Object args[2];
2094 args[0] = QCtest;
2095 args[1] = Qeq;
9f4ffeee
SM
2096 ht = Fmake_hash_table (2, args);
2097 }
2098 switch (XTYPE (o1))
2099 {
2100 case Lisp_Cons: case Lisp_Misc: case Lisp_Vectorlike:
2101 {
2102 struct Lisp_Hash_Table *h = XHASH_TABLE (ht);
2103 EMACS_UINT hash;
2104 ptrdiff_t i = hash_lookup (h, o1, &hash);
2105 if (i >= 0)
2106 { /* `o1' was seen already. */
2107 Lisp_Object o2s = HASH_VALUE (h, i);
2108 if (!NILP (Fmemq (o2, o2s)))
2109 return 1;
2110 else
2111 set_hash_value_slot (h, i, Fcons (o2, o2s));
2112 }
2113 else
2114 hash_put (h, o1, Fcons (o2, Qnil), hash);
2115 }
2116 default: ;
2117 }
2118 }
4ff1aed9 2119
6cb9cafb 2120 tail_recurse:
7b863bd5 2121 QUIT;
4ff1aed9
RS
2122 if (EQ (o1, o2))
2123 return 1;
2124 if (XTYPE (o1) != XTYPE (o2))
2125 return 0;
2126
2127 switch (XTYPE (o1))
2128 {
4ff1aed9 2129 case Lisp_Float:
6b61353c
KH
2130 {
2131 double d1, d2;
2132
2133 d1 = extract_float (o1);
2134 d2 = extract_float (o2);
2135 /* If d is a NaN, then d != d. Two NaNs should be `equal' even
b7432bb2 2136 though they are not =. */
6b61353c
KH
2137 return d1 == d2 || (d1 != d1 && d2 != d2);
2138 }
4ff1aed9
RS
2139
2140 case Lisp_Cons:
9f4ffeee 2141 if (!internal_equal (XCAR (o1), XCAR (o2), depth + 1, props, ht))
4cab5074 2142 return 0;
70949dac
KR
2143 o1 = XCDR (o1);
2144 o2 = XCDR (o2);
9f4ffeee 2145 /* FIXME: This inf-loops in a circular list! */
4cab5074 2146 goto tail_recurse;
4ff1aed9
RS
2147
2148 case Lisp_Misc:
81d1fba6 2149 if (XMISCTYPE (o1) != XMISCTYPE (o2))
6cb9cafb 2150 return 0;
4ff1aed9 2151 if (OVERLAYP (o1))
7b863bd5 2152 {
e23f814f 2153 if (!internal_equal (OVERLAY_START (o1), OVERLAY_START (o2),
9f4ffeee 2154 depth + 1, props, ht)
e23f814f 2155 || !internal_equal (OVERLAY_END (o1), OVERLAY_END (o2),
9f4ffeee 2156 depth + 1, props, ht))
6cb9cafb 2157 return 0;
c644523b
DA
2158 o1 = XOVERLAY (o1)->plist;
2159 o2 = XOVERLAY (o2)->plist;
4ff1aed9 2160 goto tail_recurse;
7b863bd5 2161 }
4ff1aed9
RS
2162 if (MARKERP (o1))
2163 {
2164 return (XMARKER (o1)->buffer == XMARKER (o2)->buffer
2165 && (XMARKER (o1)->buffer == 0
6ced1284 2166 || XMARKER (o1)->bytepos == XMARKER (o2)->bytepos));
4ff1aed9
RS
2167 }
2168 break;
2169
2170 case Lisp_Vectorlike:
4cab5074 2171 {
6b61353c 2172 register int i;
d311d28c 2173 ptrdiff_t size = ASIZE (o1);
4cab5074
KH
2174 /* Pseudovectors have the type encoded in the size field, so this test
2175 actually checks that the objects have the same type as well as the
2176 same size. */
7edbb0da 2177 if (ASIZE (o2) != size)
4cab5074 2178 return 0;
e03f7933
RS
2179 /* Boolvectors are compared much like strings. */
2180 if (BOOL_VECTOR_P (o1))
2181 {
1c0a7493
PE
2182 EMACS_INT size = bool_vector_size (o1);
2183 if (size != bool_vector_size (o2))
e03f7933 2184 return 0;
df5b4930 2185 if (memcmp (bool_vector_data (o1), bool_vector_data (o2),
2cf00efc 2186 bool_vector_bytes (size)))
e03f7933
RS
2187 return 0;
2188 return 1;
2189 }
ed73fcc1 2190 if (WINDOW_CONFIGURATIONP (o1))
48646924 2191 return compare_window_configurations (o1, o2, 0);
e03f7933 2192
876c194c 2193 /* Aside from them, only true vectors, char-tables, compiled
66699ad3 2194 functions, and fonts (font-spec, font-entity, font-object)
876c194c 2195 are sensible to compare, so eliminate the others now. */
4cab5074
KH
2196 if (size & PSEUDOVECTOR_FLAG)
2197 {
914adc42
DA
2198 if (((size & PVEC_TYPE_MASK) >> PSEUDOVECTOR_AREA_BITS)
2199 < PVEC_COMPILED)
4cab5074
KH
2200 return 0;
2201 size &= PSEUDOVECTOR_SIZE_MASK;
2202 }
2203 for (i = 0; i < size; i++)
2204 {
2205 Lisp_Object v1, v2;
7edbb0da
SM
2206 v1 = AREF (o1, i);
2207 v2 = AREF (o2, i);
9f4ffeee 2208 if (!internal_equal (v1, v2, depth + 1, props, ht))
4cab5074
KH
2209 return 0;
2210 }
2211 return 1;
2212 }
4ff1aed9
RS
2213 break;
2214
2215 case Lisp_String:
d5db4077 2216 if (SCHARS (o1) != SCHARS (o2))
4cab5074 2217 return 0;
d5db4077 2218 if (SBYTES (o1) != SBYTES (o2))
ea35ce3d 2219 return 0;
72af86bd 2220 if (memcmp (SDATA (o1), SDATA (o2), SBYTES (o1)))
4cab5074 2221 return 0;
6b61353c
KH
2222 if (props && !compare_string_intervals (o1, o2))
2223 return 0;
4cab5074 2224 return 1;
093386ca 2225
2de9f71c 2226 default:
093386ca 2227 break;
7b863bd5 2228 }
91f78c99 2229
6cb9cafb 2230 return 0;
7b863bd5
JB
2231}
2232\f
2e34157c 2233
7b863bd5 2234DEFUN ("fillarray", Ffillarray, Sfillarray, 2, 2, 0,
e9d8ddc9
MB
2235 doc: /* Store each element of ARRAY with ITEM.
2236ARRAY is a vector, string, char-table, or bool-vector. */)
5842a27b 2237 (Lisp_Object array, Lisp_Object item)
7b863bd5 2238{
d311d28c 2239 register ptrdiff_t size, idx;
e6d4aefa 2240
7650760e 2241 if (VECTORP (array))
086ca913
DA
2242 for (idx = 0, size = ASIZE (array); idx < size; idx++)
2243 ASET (array, idx, item);
e03f7933
RS
2244 else if (CHAR_TABLE_P (array))
2245 {
38583a69
KH
2246 int i;
2247
2248 for (i = 0; i < (1 << CHARTAB_SIZE_BITS_0); i++)
34dabdb7 2249 set_char_table_contents (array, i, item);
742af32f 2250 set_char_table_defalt (array, item);
e03f7933 2251 }
7650760e 2252 else if (STRINGP (array))
7b863bd5 2253 {
d5db4077 2254 register unsigned char *p = SDATA (array);
a4cf38e4
PE
2255 int charval;
2256 CHECK_CHARACTER (item);
2257 charval = XFASTINT (item);
d5db4077 2258 size = SCHARS (array);
57247650
KH
2259 if (STRING_MULTIBYTE (array))
2260 {
64a5094a
KH
2261 unsigned char str[MAX_MULTIBYTE_LENGTH];
2262 int len = CHAR_STRING (charval, str);
d311d28c 2263 ptrdiff_t size_byte = SBYTES (array);
57247650 2264
f03dc6ef
PE
2265 if (INT_MULTIPLY_OVERFLOW (SCHARS (array), len)
2266 || SCHARS (array) * len != size_byte)
2267 error ("Attempt to change byte length of a string");
436b4815
PE
2268 for (idx = 0; idx < size_byte; idx++)
2269 *p++ = str[idx % len];
57247650
KH
2270 }
2271 else
612f56df
PE
2272 for (idx = 0; idx < size; idx++)
2273 p[idx] = charval;
7b863bd5 2274 }
e03f7933 2275 else if (BOOL_VECTOR_P (array))
2cf00efc 2276 return bool_vector_fill (array, item);
7b863bd5 2277 else
89662fc3 2278 wrong_type_argument (Qarrayp, array);
7b863bd5
JB
2279 return array;
2280}
85cad579
RS
2281
2282DEFUN ("clear-string", Fclear_string, Sclear_string,
2283 1, 1, 0,
2284 doc: /* Clear the contents of STRING.
2285This makes STRING unibyte and may change its length. */)
5842a27b 2286 (Lisp_Object string)
85cad579 2287{
d311d28c 2288 ptrdiff_t len;
a085bf9d 2289 CHECK_STRING (string);
cfd23693 2290 len = SBYTES (string);
72af86bd 2291 memset (SDATA (string), 0, len);
85cad579
RS
2292 STRING_SET_CHARS (string, len);
2293 STRING_SET_UNIBYTE (string);
2294 return Qnil;
2295}
ea35ce3d 2296\f
7b863bd5
JB
2297/* ARGSUSED */
2298Lisp_Object
971de7fb 2299nconc2 (Lisp_Object s1, Lisp_Object s2)
7b863bd5 2300{
7b863bd5
JB
2301 Lisp_Object args[2];
2302 args[0] = s1;
2303 args[1] = s2;
2304 return Fnconc (2, args);
7b863bd5
JB
2305}
2306
a7ca3326 2307DEFUN ("nconc", Fnconc, Snconc, 0, MANY, 0,
e9d8ddc9 2308 doc: /* Concatenate any number of lists by altering them.
4bf8e2a3
MB
2309Only the last argument is not altered, and need not be a list.
2310usage: (nconc &rest LISTS) */)
f66c7cf8 2311 (ptrdiff_t nargs, Lisp_Object *args)
7b863bd5 2312{
f66c7cf8 2313 ptrdiff_t argnum;
7b863bd5
JB
2314 register Lisp_Object tail, tem, val;
2315
093386ca 2316 val = tail = Qnil;
7b863bd5
JB
2317
2318 for (argnum = 0; argnum < nargs; argnum++)
2319 {
2320 tem = args[argnum];
265a9e55 2321 if (NILP (tem)) continue;
7b863bd5 2322
265a9e55 2323 if (NILP (val))
7b863bd5
JB
2324 val = tem;
2325
2326 if (argnum + 1 == nargs) break;
2327
89662fc3 2328 CHECK_LIST_CONS (tem, tem);
7b863bd5
JB
2329
2330 while (CONSP (tem))
2331 {
2332 tail = tem;
cf42cb72 2333 tem = XCDR (tail);
7b863bd5
JB
2334 QUIT;
2335 }
2336
2337 tem = args[argnum + 1];
2338 Fsetcdr (tail, tem);
265a9e55 2339 if (NILP (tem))
7b863bd5
JB
2340 args[argnum + 1] = tail;
2341 }
2342
2343 return val;
2344}
2345\f
2346/* This is the guts of all mapping functions.
ea35ce3d
RS
2347 Apply FN to each element of SEQ, one by one,
2348 storing the results into elements of VALS, a C vector of Lisp_Objects.
2349 LENI is the length of VALS, which should also be the length of SEQ. */
7b863bd5
JB
2350
2351static void
e6d4aefa 2352mapcar1 (EMACS_INT leni, Lisp_Object *vals, Lisp_Object fn, Lisp_Object seq)
7b863bd5
JB
2353{
2354 register Lisp_Object tail;
2355 Lisp_Object dummy;
e6d4aefa 2356 register EMACS_INT i;
7b863bd5
JB
2357 struct gcpro gcpro1, gcpro2, gcpro3;
2358
f5c75033
DL
2359 if (vals)
2360 {
2361 /* Don't let vals contain any garbage when GC happens. */
2362 for (i = 0; i < leni; i++)
2363 vals[i] = Qnil;
7b863bd5 2364
f5c75033
DL
2365 GCPRO3 (dummy, fn, seq);
2366 gcpro1.var = vals;
2367 gcpro1.nvars = leni;
2368 }
2369 else
2370 GCPRO2 (fn, seq);
7b863bd5 2371 /* We need not explicitly protect `tail' because it is used only on lists, and
7edbb0da
SM
2372 1) lists are not relocated and 2) the list is marked via `seq' so will not
2373 be freed */
7b863bd5 2374
876c194c 2375 if (VECTORP (seq) || COMPILEDP (seq))
7b863bd5
JB
2376 {
2377 for (i = 0; i < leni; i++)
2378 {
7edbb0da 2379 dummy = call1 (fn, AREF (seq, i));
f5c75033
DL
2380 if (vals)
2381 vals[i] = dummy;
7b863bd5
JB
2382 }
2383 }
33aa0881
KH
2384 else if (BOOL_VECTOR_P (seq))
2385 {
2386 for (i = 0; i < leni; i++)
2387 {
df5b4930 2388 dummy = call1 (fn, bool_vector_ref (seq, i));
f5c75033
DL
2389 if (vals)
2390 vals[i] = dummy;
33aa0881
KH
2391 }
2392 }
ea35ce3d
RS
2393 else if (STRINGP (seq))
2394 {
d311d28c 2395 ptrdiff_t i_byte;
ea35ce3d
RS
2396
2397 for (i = 0, i_byte = 0; i < leni;)
2398 {
2399 int c;
d311d28c 2400 ptrdiff_t i_before = i;
0ab6a3d8
KH
2401
2402 FETCH_STRING_CHAR_ADVANCE (c, seq, i, i_byte);
ea35ce3d 2403 XSETFASTINT (dummy, c);
f5c75033
DL
2404 dummy = call1 (fn, dummy);
2405 if (vals)
2406 vals[i_before] = dummy;
ea35ce3d
RS
2407 }
2408 }
7b863bd5
JB
2409 else /* Must be a list, since Flength did not get an error */
2410 {
2411 tail = seq;
85946364 2412 for (i = 0; i < leni && CONSP (tail); i++)
7b863bd5 2413 {
85946364 2414 dummy = call1 (fn, XCAR (tail));
f5c75033
DL
2415 if (vals)
2416 vals[i] = dummy;
70949dac 2417 tail = XCDR (tail);
7b863bd5
JB
2418 }
2419 }
2420
2421 UNGCPRO;
2422}
2423
a7ca3326 2424DEFUN ("mapconcat", Fmapconcat, Smapconcat, 3, 3, 0,
e9d8ddc9 2425 doc: /* Apply FUNCTION to each element of SEQUENCE, and concat the results as strings.
dd8d1e71 2426In between each pair of results, stick in SEPARATOR. Thus, " " as
47cebab1 2427SEPARATOR results in spaces between the values returned by FUNCTION.
e9d8ddc9 2428SEQUENCE may be a list, a vector, a bool-vector, or a string. */)
5842a27b 2429 (Lisp_Object function, Lisp_Object sequence, Lisp_Object separator)
7b863bd5
JB
2430{
2431 Lisp_Object len;
e6d4aefa 2432 register EMACS_INT leni;
d311d28c
PE
2433 EMACS_INT nargs;
2434 ptrdiff_t i;
7b863bd5 2435 register Lisp_Object *args;
7b863bd5 2436 struct gcpro gcpro1;
799c08ac
KS
2437 Lisp_Object ret;
2438 USE_SAFE_ALLOCA;
7b863bd5 2439
88fe8140 2440 len = Flength (sequence);
4187aa82
KH
2441 if (CHAR_TABLE_P (sequence))
2442 wrong_type_argument (Qlistp, sequence);
7b863bd5
JB
2443 leni = XINT (len);
2444 nargs = leni + leni - 1;
b116683c 2445 if (nargs < 0) return empty_unibyte_string;
7b863bd5 2446
7b4cd44a 2447 SAFE_ALLOCA_LISP (args, nargs);
7b863bd5 2448
88fe8140
EN
2449 GCPRO1 (separator);
2450 mapcar1 (leni, args, function, sequence);
7b863bd5
JB
2451 UNGCPRO;
2452
85946364 2453 for (i = leni - 1; i > 0; i--)
7b863bd5 2454 args[i + i] = args[i];
b4f334f7 2455
7b863bd5 2456 for (i = 1; i < nargs; i += 2)
88fe8140 2457 args[i] = separator;
7b863bd5 2458
799c08ac 2459 ret = Fconcat (nargs, args);
233f3db6 2460 SAFE_FREE ();
799c08ac
KS
2461
2462 return ret;
7b863bd5
JB
2463}
2464
a7ca3326 2465DEFUN ("mapcar", Fmapcar, Smapcar, 2, 2, 0,
e9d8ddc9 2466 doc: /* Apply FUNCTION to each element of SEQUENCE, and make a list of the results.
47cebab1 2467The result is a list just as long as SEQUENCE.
e9d8ddc9 2468SEQUENCE may be a list, a vector, a bool-vector, or a string. */)
5842a27b 2469 (Lisp_Object function, Lisp_Object sequence)
7b863bd5
JB
2470{
2471 register Lisp_Object len;
e6d4aefa 2472 register EMACS_INT leni;
7b863bd5 2473 register Lisp_Object *args;
799c08ac
KS
2474 Lisp_Object ret;
2475 USE_SAFE_ALLOCA;
7b863bd5 2476
88fe8140 2477 len = Flength (sequence);
4187aa82
KH
2478 if (CHAR_TABLE_P (sequence))
2479 wrong_type_argument (Qlistp, sequence);
7b863bd5 2480 leni = XFASTINT (len);
799c08ac 2481
7b4cd44a 2482 SAFE_ALLOCA_LISP (args, leni);
7b863bd5 2483
88fe8140 2484 mapcar1 (leni, args, function, sequence);
7b863bd5 2485
799c08ac 2486 ret = Flist (leni, args);
233f3db6 2487 SAFE_FREE ();
799c08ac
KS
2488
2489 return ret;
7b863bd5 2490}
f5c75033
DL
2491
2492DEFUN ("mapc", Fmapc, Smapc, 2, 2, 0,
e9d8ddc9 2493 doc: /* Apply FUNCTION to each element of SEQUENCE for side effects only.
47cebab1 2494Unlike `mapcar', don't accumulate the results. Return SEQUENCE.
e9d8ddc9 2495SEQUENCE may be a list, a vector, a bool-vector, or a string. */)
5842a27b 2496 (Lisp_Object function, Lisp_Object sequence)
f5c75033 2497{
e6d4aefa 2498 register EMACS_INT leni;
f5c75033
DL
2499
2500 leni = XFASTINT (Flength (sequence));
4187aa82
KH
2501 if (CHAR_TABLE_P (sequence))
2502 wrong_type_argument (Qlistp, sequence);
f5c75033
DL
2503 mapcar1 (leni, 0, function, sequence);
2504
2505 return sequence;
2506}
7b863bd5 2507\f
7b863bd5
JB
2508/* This is how C code calls `yes-or-no-p' and allows the user
2509 to redefined it.
2510
2511 Anything that calls this function must protect from GC! */
2512
2513Lisp_Object
971de7fb 2514do_yes_or_no_p (Lisp_Object prompt)
7b863bd5
JB
2515{
2516 return call1 (intern ("yes-or-no-p"), prompt);
2517}
2518
2519/* Anything that calls this function must protect from GC! */
2520
2521DEFUN ("yes-or-no-p", Fyes_or_no_p, Syes_or_no_p, 1, 1, 0,
8cd86d04
LI
2522 doc: /* Ask user a yes-or-no question.
2523Return t if answer is yes, and nil if the answer is no.
9aea757b
CY
2524PROMPT is the string to display to ask the question. It should end in
2525a space; `yes-or-no-p' adds \"(yes or no) \" to it.
3d91e302
CY
2526
2527The user must confirm the answer with RET, and can edit it until it
2528has been confirmed.
47cebab1 2529
9f8551de
EZ
2530If dialog boxes are supported, a dialog box will be used
2531if `last-nonmenu-event' is nil, and `use-dialog-box' is non-nil. */)
5842a27b 2532 (Lisp_Object prompt)
7b863bd5
JB
2533{
2534 register Lisp_Object ans;
2535 Lisp_Object args[2];
2536 struct gcpro gcpro1;
2537
b7826503 2538 CHECK_STRING (prompt);
7b863bd5 2539
7452b7bd 2540 if ((NILP (last_nonmenu_event) || CONSP (last_nonmenu_event))
9f8551de 2541 && use_dialog_box)
1db4cfb2
RS
2542 {
2543 Lisp_Object pane, menu, obj;
3007ebfb 2544 redisplay_preserve_echo_area (4);
6c6f1994
PE
2545 pane = list2 (Fcons (build_string ("Yes"), Qt),
2546 Fcons (build_string ("No"), Qnil));
1db4cfb2 2547 GCPRO1 (pane);
ec26e1b9 2548 menu = Fcons (prompt, pane);
f0a31d70 2549 obj = Fx_popup_dialog (Qt, menu, Qnil);
1db4cfb2
RS
2550 UNGCPRO;
2551 return obj;
2552 }
2553
7b863bd5
JB
2554 args[0] = prompt;
2555 args[1] = build_string ("(yes or no) ");
2556 prompt = Fconcat (2, args);
2557
2558 GCPRO1 (prompt);
1db4cfb2 2559
7b863bd5
JB
2560 while (1)
2561 {
0ce830bc 2562 ans = Fdowncase (Fread_from_minibuffer (prompt, Qnil, Qnil, Qnil,
b24014d4 2563 Qyes_or_no_p_history, Qnil,
ba139299 2564 Qnil));
42a5b22f 2565 if (SCHARS (ans) == 3 && !strcmp (SSDATA (ans), "yes"))
7b863bd5
JB
2566 {
2567 UNGCPRO;
2568 return Qt;
2569 }
42a5b22f 2570 if (SCHARS (ans) == 2 && !strcmp (SSDATA (ans), "no"))
7b863bd5
JB
2571 {
2572 UNGCPRO;
2573 return Qnil;
2574 }
2575
2576 Fding (Qnil);
2577 Fdiscard_input ();
2f73da9c 2578 message1 ("Please answer yes or no.");
99dc4745 2579 Fsleep_for (make_number (2), Qnil);
7b863bd5 2580 }
7b863bd5
JB
2581}
2582\f
f4b50f66 2583DEFUN ("load-average", Fload_average, Sload_average, 0, 1, 0,
e9d8ddc9 2584 doc: /* Return list of 1 minute, 5 minute and 15 minute load averages.
91f78c99 2585
47cebab1
GM
2586Each of the three load averages is multiplied by 100, then converted
2587to integer.
2588
2589When USE-FLOATS is non-nil, floats will be used instead of integers.
2590These floats are not multiplied by 100.
2591
2592If the 5-minute or 15-minute load averages are not available, return a
30b1b0cf
DL
2593shortened list, containing only those averages which are available.
2594
2595An error is thrown if the load average can't be obtained. In some
2596cases making it work would require Emacs being installed setuid or
2597setgid so that it can read kernel information, and that usually isn't
2598advisable. */)
5842a27b 2599 (Lisp_Object use_floats)
7b863bd5 2600{
daa37602
JB
2601 double load_ave[3];
2602 int loads = getloadavg (load_ave, 3);
f4b50f66 2603 Lisp_Object ret = Qnil;
7b863bd5 2604
daa37602
JB
2605 if (loads < 0)
2606 error ("load-average not implemented for this operating system");
2607
f4b50f66
RS
2608 while (loads-- > 0)
2609 {
566684ea
PE
2610 Lisp_Object load = (NILP (use_floats)
2611 ? make_number (100.0 * load_ave[loads])
f4b50f66
RS
2612 : make_float (load_ave[loads]));
2613 ret = Fcons (load, ret);
2614 }
daa37602
JB
2615
2616 return ret;
2617}
7b863bd5 2618\f
955cbe7b 2619static Lisp_Object Qsubfeatures;
7b863bd5 2620
65550192 2621DEFUN ("featurep", Ffeaturep, Sfeaturep, 1, 2, 0,
b756c005 2622 doc: /* Return t if FEATURE is present in this Emacs.
91f78c99 2623
47cebab1 2624Use this to conditionalize execution of lisp code based on the
4774b68e 2625presence or absence of Emacs or environment extensions.
47cebab1
GM
2626Use `provide' to declare that a feature is available. This function
2627looks at the value of the variable `features'. The optional argument
e9d8ddc9 2628SUBFEATURE can be used to check a specific subfeature of FEATURE. */)
5842a27b 2629 (Lisp_Object feature, Lisp_Object subfeature)
7b863bd5
JB
2630{
2631 register Lisp_Object tem;
b7826503 2632 CHECK_SYMBOL (feature);
7b863bd5 2633 tem = Fmemq (feature, Vfeatures);
65550192 2634 if (!NILP (tem) && !NILP (subfeature))
37ebddef 2635 tem = Fmember (subfeature, Fget (feature, Qsubfeatures));
265a9e55 2636 return (NILP (tem)) ? Qnil : Qt;
7b863bd5
JB
2637}
2638
de0503df
SM
2639static Lisp_Object Qfuncall;
2640
a7ca3326 2641DEFUN ("provide", Fprovide, Sprovide, 1, 2, 0,
e9d8ddc9 2642 doc: /* Announce that FEATURE is a feature of the current Emacs.
47cebab1 2643The optional argument SUBFEATURES should be a list of symbols listing
e9d8ddc9 2644particular subfeatures supported in this version of FEATURE. */)
5842a27b 2645 (Lisp_Object feature, Lisp_Object subfeatures)
7b863bd5
JB
2646{
2647 register Lisp_Object tem;
b7826503 2648 CHECK_SYMBOL (feature);
37ebddef 2649 CHECK_LIST (subfeatures);
265a9e55 2650 if (!NILP (Vautoload_queue))
989e66e1
RS
2651 Vautoload_queue = Fcons (Fcons (make_number (0), Vfeatures),
2652 Vautoload_queue);
7b863bd5 2653 tem = Fmemq (feature, Vfeatures);
265a9e55 2654 if (NILP (tem))
7b863bd5 2655 Vfeatures = Fcons (feature, Vfeatures);
65550192
SM
2656 if (!NILP (subfeatures))
2657 Fput (feature, Qsubfeatures, subfeatures);
68732608 2658 LOADHIST_ATTACH (Fcons (Qprovide, feature));
65550192
SM
2659
2660 /* Run any load-hooks for this file. */
2661 tem = Fassq (feature, Vafter_load_alist);
cf42cb72 2662 if (CONSP (tem))
de0503df 2663 Fmapc (Qfuncall, XCDR (tem));
65550192 2664
7b863bd5
JB
2665 return feature;
2666}
1f79789d
RS
2667\f
2668/* `require' and its subroutines. */
2669
2670/* List of features currently being require'd, innermost first. */
2671
2a80c887 2672static Lisp_Object require_nesting_list;
1f79789d 2673
27e498e6 2674static void
971de7fb 2675require_unwind (Lisp_Object old_value)
1f79789d 2676{
27e498e6 2677 require_nesting_list = old_value;
1f79789d 2678}
7b863bd5 2679
53d5acf5 2680DEFUN ("require", Frequire, Srequire, 1, 3, 0,
e9d8ddc9 2681 doc: /* If feature FEATURE is not loaded, load it from FILENAME.
47cebab1
GM
2682If FEATURE is not a member of the list `features', then the feature
2683is not loaded; so load the file FILENAME.
2684If FILENAME is omitted, the printname of FEATURE is used as the file name,
6b61353c
KH
2685and `load' will try to load this name appended with the suffix `.elc' or
2686`.el', in that order. The name without appended suffix will not be used.
90186c68 2687See `get-load-suffixes' for the complete list of suffixes.
47cebab1
GM
2688If the optional third argument NOERROR is non-nil,
2689then return nil if the file is not found instead of signaling an error.
2690Normally the return value is FEATURE.
e9d8ddc9 2691The normal messages at start and end of loading FILENAME are suppressed. */)
5842a27b 2692 (Lisp_Object feature, Lisp_Object filename, Lisp_Object noerror)
7b863bd5 2693{
f75d7a91 2694 Lisp_Object tem;
1f79789d 2695 struct gcpro gcpro1, gcpro2;
f75d7a91 2696 bool from_file = load_in_progress;
1f79789d 2697
b7826503 2698 CHECK_SYMBOL (feature);
1f79789d 2699
5ba8f83d 2700 /* Record the presence of `require' in this file
9d5c2e7e
RS
2701 even if the feature specified is already loaded.
2702 But not more than once in any file,
06100606
RS
2703 and not when we aren't loading or reading from a file. */
2704 if (!from_file)
2705 for (tem = Vcurrent_load_list; CONSP (tem); tem = XCDR (tem))
2706 if (NILP (XCDR (tem)) && STRINGP (XCAR (tem)))
2707 from_file = 1;
2708
2709 if (from_file)
9d5c2e7e
RS
2710 {
2711 tem = Fcons (Qrequire, feature);
2712 if (NILP (Fmember (tem, Vcurrent_load_list)))
2713 LOADHIST_ATTACH (tem);
2714 }
7b863bd5 2715 tem = Fmemq (feature, Vfeatures);
91f78c99 2716
265a9e55 2717 if (NILP (tem))
7b863bd5 2718 {
d311d28c 2719 ptrdiff_t count = SPECPDL_INDEX ();
1f79789d 2720 int nesting = 0;
bcb31b2a 2721
aea6173f
RS
2722 /* This is to make sure that loadup.el gives a clear picture
2723 of what files are preloaded and when. */
bcb31b2a
RS
2724 if (! NILP (Vpurify_flag))
2725 error ("(require %s) while preparing to dump",
d5db4077 2726 SDATA (SYMBOL_NAME (feature)));
91f78c99 2727
1f79789d
RS
2728 /* A certain amount of recursive `require' is legitimate,
2729 but if we require the same feature recursively 3 times,
2730 signal an error. */
2731 tem = require_nesting_list;
2732 while (! NILP (tem))
2733 {
2734 if (! NILP (Fequal (feature, XCAR (tem))))
2735 nesting++;
2736 tem = XCDR (tem);
2737 }
f707342d 2738 if (nesting > 3)
1f79789d 2739 error ("Recursive `require' for feature `%s'",
d5db4077 2740 SDATA (SYMBOL_NAME (feature)));
1f79789d
RS
2741
2742 /* Update the list for any nested `require's that occur. */
2743 record_unwind_protect (require_unwind, require_nesting_list);
2744 require_nesting_list = Fcons (feature, require_nesting_list);
7b863bd5
JB
2745
2746 /* Value saved here is to be restored into Vautoload_queue */
2747 record_unwind_protect (un_autoload, Vautoload_queue);
2748 Vautoload_queue = Qt;
2749
1f79789d
RS
2750 /* Load the file. */
2751 GCPRO2 (feature, filename);
81a81c0f
GM
2752 tem = Fload (NILP (filename) ? Fsymbol_name (feature) : filename,
2753 noerror, Qt, Qnil, (NILP (filename) ? Qt : Qnil));
1f79789d
RS
2754 UNGCPRO;
2755
53d5acf5
RS
2756 /* If load failed entirely, return nil. */
2757 if (NILP (tem))
41857307 2758 return unbind_to (count, Qnil);
7b863bd5
JB
2759
2760 tem = Fmemq (feature, Vfeatures);
265a9e55 2761 if (NILP (tem))
1f79789d 2762 error ("Required feature `%s' was not provided",
d5db4077 2763 SDATA (SYMBOL_NAME (feature)));
7b863bd5
JB
2764
2765 /* Once loading finishes, don't undo it. */
2766 Vautoload_queue = Qt;
2767 feature = unbind_to (count, feature);
2768 }
1f79789d 2769
7b863bd5
JB
2770 return feature;
2771}
2772\f
b4f334f7
KH
2773/* Primitives for work of the "widget" library.
2774 In an ideal world, this section would not have been necessary.
2775 However, lisp function calls being as slow as they are, it turns
2776 out that some functions in the widget library (wid-edit.el) are the
2777 bottleneck of Widget operation. Here is their translation to C,
2778 for the sole reason of efficiency. */
2779
a7ca3326 2780DEFUN ("plist-member", Fplist_member, Splist_member, 2, 2, 0,
e9d8ddc9 2781 doc: /* Return non-nil if PLIST has the property PROP.
47cebab1
GM
2782PLIST is a property list, which is a list of the form
2783\(PROP1 VALUE1 PROP2 VALUE2 ...\). PROP is a symbol.
2784Unlike `plist-get', this allows you to distinguish between a missing
2785property and a property with the value nil.
e9d8ddc9 2786The value is actually the tail of PLIST whose car is PROP. */)
5842a27b 2787 (Lisp_Object plist, Lisp_Object prop)
b4f334f7
KH
2788{
2789 while (CONSP (plist) && !EQ (XCAR (plist), prop))
2790 {
2791 QUIT;
2792 plist = XCDR (plist);
2793 plist = CDR (plist);
2794 }
2795 return plist;
2796}
2797
2798DEFUN ("widget-put", Fwidget_put, Swidget_put, 3, 3, 0,
e9d8ddc9
MB
2799 doc: /* In WIDGET, set PROPERTY to VALUE.
2800The value can later be retrieved with `widget-get'. */)
5842a27b 2801 (Lisp_Object widget, Lisp_Object property, Lisp_Object value)
b4f334f7 2802{
b7826503 2803 CHECK_CONS (widget);
f3fbd155 2804 XSETCDR (widget, Fplist_put (XCDR (widget), property, value));
f7993597 2805 return value;
b4f334f7
KH
2806}
2807
2808DEFUN ("widget-get", Fwidget_get, Swidget_get, 2, 2, 0,
e9d8ddc9 2809 doc: /* In WIDGET, get the value of PROPERTY.
47cebab1 2810The value could either be specified when the widget was created, or
e9d8ddc9 2811later with `widget-put'. */)
5842a27b 2812 (Lisp_Object widget, Lisp_Object property)
b4f334f7
KH
2813{
2814 Lisp_Object tmp;
2815
2816 while (1)
2817 {
2818 if (NILP (widget))
2819 return Qnil;
b7826503 2820 CHECK_CONS (widget);
a5254817 2821 tmp = Fplist_member (XCDR (widget), property);
b4f334f7
KH
2822 if (CONSP (tmp))
2823 {
2824 tmp = XCDR (tmp);
2825 return CAR (tmp);
2826 }
2827 tmp = XCAR (widget);
2828 if (NILP (tmp))
2829 return Qnil;
2830 widget = Fget (tmp, Qwidget_type);
2831 }
2832}
2833
2834DEFUN ("widget-apply", Fwidget_apply, Swidget_apply, 2, MANY, 0,
e9d8ddc9 2835 doc: /* Apply the value of WIDGET's PROPERTY to the widget itself.
4bf8e2a3
MB
2836ARGS are passed as extra arguments to the function.
2837usage: (widget-apply WIDGET PROPERTY &rest ARGS) */)
f66c7cf8 2838 (ptrdiff_t nargs, Lisp_Object *args)
b4f334f7 2839{
b09cca6a 2840 /* This function can GC. */
b4f334f7
KH
2841 Lisp_Object newargs[3];
2842 struct gcpro gcpro1, gcpro2;
2843 Lisp_Object result;
2844
2845 newargs[0] = Fwidget_get (args[0], args[1]);
2846 newargs[1] = args[0];
2847 newargs[2] = Flist (nargs - 2, args + 2);
2848 GCPRO2 (newargs[0], newargs[2]);
2849 result = Fapply (3, newargs);
2850 UNGCPRO;
2851 return result;
2852}
dec002ca
DL
2853
2854#ifdef HAVE_LANGINFO_CODESET
2855#include <langinfo.h>
2856#endif
2857
d68beb2f
RS
2858DEFUN ("locale-info", Flocale_info, Slocale_info, 1, 1, 0,
2859 doc: /* Access locale data ITEM for the current C locale, if available.
2860ITEM should be one of the following:
30b1b0cf 2861
98aeeaa1 2862`codeset', returning the character set as a string (locale item CODESET);
30b1b0cf 2863
98aeeaa1 2864`days', returning a 7-element vector of day names (locale items DAY_n);
30b1b0cf 2865
98aeeaa1 2866`months', returning a 12-element vector of month names (locale items MON_n);
30b1b0cf 2867
d68beb2f 2868`paper', returning a list (WIDTH HEIGHT) for the default paper size,
66699ad3 2869 both measured in millimeters (locale items PAPER_WIDTH, PAPER_HEIGHT).
dec002ca
DL
2870
2871If the system can't provide such information through a call to
d68beb2f 2872`nl_langinfo', or if ITEM isn't from the list above, return nil.
dec002ca 2873
98aeeaa1
DL
2874See also Info node `(libc)Locales'.
2875
dec002ca 2876The data read from the system are decoded using `locale-coding-system'. */)
5842a27b 2877 (Lisp_Object item)
dec002ca
DL
2878{
2879 char *str = NULL;
2880#ifdef HAVE_LANGINFO_CODESET
2881 Lisp_Object val;
2882 if (EQ (item, Qcodeset))
2883 {
2884 str = nl_langinfo (CODESET);
2885 return build_string (str);
2886 }
2887#ifdef DAY_1
2888 else if (EQ (item, Qdays)) /* e.g. for calendar-day-name-array */
2889 {
2890 Lisp_Object v = Fmake_vector (make_number (7), Qnil);
77bf07e1 2891 const int days[7] = {DAY_1, DAY_2, DAY_3, DAY_4, DAY_5, DAY_6, DAY_7};
dec002ca 2892 int i;
77bf07e1
AS
2893 struct gcpro gcpro1;
2894 GCPRO1 (v);
dec002ca
DL
2895 synchronize_system_time_locale ();
2896 for (i = 0; i < 7; i++)
2897 {
2898 str = nl_langinfo (days[i]);
d7ea76b4 2899 val = build_unibyte_string (str);
dec002ca
DL
2900 /* Fixme: Is this coding system necessarily right, even if
2901 it is consistent with CODESET? If not, what to do? */
9a9d91d9
DA
2902 ASET (v, i, code_convert_string_norecord (val, Vlocale_coding_system,
2903 0));
dec002ca 2904 }
77bf07e1 2905 UNGCPRO;
dec002ca
DL
2906 return v;
2907 }
2908#endif /* DAY_1 */
2909#ifdef MON_1
2910 else if (EQ (item, Qmonths)) /* e.g. for calendar-month-name-array */
2911 {
77bf07e1
AS
2912 Lisp_Object v = Fmake_vector (make_number (12), Qnil);
2913 const int months[12] = {MON_1, MON_2, MON_3, MON_4, MON_5, MON_6, MON_7,
2914 MON_8, MON_9, MON_10, MON_11, MON_12};
dec002ca 2915 int i;
77bf07e1
AS
2916 struct gcpro gcpro1;
2917 GCPRO1 (v);
dec002ca
DL
2918 synchronize_system_time_locale ();
2919 for (i = 0; i < 12; i++)
2920 {
2921 str = nl_langinfo (months[i]);
d7ea76b4 2922 val = build_unibyte_string (str);
9a9d91d9
DA
2923 ASET (v, i, code_convert_string_norecord (val, Vlocale_coding_system,
2924 0));
dec002ca 2925 }
77bf07e1
AS
2926 UNGCPRO;
2927 return v;
dec002ca
DL
2928 }
2929#endif /* MON_1 */
2930/* LC_PAPER stuff isn't defined as accessible in glibc as of 2.3.1,
2931 but is in the locale files. This could be used by ps-print. */
2932#ifdef PAPER_WIDTH
2933 else if (EQ (item, Qpaper))
3de717bd 2934 return list2i (nl_langinfo (PAPER_WIDTH), nl_langinfo (PAPER_HEIGHT));
dec002ca
DL
2935#endif /* PAPER_WIDTH */
2936#endif /* HAVE_LANGINFO_CODESET*/
30b1b0cf 2937 return Qnil;
dec002ca 2938}
b4f334f7 2939\f
a90e80bf 2940/* base64 encode/decode functions (RFC 2045).
24c129e4
KH
2941 Based on code from GNU recode. */
2942
2943#define MIME_LINE_LENGTH 76
2944
2945#define IS_ASCII(Character) \
2946 ((Character) < 128)
2947#define IS_BASE64(Character) \
2948 (IS_ASCII (Character) && base64_char_to_value[Character] >= 0)
9a092df0
PF
2949#define IS_BASE64_IGNORABLE(Character) \
2950 ((Character) == ' ' || (Character) == '\t' || (Character) == '\n' \
2951 || (Character) == '\f' || (Character) == '\r')
2952
2953/* Used by base64_decode_1 to retrieve a non-base64-ignorable
2954 character or return retval if there are no characters left to
2955 process. */
caff31d4
KH
2956#define READ_QUADRUPLET_BYTE(retval) \
2957 do \
2958 { \
2959 if (i == length) \
2960 { \
2961 if (nchars_return) \
2962 *nchars_return = nchars; \
2963 return (retval); \
2964 } \
2965 c = from[i++]; \
2966 } \
9a092df0 2967 while (IS_BASE64_IGNORABLE (c))
24c129e4
KH
2968
2969/* Table of characters coding the 64 values. */
91433552 2970static const char base64_value_to_char[64] =
24c129e4
KH
2971{
2972 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', /* 0- 9 */
2973 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', /* 10-19 */
2974 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd', /* 20-29 */
2975 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', /* 30-39 */
2976 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', /* 40-49 */
2977 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7', /* 50-59 */
2978 '8', '9', '+', '/' /* 60-63 */
2979};
2980
2981/* Table of base64 values for first 128 characters. */
91433552 2982static const short base64_char_to_value[128] =
24c129e4
KH
2983{
2984 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 0- 9 */
2985 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 10- 19 */
2986 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 20- 29 */
2987 -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, /* 30- 39 */
2988 -1, -1, -1, 62, -1, -1, -1, 63, 52, 53, /* 40- 49 */
2989 54, 55, 56, 57, 58, 59, 60, 61, -1, -1, /* 50- 59 */
2990 -1, -1, -1, -1, -1, 0, 1, 2, 3, 4, /* 60- 69 */
2991 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, /* 70- 79 */
2992 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, /* 80- 89 */
2993 25, -1, -1, -1, -1, -1, -1, 26, 27, 28, /* 90- 99 */
2994 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, /* 100-109 */
2995 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, /* 110-119 */
2996 49, 50, 51, -1, -1, -1, -1, -1 /* 120-127 */
2997};
2998
2999/* The following diagram shows the logical steps by which three octets
3000 get transformed into four base64 characters.
3001
3002 .--------. .--------. .--------.
3003 |aaaaaabb| |bbbbcccc| |ccdddddd|
3004 `--------' `--------' `--------'
3005 6 2 4 4 2 6
3006 .--------+--------+--------+--------.
3007 |00aaaaaa|00bbbbbb|00cccccc|00dddddd|
3008 `--------+--------+--------+--------'
3009
3010 .--------+--------+--------+--------.
3011 |AAAAAAAA|BBBBBBBB|CCCCCCCC|DDDDDDDD|
3012 `--------+--------+--------+--------'
3013
3014 The octets are divided into 6 bit chunks, which are then encoded into
3015 base64 characters. */
3016
3017
f75d7a91
PE
3018static ptrdiff_t base64_encode_1 (const char *, char *, ptrdiff_t, bool, bool);
3019static ptrdiff_t base64_decode_1 (const char *, char *, ptrdiff_t, bool,
d311d28c 3020 ptrdiff_t *);
24c129e4
KH
3021
3022DEFUN ("base64-encode-region", Fbase64_encode_region, Sbase64_encode_region,
3023 2, 3, "r",
e9d8ddc9 3024 doc: /* Base64-encode the region between BEG and END.
47cebab1
GM
3025Return the length of the encoded text.
3026Optional third argument NO-LINE-BREAK means do not break long lines
e9d8ddc9 3027into shorter lines. */)
5842a27b 3028 (Lisp_Object beg, Lisp_Object end, Lisp_Object no_line_break)
24c129e4
KH
3029{
3030 char *encoded;
d311d28c
PE
3031 ptrdiff_t allength, length;
3032 ptrdiff_t ibeg, iend, encoded_length;
3033 ptrdiff_t old_pos = PT;
799c08ac 3034 USE_SAFE_ALLOCA;
24c129e4
KH
3035
3036 validate_region (&beg, &end);
3037
3038 ibeg = CHAR_TO_BYTE (XFASTINT (beg));
3039 iend = CHAR_TO_BYTE (XFASTINT (end));
3040 move_gap_both (XFASTINT (beg), ibeg);
3041
3042 /* We need to allocate enough room for encoding the text.
3043 We need 33 1/3% more space, plus a newline every 76
3044 characters, and then we round up. */
3045 length = iend - ibeg;
3046 allength = length + length/3 + 1;
3047 allength += allength / MIME_LINE_LENGTH + 1 + 6;
3048
98c6f1e3 3049 encoded = SAFE_ALLOCA (allength);
f1e59824
PE
3050 encoded_length = base64_encode_1 ((char *) BYTE_POS_ADDR (ibeg),
3051 encoded, length, NILP (no_line_break),
4b4deea2 3052 !NILP (BVAR (current_buffer, enable_multibyte_characters)));
24c129e4 3053 if (encoded_length > allength)
1088b922 3054 emacs_abort ();
24c129e4 3055
2efdd1b9
KH
3056 if (encoded_length < 0)
3057 {
3058 /* The encoding wasn't possible. */
233f3db6 3059 SAFE_FREE ();
a90e80bf 3060 error ("Multibyte character in data for base64 encoding");
2efdd1b9
KH
3061 }
3062
24c129e4
KH
3063 /* Now we have encoded the region, so we insert the new contents
3064 and delete the old. (Insert first in order to preserve markers.) */
8b835738 3065 SET_PT_BOTH (XFASTINT (beg), ibeg);
24c129e4 3066 insert (encoded, encoded_length);
233f3db6 3067 SAFE_FREE ();
24c129e4
KH
3068 del_range_byte (ibeg + encoded_length, iend + encoded_length, 1);
3069
3070 /* If point was outside of the region, restore it exactly; else just
3071 move to the beginning of the region. */
3072 if (old_pos >= XFASTINT (end))
3073 old_pos += encoded_length - (XFASTINT (end) - XFASTINT (beg));
8b835738
AS
3074 else if (old_pos > XFASTINT (beg))
3075 old_pos = XFASTINT (beg);
24c129e4
KH
3076 SET_PT (old_pos);
3077
3078 /* We return the length of the encoded text. */
3079 return make_number (encoded_length);
3080}
3081
3082DEFUN ("base64-encode-string", Fbase64_encode_string, Sbase64_encode_string,
c22554ac 3083 1, 2, 0,
e9d8ddc9 3084 doc: /* Base64-encode STRING and return the result.
47cebab1 3085Optional second argument NO-LINE-BREAK means do not break long lines
e9d8ddc9 3086into shorter lines. */)
5842a27b 3087 (Lisp_Object string, Lisp_Object no_line_break)
24c129e4 3088{
d311d28c 3089 ptrdiff_t allength, length, encoded_length;
24c129e4 3090 char *encoded;
4b2e75e6 3091 Lisp_Object encoded_string;
799c08ac 3092 USE_SAFE_ALLOCA;
24c129e4 3093
b7826503 3094 CHECK_STRING (string);
24c129e4 3095
7f8a0840
KH
3096 /* We need to allocate enough room for encoding the text.
3097 We need 33 1/3% more space, plus a newline every 76
3098 characters, and then we round up. */
d5db4077 3099 length = SBYTES (string);
7f8a0840
KH
3100 allength = length + length/3 + 1;
3101 allength += allength / MIME_LINE_LENGTH + 1 + 6;
24c129e4
KH
3102
3103 /* We need to allocate enough room for decoding the text. */
98c6f1e3 3104 encoded = SAFE_ALLOCA (allength);
24c129e4 3105
42a5b22f 3106 encoded_length = base64_encode_1 (SSDATA (string),
2efdd1b9
KH
3107 encoded, length, NILP (no_line_break),
3108 STRING_MULTIBYTE (string));
24c129e4 3109 if (encoded_length > allength)
1088b922 3110 emacs_abort ();
24c129e4 3111
2efdd1b9
KH
3112 if (encoded_length < 0)
3113 {
3114 /* The encoding wasn't possible. */
233f3db6 3115 SAFE_FREE ();
a90e80bf 3116 error ("Multibyte character in data for base64 encoding");
2efdd1b9
KH
3117 }
3118
4b2e75e6 3119 encoded_string = make_unibyte_string (encoded, encoded_length);
233f3db6 3120 SAFE_FREE ();
4b2e75e6
EZ
3121
3122 return encoded_string;
24c129e4
KH
3123}
3124
d311d28c
PE
3125static ptrdiff_t
3126base64_encode_1 (const char *from, char *to, ptrdiff_t length,
f75d7a91 3127 bool line_break, bool multibyte)
24c129e4 3128{
e6d4aefa 3129 int counter = 0;
d311d28c 3130 ptrdiff_t i = 0;
24c129e4 3131 char *e = to;
844eb643 3132 int c;
24c129e4 3133 unsigned int value;
2efdd1b9 3134 int bytes;
24c129e4
KH
3135
3136 while (i < length)
3137 {
2efdd1b9
KH
3138 if (multibyte)
3139 {
f1e59824 3140 c = STRING_CHAR_AND_LENGTH ((unsigned char *) from + i, bytes);
680d4b87
KH
3141 if (CHAR_BYTE8_P (c))
3142 c = CHAR_TO_BYTE8 (c);
3143 else if (c >= 256)
2efdd1b9 3144 return -1;
caff31d4 3145 i += bytes;
2efdd1b9
KH
3146 }
3147 else
3148 c = from[i++];
24c129e4
KH
3149
3150 /* Wrap line every 76 characters. */
3151
3152 if (line_break)
3153 {
3154 if (counter < MIME_LINE_LENGTH / 4)
3155 counter++;
3156 else
3157 {
3158 *e++ = '\n';
3159 counter = 1;
3160 }
3161 }
3162
3163 /* Process first byte of a triplet. */
3164
3165 *e++ = base64_value_to_char[0x3f & c >> 2];
3166 value = (0x03 & c) << 4;
3167
3168 /* Process second byte of a triplet. */
3169
3170 if (i == length)
3171 {
3172 *e++ = base64_value_to_char[value];
3173 *e++ = '=';
3174 *e++ = '=';
3175 break;
3176 }
3177
2efdd1b9
KH
3178 if (multibyte)
3179 {
f1e59824 3180 c = STRING_CHAR_AND_LENGTH ((unsigned char *) from + i, bytes);
680d4b87
KH
3181 if (CHAR_BYTE8_P (c))
3182 c = CHAR_TO_BYTE8 (c);
3183 else if (c >= 256)
9b40fbe6 3184 return -1;
caff31d4 3185 i += bytes;
2efdd1b9
KH
3186 }
3187 else
3188 c = from[i++];
24c129e4
KH
3189
3190 *e++ = base64_value_to_char[value | (0x0f & c >> 4)];
3191 value = (0x0f & c) << 2;
3192
3193 /* Process third byte of a triplet. */
3194
3195 if (i == length)
3196 {
3197 *e++ = base64_value_to_char[value];
3198 *e++ = '=';
3199 break;
3200 }
3201
2efdd1b9
KH
3202 if (multibyte)
3203 {
f1e59824 3204 c = STRING_CHAR_AND_LENGTH ((unsigned char *) from + i, bytes);
680d4b87
KH
3205 if (CHAR_BYTE8_P (c))
3206 c = CHAR_TO_BYTE8 (c);
3207 else if (c >= 256)
844eb643 3208 return -1;
caff31d4 3209 i += bytes;
2efdd1b9
KH
3210 }
3211 else
3212 c = from[i++];
24c129e4
KH
3213
3214 *e++ = base64_value_to_char[value | (0x03 & c >> 6)];
3215 *e++ = base64_value_to_char[0x3f & c];
3216 }
3217
24c129e4
KH
3218 return e - to;
3219}
3220
3221
3222DEFUN ("base64-decode-region", Fbase64_decode_region, Sbase64_decode_region,
47cebab1 3223 2, 2, "r",
e9d8ddc9 3224 doc: /* Base64-decode the region between BEG and END.
47cebab1 3225Return the length of the decoded text.
e9d8ddc9 3226If the region can't be decoded, signal an error and don't modify the buffer. */)
5842a27b 3227 (Lisp_Object beg, Lisp_Object end)
24c129e4 3228{
d311d28c 3229 ptrdiff_t ibeg, iend, length, allength;
24c129e4 3230 char *decoded;
d311d28c
PE
3231 ptrdiff_t old_pos = PT;
3232 ptrdiff_t decoded_length;
3233 ptrdiff_t inserted_chars;
f75d7a91 3234 bool multibyte = !NILP (BVAR (current_buffer, enable_multibyte_characters));
799c08ac 3235 USE_SAFE_ALLOCA;
24c129e4
KH
3236
3237 validate_region (&beg, &end);
3238
3239 ibeg = CHAR_TO_BYTE (XFASTINT (beg));
3240 iend = CHAR_TO_BYTE (XFASTINT (end));
3241
3242 length = iend - ibeg;
caff31d4
KH
3243
3244 /* We need to allocate enough room for decoding the text. If we are
3245 working on a multibyte buffer, each decoded code may occupy at
3246 most two bytes. */
3247 allength = multibyte ? length * 2 : length;
98c6f1e3 3248 decoded = SAFE_ALLOCA (allength);
24c129e4
KH
3249
3250 move_gap_both (XFASTINT (beg), ibeg);
f1e59824
PE
3251 decoded_length = base64_decode_1 ((char *) BYTE_POS_ADDR (ibeg),
3252 decoded, length,
caff31d4
KH
3253 multibyte, &inserted_chars);
3254 if (decoded_length > allength)
1088b922 3255 emacs_abort ();
24c129e4
KH
3256
3257 if (decoded_length < 0)
8c217645
KH
3258 {
3259 /* The decoding wasn't possible. */
233f3db6 3260 SAFE_FREE ();
a90e80bf 3261 error ("Invalid base64 data");
8c217645 3262 }
24c129e4
KH
3263
3264 /* Now we have decoded the region, so we insert the new contents
3265 and delete the old. (Insert first in order to preserve markers.) */
59f953a2 3266 TEMP_SET_PT_BOTH (XFASTINT (beg), ibeg);
2efdd1b9 3267 insert_1_both (decoded, inserted_chars, decoded_length, 0, 1, 0);
233f3db6 3268 SAFE_FREE ();
799c08ac 3269
2efdd1b9
KH
3270 /* Delete the original text. */
3271 del_range_both (PT, PT_BYTE, XFASTINT (end) + inserted_chars,
3272 iend + decoded_length, 1);
24c129e4
KH
3273
3274 /* If point was outside of the region, restore it exactly; else just
3275 move to the beginning of the region. */
3276 if (old_pos >= XFASTINT (end))
9b703a38
KH
3277 old_pos += inserted_chars - (XFASTINT (end) - XFASTINT (beg));
3278 else if (old_pos > XFASTINT (beg))
3279 old_pos = XFASTINT (beg);
e52ad9c9 3280 SET_PT (old_pos > ZV ? ZV : old_pos);
24c129e4 3281
9b703a38 3282 return make_number (inserted_chars);
24c129e4
KH
3283}
3284
3285DEFUN ("base64-decode-string", Fbase64_decode_string, Sbase64_decode_string,
3286 1, 1, 0,
e9d8ddc9 3287 doc: /* Base64-decode STRING and return the result. */)
5842a27b 3288 (Lisp_Object string)
24c129e4
KH
3289{
3290 char *decoded;
d311d28c 3291 ptrdiff_t length, decoded_length;
4b2e75e6 3292 Lisp_Object decoded_string;
799c08ac 3293 USE_SAFE_ALLOCA;
24c129e4 3294
b7826503 3295 CHECK_STRING (string);
24c129e4 3296
d5db4077 3297 length = SBYTES (string);
24c129e4 3298 /* We need to allocate enough room for decoding the text. */
98c6f1e3 3299 decoded = SAFE_ALLOCA (length);
24c129e4 3300
8ec118cd 3301 /* The decoded result should be unibyte. */
42a5b22f 3302 decoded_length = base64_decode_1 (SSDATA (string), decoded, length,
8ec118cd 3303 0, NULL);
24c129e4 3304 if (decoded_length > length)
1088b922 3305 emacs_abort ();
3d6c79c5 3306 else if (decoded_length >= 0)
2efdd1b9 3307 decoded_string = make_unibyte_string (decoded, decoded_length);
3d6c79c5
GM
3308 else
3309 decoded_string = Qnil;
24c129e4 3310
233f3db6 3311 SAFE_FREE ();
3d6c79c5 3312 if (!STRINGP (decoded_string))
a90e80bf 3313 error ("Invalid base64 data");
4b2e75e6
EZ
3314
3315 return decoded_string;
24c129e4
KH
3316}
3317
53964682 3318/* Base64-decode the data at FROM of LENGTH bytes into TO. If
f75d7a91 3319 MULTIBYTE, the decoded result should be in multibyte
9858f6c3 3320 form. If NCHARS_RETURN is not NULL, store the number of produced
caff31d4
KH
3321 characters in *NCHARS_RETURN. */
3322
d311d28c
PE
3323static ptrdiff_t
3324base64_decode_1 (const char *from, char *to, ptrdiff_t length,
f75d7a91 3325 bool multibyte, ptrdiff_t *nchars_return)
24c129e4 3326{
d311d28c 3327 ptrdiff_t i = 0; /* Used inside READ_QUADRUPLET_BYTE */
24c129e4
KH
3328 char *e = to;
3329 unsigned char c;
3330 unsigned long value;
d311d28c 3331 ptrdiff_t nchars = 0;
24c129e4 3332
9a092df0 3333 while (1)
24c129e4 3334 {
9a092df0 3335 /* Process first byte of a quadruplet. */
24c129e4 3336
9a092df0 3337 READ_QUADRUPLET_BYTE (e-to);
24c129e4
KH
3338
3339 if (!IS_BASE64 (c))
3340 return -1;
3341 value = base64_char_to_value[c] << 18;
3342
3343 /* Process second byte of a quadruplet. */
3344
9a092df0 3345 READ_QUADRUPLET_BYTE (-1);
24c129e4
KH
3346
3347 if (!IS_BASE64 (c))
3348 return -1;
3349 value |= base64_char_to_value[c] << 12;
3350
caff31d4 3351 c = (unsigned char) (value >> 16);
5a38b8c5
KH
3352 if (multibyte && c >= 128)
3353 e += BYTE8_STRING (c, e);
caff31d4
KH
3354 else
3355 *e++ = c;
3356 nchars++;
24c129e4
KH
3357
3358 /* Process third byte of a quadruplet. */
59f953a2 3359
9a092df0 3360 READ_QUADRUPLET_BYTE (-1);
24c129e4
KH
3361
3362 if (c == '=')
3363 {
9a092df0 3364 READ_QUADRUPLET_BYTE (-1);
59f953a2 3365
24c129e4
KH
3366 if (c != '=')
3367 return -1;
3368 continue;
3369 }
3370
3371 if (!IS_BASE64 (c))
3372 return -1;
3373 value |= base64_char_to_value[c] << 6;
3374
caff31d4 3375 c = (unsigned char) (0xff & value >> 8);
5a38b8c5
KH
3376 if (multibyte && c >= 128)
3377 e += BYTE8_STRING (c, e);
caff31d4
KH
3378 else
3379 *e++ = c;
3380 nchars++;
24c129e4
KH
3381
3382 /* Process fourth byte of a quadruplet. */
3383
9a092df0 3384 READ_QUADRUPLET_BYTE (-1);
24c129e4
KH
3385
3386 if (c == '=')
3387 continue;
3388
3389 if (!IS_BASE64 (c))
3390 return -1;
3391 value |= base64_char_to_value[c];
3392
caff31d4 3393 c = (unsigned char) (0xff & value);
5a38b8c5
KH
3394 if (multibyte && c >= 128)
3395 e += BYTE8_STRING (c, e);
caff31d4
KH
3396 else
3397 *e++ = c;
3398 nchars++;
24c129e4 3399 }
24c129e4 3400}
d80c6c11
GM
3401
3402
3403\f
3404/***********************************************************************
3405 ***** *****
3406 ***** Hash Tables *****
3407 ***** *****
3408 ***********************************************************************/
3409
3410/* Implemented by gerd@gnu.org. This hash table implementation was
3411 inspired by CMUCL hash tables. */
3412
3413/* Ideas:
3414
3415 1. For small tables, association lists are probably faster than
3416 hash tables because they have lower overhead.
3417
3418 For uses of hash tables where the O(1) behavior of table
3419 operations is not a requirement, it might therefore be a good idea
3420 not to hash. Instead, we could just do a linear search in the
3421 key_and_value vector of the hash table. This could be done
3422 if a `:linear-search t' argument is given to make-hash-table. */
3423
3424
d80c6c11
GM
3425/* The list of all weak hash tables. Don't staticpro this one. */
3426
dfcf3579 3427static struct Lisp_Hash_Table *weak_hash_tables;
d80c6c11
GM
3428
3429/* Various symbols. */
3430
84575e67
PE
3431static Lisp_Object Qhash_table_p;
3432static Lisp_Object Qkey, Qvalue, Qeql;
53371430 3433Lisp_Object Qeq, Qequal;
ee0403b3 3434Lisp_Object QCtest, QCsize, QCrehash_size, QCrehash_threshold, QCweakness;
955cbe7b 3435static Lisp_Object Qhash_table_test, Qkey_or_value, Qkey_and_value;
d80c6c11 3436
d80c6c11
GM
3437\f
3438/***********************************************************************
3439 Utilities
3440 ***********************************************************************/
3441
84575e67
PE
3442static void
3443CHECK_HASH_TABLE (Lisp_Object x)
3444{
3445 CHECK_TYPE (HASH_TABLE_P (x), Qhash_table_p, x);
3446}
3447
3448static void
3449set_hash_key_and_value (struct Lisp_Hash_Table *h, Lisp_Object key_and_value)
3450{
3451 h->key_and_value = key_and_value;
3452}
3453static void
3454set_hash_next (struct Lisp_Hash_Table *h, Lisp_Object next)
3455{
3456 h->next = next;
3457}
3458static void
3459set_hash_next_slot (struct Lisp_Hash_Table *h, ptrdiff_t idx, Lisp_Object val)
3460{
3461 gc_aset (h->next, idx, val);
3462}
3463static void
3464set_hash_hash (struct Lisp_Hash_Table *h, Lisp_Object hash)
3465{
3466 h->hash = hash;
3467}
3468static void
3469set_hash_hash_slot (struct Lisp_Hash_Table *h, ptrdiff_t idx, Lisp_Object val)
3470{
3471 gc_aset (h->hash, idx, val);
3472}
3473static void
3474set_hash_index (struct Lisp_Hash_Table *h, Lisp_Object index)
3475{
3476 h->index = index;
3477}
3478static void
3479set_hash_index_slot (struct Lisp_Hash_Table *h, ptrdiff_t idx, Lisp_Object val)
3480{
3481 gc_aset (h->index, idx, val);
3482}
3483
d80c6c11
GM
3484/* If OBJ is a Lisp hash table, return a pointer to its struct
3485 Lisp_Hash_Table. Otherwise, signal an error. */
3486
3487static struct Lisp_Hash_Table *
971de7fb 3488check_hash_table (Lisp_Object obj)
d80c6c11 3489{
b7826503 3490 CHECK_HASH_TABLE (obj);
d80c6c11
GM
3491 return XHASH_TABLE (obj);
3492}
3493
3494
3495/* Value is the next integer I >= N, N >= 0 which is "almost" a prime
ca9ce8f2
PE
3496 number. A number is "almost" a prime number if it is not divisible
3497 by any integer in the range 2 .. (NEXT_ALMOST_PRIME_LIMIT - 1). */
d80c6c11 3498
0de4bb68
PE
3499EMACS_INT
3500next_almost_prime (EMACS_INT n)
d80c6c11 3501{
ca9ce8f2 3502 verify (NEXT_ALMOST_PRIME_LIMIT == 11);
86fe5cfe
PE
3503 for (n |= 1; ; n += 2)
3504 if (n % 3 != 0 && n % 5 != 0 && n % 7 != 0)
3505 return n;
d80c6c11
GM
3506}
3507
3508
3509/* Find KEY in ARGS which has size NARGS. Don't consider indices for
3510 which USED[I] is non-zero. If found at index I in ARGS, set
3511 USED[I] and USED[I + 1] to 1, and return I + 1. Otherwise return
c5101a77 3512 0. This function is used to extract a keyword/argument pair from
d80c6c11
GM
3513 a DEFUN parameter list. */
3514
f66c7cf8
PE
3515static ptrdiff_t
3516get_key_arg (Lisp_Object key, ptrdiff_t nargs, Lisp_Object *args, char *used)
d80c6c11 3517{
f66c7cf8 3518 ptrdiff_t i;
59f953a2 3519
c5101a77
PE
3520 for (i = 1; i < nargs; i++)
3521 if (!used[i - 1] && EQ (args[i - 1], key))
3522 {
3523 used[i - 1] = 1;
3524 used[i] = 1;
3525 return i;
3526 }
59f953a2 3527
c5101a77 3528 return 0;
d80c6c11
GM
3529}
3530
3531
3532/* Return a Lisp vector which has the same contents as VEC but has
d311d28c
PE
3533 at least INCR_MIN more entries, where INCR_MIN is positive.
3534 If NITEMS_MAX is not -1, do not grow the vector to be any larger
3535 than NITEMS_MAX. Entries in the resulting
3536 vector that are not copied from VEC are set to nil. */
d80c6c11 3537
fa7dad5b 3538Lisp_Object
8c172e82 3539larger_vector (Lisp_Object vec, ptrdiff_t incr_min, ptrdiff_t nitems_max)
d80c6c11
GM
3540{
3541 struct Lisp_Vector *v;
d311d28c 3542 ptrdiff_t i, incr, incr_max, old_size, new_size;
91f2d272 3543 ptrdiff_t C_language_max = min (PTRDIFF_MAX, SIZE_MAX) / sizeof *v->contents;
8c172e82
PE
3544 ptrdiff_t n_max = (0 <= nitems_max && nitems_max < C_language_max
3545 ? nitems_max : C_language_max);
a54e2c05
DA
3546 eassert (VECTORP (vec));
3547 eassert (0 < incr_min && -1 <= nitems_max);
7edbb0da 3548 old_size = ASIZE (vec);
d311d28c
PE
3549 incr_max = n_max - old_size;
3550 incr = max (incr_min, min (old_size >> 1, incr_max));
3551 if (incr_max < incr)
3552 memory_full (SIZE_MAX);
3553 new_size = old_size + incr;
b3660ef6 3554 v = allocate_vector (new_size);
91f2d272 3555 memcpy (v->contents, XVECTOR (vec)->contents, old_size * sizeof *v->contents);
d80c6c11 3556 for (i = old_size; i < new_size; ++i)
91f2d272 3557 v->contents[i] = Qnil;
d80c6c11
GM
3558 XSETVECTOR (vec, v);
3559 return vec;
3560}
3561
3562
3563/***********************************************************************
3564 Low-level Functions
3565 ***********************************************************************/
3566
53371430
PE
3567static struct hash_table_test hashtest_eq;
3568struct hash_table_test hashtest_eql, hashtest_equal;
b7432bb2 3569
d80c6c11 3570/* Compare KEY1 which has hash code HASH1 and KEY2 with hash code
f75d7a91 3571 HASH2 in hash table H using `eql'. Value is true if KEY1 and
d80c6c11
GM
3572 KEY2 are the same. */
3573
f75d7a91 3574static bool
b7432bb2
SM
3575cmpfn_eql (struct hash_table_test *ht,
3576 Lisp_Object key1,
3577 Lisp_Object key2)
d80c6c11 3578{
2e5da676
GM
3579 return (FLOATP (key1)
3580 && FLOATP (key2)
e84b1dea 3581 && XFLOAT_DATA (key1) == XFLOAT_DATA (key2));
d80c6c11
GM
3582}
3583
3584
3585/* Compare KEY1 which has hash code HASH1 and KEY2 with hash code
f75d7a91 3586 HASH2 in hash table H using `equal'. Value is true if KEY1 and
d80c6c11
GM
3587 KEY2 are the same. */
3588
f75d7a91 3589static bool
b7432bb2
SM
3590cmpfn_equal (struct hash_table_test *ht,
3591 Lisp_Object key1,
3592 Lisp_Object key2)
d80c6c11 3593{
b7432bb2 3594 return !NILP (Fequal (key1, key2));
d80c6c11
GM
3595}
3596
59f953a2 3597
d80c6c11 3598/* Compare KEY1 which has hash code HASH1, and KEY2 with hash code
f75d7a91 3599 HASH2 in hash table H using H->user_cmp_function. Value is true
d80c6c11
GM
3600 if KEY1 and KEY2 are the same. */
3601
f75d7a91 3602static bool
b7432bb2
SM
3603cmpfn_user_defined (struct hash_table_test *ht,
3604 Lisp_Object key1,
3605 Lisp_Object key2)
d80c6c11 3606{
b7432bb2 3607 Lisp_Object args[3];
59f953a2 3608
b7432bb2
SM
3609 args[0] = ht->user_cmp_function;
3610 args[1] = key1;
3611 args[2] = key2;
3612 return !NILP (Ffuncall (3, args));
d80c6c11
GM
3613}
3614
3615
3616/* Value is a hash code for KEY for use in hash table H which uses
3617 `eq' to compare keys. The hash code returned is guaranteed to fit
3618 in a Lisp integer. */
3619
0de4bb68 3620static EMACS_UINT
b7432bb2 3621hashfn_eq (struct hash_table_test *ht, Lisp_Object key)
d80c6c11 3622{
61ddb1b9 3623 EMACS_UINT hash = XHASH (key) ^ XTYPE (key);
cf681889 3624 return hash;
d80c6c11
GM
3625}
3626
d80c6c11
GM
3627/* Value is a hash code for KEY for use in hash table H which uses
3628 `eql' to compare keys. The hash code returned is guaranteed to fit
3629 in a Lisp integer. */
3630
0de4bb68 3631static EMACS_UINT
b7432bb2 3632hashfn_eql (struct hash_table_test *ht, Lisp_Object key)
d80c6c11 3633{
0de4bb68 3634 EMACS_UINT hash;
cf681889
GM
3635 if (FLOATP (key))
3636 hash = sxhash (key, 0);
d80c6c11 3637 else
61ddb1b9 3638 hash = XHASH (key) ^ XTYPE (key);
cf681889 3639 return hash;
d80c6c11
GM
3640}
3641
d80c6c11
GM
3642/* Value is a hash code for KEY for use in hash table H which uses
3643 `equal' to compare keys. The hash code returned is guaranteed to fit
3644 in a Lisp integer. */
3645
0de4bb68 3646static EMACS_UINT
b7432bb2 3647hashfn_equal (struct hash_table_test *ht, Lisp_Object key)
d80c6c11 3648{
0de4bb68 3649 EMACS_UINT hash = sxhash (key, 0);
cf681889 3650 return hash;
d80c6c11
GM
3651}
3652
d80c6c11
GM
3653/* Value is a hash code for KEY for use in hash table H which uses as
3654 user-defined function to compare keys. The hash code returned is
3655 guaranteed to fit in a Lisp integer. */
3656
0de4bb68 3657static EMACS_UINT
b7432bb2 3658hashfn_user_defined (struct hash_table_test *ht, Lisp_Object key)
d80c6c11
GM
3659{
3660 Lisp_Object args[2], hash;
59f953a2 3661
b7432bb2 3662 args[0] = ht->user_hash_function;
d80c6c11
GM
3663 args[1] = key;
3664 hash = Ffuncall (2, args);
79804536 3665 return hashfn_eq (ht, hash);
d80c6c11
GM
3666}
3667
d311d28c
PE
3668/* An upper bound on the size of a hash table index. It must fit in
3669 ptrdiff_t and be a valid Emacs fixnum. */
3670#define INDEX_SIZE_BOUND \
663e2b3f 3671 ((ptrdiff_t) min (MOST_POSITIVE_FIXNUM, PTRDIFF_MAX / word_size))
d80c6c11
GM
3672
3673/* Create and initialize a new hash table.
3674
3675 TEST specifies the test the hash table will use to compare keys.
3676 It must be either one of the predefined tests `eq', `eql' or
3677 `equal' or a symbol denoting a user-defined test named TEST with
3678 test and hash functions USER_TEST and USER_HASH.
59f953a2 3679
1fd4c450 3680 Give the table initial capacity SIZE, SIZE >= 0, an integer.
d80c6c11
GM
3681
3682 If REHASH_SIZE is an integer, it must be > 0, and this hash table's
3683 new size when it becomes full is computed by adding REHASH_SIZE to
3684 its old size. If REHASH_SIZE is a float, it must be > 1.0, and the
3685 table's new size is computed by multiplying its old size with
3686 REHASH_SIZE.
3687
3688 REHASH_THRESHOLD must be a float <= 1.0, and > 0. The table will
3689 be resized when the ratio of (number of entries in the table) /
3690 (table size) is >= REHASH_THRESHOLD.
3691
3692 WEAK specifies the weakness of the table. If non-nil, it must be
ec504e6f 3693 one of the symbols `key', `value', `key-or-value', or `key-and-value'. */
d80c6c11
GM
3694
3695Lisp_Object
b7432bb2
SM
3696make_hash_table (struct hash_table_test test,
3697 Lisp_Object size, Lisp_Object rehash_size,
3698 Lisp_Object rehash_threshold, Lisp_Object weak)
d80c6c11
GM
3699{
3700 struct Lisp_Hash_Table *h;
d80c6c11 3701 Lisp_Object table;
d311d28c
PE
3702 EMACS_INT index_size, sz;
3703 ptrdiff_t i;
0de4bb68 3704 double index_float;
d80c6c11
GM
3705
3706 /* Preconditions. */
b7432bb2 3707 eassert (SYMBOLP (test.name));
a54e2c05
DA
3708 eassert (INTEGERP (size) && XINT (size) >= 0);
3709 eassert ((INTEGERP (rehash_size) && XINT (rehash_size) > 0)
0de4bb68 3710 || (FLOATP (rehash_size) && 1 < XFLOAT_DATA (rehash_size)));
a54e2c05 3711 eassert (FLOATP (rehash_threshold)
0de4bb68
PE
3712 && 0 < XFLOAT_DATA (rehash_threshold)
3713 && XFLOAT_DATA (rehash_threshold) <= 1.0);
d80c6c11 3714
1fd4c450
GM
3715 if (XFASTINT (size) == 0)
3716 size = make_number (1);
3717
0de4bb68
PE
3718 sz = XFASTINT (size);
3719 index_float = sz / XFLOAT_DATA (rehash_threshold);
d311d28c 3720 index_size = (index_float < INDEX_SIZE_BOUND + 1
0de4bb68 3721 ? next_almost_prime (index_float)
d311d28c
PE
3722 : INDEX_SIZE_BOUND + 1);
3723 if (INDEX_SIZE_BOUND < max (index_size, 2 * sz))
0de4bb68
PE
3724 error ("Hash table too large");
3725
b3660ef6
GM
3726 /* Allocate a table and initialize it. */
3727 h = allocate_hash_table ();
d80c6c11
GM
3728
3729 /* Initialize hash table slots. */
d80c6c11 3730 h->test = test;
d80c6c11
GM
3731 h->weak = weak;
3732 h->rehash_threshold = rehash_threshold;
3733 h->rehash_size = rehash_size;
878f97ff 3734 h->count = 0;
d80c6c11
GM
3735 h->key_and_value = Fmake_vector (make_number (2 * sz), Qnil);
3736 h->hash = Fmake_vector (size, Qnil);
3737 h->next = Fmake_vector (size, Qnil);
d80c6c11
GM
3738 h->index = Fmake_vector (make_number (index_size), Qnil);
3739
3740 /* Set up the free list. */
3741 for (i = 0; i < sz - 1; ++i)
e83064be 3742 set_hash_next_slot (h, i, make_number (i + 1));
d80c6c11
GM
3743 h->next_free = make_number (0);
3744
3745 XSET_HASH_TABLE (table, h);
a54e2c05
DA
3746 eassert (HASH_TABLE_P (table));
3747 eassert (XHASH_TABLE (table) == h);
d80c6c11
GM
3748
3749 /* Maybe add this hash table to the list of all weak hash tables. */
3750 if (NILP (h->weak))
6c661ec9 3751 h->next_weak = NULL;
d80c6c11
GM
3752 else
3753 {
6c661ec9
SM
3754 h->next_weak = weak_hash_tables;
3755 weak_hash_tables = h;
d80c6c11
GM
3756 }
3757
3758 return table;
3759}
3760
3761
f899c503
GM
3762/* Return a copy of hash table H1. Keys and values are not copied,
3763 only the table itself is. */
3764
2f7c71a1 3765static Lisp_Object
971de7fb 3766copy_hash_table (struct Lisp_Hash_Table *h1)
f899c503
GM
3767{
3768 Lisp_Object table;
3769 struct Lisp_Hash_Table *h2;
59f953a2 3770
b3660ef6 3771 h2 = allocate_hash_table ();
ae1d87e2 3772 *h2 = *h1;
f899c503
GM
3773 h2->key_and_value = Fcopy_sequence (h1->key_and_value);
3774 h2->hash = Fcopy_sequence (h1->hash);
3775 h2->next = Fcopy_sequence (h1->next);
3776 h2->index = Fcopy_sequence (h1->index);
3777 XSET_HASH_TABLE (table, h2);
3778
3779 /* Maybe add this hash table to the list of all weak hash tables. */
3780 if (!NILP (h2->weak))
3781 {
6c661ec9
SM
3782 h2->next_weak = weak_hash_tables;
3783 weak_hash_tables = h2;
f899c503
GM
3784 }
3785
3786 return table;
3787}
3788
3789
d80c6c11
GM
3790/* Resize hash table H if it's too full. If H cannot be resized
3791 because it's already too large, throw an error. */
3792
b0ab8123 3793static void
971de7fb 3794maybe_resize_hash_table (struct Lisp_Hash_Table *h)
d80c6c11
GM
3795{
3796 if (NILP (h->next_free))
3797 {
d311d28c
PE
3798 ptrdiff_t old_size = HASH_TABLE_SIZE (h);
3799 EMACS_INT new_size, index_size, nsize;
3800 ptrdiff_t i;
0de4bb68 3801 double index_float;
59f953a2 3802
d80c6c11
GM
3803 if (INTEGERP (h->rehash_size))
3804 new_size = old_size + XFASTINT (h->rehash_size);
3805 else
0de4bb68
PE
3806 {
3807 double float_new_size = old_size * XFLOAT_DATA (h->rehash_size);
d311d28c 3808 if (float_new_size < INDEX_SIZE_BOUND + 1)
0de4bb68
PE
3809 {
3810 new_size = float_new_size;
3811 if (new_size <= old_size)
3812 new_size = old_size + 1;
3813 }
3814 else
d311d28c 3815 new_size = INDEX_SIZE_BOUND + 1;
0de4bb68
PE
3816 }
3817 index_float = new_size / XFLOAT_DATA (h->rehash_threshold);
d311d28c 3818 index_size = (index_float < INDEX_SIZE_BOUND + 1
0de4bb68 3819 ? next_almost_prime (index_float)
d311d28c 3820 : INDEX_SIZE_BOUND + 1);
9bd1cd35 3821 nsize = max (index_size, 2 * new_size);
d311d28c 3822 if (INDEX_SIZE_BOUND < nsize)
d80c6c11
GM
3823 error ("Hash table too large to resize");
3824
1ec4b7b2
SM
3825#ifdef ENABLE_CHECKING
3826 if (HASH_TABLE_P (Vpurify_flag)
3827 && XHASH_TABLE (Vpurify_flag) == h)
3828 {
3829 Lisp_Object args[2];
3830 args[0] = build_string ("Growing hash table to: %d");
3831 args[1] = make_number (new_size);
3832 Fmessage (2, args);
3833 }
3834#endif
3835
e83064be
DA
3836 set_hash_key_and_value (h, larger_vector (h->key_and_value,
3837 2 * (new_size - old_size), -1));
3838 set_hash_next (h, larger_vector (h->next, new_size - old_size, -1));
3839 set_hash_hash (h, larger_vector (h->hash, new_size - old_size, -1));
3840 set_hash_index (h, Fmake_vector (make_number (index_size), Qnil));
d80c6c11
GM
3841
3842 /* Update the free list. Do it so that new entries are added at
3843 the end of the free list. This makes some operations like
3844 maphash faster. */
3845 for (i = old_size; i < new_size - 1; ++i)
e83064be 3846 set_hash_next_slot (h, i, make_number (i + 1));
59f953a2 3847
d80c6c11
GM
3848 if (!NILP (h->next_free))
3849 {
3850 Lisp_Object last, next;
59f953a2 3851
d80c6c11
GM
3852 last = h->next_free;
3853 while (next = HASH_NEXT (h, XFASTINT (last)),
3854 !NILP (next))
3855 last = next;
59f953a2 3856
e83064be 3857 set_hash_next_slot (h, XFASTINT (last), make_number (old_size));
d80c6c11
GM
3858 }
3859 else
3860 XSETFASTINT (h->next_free, old_size);
3861
3862 /* Rehash. */
3863 for (i = 0; i < old_size; ++i)
3864 if (!NILP (HASH_HASH (h, i)))
3865 {
0de4bb68 3866 EMACS_UINT hash_code = XUINT (HASH_HASH (h, i));
d311d28c 3867 ptrdiff_t start_of_bucket = hash_code % ASIZE (h->index);
e83064be
DA
3868 set_hash_next_slot (h, i, HASH_INDEX (h, start_of_bucket));
3869 set_hash_index_slot (h, start_of_bucket, make_number (i));
d80c6c11 3870 }
59f953a2 3871 }
d80c6c11
GM
3872}
3873
3874
3875/* Lookup KEY in hash table H. If HASH is non-null, return in *HASH
3876 the hash code of KEY. Value is the index of the entry in H
3877 matching KEY, or -1 if not found. */
3878
d3411f89 3879ptrdiff_t
0de4bb68 3880hash_lookup (struct Lisp_Hash_Table *h, Lisp_Object key, EMACS_UINT *hash)
d80c6c11 3881{
0de4bb68 3882 EMACS_UINT hash_code;
d3411f89 3883 ptrdiff_t start_of_bucket;
d80c6c11
GM
3884 Lisp_Object idx;
3885
b7432bb2
SM
3886 hash_code = h->test.hashfn (&h->test, key);
3887 eassert ((hash_code & ~INTMASK) == 0);
d80c6c11
GM
3888 if (hash)
3889 *hash = hash_code;
59f953a2 3890
7edbb0da 3891 start_of_bucket = hash_code % ASIZE (h->index);
d80c6c11
GM
3892 idx = HASH_INDEX (h, start_of_bucket);
3893
f5c75033 3894 /* We need not gcpro idx since it's either an integer or nil. */
d80c6c11
GM
3895 while (!NILP (idx))
3896 {
d311d28c 3897 ptrdiff_t i = XFASTINT (idx);
2e5da676 3898 if (EQ (key, HASH_KEY (h, i))
b7432bb2
SM
3899 || (h->test.cmpfn
3900 && hash_code == XUINT (HASH_HASH (h, i))
3901 && h->test.cmpfn (&h->test, key, HASH_KEY (h, i))))
d80c6c11
GM
3902 break;
3903 idx = HASH_NEXT (h, i);
3904 }
3905
3906 return NILP (idx) ? -1 : XFASTINT (idx);
3907}
3908
3909
3910/* Put an entry into hash table H that associates KEY with VALUE.
64a5094a
KH
3911 HASH is a previously computed hash code of KEY.
3912 Value is the index of the entry in H matching KEY. */
d80c6c11 3913
d3411f89 3914ptrdiff_t
0de4bb68
PE
3915hash_put (struct Lisp_Hash_Table *h, Lisp_Object key, Lisp_Object value,
3916 EMACS_UINT hash)
d80c6c11 3917{
d3411f89 3918 ptrdiff_t start_of_bucket, i;
d80c6c11 3919
a54e2c05 3920 eassert ((hash & ~INTMASK) == 0);
d80c6c11
GM
3921
3922 /* Increment count after resizing because resizing may fail. */
3923 maybe_resize_hash_table (h);
878f97ff 3924 h->count++;
59f953a2 3925
d80c6c11
GM
3926 /* Store key/value in the key_and_value vector. */
3927 i = XFASTINT (h->next_free);
3928 h->next_free = HASH_NEXT (h, i);
e83064be
DA
3929 set_hash_key_slot (h, i, key);
3930 set_hash_value_slot (h, i, value);
d80c6c11
GM
3931
3932 /* Remember its hash code. */
e83064be 3933 set_hash_hash_slot (h, i, make_number (hash));
d80c6c11
GM
3934
3935 /* Add new entry to its collision chain. */
7edbb0da 3936 start_of_bucket = hash % ASIZE (h->index);
e83064be
DA
3937 set_hash_next_slot (h, i, HASH_INDEX (h, start_of_bucket));
3938 set_hash_index_slot (h, start_of_bucket, make_number (i));
64a5094a 3939 return i;
d80c6c11
GM
3940}
3941
3942
3943/* Remove the entry matching KEY from hash table H, if there is one. */
3944
2749d28e 3945static void
971de7fb 3946hash_remove_from_table (struct Lisp_Hash_Table *h, Lisp_Object key)
d80c6c11 3947{
0de4bb68 3948 EMACS_UINT hash_code;
d311d28c 3949 ptrdiff_t start_of_bucket;
d80c6c11
GM
3950 Lisp_Object idx, prev;
3951
b7432bb2
SM
3952 hash_code = h->test.hashfn (&h->test, key);
3953 eassert ((hash_code & ~INTMASK) == 0);
7edbb0da 3954 start_of_bucket = hash_code % ASIZE (h->index);
d80c6c11
GM
3955 idx = HASH_INDEX (h, start_of_bucket);
3956 prev = Qnil;
3957
f5c75033 3958 /* We need not gcpro idx, prev since they're either integers or nil. */
d80c6c11
GM
3959 while (!NILP (idx))
3960 {
d311d28c 3961 ptrdiff_t i = XFASTINT (idx);
d80c6c11 3962
2e5da676 3963 if (EQ (key, HASH_KEY (h, i))
b7432bb2
SM
3964 || (h->test.cmpfn
3965 && hash_code == XUINT (HASH_HASH (h, i))
3966 && h->test.cmpfn (&h->test, key, HASH_KEY (h, i))))
d80c6c11
GM
3967 {
3968 /* Take entry out of collision chain. */
3969 if (NILP (prev))
e83064be 3970 set_hash_index_slot (h, start_of_bucket, HASH_NEXT (h, i));
d80c6c11 3971 else
e83064be 3972 set_hash_next_slot (h, XFASTINT (prev), HASH_NEXT (h, i));
d80c6c11
GM
3973
3974 /* Clear slots in key_and_value and add the slots to
3975 the free list. */
e83064be
DA
3976 set_hash_key_slot (h, i, Qnil);
3977 set_hash_value_slot (h, i, Qnil);
3978 set_hash_hash_slot (h, i, Qnil);
3979 set_hash_next_slot (h, i, h->next_free);
d80c6c11 3980 h->next_free = make_number (i);
878f97ff 3981 h->count--;
a54e2c05 3982 eassert (h->count >= 0);
d80c6c11
GM
3983 break;
3984 }
3985 else
3986 {
3987 prev = idx;
3988 idx = HASH_NEXT (h, i);
3989 }
3990 }
3991}
3992
3993
3994/* Clear hash table H. */
3995
2f7c71a1 3996static void
971de7fb 3997hash_clear (struct Lisp_Hash_Table *h)
d80c6c11 3998{
878f97ff 3999 if (h->count > 0)
d80c6c11 4000 {
d311d28c 4001 ptrdiff_t i, size = HASH_TABLE_SIZE (h);
d80c6c11
GM
4002
4003 for (i = 0; i < size; ++i)
4004 {
e83064be
DA
4005 set_hash_next_slot (h, i, i < size - 1 ? make_number (i + 1) : Qnil);
4006 set_hash_key_slot (h, i, Qnil);
4007 set_hash_value_slot (h, i, Qnil);
4008 set_hash_hash_slot (h, i, Qnil);
d80c6c11
GM
4009 }
4010
7edbb0da 4011 for (i = 0; i < ASIZE (h->index); ++i)
68b587a6 4012 ASET (h->index, i, Qnil);
d80c6c11
GM
4013
4014 h->next_free = make_number (0);
878f97ff 4015 h->count = 0;
d80c6c11
GM
4016 }
4017}
4018
4019
4020\f
4021/************************************************************************
4022 Weak Hash Tables
4023 ************************************************************************/
4024
f75d7a91 4025/* Sweep weak hash table H. REMOVE_ENTRIES_P means remove
a0b581cc 4026 entries from the table that don't survive the current GC.
f75d7a91
PE
4027 !REMOVE_ENTRIES_P means mark entries that are in use. Value is
4028 true if anything was marked. */
a0b581cc 4029
f75d7a91
PE
4030static bool
4031sweep_weak_table (struct Lisp_Hash_Table *h, bool remove_entries_p)
a0b581cc 4032{
d311d28c 4033 ptrdiff_t bucket, n;
f75d7a91 4034 bool marked;
59f953a2 4035
7edbb0da 4036 n = ASIZE (h->index) & ~ARRAY_MARK_FLAG;
a0b581cc 4037 marked = 0;
59f953a2 4038
a0b581cc
GM
4039 for (bucket = 0; bucket < n; ++bucket)
4040 {
1e546714 4041 Lisp_Object idx, next, prev;
a0b581cc
GM
4042
4043 /* Follow collision chain, removing entries that
4044 don't survive this garbage collection. */
a0b581cc 4045 prev = Qnil;
8e50cc2d 4046 for (idx = HASH_INDEX (h, bucket); !NILP (idx); idx = next)
a0b581cc 4047 {
d311d28c 4048 ptrdiff_t i = XFASTINT (idx);
fce31d69
PE
4049 bool key_known_to_survive_p = survives_gc_p (HASH_KEY (h, i));
4050 bool value_known_to_survive_p = survives_gc_p (HASH_VALUE (h, i));
f75d7a91 4051 bool remove_p;
59f953a2 4052
a0b581cc 4053 if (EQ (h->weak, Qkey))
aee625fa 4054 remove_p = !key_known_to_survive_p;
a0b581cc 4055 else if (EQ (h->weak, Qvalue))
aee625fa 4056 remove_p = !value_known_to_survive_p;
ec504e6f 4057 else if (EQ (h->weak, Qkey_or_value))
728c5d9d 4058 remove_p = !(key_known_to_survive_p || value_known_to_survive_p);
ec504e6f 4059 else if (EQ (h->weak, Qkey_and_value))
728c5d9d 4060 remove_p = !(key_known_to_survive_p && value_known_to_survive_p);
a0b581cc 4061 else
1088b922 4062 emacs_abort ();
59f953a2 4063
a0b581cc
GM
4064 next = HASH_NEXT (h, i);
4065
4066 if (remove_entries_p)
4067 {
4068 if (remove_p)
4069 {
4070 /* Take out of collision chain. */
8e50cc2d 4071 if (NILP (prev))
e83064be 4072 set_hash_index_slot (h, bucket, next);
a0b581cc 4073 else
e83064be 4074 set_hash_next_slot (h, XFASTINT (prev), next);
59f953a2 4075
a0b581cc 4076 /* Add to free list. */
e83064be 4077 set_hash_next_slot (h, i, h->next_free);
a0b581cc 4078 h->next_free = idx;
59f953a2 4079
a0b581cc 4080 /* Clear key, value, and hash. */
e83064be
DA
4081 set_hash_key_slot (h, i, Qnil);
4082 set_hash_value_slot (h, i, Qnil);
4083 set_hash_hash_slot (h, i, Qnil);
59f953a2 4084
878f97ff 4085 h->count--;
a0b581cc 4086 }
d278cde0
KS
4087 else
4088 {
4089 prev = idx;
4090 }
a0b581cc
GM
4091 }
4092 else
4093 {
4094 if (!remove_p)
4095 {
4096 /* Make sure key and value survive. */
aee625fa
GM
4097 if (!key_known_to_survive_p)
4098 {
9568e3d8 4099 mark_object (HASH_KEY (h, i));
aee625fa
GM
4100 marked = 1;
4101 }
4102
4103 if (!value_known_to_survive_p)
4104 {
9568e3d8 4105 mark_object (HASH_VALUE (h, i));
aee625fa
GM
4106 marked = 1;
4107 }
a0b581cc
GM
4108 }
4109 }
a0b581cc
GM
4110 }
4111 }
4112
4113 return marked;
4114}
4115
d80c6c11
GM
4116/* Remove elements from weak hash tables that don't survive the
4117 current garbage collection. Remove weak tables that don't survive
4118 from Vweak_hash_tables. Called from gc_sweep. */
4119
b029599f 4120NO_INLINE /* For better stack traces */
d80c6c11 4121void
971de7fb 4122sweep_weak_hash_tables (void)
d80c6c11 4123{
6c661ec9 4124 struct Lisp_Hash_Table *h, *used, *next;
f75d7a91 4125 bool marked;
a0b581cc
GM
4126
4127 /* Mark all keys and values that are in use. Keep on marking until
4128 there is no more change. This is necessary for cases like
4129 value-weak table A containing an entry X -> Y, where Y is used in a
4130 key-weak table B, Z -> Y. If B comes after A in the list of weak
4131 tables, X -> Y might be removed from A, although when looking at B
4132 one finds that it shouldn't. */
4133 do
4134 {
4135 marked = 0;
6c661ec9 4136 for (h = weak_hash_tables; h; h = h->next_weak)
a0b581cc 4137 {
eab3844f 4138 if (h->header.size & ARRAY_MARK_FLAG)
a0b581cc
GM
4139 marked |= sweep_weak_table (h, 0);
4140 }
4141 }
4142 while (marked);
d80c6c11 4143
a0b581cc 4144 /* Remove tables and entries that aren't used. */
6c661ec9 4145 for (h = weak_hash_tables, used = NULL; h; h = next)
d80c6c11 4146 {
ac0e96ee 4147 next = h->next_weak;
91f78c99 4148
eab3844f 4149 if (h->header.size & ARRAY_MARK_FLAG)
d80c6c11 4150 {
ac0e96ee 4151 /* TABLE is marked as used. Sweep its contents. */
878f97ff 4152 if (h->count > 0)
a0b581cc 4153 sweep_weak_table (h, 1);
ac0e96ee
GM
4154
4155 /* Add table to the list of used weak hash tables. */
4156 h->next_weak = used;
6c661ec9 4157 used = h;
d80c6c11
GM
4158 }
4159 }
ac0e96ee 4160
6c661ec9 4161 weak_hash_tables = used;
d80c6c11
GM
4162}
4163
4164
4165\f
4166/***********************************************************************
4167 Hash Code Computation
4168 ***********************************************************************/
4169
4170/* Maximum depth up to which to dive into Lisp structures. */
4171
4172#define SXHASH_MAX_DEPTH 3
4173
4174/* Maximum length up to which to take list and vector elements into
4175 account. */
4176
4177#define SXHASH_MAX_LEN 7
4178
3cc5a532
PE
4179/* Return a hash for string PTR which has length LEN. The hash value
4180 can be any EMACS_UINT value. */
d80c6c11 4181
3cc5a532
PE
4182EMACS_UINT
4183hash_string (char const *ptr, ptrdiff_t len)
d80c6c11 4184{
3cc5a532
PE
4185 char const *p = ptr;
4186 char const *end = p + len;
d80c6c11 4187 unsigned char c;
0de4bb68 4188 EMACS_UINT hash = 0;
d80c6c11
GM
4189
4190 while (p != end)
4191 {
4192 c = *p++;
04a2d0d3 4193 hash = sxhash_combine (hash, c);
d80c6c11 4194 }
59f953a2 4195
3cc5a532
PE
4196 return hash;
4197}
4198
4199/* Return a hash for string PTR which has length LEN. The hash
4200 code returned is guaranteed to fit in a Lisp integer. */
4201
4202static EMACS_UINT
4203sxhash_string (char const *ptr, ptrdiff_t len)
4204{
4205 EMACS_UINT hash = hash_string (ptr, len);
0de4bb68 4206 return SXHASH_REDUCE (hash);
d80c6c11
GM
4207}
4208
0de4bb68
PE
4209/* Return a hash for the floating point value VAL. */
4210
eff1c190 4211static EMACS_UINT
0de4bb68
PE
4212sxhash_float (double val)
4213{
4214 EMACS_UINT hash = 0;
4215 enum {
4216 WORDS_PER_DOUBLE = (sizeof val / sizeof hash
4217 + (sizeof val % sizeof hash != 0))
4218 };
4219 union {
4220 double val;
4221 EMACS_UINT word[WORDS_PER_DOUBLE];
4222 } u;
4223 int i;
4224 u.val = val;
4225 memset (&u.val + 1, 0, sizeof u - sizeof u.val);
4226 for (i = 0; i < WORDS_PER_DOUBLE; i++)
04a2d0d3 4227 hash = sxhash_combine (hash, u.word[i]);
0de4bb68
PE
4228 return SXHASH_REDUCE (hash);
4229}
d80c6c11
GM
4230
4231/* Return a hash for list LIST. DEPTH is the current depth in the
4232 list. We don't recurse deeper than SXHASH_MAX_DEPTH in it. */
4233
0de4bb68 4234static EMACS_UINT
971de7fb 4235sxhash_list (Lisp_Object list, int depth)
d80c6c11 4236{
0de4bb68 4237 EMACS_UINT hash = 0;
d80c6c11 4238 int i;
59f953a2 4239
d80c6c11
GM
4240 if (depth < SXHASH_MAX_DEPTH)
4241 for (i = 0;
4242 CONSP (list) && i < SXHASH_MAX_LEN;
4243 list = XCDR (list), ++i)
4244 {
0de4bb68 4245 EMACS_UINT hash2 = sxhash (XCAR (list), depth + 1);
04a2d0d3 4246 hash = sxhash_combine (hash, hash2);
d80c6c11
GM
4247 }
4248
ea284f33
KS
4249 if (!NILP (list))
4250 {
0de4bb68 4251 EMACS_UINT hash2 = sxhash (list, depth + 1);
04a2d0d3 4252 hash = sxhash_combine (hash, hash2);
ea284f33
KS
4253 }
4254
0de4bb68 4255 return SXHASH_REDUCE (hash);
d80c6c11
GM
4256}
4257
4258
4259/* Return a hash for vector VECTOR. DEPTH is the current depth in
4260 the Lisp structure. */
4261
0de4bb68 4262static EMACS_UINT
971de7fb 4263sxhash_vector (Lisp_Object vec, int depth)
d80c6c11 4264{
0de4bb68 4265 EMACS_UINT hash = ASIZE (vec);
d80c6c11
GM
4266 int i, n;
4267
7edbb0da 4268 n = min (SXHASH_MAX_LEN, ASIZE (vec));
d80c6c11
GM
4269 for (i = 0; i < n; ++i)
4270 {
0de4bb68 4271 EMACS_UINT hash2 = sxhash (AREF (vec, i), depth + 1);
04a2d0d3 4272 hash = sxhash_combine (hash, hash2);
d80c6c11
GM
4273 }
4274
0de4bb68 4275 return SXHASH_REDUCE (hash);
d80c6c11
GM
4276}
4277
d80c6c11
GM
4278/* Return a hash for bool-vector VECTOR. */
4279
0de4bb68 4280static EMACS_UINT
971de7fb 4281sxhash_bool_vector (Lisp_Object vec)
d80c6c11 4282{
1c0a7493
PE
4283 EMACS_INT size = bool_vector_size (vec);
4284 EMACS_UINT hash = size;
d80c6c11
GM
4285 int i, n;
4286
df5b4930 4287 n = min (SXHASH_MAX_LEN, bool_vector_words (size));
d80c6c11 4288 for (i = 0; i < n; ++i)
df5b4930 4289 hash = sxhash_combine (hash, bool_vector_data (vec)[i]);
d80c6c11 4290
0de4bb68 4291 return SXHASH_REDUCE (hash);
d80c6c11
GM
4292}
4293
4294
4295/* Return a hash code for OBJ. DEPTH is the current depth in the Lisp
6b61353c 4296 structure. Value is an unsigned integer clipped to INTMASK. */
d80c6c11 4297
0de4bb68 4298EMACS_UINT
971de7fb 4299sxhash (Lisp_Object obj, int depth)
d80c6c11 4300{
0de4bb68 4301 EMACS_UINT hash;
d80c6c11
GM
4302
4303 if (depth > SXHASH_MAX_DEPTH)
4304 return 0;
59f953a2 4305
d80c6c11
GM
4306 switch (XTYPE (obj))
4307 {
2de9f71c 4308 case_Lisp_Int:
d80c6c11
GM
4309 hash = XUINT (obj);
4310 break;
4311
d80c6c11 4312 case Lisp_Misc:
61ddb1b9 4313 hash = XHASH (obj);
d80c6c11
GM
4314 break;
4315
32bfb2d5
EZ
4316 case Lisp_Symbol:
4317 obj = SYMBOL_NAME (obj);
4318 /* Fall through. */
4319
d80c6c11 4320 case Lisp_String:
3cc5a532 4321 hash = sxhash_string (SSDATA (obj), SBYTES (obj));
d80c6c11
GM
4322 break;
4323
4324 /* This can be everything from a vector to an overlay. */
4325 case Lisp_Vectorlike:
4326 if (VECTORP (obj))
4327 /* According to the CL HyperSpec, two arrays are equal only if
4328 they are `eq', except for strings and bit-vectors. In
4329 Emacs, this works differently. We have to compare element
4330 by element. */
4331 hash = sxhash_vector (obj, depth);
4332 else if (BOOL_VECTOR_P (obj))
4333 hash = sxhash_bool_vector (obj);
4334 else
4335 /* Others are `equal' if they are `eq', so let's take their
4336 address as hash. */
61ddb1b9 4337 hash = XHASH (obj);
d80c6c11
GM
4338 break;
4339
4340 case Lisp_Cons:
4341 hash = sxhash_list (obj, depth);
4342 break;
4343
4344 case Lisp_Float:
0de4bb68
PE
4345 hash = sxhash_float (XFLOAT_DATA (obj));
4346 break;
d80c6c11
GM
4347
4348 default:
1088b922 4349 emacs_abort ();
d80c6c11
GM
4350 }
4351
0de4bb68 4352 return hash;
d80c6c11
GM
4353}
4354
4355
4356\f
4357/***********************************************************************
4358 Lisp Interface
4359 ***********************************************************************/
4360
4361
4362DEFUN ("sxhash", Fsxhash, Ssxhash, 1, 1, 0,
e9d8ddc9 4363 doc: /* Compute a hash code for OBJ and return it as integer. */)
5842a27b 4364 (Lisp_Object obj)
d80c6c11 4365{
0de4bb68 4366 EMACS_UINT hash = sxhash (obj, 0);
d80c6c11
GM
4367 return make_number (hash);
4368}
4369
4370
a7ca3326 4371DEFUN ("make-hash-table", Fmake_hash_table, Smake_hash_table, 0, MANY, 0,
e9d8ddc9 4372 doc: /* Create and return a new hash table.
91f78c99 4373
47cebab1
GM
4374Arguments are specified as keyword/argument pairs. The following
4375arguments are defined:
4376
4377:test TEST -- TEST must be a symbol that specifies how to compare
4378keys. Default is `eql'. Predefined are the tests `eq', `eql', and
4379`equal'. User-supplied test and hash functions can be specified via
4380`define-hash-table-test'.
4381
4382:size SIZE -- A hint as to how many elements will be put in the table.
4383Default is 65.
4384
4385:rehash-size REHASH-SIZE - Indicates how to expand the table when it
79d6f59e
CY
4386fills up. If REHASH-SIZE is an integer, increase the size by that
4387amount. If it is a float, it must be > 1.0, and the new size is the
4388old size multiplied by that factor. Default is 1.5.
47cebab1
GM
4389
4390:rehash-threshold THRESHOLD -- THRESHOLD must a float > 0, and <= 1.0.
b756c005 4391Resize the hash table when the ratio (number of entries / table size)
e1025755 4392is greater than or equal to THRESHOLD. Default is 0.8.
47cebab1
GM
4393
4394:weakness WEAK -- WEAK must be one of nil, t, `key', `value',
4395`key-or-value', or `key-and-value'. If WEAK is not nil, the table
4396returned is a weak table. Key/value pairs are removed from a weak
4397hash table when there are no non-weak references pointing to their
4398key, value, one of key or value, or both key and value, depending on
4399WEAK. WEAK t is equivalent to `key-and-value'. Default value of WEAK
4bf8e2a3
MB
4400is nil.
4401
4402usage: (make-hash-table &rest KEYWORD-ARGS) */)
f66c7cf8 4403 (ptrdiff_t nargs, Lisp_Object *args)
d80c6c11
GM
4404{
4405 Lisp_Object test, size, rehash_size, rehash_threshold, weak;
b7432bb2 4406 struct hash_table_test testdesc;
d80c6c11 4407 char *used;
f66c7cf8 4408 ptrdiff_t i;
d80c6c11
GM
4409
4410 /* The vector `used' is used to keep track of arguments that
4411 have been consumed. */
38182d90 4412 used = alloca (nargs * sizeof *used);
72af86bd 4413 memset (used, 0, nargs * sizeof *used);
d80c6c11
GM
4414
4415 /* See if there's a `:test TEST' among the arguments. */
4416 i = get_key_arg (QCtest, nargs, args, used);
c5101a77 4417 test = i ? args[i] : Qeql;
b7432bb2
SM
4418 if (EQ (test, Qeq))
4419 testdesc = hashtest_eq;
4420 else if (EQ (test, Qeql))
4421 testdesc = hashtest_eql;
4422 else if (EQ (test, Qequal))
4423 testdesc = hashtest_equal;
4424 else
d80c6c11
GM
4425 {
4426 /* See if it is a user-defined test. */
4427 Lisp_Object prop;
59f953a2 4428
d80c6c11 4429 prop = Fget (test, Qhash_table_test);
c1dd95fc 4430 if (!CONSP (prop) || !CONSP (XCDR (prop)))
692ae65c 4431 signal_error ("Invalid hash table test", test);
b7432bb2
SM
4432 testdesc.name = test;
4433 testdesc.user_cmp_function = XCAR (prop);
4434 testdesc.user_hash_function = XCAR (XCDR (prop));
4435 testdesc.hashfn = hashfn_user_defined;
4436 testdesc.cmpfn = cmpfn_user_defined;
d80c6c11 4437 }
d80c6c11
GM
4438
4439 /* See if there's a `:size SIZE' argument. */
4440 i = get_key_arg (QCsize, nargs, args, used);
c5101a77 4441 size = i ? args[i] : Qnil;
cf42cb72
SM
4442 if (NILP (size))
4443 size = make_number (DEFAULT_HASH_SIZE);
4444 else if (!INTEGERP (size) || XINT (size) < 0)
692ae65c 4445 signal_error ("Invalid hash table size", size);
d80c6c11
GM
4446
4447 /* Look for `:rehash-size SIZE'. */
4448 i = get_key_arg (QCrehash_size, nargs, args, used);
c5101a77 4449 rehash_size = i ? args[i] : make_float (DEFAULT_REHASH_SIZE);
0de4bb68
PE
4450 if (! ((INTEGERP (rehash_size) && 0 < XINT (rehash_size))
4451 || (FLOATP (rehash_size) && 1 < XFLOAT_DATA (rehash_size))))
692ae65c 4452 signal_error ("Invalid hash table rehash size", rehash_size);
59f953a2 4453
d80c6c11
GM
4454 /* Look for `:rehash-threshold THRESHOLD'. */
4455 i = get_key_arg (QCrehash_threshold, nargs, args, used);
c5101a77 4456 rehash_threshold = i ? args[i] : make_float (DEFAULT_REHASH_THRESHOLD);
0de4bb68
PE
4457 if (! (FLOATP (rehash_threshold)
4458 && 0 < XFLOAT_DATA (rehash_threshold)
4459 && XFLOAT_DATA (rehash_threshold) <= 1))
692ae65c 4460 signal_error ("Invalid hash table rehash threshold", rehash_threshold);
59f953a2 4461
ee0403b3
GM
4462 /* Look for `:weakness WEAK'. */
4463 i = get_key_arg (QCweakness, nargs, args, used);
c5101a77 4464 weak = i ? args[i] : Qnil;
ec504e6f
GM
4465 if (EQ (weak, Qt))
4466 weak = Qkey_and_value;
d80c6c11 4467 if (!NILP (weak)
f899c503 4468 && !EQ (weak, Qkey)
ec504e6f
GM
4469 && !EQ (weak, Qvalue)
4470 && !EQ (weak, Qkey_or_value)
4471 && !EQ (weak, Qkey_and_value))
692ae65c 4472 signal_error ("Invalid hash table weakness", weak);
59f953a2 4473
d80c6c11
GM
4474 /* Now, all args should have been used up, or there's a problem. */
4475 for (i = 0; i < nargs; ++i)
4476 if (!used[i])
692ae65c 4477 signal_error ("Invalid argument list", args[i]);
d80c6c11 4478
b7432bb2 4479 return make_hash_table (testdesc, size, rehash_size, rehash_threshold, weak);
d80c6c11
GM
4480}
4481
4482
f899c503 4483DEFUN ("copy-hash-table", Fcopy_hash_table, Scopy_hash_table, 1, 1, 0,
e9d8ddc9 4484 doc: /* Return a copy of hash table TABLE. */)
5842a27b 4485 (Lisp_Object table)
f899c503
GM
4486{
4487 return copy_hash_table (check_hash_table (table));
4488}
4489
4490
d80c6c11 4491DEFUN ("hash-table-count", Fhash_table_count, Shash_table_count, 1, 1, 0,
e9d8ddc9 4492 doc: /* Return the number of elements in TABLE. */)
5842a27b 4493 (Lisp_Object table)
d80c6c11 4494{
878f97ff 4495 return make_number (check_hash_table (table)->count);
d80c6c11
GM
4496}
4497
59f953a2 4498
d80c6c11
GM
4499DEFUN ("hash-table-rehash-size", Fhash_table_rehash_size,
4500 Shash_table_rehash_size, 1, 1, 0,
e9d8ddc9 4501 doc: /* Return the current rehash size of TABLE. */)
5842a27b 4502 (Lisp_Object table)
d80c6c11
GM
4503{
4504 return check_hash_table (table)->rehash_size;
4505}
59f953a2 4506
d80c6c11
GM
4507
4508DEFUN ("hash-table-rehash-threshold", Fhash_table_rehash_threshold,
4509 Shash_table_rehash_threshold, 1, 1, 0,
e9d8ddc9 4510 doc: /* Return the current rehash threshold of TABLE. */)
5842a27b 4511 (Lisp_Object table)
d80c6c11
GM
4512{
4513 return check_hash_table (table)->rehash_threshold;
4514}
59f953a2 4515
d80c6c11
GM
4516
4517DEFUN ("hash-table-size", Fhash_table_size, Shash_table_size, 1, 1, 0,
e9d8ddc9 4518 doc: /* Return the size of TABLE.
47cebab1 4519The size can be used as an argument to `make-hash-table' to create
b756c005 4520a hash table than can hold as many elements as TABLE holds
e9d8ddc9 4521without need for resizing. */)
5842a27b 4522 (Lisp_Object table)
d80c6c11
GM
4523{
4524 struct Lisp_Hash_Table *h = check_hash_table (table);
4525 return make_number (HASH_TABLE_SIZE (h));
4526}
59f953a2 4527
d80c6c11
GM
4528
4529DEFUN ("hash-table-test", Fhash_table_test, Shash_table_test, 1, 1, 0,
e9d8ddc9 4530 doc: /* Return the test TABLE uses. */)
5842a27b 4531 (Lisp_Object table)
d80c6c11 4532{
b7432bb2 4533 return check_hash_table (table)->test.name;
d80c6c11
GM
4534}
4535
59f953a2 4536
e84b1dea
GM
4537DEFUN ("hash-table-weakness", Fhash_table_weakness, Shash_table_weakness,
4538 1, 1, 0,
e9d8ddc9 4539 doc: /* Return the weakness of TABLE. */)
5842a27b 4540 (Lisp_Object table)
d80c6c11
GM
4541{
4542 return check_hash_table (table)->weak;
4543}
4544
59f953a2 4545
d80c6c11 4546DEFUN ("hash-table-p", Fhash_table_p, Shash_table_p, 1, 1, 0,
e9d8ddc9 4547 doc: /* Return t if OBJ is a Lisp hash table object. */)
5842a27b 4548 (Lisp_Object obj)
d80c6c11
GM
4549{
4550 return HASH_TABLE_P (obj) ? Qt : Qnil;
4551}
4552
4553
4554DEFUN ("clrhash", Fclrhash, Sclrhash, 1, 1, 0,
ccd8f7fe 4555 doc: /* Clear hash table TABLE and return it. */)
5842a27b 4556 (Lisp_Object table)
d80c6c11
GM
4557{
4558 hash_clear (check_hash_table (table));
ccd8f7fe
TTN
4559 /* Be compatible with XEmacs. */
4560 return table;
d80c6c11
GM
4561}
4562
4563
a7ca3326 4564DEFUN ("gethash", Fgethash, Sgethash, 2, 3, 0,
e9d8ddc9
MB
4565 doc: /* Look up KEY in TABLE and return its associated value.
4566If KEY is not found, return DFLT which defaults to nil. */)
5842a27b 4567 (Lisp_Object key, Lisp_Object table, Lisp_Object dflt)
d80c6c11
GM
4568{
4569 struct Lisp_Hash_Table *h = check_hash_table (table);
d3411f89 4570 ptrdiff_t i = hash_lookup (h, key, NULL);
d80c6c11
GM
4571 return i >= 0 ? HASH_VALUE (h, i) : dflt;
4572}
4573
4574
a7ca3326 4575DEFUN ("puthash", Fputhash, Sputhash, 3, 3, 0,
e9d8ddc9 4576 doc: /* Associate KEY with VALUE in hash table TABLE.
47cebab1 4577If KEY is already present in table, replace its current value with
a54e3482 4578VALUE. In any case, return VALUE. */)
5842a27b 4579 (Lisp_Object key, Lisp_Object value, Lisp_Object table)
d80c6c11
GM
4580{
4581 struct Lisp_Hash_Table *h = check_hash_table (table);
d3411f89 4582 ptrdiff_t i;
0de4bb68 4583 EMACS_UINT hash;
d80c6c11
GM
4584
4585 i = hash_lookup (h, key, &hash);
4586 if (i >= 0)
e83064be 4587 set_hash_value_slot (h, i, value);
d80c6c11
GM
4588 else
4589 hash_put (h, key, value, hash);
59f953a2 4590
d9c4f922 4591 return value;
d80c6c11
GM
4592}
4593
4594
a7ca3326 4595DEFUN ("remhash", Fremhash, Sremhash, 2, 2, 0,
e9d8ddc9 4596 doc: /* Remove KEY from TABLE. */)
5842a27b 4597 (Lisp_Object key, Lisp_Object table)
d80c6c11
GM
4598{
4599 struct Lisp_Hash_Table *h = check_hash_table (table);
5a2d7ab6 4600 hash_remove_from_table (h, key);
d80c6c11
GM
4601 return Qnil;
4602}
4603
4604
4605DEFUN ("maphash", Fmaphash, Smaphash, 2, 2, 0,
e9d8ddc9 4606 doc: /* Call FUNCTION for all entries in hash table TABLE.
a3a8a7da
LI
4607FUNCTION is called with two arguments, KEY and VALUE.
4608`maphash' always returns nil. */)
5842a27b 4609 (Lisp_Object function, Lisp_Object table)
d80c6c11
GM
4610{
4611 struct Lisp_Hash_Table *h = check_hash_table (table);
4612 Lisp_Object args[3];
d311d28c 4613 ptrdiff_t i;
d80c6c11
GM
4614
4615 for (i = 0; i < HASH_TABLE_SIZE (h); ++i)
4616 if (!NILP (HASH_HASH (h, i)))
4617 {
4618 args[0] = function;
4619 args[1] = HASH_KEY (h, i);
4620 args[2] = HASH_VALUE (h, i);
4621 Ffuncall (3, args);
4622 }
59f953a2 4623
d80c6c11
GM
4624 return Qnil;
4625}
4626
4627
4628DEFUN ("define-hash-table-test", Fdefine_hash_table_test,
4629 Sdefine_hash_table_test, 3, 3, 0,
e9d8ddc9 4630 doc: /* Define a new hash table test with name NAME, a symbol.
91f78c99 4631
47cebab1
GM
4632In hash tables created with NAME specified as test, use TEST to
4633compare keys, and HASH for computing hash codes of keys.
4634
4635TEST must be a function taking two arguments and returning non-nil if
4636both arguments are the same. HASH must be a function taking one
79804536
SM
4637argument and returning an object that is the hash code of the argument.
4638It should be the case that if (eq (funcall HASH x1) (funcall HASH x2))
4639returns nil, then (funcall TEST x1 x2) also returns nil. */)
5842a27b 4640 (Lisp_Object name, Lisp_Object test, Lisp_Object hash)
d80c6c11
GM
4641{
4642 return Fput (name, Qhash_table_test, list2 (test, hash));
4643}
4644
a3b210c4 4645
57916a7a 4646\f
5c302da4 4647/************************************************************************
7f3f739f 4648 MD5, SHA-1, and SHA-2
5c302da4
GM
4649 ************************************************************************/
4650
57916a7a 4651#include "md5.h"
e1b90ef6 4652#include "sha1.h"
7f3f739f
LL
4653#include "sha256.h"
4654#include "sha512.h"
57916a7a 4655
7f3f739f 4656/* ALGORITHM is a symbol: md5, sha1, sha224 and so on. */
47cebab1 4657
f1b54466 4658static Lisp_Object
7f3f739f 4659secure_hash (Lisp_Object algorithm, Lisp_Object object, Lisp_Object start, Lisp_Object end, Lisp_Object coding_system, Lisp_Object noerror, Lisp_Object binary)
57916a7a 4660{
57916a7a 4661 int i;
d311d28c 4662 ptrdiff_t size;
e6d4aefa 4663 EMACS_INT start_char = 0, end_char = 0;
d311d28c 4664 ptrdiff_t start_byte, end_byte;
e6d4aefa 4665 register EMACS_INT b, e;
57916a7a 4666 register struct buffer *bp;
e6d4aefa 4667 EMACS_INT temp;
7f3f739f
LL
4668 int digest_size;
4669 void *(*hash_func) (const char *, size_t, void *);
4670 Lisp_Object digest;
4671
4672 CHECK_SYMBOL (algorithm);
57916a7a 4673
5c302da4 4674 if (STRINGP (object))
57916a7a
GM
4675 {
4676 if (NILP (coding_system))
4677 {
5c302da4 4678 /* Decide the coding-system to encode the data with. */
57916a7a 4679
5c302da4
GM
4680 if (STRING_MULTIBYTE (object))
4681 /* use default, we can't guess correct value */
38583a69 4682 coding_system = preferred_coding_system ();
91f78c99 4683 else
5c302da4 4684 coding_system = Qraw_text;
57916a7a 4685 }
91f78c99 4686
5c302da4 4687 if (NILP (Fcoding_system_p (coding_system)))
57916a7a 4688 {
5c302da4 4689 /* Invalid coding system. */
91f78c99 4690
5c302da4
GM
4691 if (!NILP (noerror))
4692 coding_system = Qraw_text;
4693 else
692ae65c 4694 xsignal1 (Qcoding_system_error, coding_system);
57916a7a
GM
4695 }
4696
5c302da4 4697 if (STRING_MULTIBYTE (object))
38583a69 4698 object = code_convert_string (object, coding_system, Qnil, 1, 0, 1);
5c302da4 4699
d5db4077 4700 size = SCHARS (object);
8ec49c53 4701 validate_subarray (object, start, end, size, &start_char, &end_char);
57916a7a 4702
8ec49c53
PE
4703 start_byte = !start_char ? 0 : string_char_to_byte (object, start_char);
4704 end_byte = (end_char == size
4705 ? SBYTES (object)
4706 : string_char_to_byte (object, end_char));
57916a7a
GM
4707 }
4708 else
4709 {
6b61353c
KH
4710 struct buffer *prev = current_buffer;
4711
66322887 4712 record_unwind_current_buffer ();
6b61353c 4713
b7826503 4714 CHECK_BUFFER (object);
57916a7a
GM
4715
4716 bp = XBUFFER (object);
a3d794a1 4717 set_buffer_internal (bp);
91f78c99 4718
57916a7a 4719 if (NILP (start))
6b61353c 4720 b = BEGV;
57916a7a
GM
4721 else
4722 {
b7826503 4723 CHECK_NUMBER_COERCE_MARKER (start);
57916a7a
GM
4724 b = XINT (start);
4725 }
4726
4727 if (NILP (end))
6b61353c 4728 e = ZV;
57916a7a
GM
4729 else
4730 {
b7826503 4731 CHECK_NUMBER_COERCE_MARKER (end);
57916a7a
GM
4732 e = XINT (end);
4733 }
91f78c99 4734
57916a7a
GM
4735 if (b > e)
4736 temp = b, b = e, e = temp;
91f78c99 4737
6b61353c 4738 if (!(BEGV <= b && e <= ZV))
57916a7a 4739 args_out_of_range (start, end);
91f78c99 4740
57916a7a
GM
4741 if (NILP (coding_system))
4742 {
91f78c99 4743 /* Decide the coding-system to encode the data with.
5c302da4
GM
4744 See fileio.c:Fwrite-region */
4745
4746 if (!NILP (Vcoding_system_for_write))
4747 coding_system = Vcoding_system_for_write;
4748 else
4749 {
f75d7a91 4750 bool force_raw_text = 0;
5c302da4 4751
4b4deea2 4752 coding_system = BVAR (XBUFFER (object), buffer_file_coding_system);
5c302da4
GM
4753 if (NILP (coding_system)
4754 || NILP (Flocal_variable_p (Qbuffer_file_coding_system, Qnil)))
4755 {
4756 coding_system = Qnil;
4b4deea2 4757 if (NILP (BVAR (current_buffer, enable_multibyte_characters)))
5c302da4
GM
4758 force_raw_text = 1;
4759 }
4760
5e617bc2 4761 if (NILP (coding_system) && !NILP (Fbuffer_file_name (object)))
5c302da4
GM
4762 {
4763 /* Check file-coding-system-alist. */
4764 Lisp_Object args[4], val;
91f78c99 4765
5c302da4 4766 args[0] = Qwrite_region; args[1] = start; args[2] = end;
5e617bc2 4767 args[3] = Fbuffer_file_name (object);
5c302da4
GM
4768 val = Ffind_operation_coding_system (4, args);
4769 if (CONSP (val) && !NILP (XCDR (val)))
4770 coding_system = XCDR (val);
4771 }
4772
4773 if (NILP (coding_system)
4b4deea2 4774 && !NILP (BVAR (XBUFFER (object), buffer_file_coding_system)))
5c302da4
GM
4775 {
4776 /* If we still have not decided a coding system, use the
4777 default value of buffer-file-coding-system. */
4b4deea2 4778 coding_system = BVAR (XBUFFER (object), buffer_file_coding_system);
5c302da4
GM
4779 }
4780
4781 if (!force_raw_text
4782 && !NILP (Ffboundp (Vselect_safe_coding_system_function)))
4783 /* Confirm that VAL can surely encode the current region. */
1e59646d 4784 coding_system = call4 (Vselect_safe_coding_system_function,
70da6a76 4785 make_number (b), make_number (e),
1e59646d 4786 coding_system, Qnil);
5c302da4
GM
4787
4788 if (force_raw_text)
4789 coding_system = Qraw_text;
4790 }
4791
4792 if (NILP (Fcoding_system_p (coding_system)))
57916a7a 4793 {
5c302da4
GM
4794 /* Invalid coding system. */
4795
4796 if (!NILP (noerror))
4797 coding_system = Qraw_text;
4798 else
692ae65c 4799 xsignal1 (Qcoding_system_error, coding_system);
57916a7a
GM
4800 }
4801 }
4802
4803 object = make_buffer_string (b, e, 0);
a3d794a1 4804 set_buffer_internal (prev);
6b61353c
KH
4805 /* Discard the unwind protect for recovering the current
4806 buffer. */
4807 specpdl_ptr--;
57916a7a
GM
4808
4809 if (STRING_MULTIBYTE (object))
8f924df7 4810 object = code_convert_string (object, coding_system, Qnil, 1, 0, 0);
d311d28c
PE
4811 start_byte = 0;
4812 end_byte = SBYTES (object);
57916a7a
GM
4813 }
4814
7f3f739f 4815 if (EQ (algorithm, Qmd5))
e1b90ef6 4816 {
7f3f739f
LL
4817 digest_size = MD5_DIGEST_SIZE;
4818 hash_func = md5_buffer;
4819 }
4820 else if (EQ (algorithm, Qsha1))
4821 {
4822 digest_size = SHA1_DIGEST_SIZE;
4823 hash_func = sha1_buffer;
4824 }
4825 else if (EQ (algorithm, Qsha224))
4826 {
4827 digest_size = SHA224_DIGEST_SIZE;
4828 hash_func = sha224_buffer;
4829 }
4830 else if (EQ (algorithm, Qsha256))
4831 {
4832 digest_size = SHA256_DIGEST_SIZE;
4833 hash_func = sha256_buffer;
4834 }
4835 else if (EQ (algorithm, Qsha384))
4836 {
4837 digest_size = SHA384_DIGEST_SIZE;
4838 hash_func = sha384_buffer;
4839 }
4840 else if (EQ (algorithm, Qsha512))
4841 {
4842 digest_size = SHA512_DIGEST_SIZE;
4843 hash_func = sha512_buffer;
4844 }
4845 else
4846 error ("Invalid algorithm arg: %s", SDATA (Fsymbol_name (algorithm)));
57916a7a 4847
7f3f739f
LL
4848 /* allocate 2 x digest_size so that it can be re-used to hold the
4849 hexified value */
4850 digest = make_uninit_string (digest_size * 2);
57916a7a 4851
7f3f739f 4852 hash_func (SSDATA (object) + start_byte,
d311d28c 4853 end_byte - start_byte,
7f3f739f 4854 SSDATA (digest));
e1b90ef6 4855
7f3f739f
LL
4856 if (NILP (binary))
4857 {
4858 unsigned char *p = SDATA (digest);
4859 for (i = digest_size - 1; i >= 0; i--)
4860 {
4861 static char const hexdigit[16] = "0123456789abcdef";
4862 int p_i = p[i];
4863 p[2 * i] = hexdigit[p_i >> 4];
4864 p[2 * i + 1] = hexdigit[p_i & 0xf];
4865 }
4866 return digest;
4867 }
4868 else
a9041e6c 4869 return make_unibyte_string (SSDATA (digest), digest_size);
e1b90ef6
LL
4870}
4871
4872DEFUN ("md5", Fmd5, Smd5, 1, 5, 0,
4873 doc: /* Return MD5 message digest of OBJECT, a buffer or string.
4874
4875A message digest is a cryptographic checksum of a document, and the
4876algorithm to calculate it is defined in RFC 1321.
4877
4878The two optional arguments START and END are character positions
4879specifying for which part of OBJECT the message digest should be
4880computed. If nil or omitted, the digest is computed for the whole
4881OBJECT.
4882
4883The MD5 message digest is computed from the result of encoding the
4884text in a coding system, not directly from the internal Emacs form of
4885the text. The optional fourth argument CODING-SYSTEM specifies which
4886coding system to encode the text with. It should be the same coding
4887system that you used or will use when actually writing the text into a
4888file.
4889
4890If CODING-SYSTEM is nil or omitted, the default depends on OBJECT. If
4891OBJECT is a buffer, the default for CODING-SYSTEM is whatever coding
4892system would be chosen by default for writing this text into a file.
4893
4894If OBJECT is a string, the most preferred coding system (see the
4895command `prefer-coding-system') is used.
4896
4897If NOERROR is non-nil, silently assume the `raw-text' coding if the
4898guesswork fails. Normally, an error is signaled in such case. */)
4899 (Lisp_Object object, Lisp_Object start, Lisp_Object end, Lisp_Object coding_system, Lisp_Object noerror)
4900{
7f3f739f 4901 return secure_hash (Qmd5, object, start, end, coding_system, noerror, Qnil);
e1b90ef6
LL
4902}
4903
7f3f739f 4904DEFUN ("secure-hash", Fsecure_hash, Ssecure_hash, 2, 5, 0,
49241268
GM
4905 doc: /* Return the secure hash of OBJECT, a buffer or string.
4906ALGORITHM is a symbol specifying the hash to use:
4907md5, sha1, sha224, sha256, sha384 or sha512.
4908
4909The two optional arguments START and END are positions specifying for
4910which part of OBJECT to compute the hash. If nil or omitted, uses the
4911whole OBJECT.
4912
4913If BINARY is non-nil, returns a string in binary form. */)
7f3f739f 4914 (Lisp_Object algorithm, Lisp_Object object, Lisp_Object start, Lisp_Object end, Lisp_Object binary)
e1b90ef6 4915{
7f3f739f 4916 return secure_hash (algorithm, object, start, end, Qnil, Qnil, binary);
57916a7a 4917}
24c129e4 4918\f
dfcf069d 4919void
971de7fb 4920syms_of_fns (void)
7b863bd5 4921{
7f3f739f
LL
4922 DEFSYM (Qmd5, "md5");
4923 DEFSYM (Qsha1, "sha1");
4924 DEFSYM (Qsha224, "sha224");
4925 DEFSYM (Qsha256, "sha256");
4926 DEFSYM (Qsha384, "sha384");
4927 DEFSYM (Qsha512, "sha512");
4928
d80c6c11 4929 /* Hash table stuff. */
cd3520a4
JB
4930 DEFSYM (Qhash_table_p, "hash-table-p");
4931 DEFSYM (Qeq, "eq");
4932 DEFSYM (Qeql, "eql");
4933 DEFSYM (Qequal, "equal");
4934 DEFSYM (QCtest, ":test");
4935 DEFSYM (QCsize, ":size");
4936 DEFSYM (QCrehash_size, ":rehash-size");
4937 DEFSYM (QCrehash_threshold, ":rehash-threshold");
4938 DEFSYM (QCweakness, ":weakness");
4939 DEFSYM (Qkey, "key");
4940 DEFSYM (Qvalue, "value");
4941 DEFSYM (Qhash_table_test, "hash-table-test");
4942 DEFSYM (Qkey_or_value, "key-or-value");
4943 DEFSYM (Qkey_and_value, "key-and-value");
d80c6c11
GM
4944
4945 defsubr (&Ssxhash);
4946 defsubr (&Smake_hash_table);
f899c503 4947 defsubr (&Scopy_hash_table);
d80c6c11
GM
4948 defsubr (&Shash_table_count);
4949 defsubr (&Shash_table_rehash_size);
4950 defsubr (&Shash_table_rehash_threshold);
4951 defsubr (&Shash_table_size);
4952 defsubr (&Shash_table_test);
e84b1dea 4953 defsubr (&Shash_table_weakness);
d80c6c11
GM
4954 defsubr (&Shash_table_p);
4955 defsubr (&Sclrhash);
4956 defsubr (&Sgethash);
4957 defsubr (&Sputhash);
4958 defsubr (&Sremhash);
4959 defsubr (&Smaphash);
4960 defsubr (&Sdefine_hash_table_test);
59f953a2 4961
cd3520a4
JB
4962 DEFSYM (Qstring_lessp, "string-lessp");
4963 DEFSYM (Qprovide, "provide");
4964 DEFSYM (Qrequire, "require");
4965 DEFSYM (Qyes_or_no_p_history, "yes-or-no-p-history");
4966 DEFSYM (Qcursor_in_echo_area, "cursor-in-echo-area");
4967 DEFSYM (Qwidget_type, "widget-type");
7b863bd5 4968
09ab3c3b
KH
4969 staticpro (&string_char_byte_cache_string);
4970 string_char_byte_cache_string = Qnil;
4971
1f79789d
RS
4972 require_nesting_list = Qnil;
4973 staticpro (&require_nesting_list);
4974
52a9879b
RS
4975 Fset (Qyes_or_no_p_history, Qnil);
4976
29208e82 4977 DEFVAR_LISP ("features", Vfeatures,
4774b68e 4978 doc: /* A list of symbols which are the features of the executing Emacs.
47cebab1 4979Used by `featurep' and `require', and altered by `provide'. */);
6c6f1994 4980 Vfeatures = list1 (intern_c_string ("emacs"));
cd3520a4 4981 DEFSYM (Qsubfeatures, "subfeatures");
de0503df 4982 DEFSYM (Qfuncall, "funcall");
7b863bd5 4983
dec002ca 4984#ifdef HAVE_LANGINFO_CODESET
cd3520a4
JB
4985 DEFSYM (Qcodeset, "codeset");
4986 DEFSYM (Qdays, "days");
4987 DEFSYM (Qmonths, "months");
4988 DEFSYM (Qpaper, "paper");
dec002ca
DL
4989#endif /* HAVE_LANGINFO_CODESET */
4990
29208e82 4991 DEFVAR_BOOL ("use-dialog-box", use_dialog_box,
fb7ada5f 4992 doc: /* Non-nil means mouse commands use dialog boxes to ask questions.
436fa78b 4993This applies to `y-or-n-p' and `yes-or-no-p' questions asked by commands
7e861e0d
CY
4994invoked by mouse clicks and mouse menu items.
4995
4996On some platforms, file selection dialogs are also enabled if this is
4997non-nil. */);
bdd8d692
RS
4998 use_dialog_box = 1;
4999
29208e82 5000 DEFVAR_BOOL ("use-file-dialog", use_file_dialog,
fb7ada5f 5001 doc: /* Non-nil means mouse commands use a file dialog to ask for files.
1f1d0797 5002This applies to commands from menus and tool bar buttons even when
2fd0161b
CY
5003they are initiated from the keyboard. If `use-dialog-box' is nil,
5004that disables the use of a file dialog, regardless of the value of
5005this variable. */);
6b61353c
KH
5006 use_file_dialog = 1;
5007
7b863bd5
JB
5008 defsubr (&Sidentity);
5009 defsubr (&Srandom);
5010 defsubr (&Slength);
5a30fab8 5011 defsubr (&Ssafe_length);
026f59ce 5012 defsubr (&Sstring_bytes);
7b863bd5 5013 defsubr (&Sstring_equal);
0e1e9f8d 5014 defsubr (&Scompare_strings);
7b863bd5
JB
5015 defsubr (&Sstring_lessp);
5016 defsubr (&Sappend);
5017 defsubr (&Sconcat);
5018 defsubr (&Svconcat);
5019 defsubr (&Scopy_sequence);
09ab3c3b
KH
5020 defsubr (&Sstring_make_multibyte);
5021 defsubr (&Sstring_make_unibyte);
6d475204
RS
5022 defsubr (&Sstring_as_multibyte);
5023 defsubr (&Sstring_as_unibyte);
2df18cdb 5024 defsubr (&Sstring_to_multibyte);
b4480f16 5025 defsubr (&Sstring_to_unibyte);
7b863bd5
JB
5026 defsubr (&Scopy_alist);
5027 defsubr (&Ssubstring);
aebf4d42 5028 defsubr (&Ssubstring_no_properties);
7b863bd5
JB
5029 defsubr (&Snthcdr);
5030 defsubr (&Snth);
5031 defsubr (&Selt);
5032 defsubr (&Smember);
5033 defsubr (&Smemq);
008ef0ef 5034 defsubr (&Smemql);
7b863bd5
JB
5035 defsubr (&Sassq);
5036 defsubr (&Sassoc);
5037 defsubr (&Srassq);
0fb5a19c 5038 defsubr (&Srassoc);
7b863bd5 5039 defsubr (&Sdelq);
ca8dd546 5040 defsubr (&Sdelete);
7b863bd5
JB
5041 defsubr (&Snreverse);
5042 defsubr (&Sreverse);
5043 defsubr (&Ssort);
be9d483d 5044 defsubr (&Splist_get);
7b863bd5 5045 defsubr (&Sget);
be9d483d 5046 defsubr (&Splist_put);
7b863bd5 5047 defsubr (&Sput);
aebf4d42
RS
5048 defsubr (&Slax_plist_get);
5049 defsubr (&Slax_plist_put);
95f8c3b9 5050 defsubr (&Seql);
7b863bd5 5051 defsubr (&Sequal);
6b61353c 5052 defsubr (&Sequal_including_properties);
7b863bd5 5053 defsubr (&Sfillarray);
85cad579 5054 defsubr (&Sclear_string);
7b863bd5
JB
5055 defsubr (&Snconc);
5056 defsubr (&Smapcar);
5c6740c9 5057 defsubr (&Smapc);
7b863bd5 5058 defsubr (&Smapconcat);
7b863bd5
JB
5059 defsubr (&Syes_or_no_p);
5060 defsubr (&Sload_average);
5061 defsubr (&Sfeaturep);
5062 defsubr (&Srequire);
5063 defsubr (&Sprovide);
a5254817 5064 defsubr (&Splist_member);
b4f334f7
KH
5065 defsubr (&Swidget_put);
5066 defsubr (&Swidget_get);
5067 defsubr (&Swidget_apply);
24c129e4
KH
5068 defsubr (&Sbase64_encode_region);
5069 defsubr (&Sbase64_decode_region);
5070 defsubr (&Sbase64_encode_string);
5071 defsubr (&Sbase64_decode_string);
57916a7a 5072 defsubr (&Smd5);
7f3f739f 5073 defsubr (&Ssecure_hash);
d68beb2f 5074 defsubr (&Slocale_info);
b7432bb2 5075
29abe551
PE
5076 hashtest_eq.name = Qeq;
5077 hashtest_eq.user_hash_function = Qnil;
5078 hashtest_eq.user_cmp_function = Qnil;
5079 hashtest_eq.cmpfn = 0;
5080 hashtest_eq.hashfn = hashfn_eq;
5081
5082 hashtest_eql.name = Qeql;
5083 hashtest_eql.user_hash_function = Qnil;
5084 hashtest_eql.user_cmp_function = Qnil;
5085 hashtest_eql.cmpfn = cmpfn_eql;
5086 hashtest_eql.hashfn = hashfn_eql;
5087
5088 hashtest_equal.name = Qequal;
5089 hashtest_equal.user_hash_function = Qnil;
5090 hashtest_equal.user_cmp_function = Qnil;
5091 hashtest_equal.cmpfn = cmpfn_equal;
5092 hashtest_equal.hashfn = hashfn_equal;
7b863bd5 5093}