📄 pgtypes.c
字号:
case PG_TYPE_DATE: return "date"; case PG_TYPE_TIME: return "time"; case PG_TYPE_ABSTIME: return "abstime"; case PG_TYPE_DATETIME: if (PG_VERSION_GT(conn, 7.1)) return "timestamptz"; else if (PG_VERSION_LT(conn, 7.0)) return "datetime"; else return "timestamp"; case PG_TYPE_TIMESTAMP_NO_TMZONE: return "timestamp without time zone"; case PG_TYPE_TIMESTAMP: return "timestamp"; case PG_TYPE_MONEY: return "money"; case PG_TYPE_BOOL: return "bool"; case PG_TYPE_BYTEA: return "bytea"; case PG_TYPE_LO_UNDEFINED: return PG_TYPE_LO_NAME; default: /* hack until permanent type is available */ if (type == stmt->hdbc->lobj_type) return PG_TYPE_LO_NAME; /* * "unknown" can actually be used in alter table because it is * a real PG type! */ return "unknown"; }}static SQLSMALLINTgetNumericDecimalDigits(StatementClass *stmt, OID type, int col){ Int4 atttypmod = -1, default_decimal_digits = 6; QResultClass *result; ColumnInfoClass *flds; mylog("getNumericDecimalDigits: type=%d, col=%d\n", type, col); if (col < 0) return default_decimal_digits; result = SC_get_Curres(stmt); /* * Manual Result Sets -- use assigned column width (i.e., from * set_tuplefield_string) */ atttypmod = QR_get_atttypmod(result, col); if (atttypmod > -1) return (atttypmod & 0xffff); if (stmt->catalog_result) { flds = result->fields; if (flds) { int fsize = CI_get_fieldsize(flds, col); if (fsize > 0) return fsize; } return default_decimal_digits; } else { Int4 dsp_size = QR_get_display_size(result, col); if (dsp_size <= 0) return default_decimal_digits; if (dsp_size < 5) dsp_size = 5; return dsp_size; }}static Int4 /* PostgreSQL restritiction */getNumericColumnSize(StatementClass *stmt, OID type, int col){ Int4 atttypmod = -1, default_column_size = 28; QResultClass *result; ColumnInfoClass *flds; mylog("getNumericColumnSize: type=%d, col=%d\n", type, col); if (col < 0) return default_column_size; result = SC_get_Curres(stmt); /* * Manual Result Sets -- use assigned column width (i.e., from * set_tuplefield_string) */ atttypmod = QR_get_atttypmod(result, col); if (atttypmod > -1) return (atttypmod >> 16) & 0xffff; if (stmt->catalog_result) { flds = result->fields; if (flds) { int fsize = CI_get_fieldsize(flds, col); if (fsize > 0) return 2 * fsize; } return default_column_size; } else { Int4 dsp_size = QR_get_display_size(result, col); if (dsp_size <= 0) return default_column_size; dsp_size *= 2; if (dsp_size < 10) dsp_size = 10; return dsp_size; }}Int4getCharColumnSize(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; } 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 */ } } if (maxsize <= 0) return maxsize; /* The type is really unknown */ if (type == PG_TYPE_BPCHAR) { mylog("%s: BP_CHAR LONGEST: p = %d\n", func, p); if (p > 0) return p; } switch (type) { case PG_TYPE_BPCHAR: case PG_TYPE_VARCHAR: case PG_TYPE_TEXT: return maxsize; } if (handle_unknown_size_as == UNKNOWNS_AS_LONGEST) { mylog("%s: LONGEST: p = %d\n", func, p); if (p > 0) return p; } if (p > maxsize) maxsize = p; if (handle_unknown_size_as == UNKNOWNS_AS_MAX) return maxsize; else /* handle_unknown_size_as == DONT_KNOW */ return -1;}static SQLSMALLINTgetTimestampMaxDecimalDigits(StatementClass *stmt, OID type){ ConnectionClass *conn = SC_get_conn(stmt); if (PG_VERSION_LT(conn, 7.2)) return 0; return 6;}static SQLSMALLINTgetTimestampDecimalDigits(StatementClass *stmt, OID type, int col){ ConnectionClass *conn = SC_get_conn(stmt); Int4 atttypmod; QResultClass *result; mylog("getTimestampDecimalDigits: type=%d, col=%d\n", type, col); if (col < 0) return 0; if (PG_VERSION_LT(conn, 7.2)) return 0; result = SC_get_Curres(stmt); atttypmod = QR_get_atttypmod(result, col); mylog("atttypmod2=%d\n", atttypmod); return (atttypmod > -1 ? atttypmod : 6);}static SQLSMALLINTgetTimestampColumnSize(StatementClass *stmt, OID type, int col){ Int4 fixed, scale; mylog("getTimestampColumnSize: type=%d, col=%d\n", type, col); switch (type) { case PG_TYPE_TIME: fixed = 8; break; case PG_TYPE_TIME_WITH_TMZONE: fixed = 11; break; case PG_TYPE_TIMESTAMP_NO_TMZONE: fixed = 19; break; default: if (USE_ZONE) fixed = 22; else fixed = 19; break; } scale = getTimestampDecimalDigits(stmt, type, col); return (scale > 0) ? fixed + 1 + scale : fixed;}/* * This corresponds to "precision" in ODBC 2.x. * * For PG_TYPE_VARCHAR, PG_TYPE_BPCHAR, PG_TYPE_NUMERIC, SQLColumns will * override this length with the atttypmod length from pg_attribute . * * If col >= 0, then will attempt to get the info from the result set. * This is used for functions SQLDescribeCol and SQLColAttributes. */Int4 /* PostgreSQL restriction */pgtype_column_size(StatementClass *stmt, OID type, int col, int handle_unknown_size_as){ ConnectionClass *conn = SC_get_conn(stmt); ConnInfo *ci = &(conn->connInfo); switch (type) { case PG_TYPE_CHAR: return 1; case PG_TYPE_CHAR2: return 2; case PG_TYPE_CHAR4: return 4; case PG_TYPE_CHAR8: return 8; case PG_TYPE_NAME: { int value = 0; if (PG_VERSION_GT(conn, 7.4)) value = CC_get_max_idlen(conn);#ifdef NAME_FIELD_SIZE else value = NAME_FIELD_SIZE;#endif /* NAME_FIELD_SIZE */ if (0 == value) { if (PG_VERSION_GE(conn, 7.3)) value = NAMEDATALEN_V73; else value = NAMEDATALEN_V72; } return value; } case PG_TYPE_INT2: return 5; case PG_TYPE_OID: case PG_TYPE_XID: case PG_TYPE_INT4: return 10; case PG_TYPE_INT8: return 19; /* signed */ case PG_TYPE_NUMERIC: return getNumericColumnSize(stmt, type, col); case PG_TYPE_FLOAT4: case PG_TYPE_MONEY: return 7; case PG_TYPE_FLOAT8: return 15; case PG_TYPE_DATE: return 10; case PG_TYPE_TIME: return 8; case PG_TYPE_ABSTIME: case PG_TYPE_TIMESTAMP: return 22; case PG_TYPE_DATETIME: case PG_TYPE_TIMESTAMP_NO_TMZONE: /* return 22; */ return getTimestampColumnSize(stmt, type, col); case PG_TYPE_BOOL: return ci->true_is_minus1 ? 2 : 1; case PG_TYPE_LO_UNDEFINED: return SQL_NO_TOTAL; default: if (type == stmt->hdbc->lobj_type) /* hack until permanent * type is available */ return SQL_NO_TOTAL; if (PG_TYPE_BYTEA == type && ci->bytea_as_longvarbinary) return SQL_NO_TOTAL; /* Handle Character types and unknown types */ return getCharColumnSize(stmt, type, col, handle_unknown_size_as); }}/* * precision in ODBC 3.x. */SQLSMALLINTpgtype_precision(StatementClass *stmt, OID type, int col, int handle_unknown_size_as){ switch (type) { case PG_TYPE_NUMERIC: return getNumericColumnSize(stmt, type, col); case PG_TYPE_DATETIME: case PG_TYPE_TIMESTAMP_NO_TMZONE: return getTimestampDecimalDigits(stmt, type, col); } return -1;}Int4pgtype_display_size(StatementClass *stmt, OID type, int col, int handle_unknown_size_as){ int dsize; switch (type) { case PG_TYPE_INT2: return 6; case PG_TYPE_OID: case PG_TYPE_XID: return 10; case PG_TYPE_INT4: return 11; case PG_TYPE_INT8: return 20; /* signed: 19 digits + sign */ case PG_TYPE_NUMERIC: dsize = getNumericColumnSize(stmt, type, col); return dsize < 0 ? dsize : dsize + 2; case PG_TYPE_MONEY: return 15; /* ($9,999,999.99) */ case PG_TYPE_FLOAT4: return 13; case PG_TYPE_FLOAT8: return 22; /* Character types use regular precision */ default: return pgtype_column_size(stmt, type, col, handle_unknown_size_as); }}/* * The length in bytes of data transferred on an SQLGetData, SQLFetch, * or SQLFetchScroll operation if SQL_C_DEFAULT is specified. */Int4pgtype_buffer_length(StatementClass *stmt, OID type, int col, int handle_unknown_size_as){ ConnectionClass *conn = SC_get_conn(stmt); switch (type) { case PG_TYPE_INT2: return 2; /* sizeof(SQLSMALLINT) */ case PG_TYPE_OID: case PG_TYPE_XID: case PG_TYPE_INT4: return 4; /* sizeof(SQLINTEGER) */ case PG_TYPE_INT8: if (SQL_C_CHAR == pgtype_to_ctype(stmt, type)) return 20; /* signed: 19 digits + sign */ return 8; /* sizeof(SQLSBININT) */ case PG_TYPE_NUMERIC: return getNumericColumnSize(stmt, type, col) + 2; case PG_TYPE_FLOAT4: case PG_TYPE_MONEY: return 4; /* sizeof(SQLREAL) */ case PG_TYPE_FLOAT8: return 8; /* sizeof(SQLFLOAT) */ case PG_TYPE_DATE: case PG_TYPE_TIME: return 6; /* sizeof(DATE(TIME)_STRUCT) */ case PG_TYPE_ABSTIME: case PG_TYPE_DATETIME: case PG_TYPE_TIMESTAMP: case PG_TYPE_TIMESTAMP_NO_TMZONE: return 16; /* sizeof(TIMESTAMP_STRUCT) */ /* Character types use the default precision */ case PG_TYPE_VARCHAR: case PG_TYPE_BPCHAR: { int coef = 1; Int4 prec = pgtype_column_size(stmt, type, col, handle_unknown_size_as), maxvarc; if (SQL_NO_TOTAL == prec) return prec;#ifdef UNICODE_SUPPORT if (CC_is_in_unicode_driver(conn)) return prec * WCLEN;#endif /* UNICODE_SUPPORT */ /* after 7.2 */ if (PG_VERSION_GE(conn, 7.2)) coef = conn->mb_maxbyte_per_char; if (coef < 2 && (conn->connInfo).lf_conversion) /* CR -> CR/LF */ coef = 2; if (coef == 1) return prec; maxvarc = conn->connInfo.drivers.max_varchar_size; if (prec <= maxvarc && prec * coef > maxvarc) return maxvarc; return coef * prec; } default: return pgtype_column_size(stmt, type, col, handle_unknown_size_as); }}/* */Int4pgtype_desclength(StatementClass *stmt, OID type, int col, int handle_unknown_size_as){
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -