On Fri, 8 Jun 2018 at 13:47, Geoff Winkless <pgsqladmin@xxxxxxxx> wrote: > Answering my own question, looks like And just in case anyone googling the question comes across this, this example code works. #include "postgres.h" #include <string.h> #include "fmgr.h" #include "utils/geo_decls.h" #include "funcapi.h" #include "utils/array.h" #include "utils/builtins.h" #include "utils/numeric.h" #include "catalog/pg_type.h" PG_MODULE_MAGIC; PG_FUNCTION_INFO_V1(pgnumeric_x10); Datum pgnumeric_x10(PG_FUNCTION_ARGS) { Numeric v; char *r; char mybuff[1000]; double f; v=PG_GETARG_NUMERIC(0); r=numeric_normalize(v); f=atof(r)*10; sprintf(mybuff, "%f", f); v = DatumGetNumeric(DirectFunctionCall3(numeric_in, CStringGetDatum(mybuff), 0, -1)); pfree(r); PG_RETURN_NUMERIC(v); } Example of it running: =# CREATE OR REPLACE FUNCTION pgnumeric_x10(NUMERIC) RETURNS NUMERIC AS 'testpgnumchange.so', 'pgnumeric_x10' LANGUAGE C STRICT IMMUTABLE; CREATE FUNCTION Time: 0.811 ms =# select pgnumeric_x10(132387.4823487::NUMERIC); pgnumeric_x10 ---------------- 1323874.823487 (1 row) Time: 0.593 ms =# For obvious reasons I wouldn't suggest using atof on a numeric, we have our own functions for manipulating _Decimal128 which is what I'll actually be using in the end version, but this is easier to compile as an example :) Geoff