diff --git a/src/interfaces/ecpg/ecpglib/data.c b/src/interfaces/ecpg/ecpglib/data.c
index f3d326a..bc01ca9 100644
--- a/src/interfaces/ecpg/ecpglib/data.c
+++ b/src/interfaces/ecpg/ecpglib/data.c
@@ -122,6 +122,71 @@ check_special_value(char *ptr, double *retval, char **endptr)
 	return false;
 }
 
+/* imported from src/backend/utils/adt/encode.c */
+
+static unsigned
+hex_enc_len(unsigned srclen)
+{
+	return srclen << 1;
+}
+extern unsigned
+ecpg_hex_dec_len(unsigned srclen)
+{
+	return srclen >> 1;
+}
+
+static inline char
+get_hex(char c)
+{
+	static const int8 hexlookup[128] = {
+		-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
+		-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
+		-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
+		0, 1, 2, 3, 4, 5, 6, 7, 8, 9, -1, -1, -1, -1, -1, -1,
+		-1, 10, 11, 12, 13, 14, 15, -1, -1, -1, -1, -1, -1, -1, -1, -1,
+		-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
+		-1, 10, 11, 12, 13, 14, 15, -1, -1, -1, -1, -1, -1, -1, -1, -1,
+		-1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
+	};
+	int			res = -1;
+
+	if (c > 0 && c < 127)
+		res = hexlookup[(unsigned char) c];
+
+	return (char) res;
+}
+
+static unsigned
+hex_decode(const char *src, unsigned len, char *dst)
+{
+	const char *s,
+			   *srcend;
+	char		v1,
+				v2,
+			   *p;
+
+	srcend = src + len;
+	s = src;
+	p = dst;
+	while (s < srcend)
+	{
+		if (*s == ' ' || *s == '\n' || *s == '\t' || *s == '\r')
+		{
+			s++;
+			continue;
+		}
+		v1 = get_hex(*s++) << 4;
+		if (s >= srcend)
+			return -1;
+
+		v2 = get_hex(*s++);
+		*p++ = v1 | v2;
+	}
+
+	return p - dst;
+}
+
+
 bool
 ecpg_get_data(const PGresult *results, int act_tuple, int act_field, int lineno,
 			  enum ECPGttype type, enum ECPGttype ind_type,
@@ -447,6 +512,55 @@ ecpg_get_data(const PGresult *results, int act_tuple, int act_field, int lineno,
 					return false;
 					break;
 
+				case ECPGt_bytea:
+					{
+						struct ECPGgeneric_varchar *variable =
+						(struct ECPGgeneric_varchar *) (var + offset * act_tuple);
+						long		dst_size,
+									src_size,
+									dec_size;
+
+						dst_size = hex_enc_len(varcharsize);
+						src_size = size - 2;	/* exclude backslash + 'x' */
+						dec_size = src_size < dst_size ? src_size : dst_size;
+						variable->len = hex_decode(pval + 2, dec_size, variable->arr);
+
+						if (dst_size < src_size)
+						{
+							long		rcv_size = ecpg_hex_dec_len(size - 2);
+
+							/* truncation */
+							switch (ind_type)
+							{
+								case ECPGt_short:
+								case ECPGt_unsigned_short:
+									*((short *) (ind + ind_offset * act_tuple)) = rcv_size;
+									break;
+								case ECPGt_int:
+								case ECPGt_unsigned_int:
+									*((int *) (ind + ind_offset * act_tuple)) = rcv_size;
+									break;
+								case ECPGt_long:
+								case ECPGt_unsigned_long:
+									*((long *) (ind + ind_offset * act_tuple)) = rcv_size;
+									break;
+#ifdef HAVE_LONG_LONG_INT
+								case ECPGt_long_long:
+								case ECPGt_unsigned_long_long:
+									*((long long int *) (ind + ind_offset * act_tuple)) = rcv_size;
+									break;
+#endif							/* HAVE_LONG_LONG_INT */
+								default:
+									break;
+							}
+							sqlca->sqlwarn[0] = sqlca->sqlwarn[1] = 'W';
+						}
+
+						pval += size;
+
+					}
+					break;
+
 				case ECPGt_char:
 				case ECPGt_unsigned_char:
 				case ECPGt_string:
diff --git a/src/interfaces/ecpg/ecpglib/descriptor.c b/src/interfaces/ecpg/ecpglib/descriptor.c
index 8fdf560..441b4e6 100644
--- a/src/interfaces/ecpg/ecpglib/descriptor.c
+++ b/src/interfaces/ecpg/ecpglib/descriptor.c
@@ -636,11 +636,29 @@ ECPGset_desc(int lineno, const char *desc_name, int index,...)
 		{
 			case ECPGd_data:
 				{
-					if (!ecpg_store_input(lineno, true, var, &tobeinserted, false))
+					if (var->type != ECPGt_bytea)
 					{
-						ecpg_free(var);
-						va_end(args);
-						return false;
+						if (!ecpg_store_input(lineno, true, var, &tobeinserted, false))
+						{
+							ecpg_free(var);
+							va_end(args);
+							return false;
+						}
+						desc_item->is_binary = false;
+					}
+					else
+					{
+						struct ECPGgeneric_varchar *variable =
+						(struct ECPGgeneric_varchar *) (var->value);
+
+						if (!(tobeinserted = ecpg_alloc(sizeof(int) + variable->len, lineno)))
+						{
+							ecpg_free(var);
+							va_end(args);
+							return false;
+						}
+						memcpy(tobeinserted, var->value, sizeof(int) + variable->len);
+						desc_item->is_binary = true;
 					}
 
 					ecpg_free(desc_item->data); /* free() takes care of a
diff --git a/src/interfaces/ecpg/ecpglib/execute.c b/src/interfaces/ecpg/ecpglib/execute.c
index 42640ba..942bc11 100644
--- a/src/interfaces/ecpg/ecpglib/execute.c
+++ b/src/interfaces/ecpg/ecpglib/execute.c
@@ -799,6 +799,20 @@ ecpg_store_input(const int lineno, const bool force_indicator, const struct vari
 					*tobeinserted_p = mallocedval;
 				}
 				break;
+
+			case ECPGt_bytea:
+				{
+					struct ECPGgeneric_varchar *variable =
+					(struct ECPGgeneric_varchar *) (var->value);
+
+					if (!(mallocedval = (char *) ecpg_alloc(variable->len, lineno)))
+						return false;
+
+					memcpy(mallocedval, variable->arr, variable->len);
+					*tobeinserted_p = mallocedval;
+				}
+				break;
+
 			case ECPGt_varchar:
 				{
 					struct ECPGgeneric_varchar *variable =
@@ -1053,7 +1067,11 @@ ecpg_free_params(struct statement *stmt, bool print)
 		ecpg_free(stmt->paramvalues[n]);
 	}
 	ecpg_free(stmt->paramvalues);
+	ecpg_free(stmt->paramlengths);
+	ecpg_free(stmt->paramformats);
 	stmt->paramvalues = NULL;
+	stmt->paramlengths = NULL;
+	stmt->paramformats = NULL;
 	stmt->nparams = 0;
 }
 
@@ -1120,8 +1138,13 @@ ecpg_build_params(struct statement *stmt)
 	{
 		char	   *tobeinserted;
 		int			counter = 1;
+		bool		binary_format;
+		int			binary_length;
+
 
 		tobeinserted = NULL;
+		binary_length = 0;
+		binary_format = false;
 
 		/*
 		 * A descriptor is a special case since it contains many variables but
@@ -1146,12 +1169,27 @@ ecpg_build_params(struct statement *stmt)
 			{
 				if (desc_item->num == desc_counter)
 				{
-					desc_inlist.type = ECPGt_char;
+					if (!desc_item->is_binary)
+					{
+						desc_inlist.type = ECPGt_char;
+						desc_inlist.varcharsize = strlen(desc_item->data);
+					}
+					else
+					{
+						struct ECPGgeneric_varchar *variable =
+						(struct ECPGgeneric_varchar *) (desc_item->data);
+
+						binary_length = variable->len;
+						binary_format = true;
+
+						desc_inlist.type = ECPGt_bytea;
+						desc_inlist.varcharsize = binary_length;
+					}
 					desc_inlist.value = desc_item->data;
 					desc_inlist.pointer = &(desc_item->data);
-					desc_inlist.varcharsize = strlen(desc_item->data);
 					desc_inlist.arrsize = 1;
 					desc_inlist.offset = 0;
+
 					if (!desc_item->indicator)
 					{
 						desc_inlist.ind_type = ECPGt_NO_INDICATOR;
@@ -1293,6 +1331,15 @@ ecpg_build_params(struct statement *stmt)
 		{
 			if (!ecpg_store_input(stmt->lineno, stmt->force_indicator, var, &tobeinserted, false))
 				return false;
+
+			if (var->type == ECPGt_bytea)
+			{
+				struct ECPGgeneric_varchar *variable =
+				(struct ECPGgeneric_varchar *) (var->value);
+
+				binary_length = variable->len;
+				binary_format = true;
+			}
 		}
 
 		/*
@@ -1346,16 +1393,32 @@ ecpg_build_params(struct statement *stmt)
 		else
 		{
 			char	  **paramvalues;
+			int		   *paramlengths;
+			int		   *paramformats;
 
 			if (!(paramvalues = (char **) ecpg_realloc(stmt->paramvalues, sizeof(char *) * (stmt->nparams + 1), stmt->lineno)))
 			{
 				ecpg_free_params(stmt, false);
 				return false;
 			}
+			if (!(paramlengths = (int *) ecpg_realloc(stmt->paramlengths, sizeof(int) * (stmt->nparams + 1), stmt->lineno)))
+			{
+				ecpg_free_params(stmt, false);
+				return false;
+			}
+			if (!(paramformats = (int *) ecpg_realloc(stmt->paramformats, sizeof(int) * (stmt->nparams + 1), stmt->lineno)))
+			{
+				ecpg_free_params(stmt, false);
+				return false;
+			}
 
 			stmt->nparams++;
 			stmt->paramvalues = paramvalues;
+			stmt->paramlengths = paramlengths;
+			stmt->paramformats = paramformats;
 			stmt->paramvalues[stmt->nparams - 1] = tobeinserted;
+			stmt->paramlengths[stmt->nparams - 1] = binary_length;
+			stmt->paramformats[stmt->nparams - 1] = (binary_format ? 1 : 0);
 
 			/* let's see if this was an old style placeholder */
 			if (stmt->command[position] == '?')
@@ -1428,7 +1491,13 @@ ecpg_execute(struct statement *stmt)
 	ecpg_log("ecpg_execute on line %d: query: %s; with %d parameter(s) on connection %s\n", stmt->lineno, stmt->command, stmt->nparams, stmt->connection->name);
 	if (stmt->statement_type == ECPGst_execute)
 	{
-		stmt->results = PQexecPrepared(stmt->connection->connection, stmt->name, stmt->nparams, (const char *const *) stmt->paramvalues, NULL, NULL, 0);
+		stmt->results = PQexecPrepared(stmt->connection->connection,
+									   stmt->name,
+									   stmt->nparams,
+									   (const char *const *) stmt->paramvalues,
+									   (const int *) stmt->paramlengths,
+									   (const int *) stmt->paramformats,
+									   0);
 		ecpg_log("ecpg_execute on line %d: using PQexecPrepared for \"%s\"\n", stmt->lineno, stmt->command);
 	}
 	else
@@ -1440,7 +1509,12 @@ ecpg_execute(struct statement *stmt)
 		}
 		else
 		{
-			stmt->results = PQexecParams(stmt->connection->connection, stmt->command, stmt->nparams, NULL, (const char *const *) stmt->paramvalues, NULL, NULL, 0);
+			stmt->results = PQexecParams(stmt->connection->connection,
+										 stmt->command, stmt->nparams, NULL,
+										 (const char *const *) stmt->paramvalues,
+										 (const int *) stmt->paramlengths,
+										 (const int *) stmt->paramformats,
+										 0);
 			ecpg_log("ecpg_execute on line %d: using PQexecParams\n", stmt->lineno);
 		}
 	}
diff --git a/src/interfaces/ecpg/ecpglib/extern.h b/src/interfaces/ecpg/ecpglib/extern.h
index a88f341..79e451d 100644
--- a/src/interfaces/ecpg/ecpglib/extern.h
+++ b/src/interfaces/ecpg/ecpglib/extern.h
@@ -37,6 +37,13 @@ struct ECPGgeneric_varchar
 	char		arr[FLEXIBLE_ARRAY_MEMBER];
 };
 
+/* A generic bytea type. */
+struct ECPGgeneric_bytea
+{
+	int			len;
+	char		arr[FLEXIBLE_ARRAY_MEMBER];
+};
+
 /*
  * type information cache
  */
@@ -64,6 +71,8 @@ struct statement
 	char	   *oldlocale;
 	int			nparams;
 	char	  **paramvalues;
+	int		   *paramlengths;
+	int		   *paramformats;
 	PGresult   *results;
 };
 
@@ -106,6 +115,8 @@ struct descriptor_item
 	int			precision;
 	int			scale;
 	int			type;
+	bool		is_binary;
+	int			data_len;
 	struct descriptor_item *next;
 };
 
@@ -194,6 +205,7 @@ struct sqlda_compat *ecpg_build_compat_sqlda(int, PGresult *, int, enum COMPAT_M
 void		ecpg_set_compat_sqlda(int, struct sqlda_compat **, const PGresult *, int, enum COMPAT_MODE);
 struct sqlda_struct *ecpg_build_native_sqlda(int, PGresult *, int, enum COMPAT_MODE);
 void		ecpg_set_native_sqlda(int, struct sqlda_struct **, const PGresult *, int, enum COMPAT_MODE);
+unsigned	ecpg_hex_dec_len(unsigned srclen);
 
 /* SQLSTATE values generated or processed by ecpglib (intentionally
  * not exported -- users should refer to the codes directly) */
diff --git a/src/interfaces/ecpg/ecpglib/misc.c b/src/interfaces/ecpg/ecpglib/misc.c
index be9cac6..e5432a2 100644
--- a/src/interfaces/ecpg/ecpglib/misc.c
+++ b/src/interfaces/ecpg/ecpglib/misc.c
@@ -355,6 +355,9 @@ ECPGset_noind_null(enum ECPGttype type, void *ptr)
 			*(((struct ECPGgeneric_varchar *) ptr)->arr) = 0x00;
 			((struct ECPGgeneric_varchar *) ptr)->len = 0;
 			break;
+		case ECPGt_bytea:
+			((struct ECPGgeneric_bytea *) ptr)->len = 0;
+			break;
 		case ECPGt_decimal:
 			memset((char *) ptr, 0, sizeof(decimal));
 			((decimal *) ptr)->sign = NUMERIC_NULL;
@@ -428,6 +431,10 @@ ECPGis_noind_null(enum ECPGttype type, const void *ptr)
 			if (*(((const struct ECPGgeneric_varchar *) ptr)->arr) == 0x00)
 				return true;
 			break;
+		case ECPGt_bytea:
+			if (((struct ECPGgeneric_bytea *) ptr)->len == 0)
+				return true;
+			break;
 		case ECPGt_decimal:
 			if (((const decimal *) ptr)->sign == NUMERIC_NULL)
 				return true;
diff --git a/src/interfaces/ecpg/ecpglib/typename.c b/src/interfaces/ecpg/ecpglib/typename.c
index 9da1cdf..572bc78 100644
--- a/src/interfaces/ecpg/ecpglib/typename.c
+++ b/src/interfaces/ecpg/ecpglib/typename.c
@@ -48,6 +48,8 @@ ecpg_type_name(enum ECPGttype typ)
 			return "bool";
 		case ECPGt_varchar:
 			return "varchar";
+		case ECPGt_bytea:
+			return "bytea";
 		case ECPGt_char_variable:
 			return "char";
 		case ECPGt_decimal:
diff --git a/src/interfaces/ecpg/include/ecpgtype.h b/src/interfaces/ecpg/include/ecpgtype.h
index 38fb3b6..b9fc4ea 100644
--- a/src/interfaces/ecpg/include/ecpgtype.h
+++ b/src/interfaces/ecpg/include/ecpgtype.h
@@ -63,7 +63,8 @@ enum ECPGttype
 	ECPGt_EORT,					/* End of result types. */
 	ECPGt_NO_INDICATOR,			/* no indicator */
 	ECPGt_string,				/* trimmed (char *) type */
-	ECPGt_sqlda					/* C struct descriptor */
+	ECPGt_sqlda,				/* C struct descriptor */
+	ECPGt_bytea
 };
 
  /* descriptor items */
@@ -88,7 +89,7 @@ enum ECPGdtype
 	ECPGd_cardinality
 };
 
-#define IS_SIMPLE_TYPE(type) (((type) >= ECPGt_char && (type) <= ECPGt_interval) || ((type) == ECPGt_string))
+#define IS_SIMPLE_TYPE(type) (((type) >= ECPGt_char && (type) <= ECPGt_interval) || ((type) == ECPGt_string) || ((type) == ECPGt_bytea))
 
 /* we also have to handle different statement types */
 enum ECPG_statement_type
diff --git a/src/interfaces/ecpg/preproc/ecpg.header b/src/interfaces/ecpg/preproc/ecpg.header
index 8921bcb..4669dff 100644
--- a/src/interfaces/ecpg/preproc/ecpg.header
+++ b/src/interfaces/ecpg/preproc/ecpg.header
@@ -46,6 +46,7 @@ static char	pacounter_buffer[sizeof(int) * CHAR_BIT * 10 / 3]; /* a rough guess
 static struct this_type actual_type[STRUCT_DEPTH];
 static char *actual_startline[STRUCT_DEPTH];
 static int	varchar_counter = 1;
+static int	bytea_counter = 1;
 
 /* temporarily store struct members while creating the data structure */
 struct ECPGstruct_member *struct_member_list[STRUCT_DEPTH] = { NULL };
@@ -562,6 +563,7 @@ add_typedef(char *name, char *dimension, char *length, enum ECPGttype type_enum,
 		ECPGstruct_member_dup(struct_member_list[struct_level]) : NULL;
 
 		if (type_enum != ECPGt_varchar &&
+			type_enum != ECPGt_bytea &&
 			type_enum != ECPGt_char &&
 			type_enum != ECPGt_unsigned_char &&
 			type_enum != ECPGt_string &&
diff --git a/src/interfaces/ecpg/preproc/ecpg.trailer b/src/interfaces/ecpg/preproc/ecpg.trailer
index 19dc781..c44fcf9 100644
--- a/src/interfaces/ecpg/preproc/ecpg.trailer
+++ b/src/interfaces/ecpg/preproc/ecpg.trailer
@@ -550,6 +550,14 @@ var_type:	simple_type
 				$$.type_index = mm_strdup("-1");
 				$$.type_sizeof = NULL;
 			}
+			else if (strcmp($1, "bytea") == 0)
+			{
+				$$.type_enum = ECPGt_bytea;
+				$$.type_str = EMPTY;
+				$$.type_dimension = mm_strdup("-1");
+				$$.type_index = mm_strdup("-1");
+				$$.type_sizeof = NULL;
+			}
 			else if (strcmp($1, "float") == 0)
 			{
 				$$.type_enum = ECPGt_float;
@@ -627,7 +635,7 @@ var_type:	simple_type
 				/* this is for typedef'ed types */
 				struct typedefs *this = get_typedef($1);
 
-				$$.type_str = (this->type->type_enum == ECPGt_varchar) ? EMPTY : mm_strdup(this->name);
+				$$.type_str = (this->type->type_enum == ECPGt_varchar || this->type->type_enum == ECPGt_bytea) ? EMPTY : mm_strdup(this->name);
 				$$.type_enum = this->type->type_enum;
 				$$.type_dimension = this->type->type_dimension;
 				$$.type_index = this->type->type_index;
@@ -838,7 +846,7 @@ variable_list: variable
 			{ $$ = $1; }
 		| variable_list ',' variable
 		{
-			if (actual_type[struct_level].type_enum == ECPGt_varchar)
+			if (actual_type[struct_level].type_enum == ECPGt_varchar || actual_type[struct_level].type_enum == ECPGt_bytea)
 				$$ = cat_str(3, $1, mm_strdup(";"), $3);
 			else
 				$$ = cat_str(3, $1, mm_strdup(","), $3);
@@ -852,9 +860,10 @@ variable: opt_pointer ECPGColLabel opt_array_bounds opt_bit_field opt_initialize
 			char *length = $3.index2;		/* length of string */
 			char *dim_str;
 			char *vcn;
+			int *varlen_type_counter;
+			char *struct_name;
 
 			adjust_array(actual_type[struct_level].type_enum, &dimension, &length, actual_type[struct_level].type_dimension, actual_type[struct_level].type_index, strlen($1), false);
-
 			switch (actual_type[struct_level].type_enum)
 			{
 				case ECPGt_struct:
@@ -868,10 +877,21 @@ variable: opt_pointer ECPGColLabel opt_array_bounds opt_bit_field opt_initialize
 					break;
 
 				case ECPGt_varchar:
+				case ECPGt_bytea:
+					if (actual_type[struct_level].type_enum == ECPGt_varchar)
+					{
+						varlen_type_counter = &varchar_counter;
+						struct_name = " struct varchar_";
+					}
+					else
+					{
+						varlen_type_counter = &bytea_counter;
+						struct_name = " struct bytea_";
+					}
 					if (atoi(dimension) < 0)
-						type = ECPGmake_simple_type(actual_type[struct_level].type_enum, length, varchar_counter);
+						type = ECPGmake_simple_type(actual_type[struct_level].type_enum, length, *varlen_type_counter);
 					else
-						type = ECPGmake_array_type(ECPGmake_simple_type(actual_type[struct_level].type_enum, length, varchar_counter), dimension);
+						type = ECPGmake_array_type(ECPGmake_simple_type(actual_type[struct_level].type_enum, length, *varlen_type_counter), dimension);
 
 					if (strcmp(dimension, "0") == 0 || abs(atoi(dimension)) == 1)
 							dim_str=mm_strdup("");
@@ -883,12 +903,12 @@ variable: opt_pointer ECPGColLabel opt_array_bounds opt_bit_field opt_initialize
 
 					/* make sure varchar struct name is unique by adding a unique counter to its definition */
 					vcn = (char *) mm_alloc(sizeof(int) * CHAR_BIT * 10 / 3);
-					sprintf(vcn, "%d", varchar_counter);
+					sprintf(vcn, "%d", *varlen_type_counter);
 					if (strcmp(dimension, "0") == 0)
-						$$ = cat_str(7, make2_str(mm_strdup(" struct varchar_"), vcn), mm_strdup(" { int len; char arr["), mm_strdup(length), mm_strdup("]; } *"), mm_strdup($2), $4, $5);
+						$$ = cat_str(7, make2_str(mm_strdup(struct_name), vcn), mm_strdup(" { int len; char arr["), mm_strdup(length), mm_strdup("]; } *"), mm_strdup($2), $4, $5);
 					else
-						$$ = cat_str(8, make2_str(mm_strdup(" struct varchar_"), vcn), mm_strdup(" { int len; char arr["), mm_strdup(length), mm_strdup("]; } "), mm_strdup($2), dim_str, $4, $5);
-					varchar_counter++;
+						$$ = cat_str(8, make2_str(mm_strdup(struct_name), vcn), mm_strdup(" { int len; char arr["), mm_strdup(length), mm_strdup("]; } "), mm_strdup($2), dim_str, $4, $5);
+					(*varlen_type_counter)++;
 					break;
 
 				case ECPGt_char:
@@ -1354,6 +1374,7 @@ ECPGVar: SQL_VAR
 						break;
 
 					case ECPGt_varchar:
+					case ECPGt_bytea:
 						if (atoi(dimension) == -1)
 							type = ECPGmake_simple_type($5.type_enum, length, 0);
 						else
diff --git a/src/interfaces/ecpg/preproc/type.c b/src/interfaces/ecpg/preproc/type.c
index 253873d..44c8a2d 100644
--- a/src/interfaces/ecpg/preproc/type.c
+++ b/src/interfaces/ecpg/preproc/type.c
@@ -102,7 +102,7 @@ ECPGmake_simple_type(enum ECPGttype type, char *size, int counter)
 	ne->size = size;
 	ne->u.element = NULL;
 	ne->struct_sizeof = NULL;
-	ne->counter = counter;		/* only needed for varchar */
+	ne->counter = counter;		/* only needed for varchar and bytea */
 
 	return ne;
 }
@@ -175,6 +175,8 @@ get_type(enum ECPGttype type)
 			break;
 		case ECPGt_varchar:
 			return "ECPGt_varchar";
+		case ECPGt_bytea:
+			return "ECPGt_bytea";
 		case ECPGt_NO_INDICATOR:	/* no indicator */
 			return "ECPGt_NO_INDICATOR";
 			break;
@@ -424,6 +426,7 @@ ECPGdump_a_simple(FILE *o, const char *name, enum ECPGttype type,
 	{
 		char	   *variable = (char *) mm_alloc(strlen(name) + ((prefix == NULL) ? 0 : strlen(prefix)) + 4);
 		char	   *offset = (char *) mm_alloc(strlen(name) + strlen("sizeof(struct varchar_)") + 1 + strlen(varcharsize) + sizeof(int) * CHAR_BIT * 10 / 3);
+		char	   *struct_name;
 
 		switch (type)
 		{
@@ -433,6 +436,7 @@ ECPGdump_a_simple(FILE *o, const char *name, enum ECPGttype type,
 				 */
 
 			case ECPGt_varchar:
+			case ECPGt_bytea:
 
 				/*
 				 * we have to use the pointer except for arrays with given
@@ -449,10 +453,15 @@ ECPGdump_a_simple(FILE *o, const char *name, enum ECPGttype type,
 				 * If we created a varchar structure automatically, counter is
 				 * greater than 0.
 				 */
+				if (type == ECPGt_varchar)
+					struct_name = "struct varchar";
+				else
+					struct_name = "struct bytea";
+
 				if (counter)
-					sprintf(offset, "sizeof(struct varchar_%d)", counter);
+					sprintf(offset, "sizeof(%s_%d)", struct_name, counter);
 				else
-					sprintf(offset, "sizeof(struct varchar)");
+					sprintf(offset, "sizeof(%s)", struct_name);
 				break;
 			case ECPGt_char:
 			case ECPGt_unsigned_char:
diff --git a/src/interfaces/ecpg/preproc/variable.c b/src/interfaces/ecpg/preproc/variable.c
index 39bf3b2..0939de5 100644
--- a/src/interfaces/ecpg/preproc/variable.c
+++ b/src/interfaces/ecpg/preproc/variable.c
@@ -560,6 +560,7 @@ adjust_array(enum ECPGttype type_enum, char **dimension, char **length, char *ty
 
 			break;
 		case ECPGt_varchar:
+		case ECPGt_bytea:
 			/* pointer has to get dimension 0 */
 			if (pointer_len)
 				*dimension = mm_strdup("0");
diff --git a/src/interfaces/ecpg/test/ecpg_schedule b/src/interfaces/ecpg/test/ecpg_schedule
index 991b8cb..2478d03 100644
--- a/src/interfaces/ecpg/test/ecpg_schedule
+++ b/src/interfaces/ecpg/test/ecpg_schedule
@@ -32,6 +32,7 @@ test: preproc/whenever
 test: preproc/whenever_do_continue
 test: sql/array
 test: sql/binary
+test: sql/bytea
 test: sql/code100
 test: sql/copystdout
 test: sql/define
diff --git a/src/interfaces/ecpg/test/expected/sql-bytea.c b/src/interfaces/ecpg/test/expected/sql-bytea.c
new file mode 100644
index 0000000..bcaccd1
--- /dev/null
+++ b/src/interfaces/ecpg/test/expected/sql-bytea.c
@@ -0,0 +1,316 @@
+/* Processed by ecpg (regression mode) */
+/* These include files are added by the preprocessor */
+#include <ecpglib.h>
+#include <ecpgerrno.h>
+#include <sqlca.h>
+/* End of automatic include section */
+#define ECPGdebug(X,Y) ECPGdebug((X)+100,(Y))
+
+#line 1 "bytea.pgc"
+#include <stdlib.h>
+#include <string.h>
+#include <stdio.h>
+#include <time.h>
+
+
+#line 1 "regression.h"
+
+
+
+
+
+
+#line 6 "bytea.pgc"
+
+/* exec sql whenever sqlerror  sqlprint ; */
+#line 7 "bytea.pgc"
+
+
+static void
+dump_binary(char *buf, int len, int ind)
+{
+	int i;
+
+	printf("len=%d, ind=%d, data=0x", len, ind);
+	for (i = 0; i < len; ++i)
+		printf("%02x", 0xff & buf[i]);
+	printf("\n");
+}
+
+#define DATA_SIZE 0x200
+#define LACK_SIZE 13
+#
+int
+main(void)
+{
+/* exec sql begin declare section */
+	 
+	 
+	 
+	   
+	 
+
+#line 27 "bytea.pgc"
+  struct bytea_1  { int len; char arr[ DATA_SIZE ]; }  send_buf [ 2 ] ;
+ 
+#line 28 "bytea.pgc"
+  struct bytea_2  { int len; char arr[ DATA_SIZE ]; }  recv_buf [ 2 ] ;
+ 
+#line 29 "bytea.pgc"
+  struct bytea_3  { int len; char arr[ DATA_SIZE ]; } * recv_vlen_buf ;
+ 
+#line 30 "bytea.pgc"
+  struct bytea_4  { int len; char arr[ DATA_SIZE - LACK_SIZE ]; }  recv_short_buf ;
+ 
+#line 31 "bytea.pgc"
+ int ind [ 2 ] ;
+/* exec sql end declare section */
+#line 32 "bytea.pgc"
+
+	int i, j, c;
+
+#define init() { \
+	for (i = 0; i < 2; ++i) \
+	{ \
+		memset(recv_buf[i].arr, 0x0, sizeof(recv_buf[i].arr)); \
+		recv_buf[i].len = 0; \
+		ind[i] = 0; \
+	} \
+	recv_vlen_buf = NULL, \
+	memset(recv_short_buf.arr, 0x0, sizeof(recv_short_buf.arr)); \
+} \
+while (0)
+	
+
+	ECPGdebug(1, stderr);
+
+	for (i = 0; i < 2; ++i)
+	{
+		for (j = 0, c = 0xff; (c == -1 ? c = 0xff : 1), j < DATA_SIZE; ++j, --c)
+			send_buf[i].arr[j] = c;
+
+		send_buf[i].len = DATA_SIZE;
+	}
+
+	{ ECPGconnect(__LINE__, 0, "ecpg1_regression" , NULL, NULL , NULL, 0); 
+#line 58 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 58 "bytea.pgc"
+
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "create table if not exists test ( data1 bytea , data2 bytea )", ECPGt_EOIT, ECPGt_EORT);
+#line 60 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 60 "bytea.pgc"
+
+
+	{ ECPGprepare(__LINE__, NULL, 0, "ins_stmt", "insert into test values(?,?)");
+#line 62 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 62 "bytea.pgc"
+
+	{ ECPGprepare(__LINE__, NULL, 0, "sel_stmt", "select data1,data2 from test");
+#line 63 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 63 "bytea.pgc"
+
+	ECPGallocate_desc(__LINE__, "idesc");
+#line 64 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();
+#line 64 "bytea.pgc"
+
+	ECPGallocate_desc(__LINE__, "odesc");
+#line 65 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();
+#line 65 "bytea.pgc"
+
+
+	/* Test for static sql statement with normal host variable, indicator */
+	init();
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "truncate test", ECPGt_EOIT, ECPGt_EORT);
+#line 69 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 69 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "insert into test values ( $1  , $2  )", 
+	ECPGt_bytea,&(send_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, 
+	ECPGt_bytea,&(send_buf[1]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EOIT, ECPGt_EORT);
+#line 70 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 70 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "select data1 , data2 from test", ECPGt_EOIT, 
+	ECPGt_bytea,&(recv_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_2), 
+	ECPGt_int,&(ind[0]),(long)1,(long)1,sizeof(int), 
+	ECPGt_bytea,&(recv_short_buf),(long)DATA_SIZE - LACK_SIZE,(long)1,sizeof(struct bytea_4), 
+	ECPGt_int,&(ind[1]),(long)1,(long)1,sizeof(int), ECPGt_EORT);
+#line 71 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 71 "bytea.pgc"
+
+	dump_binary(recv_buf[0].arr, recv_buf[0].len, ind[0]);
+	dump_binary(recv_short_buf.arr, recv_short_buf.len, ind[1]);
+
+	/* Test for variable length array */
+	init();
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "truncate test", ECPGt_EOIT, ECPGt_EORT);
+#line 77 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 77 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "insert into test values ( $1  , $2  )", 
+	ECPGt_bytea,&(send_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, 
+	ECPGt_bytea,&(send_buf[1]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EOIT, ECPGt_EORT);
+#line 78 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 78 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "insert into test values ( $1  , $2  )", 
+	ECPGt_bytea,&(send_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, 
+	ECPGt_bytea,&(send_buf[1]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EOIT, ECPGt_EORT);
+#line 79 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 79 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "select data1 from test", ECPGt_EOIT, 
+	ECPGt_bytea,&(recv_vlen_buf),(long)DATA_SIZE,(long)0,sizeof(struct bytea_3), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EORT);
+#line 80 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 80 "bytea.pgc"
+
+	dump_binary(recv_vlen_buf[0].arr, recv_vlen_buf[0].len, 0);
+	dump_binary(recv_vlen_buf[1].arr, recv_vlen_buf[1].len, 0);
+
+	/* Test for dynamic sql statement with normal host variable, indicator */
+	init();
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "truncate test", ECPGt_EOIT, ECPGt_EORT);
+#line 86 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 86 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_execute, "ins_stmt", 
+	ECPGt_bytea,&(send_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, 
+	ECPGt_bytea,&(send_buf[1]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EOIT, ECPGt_EORT);
+#line 87 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 87 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_execute, "sel_stmt", ECPGt_EOIT, 
+	ECPGt_bytea,&(recv_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_2), 
+	ECPGt_int,&(ind[0]),(long)1,(long)1,sizeof(int), 
+	ECPGt_bytea,&(recv_short_buf),(long)DATA_SIZE - LACK_SIZE,(long)1,sizeof(struct bytea_4), 
+	ECPGt_int,&(ind[1]),(long)1,(long)1,sizeof(int), ECPGt_EORT);
+#line 88 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 88 "bytea.pgc"
+
+	dump_binary(recv_buf[0].arr, recv_buf[0].len, ind[0]);
+	dump_binary(recv_short_buf.arr, recv_short_buf.len, ind[1]);
+
+	/* Test for dynamic sql statement with sql descriptor */
+	init();
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "truncate test", ECPGt_EOIT, ECPGt_EORT);
+#line 94 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 94 "bytea.pgc"
+
+	{ ECPGset_desc(__LINE__, "idesc", 1,ECPGd_data,
+	ECPGt_bytea,&(send_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), ECPGd_EODT);
+
+#line 95 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 95 "bytea.pgc"
+
+	{ ECPGset_desc(__LINE__, "idesc", 2,ECPGd_data,
+	ECPGt_bytea,&(send_buf[1]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_1), ECPGd_EODT);
+
+#line 96 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 96 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_execute, "ins_stmt", 
+	ECPGt_descriptor, "idesc", 1L, 1L, 1L, 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EOIT, ECPGt_EORT);
+#line 97 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 97 "bytea.pgc"
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_execute, "sel_stmt", ECPGt_EOIT, 
+	ECPGt_descriptor, "odesc", 1L, 1L, 1L, 
+	ECPGt_NO_INDICATOR, NULL , 0L, 0L, 0L, ECPGt_EORT);
+#line 98 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 98 "bytea.pgc"
+
+	{ ECPGget_desc(__LINE__, "odesc", 1,ECPGd_indicator,
+	ECPGt_int,&(ind[0]),(long)1,(long)1,sizeof(int), ECPGd_data,
+	ECPGt_bytea,&(recv_buf[0]),(long)DATA_SIZE,(long)1,sizeof(struct bytea_2), ECPGd_EODT);
+
+#line 99 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 99 "bytea.pgc"
+
+	{ ECPGget_desc(__LINE__, "odesc", 2,ECPGd_indicator,
+	ECPGt_int,&(ind[1]),(long)1,(long)1,sizeof(int), ECPGd_data,
+	ECPGt_bytea,&(recv_short_buf),(long)DATA_SIZE - LACK_SIZE,(long)1,sizeof(struct bytea_4), ECPGd_EODT);
+
+#line 100 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 100 "bytea.pgc"
+
+	dump_binary(recv_buf[0].arr, recv_buf[0].len, ind[0]);
+	dump_binary(recv_short_buf.arr, recv_short_buf.len, ind[1]);
+
+	{ ECPGdo(__LINE__, 0, 1, NULL, 0, ECPGst_normal, "drop table test", ECPGt_EOIT, ECPGt_EORT);
+#line 104 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 104 "bytea.pgc"
+
+	{ ECPGtrans(__LINE__, NULL, "commit");
+#line 105 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 105 "bytea.pgc"
+
+	{ ECPGdisconnect(__LINE__, "CURRENT");
+#line 106 "bytea.pgc"
+
+if (sqlca.sqlcode < 0) sqlprint();}
+#line 106 "bytea.pgc"
+
+
+	return 0;
+}
diff --git a/src/interfaces/ecpg/test/expected/sql-bytea.stderr b/src/interfaces/ecpg/test/expected/sql-bytea.stderr
new file mode 100644
index 0000000..fd188cc
--- /dev/null
+++ b/src/interfaces/ecpg/test/expected/sql-bytea.stderr
@@ -0,0 +1,160 @@
+[NO_PID]: ECPGdebug: set to 1
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ECPGconnect: opening database ecpg1_regression on <DEFAULT> port <DEFAULT>  
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 60: query: create table if not exists test ( data1 bytea , data2 bytea ); with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 60: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 60: OK: CREATE TABLE
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: prepare_common on line 62: name ins_stmt; query: "insert into test values($1,$2)"
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: prepare_common on line 63: name sel_stmt; query: "select data1,data2 from test"
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 69: query: truncate test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 69: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 69: OK: TRUNCATE TABLE
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 70: query: insert into test values ( $1  , $2  ); with 2 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 70: using PQexecParams
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 70: parameter 1 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 70: parameter 2 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 70: OK: INSERT 0 1
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 71: query: select data1 , data2 from test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 71: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 71: correctly got 1 tuples with 2 fields
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 71: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 71: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 77: query: truncate test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 77: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 77: OK: TRUNCATE TABLE
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 78: query: insert into test values ( $1  , $2  ); with 2 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 78: using PQexecParams
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 78: parameter 1 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 78: parameter 2 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 78: OK: INSERT 0 1
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 79: query: insert into test values ( $1  , $2  ); with 2 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 79: using PQexecParams
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 79: parameter 1 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 79: parameter 2 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 79: OK: INSERT 0 1
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 80: query: select data1 from test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 80: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 80: correctly got 2 tuples with 1 fields
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_store_result on line 80: allocating memory for 2 tuples
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 80: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 80: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 86: query: truncate test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 86: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 86: OK: TRUNCATE TABLE
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 87: query: insert into test values($1,$2); with 2 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 87: using PQexecPrepared for "insert into test values($1,$2)"
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 87: parameter 1 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 87: parameter 2 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 87: OK: INSERT 0 1
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 88: query: select data1,data2 from test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 88: using PQexecPrepared for "select data1,data2 from test"
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 88: correctly got 1 tuples with 2 fields
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 88: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 88: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 94: query: truncate test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 94: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 94: OK: TRUNCATE TABLE
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 97: query: insert into test values($1,$2); with 2 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 97: using PQexecPrepared for "insert into test values($1,$2)"
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 97: parameter 1 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_free_params on line 97: parameter 2 = ~}|{zyxwvutsrqponmlkjihgfedcba`_^]\[ZYXWVUTSRQPONMLKJIHGFEDCBA@?>=<;:9876543210/.-,+*)('&%$#"! 
+	
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 97: OK: INSERT 0 1
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 98: query: select data1,data2 from test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 98: using PQexecPrepared for "select data1,data2 from test"
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 98: correctly got 1 tuples with 2 fields
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 98: putting result (1 tuples) into descriptor odesc
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ECPGget_desc: reading items for tuple 1
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 99: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ECPGget_desc: reading items for tuple 2
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_get_data on line 100: RESULT: \xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100 offset: -1; array: no
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 104: query: drop table test; with 0 parameter(s) on connection ecpg1_regression
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_execute on line 104: using PQexec
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_process_output on line 104: OK: DROP TABLE
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ECPGtrans on line 105: action "commit"; connection "ecpg1_regression"
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: deallocate_one on line 0: name sel_stmt
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: deallocate_one on line 0: name ins_stmt
+[NO_PID]: sqlca: code: 0, state: 00000
+[NO_PID]: ecpg_finish: connection ecpg1_regression closed
+[NO_PID]: sqlca: code: 0, state: 00000
diff --git a/src/interfaces/ecpg/test/expected/sql-bytea.stdout b/src/interfaces/ecpg/test/expected/sql-bytea.stdout
new file mode 100644
index 0000000..4c9ad4c
--- /dev/null
+++ b/src/interfaces/ecpg/test/expected/sql-bytea.stdout
@@ -0,0 +1,8 @@
+len=512, ind=0, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100
+len=499, ind=512, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d
+len=512, ind=0, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100
+len=512, ind=0, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100
+len=512, ind=0, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100
+len=499, ind=512, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d
+len=512, ind=0, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100
+len=499, ind=512, data=0xfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d0c0b0a09080706050403020100fffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0dfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0bfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a09f9e9d9c9b9a999897969594939291908f8e8d8c8b8a898887868584838281807f7e7d7c7b7a797877767574737271706f6e6d6c6b6a696867666564636261605f5e5d5c5b5a595857565554535251504f4e4d4c4b4a494847464544434241403f3e3d3c3b3a393837363534333231302f2e2d2c2b2a292827262524232221201f1e1d1c1b1a191817161514131211100f0e0d
diff --git a/src/interfaces/ecpg/test/sql/Makefile b/src/interfaces/ecpg/test/sql/Makefile
index b7bc034..e173ed2 100644
--- a/src/interfaces/ecpg/test/sql/Makefile
+++ b/src/interfaces/ecpg/test/sql/Makefile
@@ -23,7 +23,8 @@ TESTS = array array.c \
         quote quote.c \
         show show.c \
         twophase twophase.c \
-        insupd insupd.c
+        insupd insupd.c \
+	bytea bytea.c
 
 all: $(TESTS)
 
diff --git a/src/interfaces/ecpg/test/sql/bytea.pgc b/src/interfaces/ecpg/test/sql/bytea.pgc
new file mode 100644
index 0000000..be275a2
--- /dev/null
+++ b/src/interfaces/ecpg/test/sql/bytea.pgc
@@ -0,0 +1,109 @@
+#include <stdlib.h>
+#include <string.h>
+#include <stdio.h>
+#include <time.h>
+
+exec sql include ../regression;
+exec sql whenever sqlerror sqlprint;
+
+static void
+dump_binary(char *buf, int len, int ind)
+{
+	int i;
+
+	printf("len=%d, ind=%d, data=0x", len, ind);
+	for (i = 0; i < len; ++i)
+		printf("%02x", 0xff & buf[i]);
+	printf("\n");
+}
+
+#define DATA_SIZE 0x200
+#define LACK_SIZE 13
+#
+int
+main(void)
+{
+exec sql begin declare section;
+	bytea send_buf[2][DATA_SIZE];
+	bytea recv_buf[2][DATA_SIZE];
+	bytea recv_vlen_buf[][DATA_SIZE];
+	bytea recv_short_buf[DATA_SIZE - LACK_SIZE];
+	int ind[2];
+exec sql end declare section;
+	int i, j, c;
+
+#define init() { \
+	for (i = 0; i < 2; ++i) \
+	{ \
+		memset(recv_buf[i].arr, 0x0, sizeof(recv_buf[i].arr)); \
+		recv_buf[i].len = 0; \
+		ind[i] = 0; \
+	} \
+	recv_vlen_buf = NULL, \
+	memset(recv_short_buf.arr, 0x0, sizeof(recv_short_buf.arr)); \
+} \
+while (0)
+	
+
+	ECPGdebug(1, stderr);
+
+	for (i = 0; i < 2; ++i)
+	{
+		for (j = 0, c = 0xff; (c == -1 ? c = 0xff : 1), j < DATA_SIZE; ++j, --c)
+			send_buf[i].arr[j] = c;
+
+		send_buf[i].len = DATA_SIZE;
+	}
+
+	exec sql connect to REGRESSDB1;
+
+	exec sql create table if not exists test (data1 bytea, data2 bytea);
+
+	exec sql prepare ins_stmt from "insert into test values(?,?)";
+	exec sql prepare sel_stmt from "select data1,data2 from test";
+	exec sql allocate descriptor idesc;
+	exec sql allocate descriptor odesc;
+
+	/* Test for static sql statement with normal host variable, indicator */
+	init();
+	exec sql truncate test;
+	exec sql insert into test values(:send_buf[0], :send_buf[1]);
+	exec sql select data1,data2 into :recv_buf[0]:ind[0], :recv_short_buf:ind[1] from test;
+	dump_binary(recv_buf[0].arr, recv_buf[0].len, ind[0]);
+	dump_binary(recv_short_buf.arr, recv_short_buf.len, ind[1]);
+
+	/* Test for variable length array */
+	init();
+	exec sql truncate test;
+	exec sql insert into test values(:send_buf[0], :send_buf[1]);
+	exec sql insert into test values(:send_buf[0], :send_buf[1]);
+	exec sql select data1 into :recv_vlen_buf from test;
+	dump_binary(recv_vlen_buf[0].arr, recv_vlen_buf[0].len, 0);
+	dump_binary(recv_vlen_buf[1].arr, recv_vlen_buf[1].len, 0);
+
+	/* Test for dynamic sql statement with normal host variable, indicator */
+	init();
+	exec sql truncate test;
+	exec sql execute ins_stmt using :send_buf[0], :send_buf[1];
+	exec sql execute sel_stmt into  :recv_buf[0]:ind[0], :recv_short_buf:ind[1];
+	dump_binary(recv_buf[0].arr, recv_buf[0].len, ind[0]);
+	dump_binary(recv_short_buf.arr, recv_short_buf.len, ind[1]);
+
+	/* Test for dynamic sql statement with sql descriptor */
+	init();
+	exec sql truncate test;
+	exec sql set descriptor idesc value 1 data = :send_buf[0];
+	exec sql set descriptor idesc value 2 data = :send_buf[1];
+	exec sql execute ins_stmt using sql descriptor idesc;
+	exec sql execute sel_stmt into  sql descriptor odesc;
+	exec sql get descriptor odesc value 1 :recv_buf[0] = data, :ind[0] = indicator;
+	exec sql get descriptor odesc value 2 :recv_short_buf = data, :ind[1] = indicator;
+	dump_binary(recv_buf[0].arr, recv_buf[0].len, ind[0]);
+	dump_binary(recv_short_buf.arr, recv_short_buf.len, ind[1]);
+
+	exec sql drop table test;
+	exec sql commit;
+	exec sql disconnect;
+
+	return 0;
+}
diff --git a/src/tools/pgindent/typedefs.list b/src/tools/pgindent/typedefs.list
index 9fe950b..dd6b69a 100644
--- a/src/tools/pgindent/typedefs.list
+++ b/src/tools/pgindent/typedefs.list
@@ -330,7 +330,6 @@ ClosePortalStmt
 ClosePtrType
 Clump
 ClusterInfo
-ClusterOption
 ClusterStmt
 CmdType
 CoalesceExpr
@@ -402,6 +401,7 @@ ConversionLocation
 ConvertRowtypeExpr
 CookedConstraint
 CopyDest
+CopyInsertMethod
 CopyState
 CopyStateData
 CopyStmt
@@ -1079,6 +1079,7 @@ JOBOBJECT_BASIC_LIMIT_INFORMATION
 JOBOBJECT_BASIC_UI_RESTRICTIONS
 JOBOBJECT_SECURITY_LIMIT_INFORMATION
 JitContext
+JitInstrumentation
 JitProviderCallbacks
 JitProviderCompileExprCB
 JitProviderInit
@@ -1174,6 +1175,7 @@ LWLockMinimallyPadded
 LWLockMode
 LWLockPadded
 LabelProvider
+LagTracker
 LargeObjectDesc
 LastAttnumInfo
 Latch
@@ -1184,6 +1186,7 @@ LexemeHashKey
 LexemeInfo
 LexemeKey
 LexizeData
+LibraryInfo
 Limit
 LimitPath
 LimitState
@@ -1403,8 +1406,11 @@ PATH
 PBOOL
 PCtxtHandle
 PFN
+PGAlignedBlock
+PGAlignedXLogBlock
 PGAsyncStatusType
 PGCALL2
+PGChecksummablePage
 PGContextVisibility
 PGEvent
 PGEventConnDestroy
@@ -1611,6 +1617,7 @@ ParallelHashJoinState
 ParallelHeapScanDesc
 ParallelHeapScanDescData
 ParallelIndexScanDesc
+ParallelReadyList
 ParallelSlot
 ParallelState
 ParallelWorkerContext
@@ -1664,6 +1671,8 @@ PartitionRangeDatumKind
 PartitionScheme
 PartitionSpec
 PartitionTupleRouting
+PartitionedRelPruneInfo
+PartitionedRelPruningData
 PartitionwiseAggregateType
 PasswordType
 Path
@@ -1781,6 +1790,7 @@ PredXactList
 PredXactListElement
 PredicateLockData
 PredicateLockTargetType
+PrepParallelRestorePtrType
 PrepareStmt
 PreparedParamsData
 PreparedStatement
@@ -1931,7 +1941,6 @@ Relation
 RelationData
 RelationPtr
 RelationSyncEntry
-RelativeTime
 RelcacheCallbackFunction
 RelfilenodeMapEntry
 RelfilenodeMapKey
@@ -2070,7 +2079,6 @@ ScanDirection
 ScanKey
 ScanKeyData
 ScanKeyword
-ScanStackEntry
 ScanState
 ScanTypeControl
 SchemaQuery
@@ -2081,12 +2089,14 @@ SecLabelStmt
 SeenRelsEntry
 SelectStmt
 Selectivity
+SemTPadded
 SemiAntiJoinFactors
 SeqScan
 SeqScanState
 SeqTable
 SeqTableData
 SerCommitSeqNo
+SerializedActiveRelMaps
 SerializedReindexState
 SerializedSnapshotData
 Session
@@ -2119,6 +2129,7 @@ SharedInvalRelmapMsg
 SharedInvalSmgrMsg
 SharedInvalSnapshotMsg
 SharedInvalidationMessage
+SharedJitInstrumentation
 SharedRecordTableEntry
 SharedRecordTableKey
 SharedRecordTypmodRegistry
@@ -2201,6 +2212,7 @@ SpGistPageOpaque
 SpGistPageOpaqueData
 SpGistScanOpaque
 SpGistScanOpaqueData
+SpGistSearchItem
 SpGistState
 SpGistTypeDesc
 SpecialJoinInfo
@@ -2300,7 +2312,6 @@ TSVectorParseState
 TSVectorStat
 TState
 TStoreState
-TTOffList
 TYPCATEGORY
 T_Action
 T_WorkerStatus
@@ -2344,8 +2355,6 @@ TidPath
 TidScan
 TidScanState
 TimeADT
-TimeInterval
-TimeIntervalData
 TimeLineHistoryCmd
 TimeLineHistoryEntry
 TimeLineID
@@ -2535,6 +2544,7 @@ WindowAgg
 WindowAggPath
 WindowAggState
 WindowClause
+WindowClauseSortData
 WindowDef
 WindowFunc
 WindowFuncExprState
@@ -3113,6 +3123,7 @@ slist_mutable_iter
 slist_node
 slock_t
 smgrid
+socket_set
 spgBulkDeleteState
 spgChooseIn
 spgChooseOut
