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