* lib-src/fakemail.c (action): Convert function definitions to standard C.
[bpt/emacs.git] / src / category.c
CommitLineData
4ed46869 1/* GNU Emacs routines to deal with category tables.
114f9c96 2 Copyright (C) 1998, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
429ab54e 3 Free Software Foundation, Inc.
7976eda0 4 Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004,
114f9c96 5 2005, 2006, 2007, 2008, 2009, 2010
ce03bf76
KH
6 National Institute of Advanced Industrial Science and Technology (AIST)
7 Registration Number H14PRO021
8f924df7 8 Copyright (C) 2003
ea012abd
KH
9 National Institute of Advanced Industrial Science and Technology (AIST)
10 Registration Number H13PRO009
4ed46869
KH
11
12This file is part of GNU Emacs.
13
9ec0b715 14GNU Emacs is free software: you can redistribute it and/or modify
4ed46869 15it under the terms of the GNU General Public License as published by
9ec0b715
GM
16the Free Software Foundation, either version 3 of the License, or
17(at your option) any later version.
4ed46869
KH
18
19GNU Emacs is distributed in the hope that it will be useful,
20but WITHOUT ANY WARRANTY; without even the implied warranty of
21MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22GNU General Public License for more details.
23
24You should have received a copy of the GNU General Public License
9ec0b715 25along with GNU Emacs. If not, see <http://www.gnu.org/licenses/>. */
4ed46869
KH
26
27
28/* Here we handle three objects: category, category set, and category
29 table. Read comments in the file category.h to understand them. */
30
31#include <config.h>
32#include <ctype.h>
d7306fe6 33#include <setjmp.h>
4ed46869
KH
34#include "lisp.h"
35#include "buffer.h"
ea012abd 36#include "character.h"
4ed46869
KH
37#include "charset.h"
38#include "category.h"
e35f6ff7 39#include "keymap.h"
4ed46869
KH
40
41/* The version number of the latest category table. Each category
42 table has a unique version number. It is assigned a new number
43 also when it is modified. When a regular expression is compiled
44 into the struct re_pattern_buffer, the version number of the
45 category table (of the current buffer) at that moment is also
46 embedded in the structure.
47
48 For the moment, we are not using this feature. */
49static int category_table_version;
50
51Lisp_Object Qcategory_table, Qcategoryp, Qcategorysetp, Qcategory_table_p;
52
53/* Variables to determine word boundary. */
54Lisp_Object Vword_combining_categories, Vword_separating_categories;
55
56/* Temporary internal variable used in macro CHAR_HAS_CATEGORY. */
57Lisp_Object _temp_category_set;
58
59\f
60/* Category set staff. */
61
f57e2426 62static Lisp_Object hash_get_category_set (Lisp_Object, Lisp_Object);
cd486875
KH
63
64static Lisp_Object
65hash_get_category_set (table, category_set)
66 Lisp_Object table, category_set;
67{
68 Lisp_Object val;
69 struct Lisp_Hash_Table *h;
70 int i;
71 unsigned hash;
72
73 if (NILP (XCHAR_TABLE (table)->extras[1]))
74 XCHAR_TABLE (table)->extras[1]
75 = make_hash_table (Qequal, make_number (DEFAULT_HASH_SIZE),
76 make_float (DEFAULT_REHASH_SIZE),
77 make_float (DEFAULT_REHASH_THRESHOLD),
78 Qnil, Qnil, Qnil);
79 h = XHASH_TABLE (XCHAR_TABLE (table)->extras[1]);
80 i = hash_lookup (h, category_set, &hash);
81 if (i >= 0)
82 return HASH_KEY (h, i);
83 hash_put (h, category_set, Qnil, hash);
84 return category_set;
85}
86
87
4ed46869 88DEFUN ("make-category-set", Fmake_category_set, Smake_category_set, 1, 1, 0,
fdb82f93
PJ
89 doc: /* Return a newly created category-set which contains CATEGORIES.
90CATEGORIES is a string of category mnemonics.
91The value is a bool-vector which has t at the indices corresponding to
92those categories. */)
93 (categories)
4ed46869
KH
94 Lisp_Object categories;
95{
96 Lisp_Object val;
97 int len;
98
b7826503 99 CHECK_STRING (categories);
4ed46869
KH
100 val = MAKE_CATEGORY_SET;
101
115afec3 102 if (STRING_MULTIBYTE (categories))
95030461 103 error ("Multibyte string in `make-category-set'");
115afec3 104
d5db4077 105 len = SCHARS (categories);
4ed46869
KH
106 while (--len >= 0)
107 {
15c60737 108 Lisp_Object category;
4ed46869 109
d5db4077 110 XSETFASTINT (category, SREF (categories, len));
b7826503 111 CHECK_CATEGORY (category);
4ed46869
KH
112 SET_CATEGORY_SET (val, category, Qt);
113 }
114 return val;
115}
116
117\f
118/* Category staff. */
119
120Lisp_Object check_category_table ();
121
122DEFUN ("define-category", Fdefine_category, Sdefine_category, 2, 3, 0,
839966f3
KH
123 doc: /* Define CATEGORY as a category which is described by DOCSTRING.
124CATEGORY should be an ASCII printing character in the range ` ' to `~'.
f6d2f045
KH
125DOCSTRING is the documentation string of the category. The first line
126should be a terse text (preferably less than 16 characters),
127and the rest lines should be the full description.
fdb82f93 128The category is defined only in category table TABLE, which defaults to
839966f3 129the current buffer's category table. */)
fdb82f93 130 (category, docstring, table)
4ed46869
KH
131 Lisp_Object category, docstring, table;
132{
b7826503
PJ
133 CHECK_CATEGORY (category);
134 CHECK_STRING (docstring);
4ed46869
KH
135 table = check_category_table (table);
136
137 if (!NILP (CATEGORY_DOCSTRING (table, XFASTINT (category))))
138 error ("Category `%c' is already defined", XFASTINT (category));
905a9ed3
DN
139 if (!NILP (Vpurify_flag))
140 docstring = Fpurecopy (docstring);
4ed46869
KH
141 CATEGORY_DOCSTRING (table, XFASTINT (category)) = docstring;
142
143 return Qnil;
144}
145
146DEFUN ("category-docstring", Fcategory_docstring, Scategory_docstring, 1, 2, 0,
839966f3
KH
147 doc: /* Return the documentation string of CATEGORY, as defined in TABLE.
148TABLE should be a category table and defaults to the current buffer's
149category table. */)
fdb82f93 150 (category, table)
4ed46869
KH
151 Lisp_Object category, table;
152{
b7826503 153 CHECK_CATEGORY (category);
4ed46869
KH
154 table = check_category_table (table);
155
156 return CATEGORY_DOCSTRING (table, XFASTINT (category));
157}
158
159DEFUN ("get-unused-category", Fget_unused_category, Sget_unused_category,
160 0, 1, 0,
839966f3 161 doc: /* Return a category which is not yet defined in TABLE.
0b6694a5 162If no category remains available, return nil.
839966f3 163The optional argument TABLE specifies which category table to modify;
0b6694a5 164it defaults to the current buffer's category table. */)
fdb82f93 165 (table)
4ed46869
KH
166 Lisp_Object table;
167{
168 int i;
4ed46869
KH
169
170 table = check_category_table (table);
171
172 for (i = ' '; i <= '~'; i++)
173 if (NILP (CATEGORY_DOCSTRING (table, i)))
174 return make_number (i);
175
176 return Qnil;
177}
178
179\f
180/* Category-table staff. */
181
182DEFUN ("category-table-p", Fcategory_table_p, Scategory_table_p, 1, 1, 0,
fdb82f93
PJ
183 doc: /* Return t if ARG is a category table. */)
184 (arg)
4ed46869
KH
185 Lisp_Object arg;
186{
187 if (CHAR_TABLE_P (arg)
ed8ec86d 188 && EQ (XCHAR_TABLE (arg)->purpose, Qcategory_table))
4ed46869
KH
189 return Qt;
190 return Qnil;
191}
192
193/* If TABLE is nil, return the current category table. If TABLE is
194 not nil, check the validity of TABLE as a category table. If
195 valid, return TABLE itself, but if not valid, signal an error of
196 wrong-type-argument. */
197
198Lisp_Object
199check_category_table (table)
200 Lisp_Object table;
201{
4ed46869
KH
202 if (NILP (table))
203 return current_buffer->category_table;
88674269 204 CHECK_TYPE (!NILP (Fcategory_table_p (table)), Qcategory_table_p, table);
4ed46869 205 return table;
177c0ea7 206}
4ed46869
KH
207
208DEFUN ("category-table", Fcategory_table, Scategory_table, 0, 0, 0,
fdb82f93
PJ
209 doc: /* Return the current category table.
210This is the one specified by the current buffer. */)
211 ()
4ed46869
KH
212{
213 return current_buffer->category_table;
214}
215
216DEFUN ("standard-category-table", Fstandard_category_table,
217 Sstandard_category_table, 0, 0, 0,
fdb82f93
PJ
218 doc: /* Return the standard category table.
219This is the one used for new buffers. */)
220 ()
4ed46869
KH
221{
222 return Vstandard_category_table;
223}
224
ea012abd
KH
225
226static void
8f924df7
KH
227copy_category_entry (table, c, val)
228 Lisp_Object table, c, val;
ea012abd 229{
f4b670ef 230 val = Fcopy_sequence (val);
8f924df7
KH
231 if (CONSP (c))
232 char_table_set_range (table, XINT (XCAR (c)), XINT (XCDR (c)), val);
f4b670ef 233 else
8f924df7 234 char_table_set (table, XINT (c), val);
ea012abd
KH
235}
236
4ed46869
KH
237/* Return a copy of category table TABLE. We can't simply use the
238 function copy-sequence because no contents should be shared between
ed8ec86d 239 the original and the copy. This function is called recursively by
9da95d53 240 binding TABLE to a sub char table. */
4ed46869
KH
241
242Lisp_Object
ed8ec86d 243copy_category_table (table)
4ed46869
KH
244 Lisp_Object table;
245{
ea012abd 246 table = copy_char_table (table);
4ed46869 247
ea012abd
KH
248 if (! NILP (XCHAR_TABLE (table)->defalt))
249 XCHAR_TABLE (table)->defalt
250 = Fcopy_sequence (XCHAR_TABLE (table)->defalt);
251 XCHAR_TABLE (table)->extras[0]
252 = Fcopy_sequence (XCHAR_TABLE (table)->extras[0]);
8f924df7 253 map_char_table (copy_category_entry, Qnil, table, table);
ed8ec86d 254
4ed46869
KH
255 return table;
256}
257
258DEFUN ("copy-category-table", Fcopy_category_table, Scopy_category_table,
259 0, 1, 0,
fdb82f93
PJ
260 doc: /* Construct a new category table and return it.
261It is a copy of the TABLE, which defaults to the standard category table. */)
262 (table)
4ed46869
KH
263 Lisp_Object table;
264{
265 if (!NILP (table))
266 check_category_table (table);
267 else
268 table = Vstandard_category_table;
269
9da95d53 270 return copy_category_table (table);
4ed46869
KH
271}
272
70414a3d
KH
273DEFUN ("make-category-table", Fmake_category_table, Smake_category_table,
274 0, 0, 0,
fdb82f93
PJ
275 doc: /* Construct a new and empty category table and return it. */)
276 ()
70414a3d
KH
277{
278 Lisp_Object val;
ea012abd 279 int i;
70414a3d
KH
280
281 val = Fmake_char_table (Qcategory_table, Qnil);
282 XCHAR_TABLE (val)->defalt = MAKE_CATEGORY_SET;
8f924df7 283 for (i = 0; i < (1 << CHARTAB_SIZE_BITS_0); i++)
ea012abd 284 XCHAR_TABLE (val)->contents[i] = MAKE_CATEGORY_SET;
70414a3d
KH
285 Fset_char_table_extra_slot (val, make_number (0),
286 Fmake_vector (make_number (95), Qnil));
287 return val;
288}
289
4ed46869 290DEFUN ("set-category-table", Fset_category_table, Sset_category_table, 1, 1, 0,
839966f3
KH
291 doc: /* Specify TABLE as the category table for the current buffer.
292Return TABLE. */)
fdb82f93 293 (table)
4ed46869
KH
294 Lisp_Object table;
295{
6f598a6d 296 int idx;
4ed46869
KH
297 table = check_category_table (table);
298 current_buffer->category_table = table;
299 /* Indicate that this buffer now has a specified category table. */
f6cd0527
GM
300 idx = PER_BUFFER_VAR_IDX (category_table);
301 SET_PER_BUFFER_VALUE_P (current_buffer, idx, 1);
4ed46869
KH
302 return table;
303}
304
305\f
ea012abd
KH
306Lisp_Object
307char_category_set (c)
308 int c;
309{
310 return CHAR_TABLE_REF (current_buffer->category_table, c);
311}
312
4ed46869 313DEFUN ("char-category-set", Fchar_category_set, Schar_category_set, 1, 1, 0,
a2c2f196
JB
314 doc: /* Return the category set of CHAR.
315usage: (char-category-set CHAR) */)
fdb82f93 316 (ch)
4ed46869
KH
317 Lisp_Object ch;
318{
b7826503 319 CHECK_NUMBER (ch);
4ed46869
KH
320 return CATEGORY_SET (XFASTINT (ch));
321}
322
323DEFUN ("category-set-mnemonics", Fcategory_set_mnemonics,
324 Scategory_set_mnemonics, 1, 1, 0,
fdb82f93
PJ
325 doc: /* Return a string containing mnemonics of the categories in CATEGORY-SET.
326CATEGORY-SET is a bool-vector, and the categories \"in\" it are those
839966f3 327that are indexes where t occurs in the bool-vector.
fdb82f93
PJ
328The return value is a string containing those same categories. */)
329 (category_set)
4ed46869
KH
330 Lisp_Object category_set;
331{
332 int i, j;
333 char str[96];
334
b7826503 335 CHECK_CATEGORY_SET (category_set);
4ed46869
KH
336
337 j = 0;
338 for (i = 32; i < 127; i++)
339 if (CATEGORY_MEMBER (i, category_set))
340 str[j++] = i;
341 str[j] = '\0';
342
343 return build_string (str);
344}
345
4ed46869
KH
346void
347set_category_set (category_set, category, val)
348 Lisp_Object category_set, category, val;
349{
350 do {
351 int idx = XINT (category) / 8;
352 unsigned char bits = 1 << (XINT (category) % 8);
353
354 if (NILP (val))
355 XCATEGORY_SET (category_set)->data[idx] &= ~bits;
356 else
357 XCATEGORY_SET (category_set)->data[idx] |= bits;
358 } while (0);
359}
360
361DEFUN ("modify-category-entry", Fmodify_category_entry,
362 Smodify_category_entry, 2, 4, 0,
fdb82f93
PJ
363 doc: /* Modify the category set of CHARACTER by adding CATEGORY to it.
364The category is changed only for table TABLE, which defaults to
8f7e5042
DL
365the current buffer's category table.
366CHARACTER can be either a single character or a cons representing the
367lower and upper ends of an inclusive character range to modify.
fdb82f93
PJ
368If optional fourth argument RESET is non-nil,
369then delete CATEGORY from the category set instead of adding it. */)
370 (character, category, table, reset)
ea4943bf 371 Lisp_Object character, category, table, reset;
4ed46869 372{
4ed46869 373 Lisp_Object set_value; /* Actual value to be set in category sets. */
8f7e5042 374 Lisp_Object category_set;
ea012abd
KH
375 int start, end;
376 int from, to;
4ed46869 377
ea012abd 378 if (INTEGERP (character))
4ed46869 379 {
ea012abd
KH
380 CHECK_CHARACTER (character);
381 start = end = XFASTINT (character);
4ed46869 382 }
ea012abd 383 else
4ed46869 384 {
ea012abd 385 CHECK_CONS (character);
8f924df7
KH
386 CHECK_CHARACTER_CAR (character);
387 CHECK_CHARACTER_CDR (character);
ea012abd
KH
388 start = XFASTINT (XCAR (character));
389 end = XFASTINT (XCDR (character));
4ed46869 390 }
4ed46869 391
b7826503 392 CHECK_CATEGORY (category);
4ed46869 393 table = check_category_table (table);
4ed46869 394
4ed46869
KH
395 if (NILP (CATEGORY_DOCSTRING (table, XFASTINT (category))))
396 error ("Undefined category: %c", XFASTINT (category));
4ed46869 397
4ed46869 398 set_value = NILP (reset) ? Qt : Qnil;
4ed46869 399
ea012abd 400 while (start <= end)
4ed46869 401 {
cd486875 402 from = start, to = end;
ea012abd 403 category_set = char_table_ref_and_range (table, start, &from, &to);
0b261f59 404 if (CATEGORY_MEMBER (XFASTINT (category), category_set) != NILP (reset))
ea012abd 405 {
d8887a31
KH
406 category_set = Fcopy_sequence (category_set);
407 SET_CATEGORY_SET (category_set, category, set_value);
cd486875
KH
408 category_set = hash_get_category_set (table, category_set);
409 char_table_set_range (table, start, to, category_set);
ea012abd 410 }
ea012abd 411 start = to + 1;
4ed46869 412 }
4ed46869
KH
413
414 return Qnil;
415}
416\f
4ed46869
KH
417/* Return 1 if there is a word boundary between two word-constituent
418 characters C1 and C2 if they appear in this order, else return 0.
419 Use the macro WORD_BOUNDARY_P instead of calling this function
420 directly. */
421
422int
423word_boundary_p (c1, c2)
424 int c1, c2;
425{
426 Lisp_Object category_set1, category_set2;
427 Lisp_Object tail;
428 int default_result;
429
714b2198
KH
430 if (EQ (CHAR_TABLE_REF (Vchar_script_table, c1),
431 CHAR_TABLE_REF (Vchar_script_table, c2)))
4ed46869
KH
432 {
433 tail = Vword_separating_categories;
434 default_result = 0;
435 }
436 else
437 {
438 tail = Vword_combining_categories;
439 default_result = 1;
440 }
441
442 category_set1 = CATEGORY_SET (c1);
443 if (NILP (category_set1))
444 return default_result;
445 category_set2 = CATEGORY_SET (c2);
446 if (NILP (category_set2))
447 return default_result;
448
03699b14 449 for (; CONSP (tail); tail = XCDR (tail))
4ed46869 450 {
03699b14 451 Lisp_Object elt = XCAR (tail);
4ed46869
KH
452
453 if (CONSP (elt)
714b2198
KH
454 && (NILP (XCAR (elt))
455 || (CATEGORYP (XCAR (elt))
8a605fe8
KH
456 && CATEGORY_MEMBER (XFASTINT (XCAR (elt)), category_set1)
457 && ! CATEGORY_MEMBER (XFASTINT (XCAR (elt)), category_set2)))
714b2198
KH
458 && (NILP (XCDR (elt))
459 || (CATEGORYP (XCDR (elt))
8a605fe8 460 && ! CATEGORY_MEMBER (XFASTINT (XCDR (elt)), category_set1)
714b2198 461 && CATEGORY_MEMBER (XFASTINT (XCDR (elt)), category_set2))))
4ed46869
KH
462 return !default_result;
463 }
464 return default_result;
465}
466
467\f
dfcf069d 468void
4ed46869
KH
469init_category_once ()
470{
471 /* This has to be done here, before we call Fmake_char_table. */
d67b4f80 472 Qcategory_table = intern_c_string ("category-table");
4ed46869
KH
473 staticpro (&Qcategory_table);
474
475 /* Intern this now in case it isn't already done.
476 Setting this variable twice is harmless.
477 But don't staticpro it here--that is done in alloc.c. */
d67b4f80 478 Qchar_table_extra_slots = intern_c_string ("char-table-extra-slots");
4ed46869
KH
479
480 /* Now we are ready to set up this property, so we can
481 create category tables. */
482 Fput (Qcategory_table, Qchar_table_extra_slots, make_number (2));
483
484 Vstandard_category_table = Fmake_char_table (Qcategory_table, Qnil);
177c0ea7 485 /* Set a category set which contains nothing to the default. */
4ed46869 486 XCHAR_TABLE (Vstandard_category_table)->defalt = MAKE_CATEGORY_SET;
9da95d53 487 Fset_char_table_extra_slot (Vstandard_category_table, make_number (0),
4ed46869
KH
488 Fmake_vector (make_number (95), Qnil));
489}
490
dfcf069d 491void
4ed46869
KH
492syms_of_category ()
493{
d67b4f80 494 Qcategoryp = intern_c_string ("categoryp");
4ed46869 495 staticpro (&Qcategoryp);
d67b4f80 496 Qcategorysetp = intern_c_string ("categorysetp");
4ed46869 497 staticpro (&Qcategorysetp);
d67b4f80 498 Qcategory_table_p = intern_c_string ("category-table-p");
4ed46869
KH
499 staticpro (&Qcategory_table_p);
500
501 DEFVAR_LISP ("word-combining-categories", &Vword_combining_categories,
fdb82f93
PJ
502 doc: /* List of pair (cons) of categories to determine word boundary.
503
504Emacs treats a sequence of word constituent characters as a single
e0f24100 505word (i.e. finds no word boundary between them) only if they belong to
714b2198 506the same script. But, exceptions are allowed in the following cases.
fdb82f93 507
714b2198 508\(1) The case that characters are in different scripts is controlled
fdb82f93
PJ
509by the variable `word-combining-categories'.
510
714b2198 511Emacs finds no word boundary between characters of different scripts
fdb82f93
PJ
512if they have categories matching some element of this list.
513
514More precisely, if an element of this list is a cons of category CAT1
515and CAT2, and a multibyte character C1 which has CAT1 is followed by
516C2 which has CAT2, there's no word boundary between C1 and C2.
517
714b2198
KH
518For instance, to tell that Han characters followed by Hiragana
519characters can form a single word, the element `(?C . ?H)' should be
520in this list.
fdb82f93 521
714b2198 522\(2) The case that character are in the same script is controlled by
fdb82f93
PJ
523the variable `word-separating-categories'.
524
ecdcaa09 525Emacs finds a word boundary between characters of the same script
fdb82f93
PJ
526if they have categories matching some element of this list.
527
528More precisely, if an element of this list is a cons of category CAT1
8a605fe8
KH
529and CAT2, and a multibyte character C1 which has CAT1 but not CAT2 is
530followed by C2 which has CAT2 but not CAT1, there's a word boundary
531between C1 and C2.
fdb82f93 532
714b2198
KH
533For instance, to tell that there's a word boundary between Hiragana
534and Katakana (both are in the same script `kana'),
535the element `(?H . ?K) should be in this list. */);
4ed46869
KH
536
537 Vword_combining_categories = Qnil;
538
539 DEFVAR_LISP ("word-separating-categories", &Vword_separating_categories,
fdb82f93
PJ
540 doc: /* List of pair (cons) of categories to determine word boundary.
541See the documentation of the variable `word-combining-categories'. */);
4ed46869
KH
542
543 Vword_separating_categories = Qnil;
544
545 defsubr (&Smake_category_set);
546 defsubr (&Sdefine_category);
547 defsubr (&Scategory_docstring);
548 defsubr (&Sget_unused_category);
549 defsubr (&Scategory_table_p);
550 defsubr (&Scategory_table);
551 defsubr (&Sstandard_category_table);
552 defsubr (&Scopy_category_table);
70414a3d 553 defsubr (&Smake_category_table);
4ed46869
KH
554 defsubr (&Sset_category_table);
555 defsubr (&Schar_category_set);
556 defsubr (&Scategory_set_mnemonics);
557 defsubr (&Smodify_category_entry);
4ed46869
KH
558
559 category_table_version = 0;
560}
839966f3
KH
561
562/* arch-tag: 74ebf524-121b-4d9c-bd68-07f8d708b211
563 (do not change this comment) */