comparison src/alloc.c @ 1300:b13b79e28eb5

* alloc.c: #include "intervals.h". (init_intervals, make_interval, mark_interval, mark_interval_tree): New functions conditionally defined. (make_uninit_string): Call INITIALIZE_INTERVAL. (INIT_INTERVALS, UNMARK_BALANCE_INTERVALS, MARK_INTERVAL_TREE): New macros, conditionally defined. (mark_object): Call MARK_INTERVAL_TREE in case Lisp_String. (gc_sweep): If text properties are in use, place all unmarked intervals on the free list. Call UNMARK_BALANCE_INTERVALS on `buffer->intervals' when unmarking `buffer'. (compact_strings): Include INTERVAL_PTR_SIZE in calculation for target of bcopy when relocating strings. (init_alloc_once): Call INIT_INTERVALS. (make_pure_string): Include INTERVAL_PTR_SIZE in calculation of `size'.
author Joseph Arceneaux <jla@gnu.org>
date Fri, 02 Oct 1992 19:59:42 +0000
parents a9241dc503ab
children 0edeba6fc9fc
comparison
equal deleted inserted replaced
1299:b8337cdf2e8b 1300:b13b79e28eb5
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */ 18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
19 19
20 20
21 #include "config.h" 21 #include "config.h"
22 #include "lisp.h" 22 #include "lisp.h"
23 #include "intervals.h"
23 #include "puresize.h" 24 #include "puresize.h"
24 #ifndef standalone 25 #ifndef standalone
25 #include "buffer.h" 26 #include "buffer.h"
26 #include "window.h" 27 #include "window.h"
27 #ifdef MULTI_FRAME 28 #ifdef MULTI_FRAME
174 175
175 if (!val && size) memory_full (); 176 if (!val && size) memory_full ();
176 return val; 177 return val;
177 } 178 }
178 179
180 #ifdef USE_TEXT_PROPERTIES
181 #define INTERVAL_BLOCK_SIZE \
182 ((1020 - sizeof (struct interval_block *)) / sizeof (struct interval))
183
184 struct interval_block
185 {
186 struct interval_block *next;
187 struct interval intervals[INTERVAL_BLOCK_SIZE];
188 };
189
190 struct interval_block *interval_block;
191 static int interval_block_index;
192
193 INTERVAL interval_free_list;
194
195 static void
196 init_intervals ()
197 {
198 interval_block
199 = (struct interval_block *) malloc (sizeof (struct interval_block));
200 interval_block->next = 0;
201 bzero (interval_block->intervals, sizeof interval_block->intervals);
202 interval_block_index = 0;
203 interval_free_list = 0;
204 }
205
206 #define INIT_INTERVALS init_intervals ()
207
208 INTERVAL
209 make_interval ()
210 {
211 INTERVAL val;
212
213 if (interval_free_list)
214 {
215 val = interval_free_list;
216 interval_free_list = interval_free_list->parent;
217 }
218 else
219 {
220 if (interval_block_index == INTERVAL_BLOCK_SIZE)
221 {
222 register struct interval_block *newi
223 = (struct interval_block *) malloc (sizeof (struct interval_block));
224
225 if (!newi)
226 memory_full ();
227
228 VALIDATE_LISP_STORAGE (newi, sizeof *newi);
229 newi->next = interval_block;
230 interval_block = newi;
231 interval_block_index = 0;
232 }
233 val = &interval_block->intervals[interval_block_index++];
234 }
235 consing_since_gc += sizeof (struct interval);
236 RESET_INTERVAL (val);
237 return val;
238 }
239
240 static int total_free_intervals, total_intervals;
241
242 /* Mark the pointers of one interval. */
243
244 static void
245 mark_interval (i)
246 register INTERVAL i;
247 {
248 if (XMARKBIT (i->plist))
249 abort ();
250 mark_object (&i->plist);
251 XMARK (i->plist);
252 }
253
254 static void
255 mark_interval_tree (tree)
256 register INTERVAL tree;
257 {
258 if (XMARKBIT (tree->plist))
259 return;
260
261 traverse_intervals (tree, 1, &mark_interval);
262 }
263
264 #define MARK_INTERVAL_TREE(i) \
265 { if (!NULL_INTERVAL_P (i)) mark_interval_tree (i); }
266
267 #define UNMARK_BALANCE_INTERVALS(i) \
268 { \
269 if (! NULL_INTERVAL_P (i)) \
270 { \
271 XUNMARK ((Lisp_Object) (i->parent)); \
272 i = balance_intervals (i); \
273 } \
274 }
275
276 #else /* no interval use */
277
278 #define INIT_INTERVALS
279
280 #define UNMARK_BALANCE_INTERVALS(i)
281 #define MARK_INTERVAL_TREE(i)
282
283 #endif /* no interval use */
284
179 #ifdef LISP_FLOAT_TYPE 285 #ifdef LISP_FLOAT_TYPE
180 /* Allocation of float cells, just like conses */ 286 /* Allocation of float cells, just like conses */
181 /* We store float cells inside of float_blocks, allocating a new 287 /* We store float cells inside of float_blocks, allocating a new
182 float_block with malloc whenever necessary. Float cells reclaimed by 288 float_block with malloc whenever necessary. Float cells reclaimed by
183 GC are put on a free list to be reallocated before allocating 289 GC are put on a free list to be reallocated before allocating
739 (struct Lisp_String *) current_string_block->chars); 845 (struct Lisp_String *) current_string_block->chars);
740 } 846 }
741 847
742 XSTRING (val)->size = length; 848 XSTRING (val)->size = length;
743 XSTRING (val)->data[length] = 0; 849 XSTRING (val)->data[length] = 0;
850 INITIALIZE_INTERVAL (XSTRING (val), NULL_INTERVAL);
744 851
745 return val; 852 return val;
746 } 853 }
747 854
748 /* Return a newly created vector or string with specified arguments as 855 /* Return a newly created vector or string with specified arguments as
831 make_pure_string (data, length) 938 make_pure_string (data, length)
832 char *data; 939 char *data;
833 int length; 940 int length;
834 { 941 {
835 register Lisp_Object new; 942 register Lisp_Object new;
836 register int size = sizeof (int) + length + 1; 943 register int size = sizeof (int) + INTERVAL_PTR_SIZE + length + 1;
837 944
838 if (pureptr + size > PURESIZE) 945 if (pureptr + size > PURESIZE)
839 error ("Pure Lisp storage exhausted"); 946 error ("Pure Lisp storage exhausted");
840 XSET (new, Lisp_String, PUREBEG + pureptr); 947 XSET (new, Lisp_String, PUREBEG + pureptr);
841 XSTRING (new)->size = length; 948 XSTRING (new)->size = length;
1300 { 1407 {
1301 case Lisp_String: 1408 case Lisp_String:
1302 { 1409 {
1303 register struct Lisp_String *ptr = XSTRING (obj); 1410 register struct Lisp_String *ptr = XSTRING (obj);
1304 1411
1412 MARK_INTERVAL_TREE (ptr->intervals);
1305 if (ptr->size & MARKBIT) 1413 if (ptr->size & MARKBIT)
1306 /* A large string. Just set ARRAY_MARK_FLAG. */ 1414 /* A large string. Just set ARRAY_MARK_FLAG. */
1307 ptr->size |= ARRAY_MARK_FLAG; 1415 ptr->size |= ARRAY_MARK_FLAG;
1308 else 1416 else
1309 { 1417 {
1485 register Lisp_Object *ptr; 1593 register Lisp_Object *ptr;
1486 1594
1487 /* This is the buffer's markbit */ 1595 /* This is the buffer's markbit */
1488 mark_object (&buffer->name); 1596 mark_object (&buffer->name);
1489 XMARK (buffer->name); 1597 XMARK (buffer->name);
1598
1599 MARK_INTERVAL_TREE (buffer->intervals);
1490 1600
1491 #if 0 1601 #if 0
1492 mark_object (buffer->syntax_table); 1602 mark_object (buffer->syntax_table);
1493 1603
1494 /* Mark the various string-pointers in the buffer object. 1604 /* Mark the various string-pointers in the buffer object.
1581 } 1691 }
1582 total_floats = num_used; 1692 total_floats = num_used;
1583 total_free_floats = num_free; 1693 total_free_floats = num_free;
1584 } 1694 }
1585 #endif /* LISP_FLOAT_TYPE */ 1695 #endif /* LISP_FLOAT_TYPE */
1696
1697 #ifdef USE_TEXT_PROPERTIES
1698 /* Put all unmarked intervals on free list */
1699 {
1700 register struct interval_block *iblk;
1701 register int lim = interval_block_index;
1702 register int num_free = 0, num_used = 0;
1703
1704 interval_free_list = 0;
1705
1706 for (iblk = interval_block; iblk; iblk = iblk->next)
1707 {
1708 register int i;
1709
1710 for (i = 0; i < lim; i++)
1711 {
1712 if (! XMARKBIT (iblk->intervals[i].plist))
1713 {
1714 iblk->intervals[i].parent = interval_free_list;
1715 interval_free_list = &iblk->intervals[i];
1716 num_free++;
1717 }
1718 else
1719 {
1720 num_used++;
1721 XUNMARK (iblk->intervals[i].plist);
1722 }
1723 }
1724 lim = INTERVAL_BLOCK_SIZE;
1725 }
1726 total_intervals = num_used;
1727 total_free_intervals = num_free;
1728 }
1729 #endif /* USE_TEXT_PROPERTIES */
1586 1730
1587 /* Put all unmarked symbols on free list */ 1731 /* Put all unmarked symbols on free list */
1588 { 1732 {
1589 register struct symbol_block *sblk; 1733 register struct symbol_block *sblk;
1590 register int lim = symbol_block_index; 1734 register int lim = symbol_block_index;
1668 buffer = next; 1812 buffer = next;
1669 } 1813 }
1670 else 1814 else
1671 { 1815 {
1672 XUNMARK (buffer->name); 1816 XUNMARK (buffer->name);
1817 UNMARK_BALANCE_INTERVALS (buffer->intervals);
1673 1818
1674 #if 0 1819 #if 0
1675 /* Each `struct Lisp_String *' was turned into a Lisp_Object 1820 /* Each `struct Lisp_String *' was turned into a Lisp_Object
1676 for purposes of marking and relocation. 1821 for purposes of marking and relocation.
1677 Turn them back into C pointers now. */ 1822 Turn them back into C pointers now. */
1803 newaddr = (struct Lisp_String *) &to_sb->chars[to_pos]; 1948 newaddr = (struct Lisp_String *) &to_sb->chars[to_pos];
1804 to_pos += STRING_FULLSIZE (size); 1949 to_pos += STRING_FULLSIZE (size);
1805 1950
1806 /* Copy the string itself to the new place. */ 1951 /* Copy the string itself to the new place. */
1807 if (nextstr != newaddr) 1952 if (nextstr != newaddr)
1808 bcopy (nextstr, newaddr, size + 1 + sizeof (int)); 1953 bcopy (nextstr, newaddr, size + 1 + sizeof (int)
1954 + INTERVAL_PTR_SIZE);
1809 1955
1810 /* Go through NEXTSTR's chain of references 1956 /* Go through NEXTSTR's chain of references
1811 and make each slot in the chain point to 1957 and make each slot in the chain point to
1812 the new address of this string. */ 1958 the new address of this string. */
1813 size = newaddr->size; 1959 size = newaddr->size;
1880 init_symbol (); 2026 init_symbol ();
1881 init_marker (); 2027 init_marker ();
1882 #ifdef LISP_FLOAT_TYPE 2028 #ifdef LISP_FLOAT_TYPE
1883 init_float (); 2029 init_float ();
1884 #endif /* LISP_FLOAT_TYPE */ 2030 #endif /* LISP_FLOAT_TYPE */
2031 INIT_INTERVALS;
2032
1885 ignore_warnings = 0; 2033 ignore_warnings = 0;
1886 gcprolist = 0; 2034 gcprolist = 0;
1887 staticidx = 0; 2035 staticidx = 0;
1888 consing_since_gc = 0; 2036 consing_since_gc = 0;
1889 gc_cons_threshold = 100000; 2037 gc_cons_threshold = 100000;