[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[no subject]
From: |
Gavin D. Smith |
Date: |
Thu, 13 Apr 2023 06:44:24 -0400 (EDT) |
branch: master
commit ff2b5d22ee2807e4f88d38d0ebc2ea41f496c98e
Author: Gavin Smith <gavinsmith0123@gmail.com>
AuthorDate: Thu Apr 13 11:44:13 2023 +0100
* tp/Texinfo/XS/parsetexi/tree.c (spare_element, new_element)
(destroy_element, reset_obstacks): Reuse storage from
destroy_element, which is called a lot from abort_empty_line.
* tp/Texinfo/XS/parsetexi/end_line.c (end_line): Disable
check for infinite loop when closing commands.
---
ChangeLog | 8 ++++++++
tp/Texinfo/XS/parsetexi/end_line.c | 3 ++-
tp/Texinfo/XS/parsetexi/tree.c | 25 ++++++++++++++++++++++---
3 files changed, 32 insertions(+), 4 deletions(-)
diff --git a/ChangeLog b/ChangeLog
index d4b1ebf024..ef33a58083 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+2023-04-13 Gavin Smith <gavinsmith0123@gmail.com>
+
+ * tp/Texinfo/XS/parsetexi/tree.c (spare_element, new_element)
+ (destroy_element, reset_obstacks): Reuse storage from
+ destroy_element, which is called a lot from abort_empty_line.
+ * tp/Texinfo/XS/parsetexi/end_line.c (end_line): Disable
+ check for infinite loop when closing commands.
+
2023-04-12 Gavin Smith <gavinsmith0123@gmail.com>
* tp/Texinfo/XS/parsetexi/tree_types.h (ELEMENT):
diff --git a/tp/Texinfo/XS/parsetexi/end_line.c
b/tp/Texinfo/XS/parsetexi/end_line.c
index d40721c508..5ecef0d4bc 100644
--- a/tp/Texinfo/XS/parsetexi/end_line.c
+++ b/tp/Texinfo/XS/parsetexi/end_line.c
@@ -2016,7 +2016,8 @@ end_line (ELEMENT *current)
}
}
- if (current == current_old)
+ /* Check is disabled as new_element can reuse storage. */
+ if (0 && current == current_old)
fatal ("infinite loop when closing commands");
current = end_line (current);
diff --git a/tp/Texinfo/XS/parsetexi/tree.c b/tp/Texinfo/XS/parsetexi/tree.c
index 2766409388..9aefea3d24 100644
--- a/tp/Texinfo/XS/parsetexi/tree.c
+++ b/tp/Texinfo/XS/parsetexi/tree.c
@@ -33,12 +33,19 @@ alloc_and_zero (size_t size)
return calloc (1, size);
}
+/* Used with destroy_element to reuse storage, e.g. from
+ abort_empty_line. Reduces memory use slightly (about 5% from testing)
+ for large manuals. */
+static ELEMENT *spare_element;
+
#define obstack_chunk_alloc alloc_and_zero
#define obstack_chunk_free free
void
reset_obstacks (void)
{
+ spare_element = 0;
+
if (obs_element_first)
obstack_free (&obs_element, obs_element_first);
@@ -54,10 +61,20 @@ static ELEMENT *alloc_element (void)
ELEMENT *
new_element (enum element_type type)
{
- ELEMENT *e = alloc_element ();
+ ELEMENT *e;
- /* alloc_element zeroes *e. We assume null pointers have bit representation
- of all zeroes. */
+ if (spare_element)
+ {
+ e = spare_element;
+ spare_element = 0;
+ memset (e, 0, sizeof (ELEMENT));
+ }
+ else
+ {
+ e = alloc_element ();
+ /* alloc_element zeroes *e. We assume null pointers have bit
+ representation of all zeroes. */
+ }
e->type = type;
@@ -131,6 +148,8 @@ destroy_element (ELEMENT *e)
destroy_associated_info (&e->extra_info);
destroy_associated_info (&e->info_info);
+ spare_element = e;
+
/* freed in reset_obstacks */
/* free (e); */
}