From a8d2820e6d428a9ca7315e9ed1dcd8a16f68e427 Mon Sep 17 00:00:00 2001
From: Bruce Momjian <bruce@momjian.us>
Date: Sat, 22 May 1999 04:12:29 +0000
Subject: [PATCH] Fix for DEFAULT ''.

---
 src/backend/catalog/heap.c          | 23 ++++-------------------
 src/backend/parser/parse_coerce.c   | 18 ++++++++++++------
 src/backend/parser/parse_expr.c     |  8 +++++---
 src/backend/parser/parse_func.c     |  9 ++++-----
 src/backend/parser/parse_node.c     |  6 ++----
 src/backend/parser/parse_relation.c |  6 ++++--
 src/backend/parser/parse_target.c   | 10 ++++++----
 src/include/parser/parse_coerce.h   |  5 +++--
 8 files changed, 40 insertions(+), 45 deletions(-)

diff --git a/src/backend/catalog/heap.c b/src/backend/catalog/heap.c
index 6775eebbdd7..c82a258a3b2 100644
--- a/src/backend/catalog/heap.c
+++ b/src/backend/catalog/heap.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/catalog/heap.c,v 1.83 1999/05/21 18:33:12 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/catalog/heap.c,v 1.84 1999/05/22 04:12:24 momjian Exp $
  *
  *
  * INTERFACE ROUTINES
@@ -1538,26 +1538,11 @@ start:
 
 	if (type != atp->atttypid)
 	{
-		/*
-		 *	Though these types are binary compatible, bpchar has a fixed
-		 *	length on the disk, requiring non-bpchar types to be padded
-		 *	before storage in the default table.  bjm 1999/05/18
-		 */
-		if (1==0 && atp->atttypid == BPCHAROID &&
-			(type == TEXTOID || type == BPCHAROID || type == UNKNOWNOID))
-		{
-
-			FuncCall   *n = makeNode(FuncCall);
-
-			n->funcname = typeidTypeName(atp->atttypid);
-			n->args = lcons((Node *)expr, NIL);
-			expr = transformExpr(NULL, (Node *) n, EXPR_COLUMN_FIRST);
-
-		}
-		else if (IS_BINARY_COMPATIBLE(type, atp->atttypid))
+		if (IS_BINARY_COMPATIBLE(type, atp->atttypid))
 			; /* use without change */
 		else if (can_coerce_type(1, &(type), &(atp->atttypid)))
-			expr = coerce_type(NULL, (Node *)expr, type, atp->atttypid);
+			expr = coerce_type(NULL, (Node *)expr, type, atp->atttypid,
+														 atp->atttypmod);
 		else if (IsA(expr, Const))
 		{
 			if (*cast != 0)
diff --git a/src/backend/parser/parse_coerce.c b/src/backend/parser/parse_coerce.c
index a3a93f17f1a..a481ecfa0a0 100644
--- a/src/backend/parser/parse_coerce.c
+++ b/src/backend/parser/parse_coerce.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_coerce.c,v 2.14 1999/05/22 02:55:57 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_coerce.c,v 2.15 1999/05/22 04:12:26 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -35,7 +35,8 @@ static Oid PreferredType(CATEGORY category, Oid type);
  * Convert a function argument to a different type.
  */
 Node *
-coerce_type(ParseState *pstate, Node *node, Oid inputTypeId, Oid targetTypeId)
+coerce_type(ParseState *pstate, Node *node, Oid inputTypeId, Oid targetTypeId,
+		int32 atttypmod)
 {
 	Node	   *result = NULL;
 	Oid			infunc;
@@ -82,11 +83,16 @@ coerce_type(ParseState *pstate, Node *node, Oid inputTypeId, Oid targetTypeId)
 				con->consttype = targetTypeId;
 				con->constlen = typeLen(typeidType(targetTypeId));
 
-				/* use "-1" for varchar() type */
+				/*
+				 *	Use "-1" for varchar() type.
+				 *	For char(), we need to pad out the type with the proper
+				 *	number of spaces.  This was a major problem for
+				 *  DEFAULT string constants to char() types.
+				 */
 				con->constvalue = (Datum) fmgr(infunc,
 											   val,
 											   typeidTypElem(targetTypeId),
-											   -1);
+								(targetTypeId != BPCHAROID) ? -1 : atttypmod);
 				con->constisnull = false;
 				con->constbyval = typeByVal(typeidType(targetTypeId));
 				con->constisset = false;
@@ -100,7 +106,7 @@ coerce_type(ParseState *pstate, Node *node, Oid inputTypeId, Oid targetTypeId)
 		result = node;
 
 	return result;
-}	/* coerce_type() */
+}
 
 
 /* can_coerce_type()
@@ -178,7 +184,7 @@ can_coerce_type(int nargs, Oid *input_typeids, Oid *func_typeids)
 	}
 
 	return true;
-}	/* can_coerce_type() */
+}
 
 
 /* TypeCategory()
diff --git a/src/backend/parser/parse_expr.c b/src/backend/parser/parse_expr.c
index f25e93eda17..8245beed110 100644
--- a/src/backend/parser/parse_expr.c
+++ b/src/backend/parser/parse_expr.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_expr.c,v 1.46 1999/05/18 23:40:05 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_expr.c,v 1.47 1999/05/22 04:12:26 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -417,7 +417,8 @@ transformExpr(ParseState *pstate, Node *expr, int precedence)
 					}
 					else if (can_coerce_type(1, &c->casetype, &ptype))
 					{
-						c->defresult = coerce_type(pstate, c->defresult, c->casetype, ptype);
+						c->defresult = coerce_type(pstate, c->defresult,
+													c->casetype, ptype, -1);
 						c->casetype = ptype;
 					}
 					else
@@ -439,7 +440,8 @@ transformExpr(ParseState *pstate, Node *expr, int precedence)
 					{
 						if (can_coerce_type(1, &wtype, &ptype))
 						{
-							w->result = coerce_type(pstate, w->result, wtype, ptype);
+							w->result = coerce_type(pstate, w->result, wtype,
+													ptype, -1);
 						}
 						else
 						{
diff --git a/src/backend/parser/parse_func.c b/src/backend/parser/parse_func.c
index a825f5ab8d6..6a4258048b9 100644
--- a/src/backend/parser/parse_func.c
+++ b/src/backend/parser/parse_func.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_func.c,v 1.44 1999/05/17 17:03:33 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_func.c,v 1.45 1999/05/22 04:12:27 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -352,7 +352,6 @@ ParseFuncOrColumn(ParseState *pstate, char *funcname, List *fargs,
 		}
 		else
 		{
-
 			/*
 			 * Parsing aggregates.
 			 */
@@ -361,7 +360,6 @@ ParseFuncOrColumn(ParseState *pstate, char *funcname, List *fargs,
 			int				ncandidates;
 			CandidateList	candidates;
 
-
 			/*
 			 * the aggregate COUNT is a special case, ignore its base
 			 * type.  Treat it as zero
@@ -392,7 +390,8 @@ ParseFuncOrColumn(ParseState *pstate, char *funcname, List *fargs,
 				type = agg_select_candidate(basetype, candidates);
 				if (OidIsValid(type))
 				{
-					lfirst(fargs) = coerce_type(pstate, lfirst(fargs), basetype, type);
+					lfirst(fargs) = coerce_type(pstate, lfirst(fargs),
+												basetype, type, -1);
 					basetype = type;
 
 					return (Node *) ParseAgg(pstate, funcname, basetype,
@@ -1316,7 +1315,7 @@ make_arguments(ParseState *pstate,
 			lfirst(current_fargs) = coerce_type(pstate,
 												lfirst(current_fargs),
 												input_typeids[i],
-												function_typeids[i]);
+												function_typeids[i], -1);
 		}
 	}
 }
diff --git a/src/backend/parser/parse_node.c b/src/backend/parser/parse_node.c
index c16f6a73559..0e56276a0cf 100644
--- a/src/backend/parser/parse_node.c
+++ b/src/backend/parser/parse_node.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_node.c,v 1.25 1999/05/10 00:45:28 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_node.c,v 1.26 1999/05/22 04:12:27 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -75,9 +75,7 @@ make_operand(char *opname,
 
 		/* must coerce? */
 		if (true_typeId != orig_typeId)
-		{
-			result = coerce_type(NULL, tree, orig_typeId, true_typeId);
-		}
+			result = coerce_type(NULL, tree, orig_typeId, true_typeId, -1);
 	}
 	/* otherwise, this is a NULL value */
 	else
diff --git a/src/backend/parser/parse_relation.c b/src/backend/parser/parse_relation.c
index 88eec405b9a..07919e1b317 100644
--- a/src/backend/parser/parse_relation.c
+++ b/src/backend/parser/parse_relation.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_relation.c,v 1.20 1999/05/17 17:03:34 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_relation.c,v 1.21 1999/05/22 04:12:28 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -445,7 +445,9 @@ checkTargetTypes(ParseState *pstate, char *target_colname,
 	{
 		if (can_coerce_type(1, &attrtype_id, &attrtype_target))
 		{
-			Node	   *expr = coerce_type(pstate, expr, attrtype_id, attrtype_target);
+			Node	   *expr = coerce_type(pstate, expr, attrtype_id,
+											attrtype_target,
+			get_atttypmod(pstate->p_target_relation->rd_id, resdomno_target));
 
 			elog(ERROR, "Type %s(%d) can be coerced to match target column %s(%d)",
 				 colname, get_atttypmod(rte->relid, resdomno_id),
diff --git a/src/backend/parser/parse_target.c b/src/backend/parser/parse_target.c
index 0a7912d76d2..1294326f3d4 100644
--- a/src/backend/parser/parse_target.c
+++ b/src/backend/parser/parse_target.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_target.c,v 1.37 1999/05/17 17:03:35 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/parser/parse_target.c,v 1.38 1999/05/22 04:12:28 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -121,7 +121,9 @@ MakeTargetEntryIdent(ParseState *pstate,
 		{
 			if (can_coerce_type(1, &attrtype_id, &attrtype_target))
 			{
-				expr = coerce_type(pstate, node, attrtype_id, attrtype_target);
+				expr = coerce_type(pstate, node, attrtype_id,
+									attrtype_target,
+			get_atttypmod(pstate->p_target_relation->rd_id, resdomno_target));
 				expr = transformExpr(pstate, expr, EXPR_COLUMN_FIRST);
 				tent = MakeTargetEntryExpr(pstate, *resname, expr, false, false);
 				expr = tent->expr;
@@ -666,7 +668,7 @@ CoerceTargetExpr(ParseState *pstate,
 {
 	if (can_coerce_type(1, &type_id, &attrtype))
 	{
-		expr = coerce_type(pstate, expr, type_id, attrtype);
+		expr = coerce_type(pstate, expr, type_id, attrtype, -1);
 	}
 
 #ifndef DISABLE_STRING_HACKS
@@ -683,7 +685,7 @@ CoerceTargetExpr(ParseState *pstate,
 		{
 		}
 		else if (can_coerce_type(1, &type_id, &text_id))
-			expr = coerce_type(pstate, expr, type_id, text_id);
+			expr = coerce_type(pstate, expr, type_id, text_id, -1);
 		else
 			expr = NULL;
 	}
diff --git a/src/include/parser/parse_coerce.h b/src/include/parser/parse_coerce.h
index 72e582550a2..d8cc6b7697d 100644
--- a/src/include/parser/parse_coerce.h
+++ b/src/include/parser/parse_coerce.h
@@ -6,7 +6,7 @@
  *
  * Copyright (c) 1994, Regents of the University of California
  *
- * $Id: parse_coerce.h,v 1.9 1999/03/10 05:05:58 tgl Exp $
+ * $Id: parse_coerce.h,v 1.10 1999/05/22 04:12:29 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -121,6 +121,7 @@ extern bool IsPreferredType(CATEGORY category, Oid type);
 extern CATEGORY TypeCategory(Oid type);
 
 extern bool can_coerce_type(int nargs, Oid *input_typeids, Oid *func_typeids);
-extern Node *coerce_type(ParseState *pstate, Node *node, Oid inputTypeId, Oid targetTypeId);
+extern Node *coerce_type(ParseState *pstate, Node *node, Oid inputTypeId,
+						 Oid targetTypeId, int32 atttypmod);
 
 #endif	 /* PARSE_COERCE_H */
-- 
GitLab