⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 convert.c

📁 在Linux/Unix下面访问WINDOWS SQLSERVER 的ODBC驱动程序
💻 C
📖 第 1 页 / 共 5 页
字号:
					cr->u.Data2 = n;					n = 0;					break;				case 8+1 + 4+1 + 4:					if (c != '-')						return TDS_CONVERT_SYNTAX;					cr->u.Data3 = n;					n = 0;					break;				case 8+1 + 4+1 + 4+1 + 4:					/* skip last (optional) dash */					if (c == '-') {						if (--srclen < 32 + 3)							return TDS_CONVERT_SYNTAX;						c = (++src)[i];					}					/* fall through */				default:					n = n << 4;					if (c >= '0' && c <= '9')						n += c - '0';					else {						c &= 0x20 ^ 0xff;						if (c >= 'A' && c <= 'F')							n += c - ('A' - 10);						else							return TDS_CONVERT_SYNTAX;					}					if (i > (16 + 2) && !(i & 1)) {						cr->u.Data4[(i >> 1) - 10] = n;						n = 0;					}				}			}		}		return sizeof(TDS_UNIQUE);	default:		return TDS_CONVERT_NOAVAIL;		break;	}			/* end switch */}				/* tds_convert_char */static TDS_INTtds_convert_bit(int srctype, const TDS_CHAR * src, int desttype, CONV_RESULT * cr){	int canonic = src[0] ? 1 : 0;	switch (desttype) {	case TDS_CONVERT_CHAR:		if (cr->cc.len)			cr->cc.c[0] = '0' + canonic;		return 1;	case CASE_ALL_CHAR:		cr->c = (TDS_CHAR *) malloc(2);		test_alloc(cr->c);		cr->c[0] = '0' + canonic;		cr->c[1] = 0;		return 1;		break;	case CASE_ALL_BINARY:		return binary_to_result(src, 1, cr);		break;	case SYBINT1:		cr->ti = canonic;		return sizeof(TDS_TINYINT);		break;	case SYBINT2:		cr->si = canonic;		return sizeof(TDS_SMALLINT);		break;	case SYBINT4:		cr->i = canonic;		return sizeof(TDS_INT);		break;	case SYBINT8:		cr->bi = canonic;		return sizeof(TDS_INT8);		break;	case SYBFLT8:		cr->f = canonic;		return sizeof(TDS_FLOAT);		break;	case SYBREAL:		cr->r = (TDS_REAL) canonic;		return sizeof(TDS_REAL);		break;	case SYBBIT:	case SYBBITN:		cr->ti = src[0];		return sizeof(TDS_TINYINT);		break;	case SYBMONEY:	case SYBMONEY4:		return tds_convert_int1(SYBINT1, (src[0]) ? "\1" : "\0", desttype, cr);		break;	case SYBNUMERIC:	case SYBDECIMAL:		return stringz_to_numeric(canonic ? "1" : "0", cr);		break;		/* conversions not allowed */	case SYBUNIQUE:	case SYBDATETIME4:	case SYBDATETIME:	case SYBDATETIMN:	default:		break;	}	return TDS_CONVERT_NOAVAIL;}static TDS_INTtds_convert_int1(int srctype, const TDS_CHAR * src, int desttype, CONV_RESULT * cr){	TDS_TINYINT buf;	TDS_CHAR tmp_str[5];	buf = *((TDS_TINYINT *) src);	switch (desttype) {	case TDS_CONVERT_CHAR:	case CASE_ALL_CHAR:		sprintf(tmp_str, "%d", buf);		return string_to_result(tmp_str, cr);		break;	case CASE_ALL_BINARY:		return binary_to_result(src, 1, cr);		break;	case SYBINT1:		cr->ti = buf;		return sizeof(TDS_TINYINT);		break;	case SYBINT2:		cr->si = buf;		return sizeof(TDS_SMALLINT);		break;	case SYBINT4:		cr->i = buf;		return sizeof(TDS_INT);		break;	case SYBINT8:		cr->bi = buf;		return sizeof(TDS_INT8);		break;	case SYBBIT:	case SYBBITN:		cr->ti = buf ? 1 : 0;		return sizeof(TDS_TINYINT);		break;	case SYBFLT8:		cr->f = buf;		return sizeof(TDS_FLOAT);		break;	case SYBREAL:		cr->r = buf;		return sizeof(TDS_REAL);		break;	case SYBMONEY4:		cr->m4.mny4 = buf * 10000;		return sizeof(TDS_MONEY4);		break;	case SYBMONEY:		cr->m.mny = buf * 10000;		return sizeof(TDS_MONEY);		break;	case SYBNUMERIC:	case SYBDECIMAL:		sprintf(tmp_str, "%d", buf);		return stringz_to_numeric(tmp_str, cr);		break;		/* conversions not allowed */	case SYBUNIQUE:	case SYBDATETIME4:	case SYBDATETIME:	case SYBDATETIMN:	default:		break;	}	return TDS_CONVERT_NOAVAIL;}static TDS_INTtds_convert_int2(int srctype, const TDS_CHAR * src, int desttype, CONV_RESULT * cr){	TDS_SMALLINT buf;	TDS_CHAR tmp_str[16];	memcpy(&buf, src, sizeof(buf));	switch (desttype) {	case TDS_CONVERT_CHAR:	case CASE_ALL_CHAR:		sprintf(tmp_str, "%d", buf);		return string_to_result(tmp_str, cr);		break;	case CASE_ALL_BINARY:		return binary_to_result(src, 2, cr);		break;	case SYBINT1:		if (!IS_TINYINT(buf))			return TDS_CONVERT_OVERFLOW;		cr->ti = (TDS_TINYINT) buf;		return sizeof(TDS_TINYINT);		break;	case SYBINT2:		cr->si = buf;		return sizeof(TDS_SMALLINT);		break;	case SYBINT4:		cr->i = buf;		return sizeof(TDS_INT);		break;	case SYBINT8:		cr->bi = buf;		return sizeof(TDS_INT8);		break;	case SYBBIT:	case SYBBITN:		cr->ti = buf ? 1 : 0;		return sizeof(TDS_TINYINT);		break;	case SYBFLT8:		cr->f = buf;		return sizeof(TDS_FLOAT);		break;	case SYBREAL:		cr->r = buf;		return sizeof(TDS_REAL);		break;	case SYBMONEY4:		cr->m4.mny4 = buf * 10000;		return sizeof(TDS_MONEY4);		break;	case SYBMONEY:		cr->m.mny = buf * 10000;		return sizeof(TDS_MONEY);		break;	case SYBNUMERIC:	case SYBDECIMAL:		sprintf(tmp_str, "%d", buf);		return stringz_to_numeric(tmp_str, cr);		break;		/* conversions not allowed */	case SYBUNIQUE:	case SYBDATETIME4:	case SYBDATETIME:	case SYBDATETIMN:	default:		break;	}	return TDS_CONVERT_NOAVAIL;}static TDS_INTtds_convert_int4(int srctype, const TDS_CHAR * src, int desttype, CONV_RESULT * cr){	TDS_INT buf;	TDS_CHAR tmp_str[16];	memcpy(&buf, src, sizeof(buf));	switch (desttype) {	case TDS_CONVERT_CHAR:	case CASE_ALL_CHAR:		sprintf(tmp_str, "%d", buf);		return string_to_result(tmp_str, cr);		break;	case CASE_ALL_BINARY:		return binary_to_result(src, 4, cr);		break;	case SYBINT1:		if (!IS_TINYINT(buf))			return TDS_CONVERT_OVERFLOW;		cr->ti = buf;		return sizeof(TDS_TINYINT);		break;	case SYBINT2:		if (!IS_SMALLINT(buf))			return TDS_CONVERT_OVERFLOW;		cr->si = buf;		return sizeof(TDS_SMALLINT);		break;	case SYBINT4:		cr->i = buf;		return sizeof(TDS_INT);		break;	case SYBINT8:		cr->bi = buf;		return sizeof(TDS_INT8);		break;	case SYBBIT:	case SYBBITN:		cr->ti = buf ? 1 : 0;		return sizeof(TDS_TINYINT);		break;	case SYBFLT8:		cr->f = buf;		return sizeof(TDS_FLOAT);		break;	case SYBREAL:		cr->r = (TDS_REAL) buf;		return sizeof(TDS_REAL);		break;	case SYBMONEY4:		if (buf > 214748 || buf < -214748)			return TDS_CONVERT_OVERFLOW;		cr->m4.mny4 = buf * 10000;		return sizeof(TDS_MONEY4);		break;	case SYBMONEY:		cr->m.mny = (TDS_INT8) buf *10000;		return sizeof(TDS_MONEY);		break;	case SYBNUMERIC:	case SYBDECIMAL:		sprintf(tmp_str, "%d", buf);		return stringz_to_numeric(tmp_str, cr);		break;		/* conversions not allowed */	case SYBUNIQUE:	case SYBDATETIME4:	case SYBDATETIME:	case SYBDATETIMN:	default:		break;	}	return TDS_CONVERT_NOAVAIL;}static TDS_INTtds_convert_int8(int srctype, const TDS_CHAR * src, int desttype, CONV_RESULT * cr){	TDS_INT8 buf;	TDS_CHAR tmp_str[24];	memcpy(&buf, src, sizeof(buf));	switch (desttype) {	case TDS_CONVERT_CHAR:	case CASE_ALL_CHAR:		/* TODO: fix for all platform. Search for lltoa/_i64toa */#if defined(WIN32) 		_i64toa(buf, tmp_str, 10);#elif SIZEOF_LONG < 8		sprintf(tmp_str, "%" TDS_I64_FORMAT, buf);#else		sprintf(tmp_str, "%ld", buf);#endif		return string_to_result(tmp_str, cr);		break;	case CASE_ALL_BINARY:		return binary_to_result(src, sizeof(TDS_INT8), cr);		break;	case SYBINT1:		if (!IS_TINYINT(buf))			return TDS_CONVERT_OVERFLOW;		cr->ti = (TDS_TINYINT) buf;		return sizeof(TDS_TINYINT);		break;	case SYBINT2:		if (!IS_SMALLINT(buf))			return TDS_CONVERT_OVERFLOW;		cr->si = (TDS_SMALLINT) buf;		return sizeof(TDS_SMALLINT);		break;	case SYBINT4:		if (!IS_INT(buf))			return TDS_CONVERT_OVERFLOW;		cr->i = (TDS_INT) buf;		return sizeof(TDS_INT);		break;	case SYBINT8:		cr->bi = buf;		return sizeof(TDS_INT8);		break;	case SYBBIT:	case SYBBITN:		cr->ti = buf ? 1 : 0;		return sizeof(TDS_TINYINT);		break;	case SYBFLT8:		cr->f = (TDS_FLOAT) buf;		return sizeof(TDS_FLOAT);		break;	case SYBREAL:		cr->r = (TDS_REAL) buf;		return sizeof(TDS_REAL);		break;	case SYBMONEY4:		if (buf > 214748 || buf < -214748)			return TDS_CONVERT_OVERFLOW;		cr->m4.mny4 = (TDS_INT) (buf * 10000);		return sizeof(TDS_MONEY4);		break;	case SYBMONEY:		if (buf > (TDS_INT8_MAX / 10000) || buf < (TDS_INT8_MIN / 10000))			return TDS_CONVERT_OVERFLOW;		cr->m.mny = buf * 10000;		return sizeof(TDS_MONEY);		break;	case SYBNUMERIC:	case SYBDECIMAL:		/* TODO portability problem. See above */#if defined(WIN32) 		_i64toa(buf, tmp_str, 10);#elif SIZEOF_LONG < 8		sprintf(tmp_str, "%" TDS_I64_FORMAT, buf);#else		sprintf(tmp_str, "%ld", buf);#endif		return stringz_to_numeric(tmp_str, cr);		break;		/* conversions not allowed */	case SYBUNIQUE:	case SYBDATETIME4:	case SYBDATETIME:	case SYBDATETIMN:	default:		break;	}	return TDS_CONVERT_NOAVAIL;}static TDS_INTtds_convert_numeric(int srctype, const TDS_NUMERIC * src, TDS_INT srclen, int desttype, CONV_RESULT * cr){	char tmpstr[MAXPRECISION];	TDS_INT i, ret;	TDS_INT8 bi;	switch (desttype) {	case TDS_CONVERT_CHAR:	case CASE_ALL_CHAR:		if (tds_numeric_to_string(src, tmpstr) < 0)			return TDS_CONVERT_FAIL;		return string_to_result(tmpstr, cr);		break;	case CASE_ALL_BINARY:		return binary_to_result(src, sizeof(TDS_NUMERIC), cr);		break;	case SYBINT1:		cr->n = *src;		ret = tds_numeric_change_prec_scale(&(cr->n), 3, 0);		if (ret < 0)			return ret;		if (cr->n.array[1] || (cr->n.array[0] && cr->n.array[2]))			return TDS_CONVERT_OVERFLOW;		cr->ti = cr->n.array[2];		return sizeof(TDS_TINYINT);		break;	case SYBINT2:		cr->n = *src;		ret = tds_numeric_change_prec_scale(&(cr->n), 5, 0);		if (ret < 0)			return ret;		if (cr->n.array[1])			return TDS_CONVERT_OVERFLOW;		i = TDS_GET_UA2BE(&(cr->n.array[2]));		if (cr->n.array[0])			i = -i;		if (((i >> 15) ^ cr->n.array[0]) & 1)			return TDS_CONVERT_OVERFLOW;		cr->si = (TDS_SMALLINT) i;		return sizeof(TDS_SMALLINT);		break;	case SYBINT4:		cr->n = *src;		ret = tds_numeric_change_prec_scale(&(cr->n), 10, 0);		if (ret < 0)			return ret;		if (cr->n.array[1])			return TDS_CONVERT_OVERFLOW;		i = TDS_GET_UA4BE(&(cr->n.array[2]));		if (cr->n.array[0])			i = -i;		if (((i >> 31) ^ cr->n.array[0]) & 1)			return TDS_CONVERT_OVERFLOW;		cr->i = i;		return sizeof(TDS_INT);		break;	case SYBINT8:		cr->n = *src;		ret = tds_numeric_change_prec_scale(&(cr->n), 20, 0);		if (ret < 0)			return ret;		if (cr->n.array[1])			return TDS_CONVERT_OVERFLOW;		bi = TDS_GET_UA4BE(&(cr->n.array[2]));		bi = (bi << 32) + TDS_GET_UA4BE(&(cr->n.array[6]));		if (cr->n.array[0])			bi = -bi;		if (((bi >> 63) ^ cr->n.array[0]) & 1)			return TDS_CONVERT_OVERFLOW;		cr->bi = bi;		return sizeof(TDS_INT8);		break;	case SYBBIT:	case SYBBITN:		cr->ti = 0;		for (i = tds_numeric_bytes_per_prec[src->precision]; --i > 0;)			if (src->array[i] != 0) {				cr->ti = 1;				break;			}		return sizeof(TDS_TINYINT);		break;	case SYBNUMERIC:	case SYBDECIMAL:		{			unsigned char prec = cr->n.precision, scale = cr->n.scale;			cr->n = *src;			return tds_numeric_change_prec_scale(&(cr->n), prec, scale);		}		break;	case SYBFLT8:		if (tds_numeric_to_string(src, tmpstr) < 0)			return TDS_CONVERT_FAIL;		cr->f = atof(tmpstr);		return 8;		break;	case SYBREAL:		if (tds_numeric_to_string(src, tmpstr) < 0)			return TDS_CONVERT_FAIL;		cr->r = (TDS_REAL) atof(tmpstr);		return 4;		break;		/* TODO conversions to money */		/* conversions not allowed */	case SYBUNIQUE:	case SYBDATETIME4:	case SYBDATETIME:	case SYBDATETIMN:	default:		break;	}	return TDS_CONVERT_NOAVAIL;}static TDS_INTtds_convert_money4(int srctype, const TDS_CHAR * src, int srclen, int desttype, CONV_RESULT * cr){	TDS_MONEY4 mny;	long dollars, fraction;	char tmp_str[33];	char *p;	memcpy(&mny, src, sizeof(mny));	switch (desttype) {	case TDS_CONVERT_CHAR:	case CASE_ALL_CHAR:		/*		 * round to 2 decimal digits		 * rounding with dollars = (mny.mny4 + 5000) /10000		 * can give arithmetic overflow so I use		 * dollars = (mny.mny4/50 + 1)/2 		 */		/* TODO round also all conversions to int and from money ?? */		p = tmp_str;		if (mny.mny4 < 0) {			*p++ = '-';			/* here (-mny.mny4 / 50 + 1 ) / 2 can cause overflow in -mny.mny4 */			dollars = -(mny.mny4 / 50 - 1 ) / 2;		} else {			dollars = (mny.mny4 / 50 + 1 ) / 2;		}		/* print only 2 decimal digits as server does */		sprintf(p, "%ld.%02lu", dollars / 100, dollars % 100);		return string_to_result(tmp_str, cr);		break;	case CASE_ALL_BINARY:		return binary_to_result(src, sizeof(TDS_MONEY4), cr);		break;	case SYBINT1:		dollars = mny.mny4 / 10000;		if (!IS_TINYINT(dollars))			return TDS_CONVERT_OVERFLOW;		cr->ti = (TDS_TINYINT) dollars;		return sizeof(TDS_TINYINT);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -