Mercurial > hg > xemacs-beta
annotate src/opaque.c @ 5283:be436ac36ba4
Don't share a counter when checking for circularity, list_merge().
src/ChangeLog addition:
2010-10-12 Aidan Kehoe <kehoea@parhasard.net>
* fns.c (list_merge):
Circularity checking here needs to be done independently for each
list, they can't share a loop counter. Thank you for the bug
report, Robert Pluim!
tests/ChangeLog addition:
2010-10-12 Aidan Kehoe <kehoea@parhasard.net>
* automated/lisp-tests.el:
Make sure circularity checking with #'merge is sane.
author | Aidan Kehoe <kehoea@parhasard.net> |
---|---|
date | Tue, 12 Oct 2010 18:14:12 +0100 |
parents | 71ee43b8a74d |
children | 308d34e9f07d |
rev | line source |
---|---|
428 | 1 /* Opaque Lisp objects. |
2 Copyright (C) 1993, 1994, 1995 Sun Microsystems, Inc. | |
5127
a9c41067dd88
more cleanups, terminology clarification, lots of doc work
Ben Wing <ben@xemacs.org>
parents:
5125
diff
changeset
|
3 Copyright (C) 1995, 1996, 2002, 2010 Ben Wing. |
428 | 4 |
5 This file is part of XEmacs. | |
6 | |
7 XEmacs is free software; you can redistribute it and/or modify it | |
8 under the terms of the GNU General Public License as published by the | |
9 Free Software Foundation; either version 2, or (at your option) any | |
10 later version. | |
11 | |
12 XEmacs is distributed in the hope that it will be useful, but WITHOUT | |
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
15 for more details. | |
16 | |
17 You should have received a copy of the GNU General Public License | |
18 along with XEmacs; see the file COPYING. If not, write to | |
19 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, | |
20 Boston, MA 02111-1307, USA. */ | |
21 | |
22 /* Synched up with: Not in FSF. */ | |
23 | |
24 /* Written by Ben Wing, October 1993. */ | |
25 | |
26 /* "Opaque" is used internally to hold keep track of allocated memory | |
27 so it gets GC'd properly, and to store arbitrary data in places | |
28 where a Lisp_Object is required and which may get GC'd. (e.g. as | |
29 the argument to record_unwind_protect()). Once created in C, | |
30 opaque objects cannot be resized. | |
31 | |
32 OPAQUE OBJECTS SHOULD NEVER ESCAPE TO THE LISP LEVEL. Some code | |
33 depends on this. As such, opaque objects are a generalization | |
34 of the Qunbound marker. | |
35 */ | |
36 | |
37 #include <config.h> | |
38 #include "lisp.h" | |
39 #include "opaque.h" | |
40 | |
3263 | 41 #ifndef NEW_GC |
428 | 42 Lisp_Object Vopaque_ptr_free_list; |
3263 | 43 #endif /* not NEW_GC */ |
428 | 44 |
45 /* Should never, ever be called. (except by an external debugger) */ | |
46 static void | |
2286 | 47 print_opaque (Lisp_Object obj, Lisp_Object printcharfun, |
48 int UNUSED (escapeflag)) | |
428 | 49 { |
442 | 50 const Lisp_Opaque *p = XOPAQUE (obj); |
428 | 51 |
800 | 52 write_fmt_string |
53 (printcharfun, | |
5146
88bd4f3ef8e4
make lrecord UID's have a separate UID space for each object, resurrect debug SOE code in extents.c
Ben Wing <ben@xemacs.org>
parents:
5127
diff
changeset
|
54 "#<INTERNAL OBJECT (XEmacs bug?) (opaque, size=%lu) 0x%x>", |
88bd4f3ef8e4
make lrecord UID's have a separate UID space for each object, resurrect debug SOE code in extents.c
Ben Wing <ben@xemacs.org>
parents:
5127
diff
changeset
|
55 (long)(p->size), LISP_OBJECT_UID (obj)); |
428 | 56 } |
57 | |
665 | 58 inline static Bytecount |
59 aligned_sizeof_opaque (Bytecount opaque_size) | |
456 | 60 { |
826 | 61 return MAX_ALIGN_SIZE (offsetof (Lisp_Opaque, data) + opaque_size); |
456 | 62 } |
63 | |
665 | 64 static Bytecount |
5127
a9c41067dd88
more cleanups, terminology clarification, lots of doc work
Ben Wing <ben@xemacs.org>
parents:
5125
diff
changeset
|
65 sizeof_opaque (Lisp_Object obj) |
428 | 66 { |
5127
a9c41067dd88
more cleanups, terminology clarification, lots of doc work
Ben Wing <ben@xemacs.org>
parents:
5125
diff
changeset
|
67 return aligned_sizeof_opaque (XOPAQUE (obj)->size); |
428 | 68 } |
69 | |
70 /* Return an opaque object of size SIZE. | |
71 If DATA is OPAQUE_CLEAR, the object's data is memset to '\0' bytes. | |
72 If DATA is OPAQUE_UNINIT, the object's data is uninitialized. | |
73 Else the object's data is initialized by copying from DATA. */ | |
74 Lisp_Object | |
665 | 75 make_opaque (const void *data, Bytecount size) |
428 | 76 { |
5117
3742ea8250b5
Checking in final CVS version of workspace 'ben-lisp-object'
Ben Wing <ben@xemacs.org>
parents:
3017
diff
changeset
|
77 Lisp_Object obj = |
3742ea8250b5
Checking in final CVS version of workspace 'ben-lisp-object'
Ben Wing <ben@xemacs.org>
parents:
3017
diff
changeset
|
78 ALLOC_SIZED_LISP_OBJECT (aligned_sizeof_opaque (size), opaque); |
3742ea8250b5
Checking in final CVS version of workspace 'ben-lisp-object'
Ben Wing <ben@xemacs.org>
parents:
3017
diff
changeset
|
79 Lisp_Opaque *p = XOPAQUE (obj); |
428 | 80 p->size = size; |
81 | |
82 if (data == OPAQUE_CLEAR) | |
83 memset (p->data, '\0', size); | |
84 else if (data == OPAQUE_UNINIT) | |
85 DO_NOTHING; | |
86 else | |
87 memcpy (p->data, data, size); | |
88 | |
5117
3742ea8250b5
Checking in final CVS version of workspace 'ben-lisp-object'
Ben Wing <ben@xemacs.org>
parents:
3017
diff
changeset
|
89 return obj; |
428 | 90 } |
91 | |
92 /* This will not work correctly for opaques with subobjects! */ | |
93 | |
94 static int | |
4906
6ef8256a020a
implement equalp in C, fix case-folding, add equal() method for keymaps
Ben Wing <ben@xemacs.org>
parents:
3263
diff
changeset
|
95 equal_opaque (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth), |
6ef8256a020a
implement equalp in C, fix case-folding, add equal() method for keymaps
Ben Wing <ben@xemacs.org>
parents:
3263
diff
changeset
|
96 int UNUSED (foldcase)) |
428 | 97 { |
665 | 98 Bytecount size; |
428 | 99 return ((size = XOPAQUE_SIZE (obj1)) == XOPAQUE_SIZE (obj2) && |
100 !memcmp (XOPAQUE_DATA (obj1), XOPAQUE_DATA (obj2), size)); | |
101 } | |
102 | |
103 /* This will not work correctly for opaques with subobjects! */ | |
104 | |
2515 | 105 static Hashcode |
5191
71ee43b8a74d
Add #'equalp as a hash test by default; add #'define-hash-table-test, GNU API
Aidan Kehoe <kehoea@parhasard.net>
parents:
5146
diff
changeset
|
106 hash_opaque (Lisp_Object obj, int UNUSED (depth), int UNUSED (equalp)) |
428 | 107 { |
108 if (XOPAQUE_SIZE (obj) == sizeof (unsigned long)) | |
2515 | 109 return *((Hashcode *) XOPAQUE_DATA (obj)); |
428 | 110 else |
111 return memory_hash (XOPAQUE_DATA (obj), XOPAQUE_SIZE (obj)); | |
112 } | |
113 | |
1204 | 114 static const struct memory_description opaque_description[] = { |
428 | 115 { XD_END } |
116 }; | |
117 | |
5118
e0db3c197671
merge up to latest default branch, doesn't compile yet
Ben Wing <ben@xemacs.org>
diff
changeset
|
118 DEFINE_DUMPABLE_SIZABLE_LISP_OBJECT ("opaque", opaque, |
e0db3c197671
merge up to latest default branch, doesn't compile yet
Ben Wing <ben@xemacs.org>
diff
changeset
|
119 0, print_opaque, 0, |
e0db3c197671
merge up to latest default branch, doesn't compile yet
Ben Wing <ben@xemacs.org>
diff
changeset
|
120 equal_opaque, hash_opaque, |
e0db3c197671
merge up to latest default branch, doesn't compile yet
Ben Wing <ben@xemacs.org>
diff
changeset
|
121 opaque_description, |
e0db3c197671
merge up to latest default branch, doesn't compile yet
Ben Wing <ben@xemacs.org>
diff
changeset
|
122 sizeof_opaque, Lisp_Opaque); |
428 | 123 |
124 /* stuff to handle opaque pointers */ | |
125 | |
126 /* Should never, ever be called. (except by an external debugger) */ | |
127 static void | |
2286 | 128 print_opaque_ptr (Lisp_Object obj, Lisp_Object printcharfun, |
129 int UNUSED (escapeflag)) | |
428 | 130 { |
442 | 131 const Lisp_Opaque_Ptr *p = XOPAQUE_PTR (obj); |
428 | 132 |
800 | 133 write_fmt_string |
134 (printcharfun, | |
5146
88bd4f3ef8e4
make lrecord UID's have a separate UID space for each object, resurrect debug SOE code in extents.c
Ben Wing <ben@xemacs.org>
parents:
5127
diff
changeset
|
135 "#<INTERNAL OBJECT (XEmacs bug?) (opaque-ptr, adr=0x%lx) 0x%x>", |
88bd4f3ef8e4
make lrecord UID's have a separate UID space for each object, resurrect debug SOE code in extents.c
Ben Wing <ben@xemacs.org>
parents:
5127
diff
changeset
|
136 (long)(p->ptr), LISP_OBJECT_UID (obj)); |
428 | 137 } |
138 | |
139 static int | |
4906
6ef8256a020a
implement equalp in C, fix case-folding, add equal() method for keymaps
Ben Wing <ben@xemacs.org>
parents:
3263
diff
changeset
|
140 equal_opaque_ptr (Lisp_Object obj1, Lisp_Object obj2, int UNUSED (depth), |
6ef8256a020a
implement equalp in C, fix case-folding, add equal() method for keymaps
Ben Wing <ben@xemacs.org>
parents:
3263
diff
changeset
|
141 int UNUSED (foldcase)) |
428 | 142 { |
143 return (XOPAQUE_PTR (obj1)->ptr == XOPAQUE_PTR (obj2)->ptr); | |
144 } | |
145 | |
2515 | 146 static Hashcode |
5191
71ee43b8a74d
Add #'equalp as a hash test by default; add #'define-hash-table-test, GNU API
Aidan Kehoe <kehoea@parhasard.net>
parents:
5146
diff
changeset
|
147 hash_opaque_ptr (Lisp_Object obj, int UNUSED (depth), int UNUSED (equalp)) |
428 | 148 { |
2515 | 149 return (Hashcode) XOPAQUE_PTR (obj)->ptr; |
428 | 150 } |
151 | |
1575 | 152 static const struct memory_description opaque_ptr_description[] = { |
153 { XD_END } | |
154 }; | |
155 | |
5118
e0db3c197671
merge up to latest default branch, doesn't compile yet
Ben Wing <ben@xemacs.org>
diff
changeset
|
156 DEFINE_NODUMP_LISP_OBJECT ("opaque-ptr", opaque_ptr, |
5124
623d57b7fbe8
separate regular and disksave finalization, print method fixes.
Ben Wing <ben@xemacs.org>
parents:
5118
diff
changeset
|
157 0, print_opaque_ptr, 0, |
623d57b7fbe8
separate regular and disksave finalization, print method fixes.
Ben Wing <ben@xemacs.org>
parents:
5118
diff
changeset
|
158 equal_opaque_ptr, hash_opaque_ptr, |
623d57b7fbe8
separate regular and disksave finalization, print method fixes.
Ben Wing <ben@xemacs.org>
parents:
5118
diff
changeset
|
159 opaque_ptr_description, Lisp_Opaque_Ptr); |
428 | 160 |
161 Lisp_Object | |
162 make_opaque_ptr (void *val) | |
163 { | |
3263 | 164 #ifdef NEW_GC |
5127
a9c41067dd88
more cleanups, terminology clarification, lots of doc work
Ben Wing <ben@xemacs.org>
parents:
5125
diff
changeset
|
165 Lisp_Object res = ALLOC_NORMAL_LISP_OBJECT (opaque_ptr); |
3263 | 166 #else /* not NEW_GC */ |
1204 | 167 Lisp_Object res = alloc_managed_lcrecord (Vopaque_ptr_free_list); |
3263 | 168 #endif /* not NEW_GC */ |
428 | 169 set_opaque_ptr (res, val); |
170 return res; | |
171 } | |
172 | |
173 /* Be very very careful with this. Same admonitions as with | |
174 free_cons() apply. */ | |
175 | |
176 void | |
177 free_opaque_ptr (Lisp_Object ptr) | |
178 { | |
3263 | 179 #ifdef NEW_GC |
5127
a9c41067dd88
more cleanups, terminology clarification, lots of doc work
Ben Wing <ben@xemacs.org>
parents:
5125
diff
changeset
|
180 free_normal_lisp_object (ptr); |
3263 | 181 #else /* not NEW_GC */ |
428 | 182 free_managed_lcrecord (Vopaque_ptr_free_list, ptr); |
3263 | 183 #endif /* not NEW_GC */ |
428 | 184 } |
185 | |
3263 | 186 #ifndef NEW_GC |
428 | 187 void |
1204 | 188 reinit_opaque_early (void) |
428 | 189 { |
647 | 190 Vopaque_ptr_free_list = make_lcrecord_list (sizeof (Lisp_Opaque_Ptr), |
191 &lrecord_opaque_ptr); | |
428 | 192 staticpro_nodump (&Vopaque_ptr_free_list); |
193 } | |
3263 | 194 #endif /* not NEW_GC */ |
428 | 195 |
196 void | |
197 init_opaque_once_early (void) | |
198 { | |
5117
3742ea8250b5
Checking in final CVS version of workspace 'ben-lisp-object'
Ben Wing <ben@xemacs.org>
parents:
3017
diff
changeset
|
199 INIT_LISP_OBJECT (opaque); |
3742ea8250b5
Checking in final CVS version of workspace 'ben-lisp-object'
Ben Wing <ben@xemacs.org>
parents:
3017
diff
changeset
|
200 INIT_LISP_OBJECT (opaque_ptr); |
442 | 201 |
3263 | 202 #ifndef NEW_GC |
1204 | 203 reinit_opaque_early (); |
3263 | 204 #endif /* not NEW_GC */ |
428 | 205 } |