static int getAtttypmodEtc(const StatementClass *stmt, int col, int *adtsize_or_longestlen) { int atttypmod = -1; if (NULL != adtsize_or_longestlen) *adtsize_or_longestlen = PG_ADT_UNSET; if (col >= 0) { const QResultClass *res; if (res = SC_get_Curres(stmt), NULL != res) { atttypmod = QR_get_atttypmod(res, col); if (NULL != adtsize_or_longestlen) { if (stmt->catalog_result) *adtsize_or_longestlen = QR_get_fieldsize(res, col); else { *adtsize_or_longestlen = QR_get_display_size(res, col); if (PG_TYPE_NUMERIC == QR_get_field_type(res, col) && atttypmod < 0 && *adtsize_or_longestlen > 0) { SQLULEN i; size_t sval, maxscale = 0; const char *tval, *sptr; for (i = 0; i < res->num_cached_rows; i++) { tval = QR_get_value_backend_text(res, i, col); if (NULL != tval) { sptr = strchr(tval, '.'); if (NULL != sptr) { sval = strlen(tval) - (sptr + 1 - tval); if (sval > maxscale) maxscale = sval; } } } *adtsize_or_longestlen += (int) (maxscale << 16); } } } } } return atttypmod; }
Int4 getCharColumnSize(StatementClass *stmt, OID type, int col, int handle_unknown_size_as) { CSTR func = "getCharColumnSize"; int p = -1, attlen = -1, adtsize = -1, maxsize; QResultClass *result; ConnectionClass *conn = SC_get_conn(stmt); ConnInfo *ci = &(conn->connInfo); mylog("%s: type=%d, col=%d, unknown = %d\n", func, type, col, handle_unknown_size_as); /* Assign Maximum size based on parameters */ switch (type) { case PG_TYPE_TEXT: if (ci->drivers.text_as_longvarchar) maxsize = ci->drivers.max_longvarchar_size; else maxsize = ci->drivers.max_varchar_size; break; case PG_TYPE_VARCHAR: case PG_TYPE_BPCHAR: maxsize = ci->drivers.max_varchar_size; break; default: if (ci->drivers.unknowns_as_longvarchar) maxsize = ci->drivers.max_longvarchar_size; else maxsize = ci->drivers.max_varchar_size; break; } #ifdef UNICODE_SUPPORT if (CC_is_in_unicode_driver(conn) && isSqlServr() && maxsize > 4000) maxsize = 4000; #endif /* UNICODE_SUPPORT */ if (maxsize == TEXT_FIELD_SIZE + 1) /* magic length for testing */ { if (PG_VERSION_GE(SC_get_conn(stmt), 7.1)) maxsize = 0; else maxsize = TEXT_FIELD_SIZE; } /* * Static ColumnSize (i.e., the Maximum ColumnSize of the datatype) This * has nothing to do with a result set. */ if (col < 0) return maxsize; if (result = SC_get_Curres(stmt), NULL == result) return maxsize; /* * Catalog Result Sets -- use assigned column width (i.e., from * set_tuplefield_string) */ adtsize = QR_get_fieldsize(result, col); if (stmt->catalog_result) { if (adtsize > 0) return adtsize; return maxsize; } p = QR_get_display_size(result, col); /* longest */ attlen = QR_get_atttypmod(result, col); /* Size is unknown -- handle according to parameter */ if (attlen > 0) /* maybe the length is known */ { if (attlen >= p) return attlen; switch (type) { case PG_TYPE_VARCHAR: case PG_TYPE_BPCHAR: #if (ODBCVER >= 0x0300) return attlen; #else if (CC_is_in_unicode_driver(conn) || conn->ms_jet) return attlen; return p; #endif /* ODBCVER */ } } /* The type is really unknown */ switch (handle_unknown_size_as) { case UNKNOWNS_AS_DONTKNOW: return -1; case UNKNOWNS_AS_LONGEST: mylog("%s: LONGEST: p = %d\n", func, p); if (p > 0) return p; break; case UNKNOWNS_AS_MAX: break; default: return -1; } if (maxsize <= 0) return maxsize; switch (type) { case PG_TYPE_BPCHAR: case PG_TYPE_VARCHAR: case PG_TYPE_TEXT: return maxsize; } if (p > maxsize) maxsize = p; return maxsize; }