summaryrefslogtreecommitdiff
path: root/libguile/tags.h
blob: f5009027d2145002bb4d178aa9a0c78909b36a79 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
/* classes: h_files */

#ifndef SCM_TAGS_H
#define SCM_TAGS_H

/* Copyright (C) 1995,1996,1997,1998,1999,2000,2001,2002,2003,2004,2008,2009,2010,2011
 * Free Software Foundation, Inc.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public License
 * as published by the Free Software Foundation; either version 3 of
 * the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 * 02110-1301 USA
 */



/** This file defines the format of SCM values and cons pairs.
 ** It is here that tag bits are assigned for various purposes.
 **/

/* picks up scmconfig.h too */
#include "libguile/__scm.h"



/* In the beginning was the Word:
 *
 * For the representation of scheme objects and their handling, Guile provides
 * two types:  scm_t_bits and SCM.
 *
 * - scm_t_bits values can hold bit patterns of non-objects and objects:
 *
 *   Non-objects -- in this case the value may not be changed into a SCM value
 *   in any way.
 *
 *   Objects -- in this case the value may be changed into a SCM value using
 *   the SCM_PACK macro.
 *
 * - SCM values can hold proper scheme objects only.  They can be changed into
 *   a scm_t_bits value using the SCM_UNPACK macro.
 *
 * When working in the domain of scm_t_bits values, programmers must keep
 * track of any scm_t_bits value they create that is not a proper scheme
 * object.  This makes sure that in the domain of SCM values developers can
 * rely on the fact that they are dealing with proper scheme objects only.
 * Thus, the distinction between scm_t_bits and SCM values helps to identify
 * those parts of the code where special care has to be taken not to create
 * bad SCM values.
 */

/* For dealing with the bit level representation of scheme objects we define
 * scm_t_bits:
 */

typedef scm_t_int64  scm_t_signed_bits;
typedef scm_t_uint64 scm_t_bits;

#define SCM_T_SIGNED_BITS_MAX SCM_T_INT64_MAX
#define SCM_T_SIGNED_BITS_MIN SCM_T_INT64_MIN
#define SCM_T_BITS_MAX        SCM_T_UINT64_MAX


/* But as external interface, we define SCM.
 */
union SCM
{
  scm_t_bits as_bits;

  /* If you set a field of the SCM union, it needs to set all the bits.
     The following types are not guaranteed to do so, so we put them in
     a sub-union, to indicate that they are for read access only.  */
  union SCM_read_only {
#if SCM_IS_BIG_ENDIAN
  struct { scm_t_uint32 high, low; } as_uint32;
#else
  struct { scm_t_uint32 low, high; } as_uint32;
#endif
  } read;
};

typedef union SCM SCM;


#define SCM_UNPACK(x) ((x).as_bits)
#define SCM_PACK(x) ((SCM) { (scm_t_bits) (x) })


/* SCM values can not be compared by using the operator ==.  Use the following
 * macro instead, which is the equivalent of the scheme predicate 'eq?'.
 */
#define scm_is_eq(x, y) (SCM_UNPACK (x) == SCM_UNPACK (y))



/* Representation of scheme objects:
 *
 * Guile's type system is designed to work on systems where scm_t_bits and SCM
 * variables consist of at least 32 bits.  The objects that a SCM variable can
 * represent belong to one of the following two major categories:
 *
 * - Immediates -- meaning that the SCM variable contains an entire Scheme
 *   object.  That means, all the object's data (including the type tagging
 *   information that is required to identify the object's type) must fit into
 *   32 bits.
 *
 * - Non-immediates -- meaning that the SCM variable holds a pointer into the
 *   heap of cells (see below).  On systems where a pointer needs more than 32
 *   bits this means that scm_t_bits and SCM variables need to be large enough
 *   to hold such pointers.  In contrast to immediates, the object's data of
 *   a non-immediate can consume arbitrary amounts of memory: The heap cell
 *   being pointed to consists of at least two scm_t_bits variables and thus
 *   can be used to hold pointers to malloc'ed memory of any size.
 *
 * The 'heap' is the memory area that is under control of Guile's
 * garbage collector.  The size of the pointed-to memory will be at
 * least 8 bytes, and its address will be 8-byte aligned.
 *
 * This eight-byte alignment means that for a non-immediate -- a heap
 * object -- that the three least significant bits of its address will
 * be zero.  Guile can then use these bits as type tags.  These lowest
 * three bits are called tc3-bits, where tc stands for type-code.
 *
 * For a given SCM value, the distinction whether it holds an immediate
 * or non-immediate object is based on the tc3-bits of its scm_t_bits
 * equivalent: If the tc3-bits equal #b000, then the SCM value holds a
 * non-immediate, and the scm_t_bits variable's value is just the
 * pointer to the heap cell.
 *
 * Summarized, the data of a scheme object that is represented by a SCM
 * variable consists of a) the SCM variable itself, b) in case of
 * non-immediates the heap data that the SCM object points to, c) in
 * case of non-immediates potentially additional data outside of the
 * heap (like for example malloc'ed data), and d) in case of
 * non-immediates potentially additional data inside of the heap, since
 * data stored in b) and c) may hold references to other cells.
 */


/* Let's take a breather and define some helpers to access Scheme values
   from the heap.

   Though C99 doesn't specify whether pointers are represented the same
   way in memory as integers are, it seems to be universal, besides
   UNICOS.  We make that assumption, having checked at configure-time
   that it does indeed hold true on this platform.  */

#if SCM_SIZEOF_VOID_P == 4
#define SCM_TO_POINTER(x) ((void *)((x).read.as_uint32.low))
#elif SCM_SIZEOF_VOID_P == 8
#define SCM_TO_POINTER(x) ((void *)((x).as_bits))
#else
#error Unhandled word size.
#endif

#define SCM_FROM_POINTER(x) SCM_PACK ((scm_t_bits)x)

#define SCM_HEAP_POINTER(x) ((SCM *) SCM_TO_POINTER (x))
#define SCM_HEAP_OBJECT(x, n)                   \
  (SCM_HEAP_POINTER (x) [(n)])
#define SCM_SET_HEAP_OBJECT(x, n, o)            \
  SCM_HEAP_OBJECT (x, n) = (o)

#define SCM_HEAP_DATA(x, n)                     \
  (SCM_HEAP_OBJECT (x, n).as_bits)
#define SCM_SET_HEAP_DATA(x, n, b)              \
  SCM_HEAP_DATA (x, n) = (b)

/*
 *
 * Immediates
 *
 * Operations on immediate objects can typically be processed faster than on
 * non-immediates.  The reason is that the object's data can be extracted
 * directly from the SCM variable (or rather a corresponding scm_t_bits
 * variable), instead of having to perform additional memory accesses to
 * obtain the object's data from the heap.  In order to get the best possible
 * performance frequently used data types should be realized as immediates.
 * This is, as has been mentioned above, only possible if the objects can be
 * represented with 32 bits (including type tagging).
 *
 * In Guile, the following data types and special objects are realized as
 * immediates: booleans, characters, small integers (see below), the empty
 * list, the end of file object, the 'unspecified' object (which is delivered
 * as a return value by functions for which the return value is unspecified),
 * a 'nil' object used in the elisp-compatibility mode and certain other
 * 'special' objects which are only used internally in Guile.
 *
 * Integers in Guile can be arbitrarily large.  On the other hand, integers
 * are one of the most frequently used data types.  Especially integers with
 * less than 32 bits are commonly used.  Thus, internally and transparently
 * for application code guile distinguishes between small and large integers.
 * Whether an integer is a large or a small integer depends on the number of
 * bits needed to represent its value.  Small integers are those which can be
 * represented as immediates.  Since they don't require more than a fixed
 * number of bits for their representation, they are also known as 'fixnums'.
 *
 * The tc3-combinations #b010 and #b110 are used to represent small integers,
 * which allows to use the most significant bit of the tc3-bits to be part of
 * the integer value being represented.  This means that all integers with up
 * to 30 bits (including one bit for the sign) can be represented as
 * immediates.  On systems where SCM and scm_t_bits variables hold more than
 * 32 bits, the amount of bits usable for small integers will even be larger.
 * The tc3-code #b100 is shared among booleans, characters and the other
 * special objects listed above.
 *
 *
 * Non-Immediates
 *
 * All object types not mentioned above in the list of immedate objects are
 * represented as non-immediates.  Whether a non-immediate scheme object is
 * represented by a single-cell or a double-cell depends on the object's type,
 * namely on the set of attributes that have to be stored with objects of that
 * type.  Every non-immediate type is allowed to define its own layout and
 * interpretation of the data stored in its cell (with some restrictions, see
 * below).
 *
 * One of the design goals of guile's type system is to make it possible to
 * store a scheme pair with as little memory usage as possible.  The minimum
 * amount of memory that is required to store two scheme objects (car and cdr
 * of a pair) is the amount of memory required by two scm_t_bits or SCM
 * variables.  Therefore pairs in guile are stored in single-cells.
 *
 * Another design goal for the type system is to store procedure objects
 * created by lambda expresssions (closures) and class instances (goops
 * objects) with as little memory usage as possible.  Closures are represented
 * by a reference to the function code and a reference to the closure's
 * environment.  Class instances are represented by a reference to the
 * instance's class definition and a reference to the instance's data.  Thus,
 * closures as well as class instances also can be stored in single-cells.
 *
 * Certain other non-immediate types also store their data in single-cells.
 * By design decision, the heap is split into areas for single-cells and
 * double-cells, but not into areas for single-cells-holding-pairs and areas
 * for single-cells-holding-non-pairs.  Any single-cell on the heap therefore
 * can hold pairs (consisting of two scm_t_bits variables representing two
 * scheme objects - the car and cdr of the pair) and non-pairs (consisting of
 * two scm_t_bits variables that hold bit patterns as defined by the layout of
 * the corresponding object's type).
 *
 *
 * Garbage collection
 *
 * During garbage collection, unreachable cells on the heap will be freed.
 * That is, the garbage collector will detect cells which have no SCM variable
 * pointing towards them.  In order to properly release all memory belonging
 * to the object to which a cell belongs, the gc needs to be able to interpret
 * the cell contents in the correct way.  That means that the gc needs to be
 * able to determine the object type associated with a cell only from the cell
 * itself.
 *
 * Consequently, if the gc detects an unreachable single-cell, those two
 * scm_t_bits variables must provide enough information to determine whether
 * they belong to a pair (i. e. both scm_t_bits variables represent valid
 * scheme objects), to a closure, a class instance or if they belong to any
 * other non-immediate.  Guile's type system is designed to make it possible
 * to determine a the type to which a cell belongs in the majority of cases
 * from the cell's first scm_t_bits variable.  (Given a SCM variable X holding
 * a non-immediate object, the macro SCM_CELL_TYPE(X) will deliver the
 * corresponding cell's first scm_t_bits variable.)
 *
 * If the cell holds a scheme pair, then we already know that the first
 * scm_t_bits variable of the cell will hold a scheme object with one of the
 * following tc3-codes: #b000 (non-immediate), #b010 (small integer), #b110
 * (small integer), #b100 (non-integer immediate).  All these tc3-codes have
 * in common, that their least significant bit is #b0.  This fact is used by
 * the garbage collector to identify cells that hold pairs.  The remaining
 * tc3-codes are assigned as follows: #b001 (class instance or, more
 * precisely, a struct, of which a class instance is a special case), #b011
 * (closure), #b101/#b111 (all remaining non-immediate types).
 *
 *
 * Summary of type codes of scheme objects (SCM variables)
 *
 * Here is a summary of tagging bits as they might occur in a scheme object.
 * The notation is as follows: tc stands for type code as before, tc<n> with n
 * being a number indicates a type code formed by the n least significant bits
 * of the SCM variables corresponding scm_t_bits value.
 *
 * Note that (as has been explained above) tc1==1 can only occur in the first
 * scm_t_bits variable of a cell belonging to a non-immediate object that is
 * not a pair.  For an explanation of the tc tags with tc1==1, see the next
 * section with the summary of the type codes on the heap.
 *
 * tc1:
 *   0:  For scheme objects, tc1==0 must be fulfilled.
 *  (1:  This can never be the case for a scheme object.)
 *
 * tc2:
 *   00:  Either a non-immediate or some non-integer immediate
 *  (01:  This can never be the case for a scheme object.)
 *   10:  Small integer
 *  (11:  This can never be the case for a scheme object.)
 *
 * tc3:
 *   000:  a non-immediate object (pair, closure, class instance etc.)
 *  (001:  This can never be the case for a scheme object.)
 *   010:  an even small integer (least significant bit is 0).
 *  (011:  This can never be the case for a scheme object.)
 *   100:  Non-integer immediate
 *  (101:  This can never be the case for a scheme object.)
 *   110:  an odd small integer (least significant bit is 1).
 *  (111:  This can never be the case for a scheme object.)
 *
 * The remaining bits of the non-immediate objects form the pointer to the
 * heap cell.  The remaining bits of the small integers form the integer's
 * value and sign.  Thus, the only scheme objects for which a further
 * subdivision is of interest are the ones with tc3==100.
 *
 * tc8 (for objects with tc3==100):
 *   00000-100:  special objects ('flags')
 *   00001-100:  characters
 *   00010-100:  unused
 *   00011-100:  unused
 *
 *
 * Summary of type codes on the heap
 *
 * Here is a summary of tagging in scm_t_bits values as they might occur in
 * the first scm_t_bits variable of a heap cell.
 *
 * tc1:
 *   0:  the cell belongs to a pair.
 *   1:  the cell belongs to a non-pair.
 *
 * tc2:
 *   00:  the cell belongs to a pair with no short integer in its car.
 *   01:  the cell belongs to a non-pair (struct or some other non-immediate).
 *   10:  the cell belongs to a pair with a short integer in its car.
 *   11:  the cell belongs to a non-pair (closure or some other non-immediate).
 *
 * tc3:
 *   000:  the cell belongs to a pair with a non-immediate in its car.
 *   001:  the cell belongs to a struct
 *   010:  the cell belongs to a pair with an even short integer in its car.
 *   011:  the cell belongs to a closure
 *   100:  the cell belongs to a pair with a non-integer immediate in its car.
 *   101:  the cell belongs to some other non-immediate.
 *   110:  the cell belongs to a pair with an odd short integer in its car.
 *   111:  the cell belongs to some other non-immediate.
 *
 * tc7 (for tc3==1x1):
 *   See below for the list of types.  Note the special case of scm_tc7_vector
 *   and scm_tc7_wvect:  vectors and weak vectors are treated the same in many
 *   cases.  Thus, their tc7-codes are chosen to only differ in one bit.  This
 *   makes it possible to check an object at the same time for being a vector
 *   or a weak vector by comparing its tc7 code with that bit masked (using
 *   the TYP7S macro).  Three more special tc7-codes are of interest:
 *   numbers, ports and smobs in fact each represent collections of types,
 *   which are subdivided using tc16-codes.
 *
 * tc16 (for tc7==scm_tc7_smob):
 *   The largest part of the space of smob types is not subdivided in a
 *   predefined way, since smobs can be added arbitrarily by user C code.
 */



/* Checking if a SCM variable holds an immediate or a non-immediate object:
 * This check can either be performed by checking for tc3==000 or tc3==00x,
 * since for a SCM variable it is known that tc1==0.  */
#define SCM_IMP(x) 		(6 & SCM_UNPACK (x))
#define SCM_NIMP(x) 		(!SCM_IMP (x))

/* Checking if a SCM variable holds an immediate integer: See numbers.h for
 * the definition of the following macros: SCM_I_FIXNUM_BIT,
 * SCM_MOST_POSITIVE_FIXNUM, SCM_I_INUMP, SCM_I_MAKINUM, SCM_I_INUM.  */

/* Checking if a SCM variable holds a pair (for historical reasons, in Guile
 * also known as a cons-cell): This is done by first checking that the SCM
 * variable holds a non-immediate, and second, by checking that tc1==0 holds
 * for the SCM_CELL_TYPE of the SCM variable.  
*/

#define SCM_I_CONSP(x)  (!SCM_IMP (x) && ((1 & SCM_CELL_TYPE (x)) == 0))



/* Definitions for tc2: */

#define scm_tc2_int              2


/* Definitions for tc3: */

#define SCM_ITAG3(x) 		 (7 & SCM_UNPACK (x))
#define SCM_TYP3(x) 		 (7 & SCM_CELL_TYPE (x))

#define scm_tc3_cons	 	 0
#define scm_tc3_struct    	 1
#define scm_tc3_int_1		 (scm_tc2_int + 0)
#define scm_tc3_unused		 3
#define scm_tc3_imm24		 4
#define scm_tc3_tc7_1		 5
#define scm_tc3_int_2		 (scm_tc2_int + 4)
#define scm_tc3_tc7_2		 7


/* Definitions for tc7: */

#define SCM_ITAG7(x) 		(127 & SCM_UNPACK (x))
#define SCM_TYP7(x) 		(0x7f &        SCM_CELL_TYPE (x))
#define SCM_TYP7S(x) 		((0x7f & ~2) & SCM_CELL_TYPE (x))

#define scm_tc7_symbol		5
#define scm_tc7_variable        7

/* couple */
#define scm_tc7_vector		13
#define scm_tc7_wvect		15

#define scm_tc7_string		21
#define scm_tc7_number		23
#define scm_tc7_stringbuf       39
#define scm_tc7_bytevector	77

#define scm_tc7_pointer		31
#define scm_tc7_hashtable	29
#define scm_tc7_fluid		37
#define scm_tc7_dynamic_state	45

#define scm_tc7_frame		47
#define scm_tc7_objcode		53
#define scm_tc7_vm		55
#define scm_tc7_vm_cont		71

#define scm_tc7_prompt		61
#define scm_tc7_with_fluids	63
#define scm_tc7_unused_19	69
#define scm_tc7_program		79
#define scm_tc7_unused_9	85
#define scm_tc7_unused_10	87
#define scm_tc7_unused_20	93
#define scm_tc7_unused_11	95
#define scm_tc7_unused_12	101
#define scm_tc7_unused_18	103
#define scm_tc7_unused_13	109
#define scm_tc7_unused_14	111
#define scm_tc7_unused_15	117
#define scm_tc7_unused_16	119

/* There are 256 port subtypes.  */
#define scm_tc7_port		125

/* There are 256 smob subtypes.  [**] If you change scm_tc7_smob, you must
 * also change the places it is hard coded in this file and possibly others.
 * Dirk:FIXME:: Any hard coded reference to scm_tc7_smob must be replaced by a
 * symbolic reference.  */
#define scm_tc7_smob		127 /* DO NOT CHANGE [**] */


/* Definitions for tc16: */
#define SCM_TYP16(x) 		(0xffff & SCM_CELL_TYPE (x))
#define SCM_TYP16_PREDICATE(tag, x) (!SCM_IMP (x) && SCM_TYP16 (x) == (tag))




/* {Immediate Values}
 */

enum scm_tc8_tags
{
  scm_tc8_flag = scm_tc3_imm24 + 0x00,  /* special objects ('flags') */
  scm_tc8_char = scm_tc3_imm24 + 0x08,  /* characters */
  scm_tc8_unused_0 = scm_tc3_imm24 + 0x10,
  scm_tc8_unused_1 = scm_tc3_imm24 + 0x18
};

#define SCM_ITAG8(X)		(SCM_UNPACK (X) & 0xff)
#define SCM_MAKE_ITAG8_BITS(X, TAG) (((X) << 8) + TAG)
#define SCM_MAKE_ITAG8(X, TAG)	(SCM_PACK (SCM_MAKE_ITAG8_BITS (X, TAG)))
#define SCM_ITAG8_DATA(X)	(SCM_UNPACK (X) >> 8)



/* Flags (special objects).  The indices of the flags must agree with the
 * declarations in print.c: iflagnames.  */

#define SCM_IFLAGP(n)    (SCM_ITAG8 (n) == scm_tc8_flag)
#define SCM_MAKIFLAG_BITS(n)  (SCM_MAKE_ITAG8_BITS ((n), scm_tc8_flag))
#define SCM_IFLAGNUM(n)  (SCM_ITAG8_DATA (n))

/*
 * IMPORTANT NOTE regarding IFLAG numbering!!!
 *
 * Several macros depend upon careful IFLAG numbering of SCM_BOOL_F,
 * SCM_BOOL_T, SCM_ELISP_NIL, SCM_EOL, and the two SCM_XXX_*_DONT_USE
 * constants.  In particular:
 *
 * - SCM_BOOL_F and SCM_BOOL_T must differ in exactly one bit position.
 *   (used to implement scm_is_bool_and_not_nil, aka scm_is_bool)
 *
 * - SCM_ELISP_NIL and SCM_BOOL_F must differ in exactly one bit position.
 *   (used to implement scm_is_false_or_nil and
 *    scm_is_true_and_not_nil)
 *
 * - SCM_ELISP_NIL and SCM_EOL must differ in exactly one bit position.
 *   (used to implement scm_is_null_or_nil)
 *
 * - SCM_ELISP_NIL, SCM_BOOL_F, SCM_EOL, SCM_XXX_ANOTHER_LISP_FALSE_DONT_USE
 *   must all be equal except for two bit positions.
 *   (used to implement scm_is_lisp_false)
 *
 * - SCM_ELISP_NIL, SCM_BOOL_F, SCM_BOOL_T, SCM_XXX_ANOTHER_BOOLEAN_DONT_USE_0
 *   must all be equal except for two bit positions.
 *   (used to implement scm_is_bool_or_nil)
 *
 * These properties allow the aforementioned macros to be implemented
 * by bitwise ANDing with a mask and then comparing with a constant,
 * using as a common basis the macro SCM_MATCHES_BITS_IN_COMMON,
 * defined below.  The properties are checked at compile-time using
 * `verify' macros near the top of boolean.c and pairs.c.
 */
#define SCM_BOOL_F_BITS		SCM_MAKIFLAG_BITS (0)
#define SCM_ELISP_NIL_BITS	SCM_MAKIFLAG_BITS (1)

#define SCM_BOOL_F		SCM_PACK (SCM_BOOL_F_BITS)
#define SCM_ELISP_NIL		SCM_PACK (SCM_ELISP_NIL_BITS)

#ifdef BUILDING_LIBGUILE
#define SCM_XXX_ANOTHER_LISP_FALSE_DONT_USE	SCM_MAKIFLAG_BITS (2)
#endif

#define SCM_EOL_BITS		SCM_MAKIFLAG_BITS (3)
#define SCM_BOOL_T_BITS 	SCM_MAKIFLAG_BITS (4)

#define SCM_EOL			SCM_PACK (SCM_EOL_BITS)
#define SCM_BOOL_T 		SCM_PACK (SCM_BOOL_T_BITS)

#ifdef BUILDING_LIBGUILE
#define SCM_XXX_ANOTHER_BOOLEAN_DONT_USE_0	SCM_MAKIFLAG_BITS (5)
#define SCM_XXX_ANOTHER_BOOLEAN_DONT_USE_1	SCM_MAKIFLAG_BITS (6)
#define SCM_XXX_ANOTHER_BOOLEAN_DONT_USE_2	SCM_MAKIFLAG_BITS (7)
#endif

#define SCM_UNSPECIFIED_BITS	SCM_MAKIFLAG_BITS (8)
#define SCM_UNDEFINED_BITS	SCM_MAKIFLAG_BITS (9)
#define SCM_EOF_VAL_BITS 	SCM_MAKIFLAG_BITS (10)

#define SCM_UNSPECIFIED		SCM_PACK (SCM_UNSPECIFIED_BITS)
#define SCM_UNDEFINED	 	SCM_PACK (SCM_UNDEFINED_BITS)
#define SCM_EOF_VAL 		SCM_PACK (SCM_EOF_VAL_BITS)

/* When a variable is unbound this is marked by the SCM_UNDEFINED
 * value.  The following is an unbound value which can be handled on
 * the Scheme level, i.e., it can be stored in and retrieved from a
 * Scheme variable.  This value is only intended to mark an unbound
 * slot in GOOPS.  It is needed now, but we should probably rewrite
 * the code which handles this value in C so that SCM_UNDEFINED can be
 * used instead.  It is not ideal to let this kind of unique and
 * strange values loose on the Scheme level.  */
#define SCM_UNBOUND_BITS	SCM_MAKIFLAG_BITS (11)
#define SCM_UNBOUND		SCM_PACK (SCM_UNBOUND_BITS)

#define SCM_UNBNDP(x)		(scm_is_eq ((x), SCM_UNDEFINED))

/*
 * SCM_MATCHES_BITS_IN_COMMON(x,a,b) returns 1 if and only if x
 * matches both a and b in every bit position where a and b are equal;
 * otherwise it returns 0.  Bit positions where a and b differ are
 * ignored.
 *
 * This is used to efficiently compare against two values which differ
 * in exactly one bit position, or against four values which differ in
 * exactly two bit positions.  It is the basis for the following
 * macros:
 *
 *   scm_is_null_or_nil,
 *   scm_is_false_or_nil,
 *   scm_is_true_and_not_nil,
 *   scm_is_lisp_false,
 *   scm_is_lisp_true,
 *   scm_is_bool_and_not_nil (aka scm_is_bool)
 *   scm_is_bool_or_nil.
 */
#define SCM_MATCHES_BITS_IN_COMMON(x,a,b)				\
  ((SCM_UNPACK(x) & ~(SCM_UNPACK(a) ^ SCM_UNPACK(b))) ==		\
   (SCM_UNPACK(a) & SCM_UNPACK(b)))

/*
 * These macros are used for compile-time verification that the
 * constants have the properties needed for the above macro to work
 * properly.
 */
#ifdef BUILDING_LIBGUILE
#define SCM_WITH_LEAST_SIGNIFICANT_1_BIT_CLEARED(x)  ((x) & ((x)-1))
#define SCM_HAS_EXACTLY_ONE_BIT_SET(x)					\
  ((x) != 0 && SCM_WITH_LEAST_SIGNIFICANT_1_BIT_CLEARED (x) == 0)
#define SCM_HAS_EXACTLY_TWO_BITS_SET(x)					\
  (SCM_HAS_EXACTLY_ONE_BIT_SET (SCM_WITH_LEAST_SIGNIFICANT_1_BIT_CLEARED (x)))

#define SCM_BITS_DIFFER_IN_EXACTLY_ONE_BIT_POSITION(a,b)		\
  (SCM_HAS_EXACTLY_ONE_BIT_SET ((a) ^ (b)))
#define SCM_BITS_DIFFER_IN_EXACTLY_TWO_BIT_POSITIONS(a,b,c,d)		\
  (SCM_HAS_EXACTLY_TWO_BITS_SET (((a) ^ (b)) |                          \
                                 ((b) ^ (c)) |                          \
                                 ((c) ^ (d))))
#endif /* BUILDING_LIBGUILE */


/* Dispatching aids:

   When switching on SCM_TYP7 of a SCM value, use these fake case
   labels to catch types that use fewer than 7 bits for tagging.  */

/* For cons pairs with immediate values in the CAR
 */

#define scm_tcs_cons_imcar \
       scm_tc2_int + 0:   case scm_tc2_int + 4:   case scm_tc3_imm24 + 0:\
  case scm_tc2_int + 8:   case scm_tc2_int + 12:  case scm_tc3_imm24 + 8:\
  case scm_tc2_int + 16:  case scm_tc2_int + 20:  case scm_tc3_imm24 + 16:\
  case scm_tc2_int + 24:  case scm_tc2_int + 28:  case scm_tc3_imm24 + 24:\
  case scm_tc2_int + 32:  case scm_tc2_int + 36:  case scm_tc3_imm24 + 32:\
  case scm_tc2_int + 40:  case scm_tc2_int + 44:  case scm_tc3_imm24 + 40:\
  case scm_tc2_int + 48:  case scm_tc2_int + 52:  case scm_tc3_imm24 + 48:\
  case scm_tc2_int + 56:  case scm_tc2_int + 60:  case scm_tc3_imm24 + 56:\
  case scm_tc2_int + 64:  case scm_tc2_int + 68:  case scm_tc3_imm24 + 64:\
  case scm_tc2_int + 72:  case scm_tc2_int + 76:  case scm_tc3_imm24 + 72:\
  case scm_tc2_int + 80:  case scm_tc2_int + 84:  case scm_tc3_imm24 + 80:\
  case scm_tc2_int + 88:  case scm_tc2_int + 92:  case scm_tc3_imm24 + 88:\
  case scm_tc2_int + 96:  case scm_tc2_int + 100: case scm_tc3_imm24 + 96:\
  case scm_tc2_int + 104: case scm_tc2_int + 108: case scm_tc3_imm24 + 104:\
  case scm_tc2_int + 112: case scm_tc2_int + 116: case scm_tc3_imm24 + 112:\
  case scm_tc2_int + 120: case scm_tc2_int + 124: case scm_tc3_imm24 + 120

/* For cons pairs with non-immediate values in the SCM_CAR
 */
#define scm_tcs_cons_nimcar \
       scm_tc3_cons + 0:\
  case scm_tc3_cons + 8:\
  case scm_tc3_cons + 16:\
  case scm_tc3_cons + 24:\
  case scm_tc3_cons + 32:\
  case scm_tc3_cons + 40:\
  case scm_tc3_cons + 48:\
  case scm_tc3_cons + 56:\
  case scm_tc3_cons + 64:\
  case scm_tc3_cons + 72:\
  case scm_tc3_cons + 80:\
  case scm_tc3_cons + 88:\
  case scm_tc3_cons + 96:\
  case scm_tc3_cons + 104:\
  case scm_tc3_cons + 112:\
  case scm_tc3_cons + 120

/* For structs
 */
#define scm_tcs_struct \
       scm_tc3_struct + 0:\
  case scm_tc3_struct + 8:\
  case scm_tc3_struct + 16:\
  case scm_tc3_struct + 24:\
  case scm_tc3_struct + 32:\
  case scm_tc3_struct + 40:\
  case scm_tc3_struct + 48:\
  case scm_tc3_struct + 56:\
  case scm_tc3_struct + 64:\
  case scm_tc3_struct + 72:\
  case scm_tc3_struct + 80:\
  case scm_tc3_struct + 88:\
  case scm_tc3_struct + 96:\
  case scm_tc3_struct + 104:\
  case scm_tc3_struct + 112:\
  case scm_tc3_struct + 120



#endif  /* SCM_TAGS_H */

/*
  Local Variables:
  c-file-style: "gnu"
  End:
*/