diff options
author | Heikki Linnakangas <heikki.linnakangas@iki.fi> | 2016-08-31 16:00:28 +0300 |
---|---|---|
committer | Heikki Linnakangas <heikki.linnakangas@iki.fi> | 2016-08-31 16:00:28 +0300 |
commit | 14cca1bf8e31ed39dbc26dd6c610f1113e759972 (patch) | |
tree | 489757c243e8ec3564adfe383f494426dc0e16ae /src/include/postgres.h | |
parent | 0e0f43d6fdc2e1fbd5261245ed4cf85302a3f653 (diff) | |
download | postgresql-14cca1bf8e31ed39dbc26dd6c610f1113e759972.tar.gz postgresql-14cca1bf8e31ed39dbc26dd6c610f1113e759972.zip |
Use static inline functions for float <-> Datum conversions.
Now that we are OK with using static inline functions, we can use them
to avoid function call overhead of pass-by-val versions of Float4GetDatum,
DatumGetFloat8, and Float8GetDatum. Those functions are only a few CPU
instructions long, but they could not be written into macros previously,
because we need a local union variable for the conversion.
I kept the pass-by-ref versions as regular functions. They are very simple
too, but they call palloc() anyway, so shaving a few instructions from the
function call doesn't seem so important there.
Discussion: <dbb82a4a-2c15-ba27-dd0a-009d2aa72b77@iki.fi>
Diffstat (limited to 'src/include/postgres.h')
-rw-r--r-- | src/include/postgres.h | 63 |
1 files changed, 61 insertions, 2 deletions
diff --git a/src/include/postgres.h b/src/include/postgres.h index fb1933f8f28..d999013238a 100644 --- a/src/include/postgres.h +++ b/src/include/postgres.h @@ -657,6 +657,14 @@ extern Datum Int64GetDatum(int64 X); #endif /* + * Float <-> Datum conversions + * + * These have to be implemented as inline functions rather than macros, when + * passing by value, because many machines pass int and float function + * parameters/results differently; so we need to play weird games with unions. + */ + +/* * DatumGetFloat4 * Returns 4-byte floating point value of a datum. * @@ -664,7 +672,18 @@ extern Datum Int64GetDatum(int64 X); */ #ifdef USE_FLOAT4_BYVAL -extern float4 DatumGetFloat4(Datum X); +static inline float4 +DatumGetFloat4(Datum X) +{ + union + { + int32 value; + float4 retval; + } myunion; + + myunion.value = GET_4_BYTES(X); + return myunion.retval; +} #else #define DatumGetFloat4(X) (* ((float4 *) DatumGetPointer(X))) #endif @@ -676,8 +695,22 @@ extern float4 DatumGetFloat4(Datum X); * Note: if float4 is pass by reference, this function returns a reference * to palloc'd space. */ +#ifdef USE_FLOAT4_BYVAL +static inline Datum +Float4GetDatum(float4 X) +{ + union + { + float4 value; + int32 retval; + } myunion; + myunion.value = X; + return SET_4_BYTES(myunion.retval); +} +#else extern Datum Float4GetDatum(float4 X); +#endif /* * DatumGetFloat8 @@ -687,7 +720,18 @@ extern Datum Float4GetDatum(float4 X); */ #ifdef USE_FLOAT8_BYVAL -extern float8 DatumGetFloat8(Datum X); +static inline float8 +DatumGetFloat8(Datum X) +{ + union + { + int64 value; + float8 retval; + } myunion; + + myunion.value = GET_8_BYTES(X); + return myunion.retval; +} #else #define DatumGetFloat8(X) (* ((float8 *) DatumGetPointer(X))) #endif @@ -700,7 +744,22 @@ extern float8 DatumGetFloat8(Datum X); * to palloc'd space. */ +#ifdef USE_FLOAT8_BYVAL +static inline Datum +Float8GetDatum(float8 X) +{ + union + { + float8 value; + int64 retval; + } myunion; + + myunion.value = X; + return SET_8_BYTES(myunion.retval); +} +#else extern Datum Float8GetDatum(float8 X); +#endif /* |