v8-0011-error-safe-for-casting-float4-to-other-types-per-pg_cast.patch
text/x-patch
Filename: v8-0011-error-safe-for-casting-float4-to-other-types-per-pg_cast.patch
Type: text/x-patch
Part: 8
Patch
Same data as JSON:
GET /api/v1/attachments/:id/patch
the parsed metadata as JSON — format, series position, per-file stats; never the diff bytes.
API reference →
Format: format-patch
Series: patch v8-0011
Subject: error safe for casting float4 to other types per pg_cast
| File | + | − |
|---|---|---|
| src/backend/utils/adt/float.c | 10 | 2 |
| src/backend/utils/adt/int8.c | 5 | 1 |
| src/backend/utils/adt/numeric.c | 2 | 1 |
From 0fcd9f5fac1a1d418d35fe642775b2db6932d3f8 Mon Sep 17 00:00:00 2001
From: jian he <jian.universality@gmail.com>
Date: Thu, 9 Oct 2025 18:33:57 +0800
Subject: [PATCH v8 11/20] error safe for casting float4 to other types per
pg_cast
select castsource::regtype, casttarget::regtype, castfunc,
castcontext,castmethod, pp.prosrc, pp.proname from pg_cast pc join pg_proc pp on
pp.oid = pc.castfunc and pc.castfunc > 0
and castsource::regtype = 'float4'::regtype
order by castsource::regtype;
castsource | casttarget | castfunc | castcontext | castmethod | prosrc | proname
------------+------------------+----------+-------------+------------+----------------+---------
real | bigint | 653 | a | f | ftoi8 | int8
real | smallint | 238 | a | f | ftoi2 | int2
real | integer | 319 | a | f | ftoi4 | int4
real | double precision | 311 | i | f | ftod | float8
real | numeric | 1742 | a | f | float4_numeric | numeric
(5 rows)
discussion: https://postgr.es/m/CADkLM=fv1JfY4Ufa-jcwwNbjQixNViskQ8jZu3Tz_p656i_4hQ@mail.gmail.com
---
src/backend/utils/adt/float.c | 12 ++++++++++--
src/backend/utils/adt/int8.c | 6 +++++-
src/backend/utils/adt/numeric.c | 3 ++-
3 files changed, 17 insertions(+), 4 deletions(-)
diff --git a/src/backend/utils/adt/float.c b/src/backend/utils/adt/float.c
index 7b97d2be6ca..dd8a2ff378b 100644
--- a/src/backend/utils/adt/float.c
+++ b/src/backend/utils/adt/float.c
@@ -1298,10 +1298,14 @@ ftoi4(PG_FUNCTION_ARGS)
/* Range check */
if (unlikely(isnan(num) || !FLOAT4_FITS_IN_INT32(num)))
- ereport(ERROR,
+ {
+ errsave(fcinfo->context,
(errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
errmsg("integer out of range")));
+ PG_RETURN_NULL();
+ }
+
PG_RETURN_INT32((int32) num);
}
@@ -1323,10 +1327,14 @@ ftoi2(PG_FUNCTION_ARGS)
/* Range check */
if (unlikely(isnan(num) || !FLOAT4_FITS_IN_INT16(num)))
- ereport(ERROR,
+ {
+ errsave(fcinfo->context,
(errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
errmsg("smallint out of range")));
+ PG_RETURN_NULL();
+ }
+
PG_RETURN_INT16((int16) num);
}
diff --git a/src/backend/utils/adt/int8.c b/src/backend/utils/adt/int8.c
index 3b2d100be92..bcdb020a91c 100644
--- a/src/backend/utils/adt/int8.c
+++ b/src/backend/utils/adt/int8.c
@@ -1303,10 +1303,14 @@ ftoi8(PG_FUNCTION_ARGS)
/* Range check */
if (unlikely(isnan(num) || !FLOAT4_FITS_IN_INT64(num)))
- ereport(ERROR,
+ {
+ errsave(fcinfo->context,
(errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
errmsg("bigint out of range")));
+ PG_RETURN_NULL();
+ }
+
PG_RETURN_INT64((int64) num);
}
diff --git a/src/backend/utils/adt/numeric.c b/src/backend/utils/adt/numeric.c
index ce5f71109e7..8839b095f60 100644
--- a/src/backend/utils/adt/numeric.c
+++ b/src/backend/utils/adt/numeric.c
@@ -4668,7 +4668,8 @@ float4_numeric(PG_FUNCTION_ARGS)
init_var(&result);
/* Assume we need not worry about leading/trailing spaces */
- (void) set_var_from_str(buf, buf, &result, &endptr, NULL);
+ if (!set_var_from_str(buf, buf, &result, &endptr, fcinfo->context))
+ PG_RETURN_NULL();
res = make_result(&result);
--
2.34.1