@@ -667,6 +667,12 @@ validate_interval_value(PG_FUNCTION_ARGS)
667667}
668668
669669
670+ /*
671+ * ------------------
672+ * Helper functions
673+ * ------------------
674+ */
675+
670676/*
671677 * Check if interval is insignificant to avoid infinite loops while adding
672678 * new partitions
@@ -678,17 +684,19 @@ validate_interval_value(PG_FUNCTION_ARGS)
678684static bool
679685interval_is_trivial (Oid atttype , Datum interval , Oid interval_type )
680686{
687+ Oid plus_op_func ;
688+ Datum plus_op_result ;
689+ Oid plus_op_result_type ;
690+
681691 Datum default_value ;
682- Datum op_result ;
683- Oid op_result_type ;
684- Operator op ;
685- Oid op_func ;
692+
686693 FmgrInfo cmp_func ;
687694 int32 cmp_result ;
688695
689696 /*
690- * Generate default value. For float4 and float8 values we also check
691- * that they aren't NaN or INF
697+ * Generate default value.
698+ *
699+ * For float4 and float8 values we also check that they aren't NaN or INF.
692700 */
693701 switch (atttype )
694702 {
@@ -697,69 +705,70 @@ interval_is_trivial(Oid atttype, Datum interval, Oid interval_type)
697705 case INT8OID :
698706 default_value = Int16GetDatum (0 );
699707 break ;
708+
700709 case FLOAT4OID :
701710 {
702- float4 f = DatumGetFloat4 (interval );
711+ float4 f = DatumGetFloat4 (interval );
703712
704713 if (isnan (f ) || is_infinite (f ))
705714 elog (ERROR , "invalid floating point interval" );
706715 default_value = Float4GetDatum (0 );
707- break ;
708716 }
717+ break ;
718+
709719 case FLOAT8OID :
710720 {
711- float8 f = DatumGetFloat8 (interval );
721+ float8 f = DatumGetFloat8 (interval );
712722
713723 if (isnan (f ) || is_infinite (f ))
714724 elog (ERROR , "invalid floating point interval" );
715725 default_value = Float8GetDatum (0 );
716- break ;
717726 }
727+ break ;
728+
718729 case NUMERICOID :
719730 {
720- Numeric ni = DatumGetNumeric (interval );
721- Numeric numeric ;
731+ Numeric ni = DatumGetNumeric (interval ),
732+ numeric ;
722733
723734 /* Test for NaN */
724735 if (numeric_is_nan (ni ))
725736 elog (ERROR , "invalid numeric interval" );
726737
727738 /* Building default value */
728- numeric = DatumGetNumeric (DirectFunctionCall3 (numeric_in ,
729- CStringGetDatum ("0" ),
730- ObjectIdGetDatum (InvalidOid ),
731- Int32GetDatum (-1 )));
739+ numeric = DatumGetNumeric (
740+ DirectFunctionCall3 (numeric_in ,
741+ CStringGetDatum ("0" ),
742+ ObjectIdGetDatum (InvalidOid ),
743+ Int32GetDatum (-1 )));
732744 default_value = NumericGetDatum (numeric );
733- break ;
734745 }
746+ break ;
747+
735748 case TIMESTAMPOID :
736749 case TIMESTAMPTZOID :
737750 default_value = TimestampGetDatum (GetCurrentTimestamp ());
738751 break ;
752+
739753 case DATEOID :
740754 {
741- Datum ts = TimestampGetDatum (GetCurrentTimestamp ());
755+ Datum ts = TimestampGetDatum (GetCurrentTimestamp ());
742756
743757 default_value = perform_type_cast (ts , TIMESTAMPTZOID , DATEOID , NULL );
744- break ;
745758 }
759+ break ;
760+
746761 default :
747762 return false;
748763 }
749764
750765 /* Find suitable addition operator for default value and interval */
751- op = get_binary_operator ("+" , atttype , interval_type );
752- if (!op )
753- elog (ERROR , "missing \"+\" operator for types %s and %s" ,
754- format_type_be (atttype ),
755- format_type_be (interval_type ));
766+ extract_op_func_and_ret_type ("+" , atttype , interval_type ,
767+ & plus_op_func ,
768+ & plus_op_result_type );
756769
757- op_func = oprfuncid (op );
758- op_result_type = get_operator_ret_type (op );
759- ReleaseSysCache (op );
760-
761- /* Invoke addition operator and get a result*/
762- op_result = OidFunctionCall2 (op_func , default_value , interval );
770+ /* Invoke addition operator and get a result */
771+ plus_op_result = OidFunctionCall2 (plus_op_func , default_value , interval );
763772
764773 /*
765774 * If operator result type isn't the same as original value then
@@ -768,40 +777,38 @@ interval_is_trivial(Oid atttype, Datum interval, Oid interval_type)
768777 * to a date then we'll get a timestamp which is one second later than
769778 * original date (obviously). But when we convert it back to a date we will
770779 * get the same original value meaning that one second interval wouldn't
771- * change original value anyhow. We should consider such interval
772- * as trivial
780+ * change original value anyhow. We should consider such interval as trivial
773781 */
774- if (op_result_type != atttype )
782+ if (plus_op_result_type != atttype )
775783 {
776- op_result = perform_type_cast (op_result , op_result_type , atttype , NULL );
777- op_result_type = atttype ;
784+ plus_op_result = perform_type_cast (plus_op_result ,
785+ plus_op_result_type ,
786+ atttype , NULL );
787+ plus_op_result_type = atttype ;
778788 }
779789
780790 /*
781- * Compare it to the default_value. If they are the same then obviously
782- * interval is trivial
791+ * Compare it to the default_value.
792+ *
793+ * If they are the same then obviously interval is trivial.
783794 */
784795 fill_type_cmp_fmgr_info (& cmp_func ,
785796 getBaseType (atttype ),
786- getBaseType (op_result_type ));
797+ getBaseType (plus_op_result_type ));
798+
787799 cmp_result = DatumGetInt32 (FunctionCall2 (& cmp_func ,
788800 default_value ,
789- op_result ));
801+ plus_op_result ));
790802 if (cmp_result == 0 )
791803 return true;
792- else if (cmp_result > 0 ) /* Negative interval? */
804+
805+ else if (cmp_result > 0 ) /* Negative interval? */
793806 elog (ERROR , "interval must not be negative" );
794807
808+ /* Everything is OK */
795809 return false;
796810}
797811
798-
799- /*
800- * ------------------
801- * Helper functions
802- * ------------------
803- */
804-
805812/*
806813 * Drop old partition constraint and create
807814 * a new one with specified boundaries
0 commit comments