4141#include "utils/syscache.h"
4242#include "utils/varlena.h"
4343
44- static char * format_operator_internal (Oid operator_oid ,bool force_qualify );
45- static char * format_procedure_internal (Oid procedure_oid ,bool force_qualify );
4644static void parseNameAndArgTypes (const char * string ,bool allowNone ,
4745List * * names ,int * nargs ,Oid * argtypes );
4846
@@ -323,24 +321,32 @@ to_regprocedure(PG_FUNCTION_ARGS)
323321char *
324322format_procedure (Oid procedure_oid )
325323{
326- return format_procedure_internal (procedure_oid ,false );
324+ return format_procedure_extended (procedure_oid ,0 );
327325}
328326
329327char *
330328format_procedure_qualified (Oid procedure_oid )
331329{
332- return format_procedure_internal (procedure_oid ,true );
330+ return format_procedure_extended (procedure_oid ,FORMAT_PROC_FORCE_QUALIFY );
333331}
334332
335333/*
334+ * format_procedure_extended - converts procedure OID to "pro_name(args)"
335+ *
336+ * This exports the useful functionality of regprocedureout for use
337+ * in other backend modules. The result is a palloc'd string, or NULL.
338+ *
336339 * Routine to produce regprocedure names; see format_procedure above.
337340 *
338- * force_qualify says whether to schema-qualify; if true, the name is always
339- * qualified regardless of search_path visibility. Otherwise the name is only
340- * qualified if the function is not in path.
341+ * The following bits in 'flags' modify the behavior:
342+ * - FORMAT_PROC_INVALID_AS_NULL
343+ *if the procedure OID is invalid or unknown, return NULL instead
344+ *of the numeric OID.
345+ * - FORMAT_PROC_FORCE_QUALIFY
346+ *always schema-qualify procedure names, regardless of search_path
341347 */
342- static char *
343- format_procedure_internal (Oid procedure_oid ,bool force_qualify )
348+ char *
349+ format_procedure_extended (Oid procedure_oid ,bits16 flags )
344350{
345351char * result ;
346352HeapTuple proctup ;
@@ -365,7 +371,8 @@ format_procedure_internal(Oid procedure_oid, bool force_qualify)
365371 * Would this proc be found (given the right args) by regprocedurein?
366372 * If not, or if caller requests it, we need to qualify it.
367373 */
368- if (!force_qualify && FunctionIsVisible (procedure_oid ))
374+ if ((flags & FORMAT_PROC_FORCE_QUALIFY )== 0 &&
375+ FunctionIsVisible (procedure_oid ))
369376nspname = NULL ;
370377else
371378nspname = get_namespace_name (procform -> pronamespace );
@@ -379,7 +386,7 @@ format_procedure_internal(Oid procedure_oid, bool force_qualify)
379386if (i > 0 )
380387appendStringInfoChar (& buf ,',' );
381388appendStringInfoString (& buf ,
382- force_qualify ?
389+ ( flags & FORMAT_PROC_FORCE_QUALIFY ) != 0 ?
383390format_type_be_qualified (thisargtype ) :
384391format_type_be (thisargtype ));
385392}
@@ -389,6 +396,11 @@ format_procedure_internal(Oid procedure_oid, bool force_qualify)
389396
390397ReleaseSysCache (proctup );
391398}
399+ else if ((flags & FORMAT_PROC_INVALID_AS_NULL )!= 0 )
400+ {
401+ /* If object is undefined, return NULL as wanted by caller */
402+ result = NULL ;
403+ }
392404else
393405{
394406/* If OID doesn't match any pg_proc entry, return it numerically */
@@ -747,13 +759,20 @@ to_regoperator(PG_FUNCTION_ARGS)
747759}
748760
749761/*
750- *format_operator - converts operator OID to "opr_name(args)"
762+ *format_operator_extended - converts operator OID to "opr_name(args)"
751763 *
752764 * This exports the useful functionality of regoperatorout for use
753- * in other backend modules. The result is a palloc'd string.
765+ * in other backend modules. The result is a palloc'd string, or NULL.
766+ *
767+ * The following bits in 'flags' modify the behavior:
768+ * - FORMAT_OPERATOR_INVALID_AS_NULL
769+ *if the operator OID is invalid or unknown, return NULL instead
770+ *of the numeric OID.
771+ * - FORMAT_OPERATOR_FORCE_QUALIFY
772+ *always schema-qualify operator names, regardless of search_path
754773 */
755- static char *
756- format_operator_internal (Oid operator_oid ,bool force_qualify )
774+ char *
775+ format_operator_extended (Oid operator_oid ,bits16 flags )
757776{
758777char * result ;
759778HeapTuple opertup ;
@@ -776,7 +795,8 @@ format_operator_internal(Oid operator_oid, bool force_qualify)
776795 * Would this oper be found (given the right args) by regoperatorin?
777796 * If not, or if caller explicitly requests it, we need to qualify it.
778797 */
779- if (force_qualify || !OperatorIsVisible (operator_oid ))
798+ if ((flags & FORMAT_OPERATOR_FORCE_QUALIFY )!= 0 ||
799+ !OperatorIsVisible (operator_oid ))
780800{
781801nspname = get_namespace_name (operform -> oprnamespace );
782802appendStringInfo (& buf ,"%s." ,
@@ -787,15 +807,15 @@ format_operator_internal(Oid operator_oid, bool force_qualify)
787807
788808if (operform -> oprleft )
789809appendStringInfo (& buf ,"%s," ,
790- force_qualify ?
810+ ( flags & FORMAT_OPERATOR_FORCE_QUALIFY ) != 0 ?
791811format_type_be_qualified (operform -> oprleft ) :
792812format_type_be (operform -> oprleft ));
793813else
794814appendStringInfoString (& buf ,"NONE," );
795815
796816if (operform -> oprright )
797817appendStringInfo (& buf ,"%s)" ,
798- force_qualify ?
818+ ( flags & FORMAT_OPERATOR_FORCE_QUALIFY ) != 0 ?
799819format_type_be_qualified (operform -> oprright ) :
800820format_type_be (operform -> oprright ));
801821else
@@ -805,6 +825,11 @@ format_operator_internal(Oid operator_oid, bool force_qualify)
805825
806826ReleaseSysCache (opertup );
807827}
828+ else if ((flags & FORMAT_OPERATOR_INVALID_AS_NULL )!= 0 )
829+ {
830+ /* If object is undefined, return NULL as wanted by caller */
831+ result = NULL ;
832+ }
808833else
809834{
810835/*
@@ -820,13 +845,14 @@ format_operator_internal(Oid operator_oid, bool force_qualify)
820845char *
821846format_operator (Oid operator_oid )
822847{
823- return format_operator_internal (operator_oid ,false );
848+ return format_operator_extended (operator_oid ,0 );
824849}
825850
826851char *
827852format_operator_qualified (Oid operator_oid )
828853{
829- return format_operator_internal (operator_oid , true);
854+ return format_operator_extended (operator_oid ,
855+ FORMAT_OPERATOR_FORCE_QUALIFY );
830856}
831857
832858void