From 76ef2ae62de3a65f7dc1b9e32efa8bd032eb7eee Mon Sep 17 00:00:00 2001 From: "dgrowley@gmail.com" Date: Wed, 10 Jun 2020 11:06:17 +1200 Subject: [PATCH 2/2] Have pg_itoa, pg_ltoa and pg_lltoa return the length of the string Core by no means makes excessive use of these functions, but quite a large number of those usages do require the caller to call strlen() on the string. This is quite wasteful since these functions do have a good idea of the length of the string already, so we might as well just have them return that. --- src/backend/access/common/printsimple.c | 10 ++++---- src/backend/utils/adt/int.c | 4 +--- src/backend/utils/adt/numutils.c | 32 +++++++++++++++---------- src/include/utils/builtins.h | 6 ++--- 4 files changed, 29 insertions(+), 23 deletions(-) diff --git a/src/backend/access/common/printsimple.c b/src/backend/access/common/printsimple.c index 0f0b54bdae..df27700df9 100644 --- a/src/backend/access/common/printsimple.c +++ b/src/backend/access/common/printsimple.c @@ -103,9 +103,10 @@ printsimple(TupleTableSlot *slot, DestReceiver *self) { int32 num = DatumGetInt32(value); char str[12]; /* sign, 10 digits and '\0' */ + int len; - pg_ltoa(num, str); - pq_sendcountedtext(&buf, str, strlen(str), false); + len = pg_ltoa(num, str); + pq_sendcountedtext(&buf, str, len, false); } break; @@ -113,9 +114,10 @@ printsimple(TupleTableSlot *slot, DestReceiver *self) { int64 num = DatumGetInt64(value); char str[MAXINT8LEN + 1]; + int len; - pg_lltoa(num, str); - pq_sendcountedtext(&buf, str, strlen(str), false); + len = pg_lltoa(num, str); + pq_sendcountedtext(&buf, str, len, false); } break; diff --git a/src/backend/utils/adt/int.c b/src/backend/utils/adt/int.c index 63c59c56b3..418c13e1b4 100644 --- a/src/backend/utils/adt/int.c +++ b/src/backend/utils/adt/int.c @@ -191,9 +191,7 @@ int2vectorout(PG_FUNCTION_ARGS) { if (num != 0) *rp++ = ' '; - pg_itoa(int2Array->values[num], rp); - while (*++rp != '\0') - ; + rp += pg_itoa(int2Array->values[num], rp); } *rp = '\0'; PG_RETURN_CSTRING(result); diff --git a/src/backend/utils/adt/numutils.c b/src/backend/utils/adt/numutils.c index 13877fdc1d..608539b0ce 100644 --- a/src/backend/utils/adt/numutils.c +++ b/src/backend/utils/adt/numutils.c @@ -327,16 +327,17 @@ invalid_syntax: /* * pg_itoa: converts a signed 16-bit integer to its string representation + * and returns strlen(a). * * Caller must ensure that 'a' points to enough memory to hold the result * (at least 7 bytes, counting a leading sign and trailing NUL). * * It doesn't seem worth implementing this separately. */ -void +int pg_itoa(int16 i, char *a) { - pg_ltoa((int32) i, a); + return pg_ltoa((int32) i, a); } /* @@ -404,26 +405,28 @@ pg_ultoa_n(uint32 value, char *a) } /* - * NUL-terminate the output of pg_ultoa_n. + * pg_ltoa: converts a signed 32-bit integer to its string representation and + * returns strlen(a). * * It is the caller's responsibility to ensure that a is at least 12 bytes long, * which is enough room to hold a minus sign, a maximally long int32, and the * above terminating NUL. */ -void +int pg_ltoa(int32 value, char *a) { uint32 uvalue = (uint32) value; - int len; + int len = 0; if (value < 0) { uvalue = (uint32) 0 - uvalue; - *a++ = '-'; + a[len++] = '-'; } - len = pg_ultoa_n(uvalue, a); + len += pg_ultoa_n(uvalue, a + len); a[len] = '\0'; + return len; } /* @@ -512,24 +515,27 @@ pg_ulltoa_n(uint64 value, char *a) } /* - * pg_lltoa: convert a signed 64-bit integer to its string representation + * pg_lltoa: converts a signed 64-bit integer to its string representation and + * returns strlen(a). * * Caller must ensure that 'a' points to enough memory to hold the result * (at least MAXINT8LEN + 1 bytes, counting a leading sign and trailing NUL). */ -void +int pg_lltoa(int64 value, char *a) { - int len; + int len = 0; uint64 uvalue = value; if (value < 0) { - *a++ = '-'; uvalue = (uint64) 0 - uvalue; + a[len++] = '-'; } - len = pg_ulltoa_n(uvalue, a); - a[len] = 0; + + len += pg_ulltoa_n(uvalue, a + len); + a[len] = '\0'; + return len; } diff --git a/src/include/utils/builtins.h b/src/include/utils/builtins.h index a352a8b773..019c150f22 100644 --- a/src/include/utils/builtins.h +++ b/src/include/utils/builtins.h @@ -47,11 +47,11 @@ extern int namestrcmp(Name name, const char *str); extern int32 pg_atoi(const char *s, int size, int c); extern int16 pg_strtoint16(const char *s); extern int32 pg_strtoint32(const char *s); -extern void pg_itoa(int16 i, char *a); +extern int pg_itoa(int16 i, char *a); int pg_ultoa_n(uint32 l, char *a); int pg_ulltoa_n(uint64 l, char *a); -extern void pg_ltoa(int32 l, char *a); -extern void pg_lltoa(int64 ll, char *a); +extern int pg_ltoa(int32 l, char *a); +extern int pg_lltoa(int64 ll, char *a); extern char *pg_ultostr_zeropad(char *str, uint32 value, int32 minwidth); extern char *pg_ultostr(char *str, uint32 value); extern uint64 pg_strtouint64(const char *str, char **endptr, int base); -- 2.25.1