Skip to content

Commit 3c080fb

Browse files
committed
Simplify newNode() by removing special cases
- Remove MemoryContextAllocZeroAligned(). It was supposed to be a faster version of MemoryContextAllocZero(), but modern compilers turn the MemSetLoop() into a call to memset() anyway, making it more or less identical to MemoryContextAllocZero(). That was the only user of MemSetTest, MemSetLoop, so remove those too, as well as palloc0fast(). - Convert newNode() to a static inline function. When this was originally originally written, it was written as a macro because testing showed that gcc didn't inline the size check as we intended. Modern compiler versions do, and now that it just calls palloc0() there is no size-check to inline anyway. One nice effect is that the palloc0() takes one less argument than MemoryContextAllocZeroAligned(), which saves a few instructions in the callers of newNode(). Reviewed-by: Peter Eisentraut, Tom Lane, John Naylor, Thomas Munro Discussion: https://www.postgresql.org/message-id/b51f1fa7-7e6a-4ecc-936d-90a8a1659e7c@iki.fi
1 parent 2084701 commit 3c080fb

File tree

7 files changed

+9
-139
lines changed

7 files changed

+9
-139
lines changed

src/backend/nodes/Makefile

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,6 @@ OBJS = \
2323
makefuncs.o \
2424
multibitmapset.o \
2525
nodeFuncs.o \
26-
nodes.o \
2726
outfuncs.o \
2827
params.o \
2928
print.o \

src/backend/nodes/meson.build

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ backend_sources += files(
77
'makefuncs.c',
88
'multibitmapset.c',
99
'nodeFuncs.c',
10-
'nodes.c',
1110
'params.c',
1211
'print.c',
1312
'read.c',

src/backend/nodes/nodes.c

Lines changed: 0 additions & 31 deletions
This file was deleted.

src/backend/utils/mmgr/mcxt.c

Lines changed: 0 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -1091,44 +1091,6 @@ MemoryContextAllocZero(MemoryContext context, Size size)
10911091
return ret;
10921092
}
10931093

1094-
/*
1095-
* MemoryContextAllocZeroAligned
1096-
* MemoryContextAllocZero where length is suitable for MemSetLoop
1097-
*
1098-
* This might seem overly specialized, but it's not because newNode()
1099-
* is so often called with compile-time-constant sizes.
1100-
*/
1101-
void *
1102-
MemoryContextAllocZeroAligned(MemoryContext context, Size size)
1103-
{
1104-
void *ret;
1105-
1106-
Assert(MemoryContextIsValid(context));
1107-
AssertNotInCriticalSection(context);
1108-
1109-
if (!AllocSizeIsValid(size))
1110-
elog(ERROR, "invalid memory alloc request size %zu", size);
1111-
1112-
context->isReset = false;
1113-
1114-
ret = context->methods->alloc(context, size);
1115-
if (unlikely(ret == NULL))
1116-
{
1117-
MemoryContextStats(TopMemoryContext);
1118-
ereport(ERROR,
1119-
(errcode(ERRCODE_OUT_OF_MEMORY),
1120-
errmsg("out of memory"),
1121-
errdetail("Failed on request of size %zu in memory context \"%s\".",
1122-
size, context->name)));
1123-
}
1124-
1125-
VALGRIND_MEMPOOL_ALLOC(context, ret, size);
1126-
1127-
MemSetLoop(ret, 0, size);
1128-
1129-
return ret;
1130-
}
1131-
11321094
/*
11331095
* MemoryContextAllocExtended
11341096
* Allocate space within the specified context using the given flags.

src/include/c.h

Lines changed: 0 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1060,30 +1060,6 @@ extern void ExceptionalCondition(const char *conditionName,
10601060
} while (0)
10611061

10621062

1063-
/*
1064-
* MemSetTest/MemSetLoop are a variant version that allow all the tests in
1065-
* MemSet to be done at compile time in cases where "val" and "len" are
1066-
* constants *and* we know the "start" pointer must be word-aligned.
1067-
* If MemSetTest succeeds, then it is okay to use MemSetLoop, otherwise use
1068-
* MemSetAligned. Beware of multiple evaluations of the arguments when using
1069-
* this approach.
1070-
*/
1071-
#define MemSetTest(val, len) \
1072-
( ((len) & LONG_ALIGN_MASK) == 0 && \
1073-
(len) <= MEMSET_LOOP_LIMIT && \
1074-
MEMSET_LOOP_LIMIT != 0 && \
1075-
(val) == 0 )
1076-
1077-
#define MemSetLoop(start, val, len) \
1078-
do \
1079-
{ \
1080-
long * _start = (long *) (start); \
1081-
long * _stop = (long *) ((char *) _start + (Size) (len)); \
1082-
\
1083-
while (_start < _stop) \
1084-
*_start++ = 0; \
1085-
} while (0)
1086-
10871063
/*
10881064
* Macros for range-checking float values before converting to integer.
10891065
* We must be careful here that the boundary values are expressed exactly

src/include/nodes/nodes.h

Lines changed: 9 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -139,39 +139,18 @@ typedef struct Node
139139
*
140140
* !WARNING!: Avoid using newNode directly. You should be using the
141141
* macro makeNode. eg. to create a Query node, use makeNode(Query)
142-
*
143-
* Note: the size argument should always be a compile-time constant, so the
144-
* apparent risk of multiple evaluation doesn't matter in practice.
145-
*/
146-
#ifdef __GNUC__
147-
148-
/* With GCC, we can use a compound statement within an expression */
149-
#define newNode(size, tag) \
150-
({ Node *_result; \
151-
AssertMacro((size) >= sizeof(Node)); /* need the tag, at least */ \
152-
_result = (Node *) palloc0fast(size); \
153-
_result->type = (tag); \
154-
_result; \
155-
})
156-
#else
157-
158-
/*
159-
* There is no way to dereference the palloc'ed pointer to assign the
160-
* tag, and also return the pointer itself, so we need a holder variable.
161-
* Fortunately, this macro isn't recursive so we just define
162-
* a global variable for this purpose.
163142
*/
164-
extern PGDLLIMPORT Node *newNodeMacroHolder;
143+
static inline Node *
144+
newNode(size_t size, NodeTag tag)
145+
{
146+
Node *result;
165147

166-
#define newNode(size, tag) \
167-
( \
168-
AssertMacro((size) >= sizeof(Node)), /* need the tag, at least */ \
169-
newNodeMacroHolder = (Node *) palloc0fast(size), \
170-
newNodeMacroHolder->type = (tag), \
171-
newNodeMacroHolder \
172-
)
173-
#endif /* __GNUC__ */
148+
Assert(size >= sizeof(Node)); /* need the tag, at least */
149+
result = (Node *) palloc0(size);
150+
result->type = tag;
174151

152+
return result;
153+
}
175154

176155
#define makeNode(_type_) ((_type_ *) newNode(sizeof(_type_),T_##_type_))
177156
#define NodeSetTag(nodeptr,t) (((Node*)(nodeptr))->type = (t))

src/include/utils/palloc.h

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,6 @@ extern PGDLLIMPORT MemoryContext CurrentMemoryContext;
7070
*/
7171
extern void *MemoryContextAlloc(MemoryContext context, Size size);
7272
extern void *MemoryContextAllocZero(MemoryContext context, Size size);
73-
extern void *MemoryContextAllocZeroAligned(MemoryContext context, Size size);
7473
extern void *MemoryContextAllocExtended(MemoryContext context,
7574
Size size, int flags);
7675
extern void *MemoryContextAllocAligned(MemoryContext context,
@@ -109,19 +108,6 @@ extern void pfree(void *pointer);
109108
#define repalloc_array(pointer, type, count) ((type *) repalloc(pointer, sizeof(type) * (count)))
110109
#define repalloc0_array(pointer, type, oldcount, count) ((type *) repalloc0(pointer, sizeof(type) * (oldcount), sizeof(type) * (count)))
111110

112-
/*
113-
* The result of palloc() is always word-aligned, so we can skip testing
114-
* alignment of the pointer when deciding which MemSet variant to use.
115-
* Note that this variant does not offer any advantage, and should not be
116-
* used, unless its "sz" argument is a compile-time constant; therefore, the
117-
* issue that it evaluates the argument multiple times isn't a problem in
118-
* practice.
119-
*/
120-
#define palloc0fast(sz) \
121-
( MemSetTest(0, sz) ? \
122-
MemoryContextAllocZeroAligned(CurrentMemoryContext, sz) : \
123-
MemoryContextAllocZero(CurrentMemoryContext, sz) )
124-
125111
/* Higher-limit allocators. */
126112
extern void *MemoryContextAllocHuge(MemoryContext context, Size size);
127113
extern pg_nodiscard void *repalloc_huge(void *pointer, Size size);

0 commit comments

Comments
 (0)