summaryrefslogtreecommitdiff
path: root/sql/field.cc
diff options
context:
space:
mode:
authorAlfranio Correia <alfranio.correia@sun.com>2009-12-17 00:09:52 +0000
committerAlfranio Correia <alfranio.correia@sun.com>2009-12-17 00:09:52 +0000
commit013cc668df5e553cc93527ae002ef1be3b6cdf10 (patch)
treee7d2073fc03c4d483a2006572c2db6a9fdee7ec1 /sql/field.cc
parent42cfe5b43c7165ebecb07f3e575b8fd94826c398 (diff)
parentd6e7402d426b8c07b577582007a98074d42a28d4 (diff)
downloadmariadb-git-013cc668df5e553cc93527ae002ef1be3b6cdf10.tar.gz
merging from 5.1 to rep+2 starting at gca(5.1, next-mr) == build@mysql.com-20091208092611-pbno5awyb0v38hs7
Fixed conflicts in: - binlog.binlog_unsafe - rpl.rpl_slow_query_log
Diffstat (limited to 'sql/field.cc')
-rw-r--r--sql/field.cc44
1 files changed, 44 insertions, 0 deletions
diff --git a/sql/field.cc b/sql/field.cc
index 3fa47e81c41..21082550ba7 100644
--- a/sql/field.cc
+++ b/sql/field.cc
@@ -2530,6 +2530,50 @@ Field_new_decimal::Field_new_decimal(uint32 len_arg,
}
+Field *Field_new_decimal::create_from_item (Item *item)
+{
+ uint8 dec= item->decimals;
+ uint8 intg= item->decimal_precision() - dec;
+ uint32 len= item->max_length;
+
+ DBUG_ASSERT (item->result_type() == DECIMAL_RESULT);
+
+ /*
+ Trying to put too many digits overall in a DECIMAL(prec,dec)
+ will always throw a warning. We must limit dec to
+ DECIMAL_MAX_SCALE however to prevent an assert() later.
+ */
+
+ if (dec > 0)
+ {
+ signed int overflow;
+
+ dec= min(dec, DECIMAL_MAX_SCALE);
+
+ /*
+ If the value still overflows the field with the corrected dec,
+ we'll throw out decimals rather than integers. This is still
+ bad and of course throws a truncation warning.
+ +1: for decimal point
+ */
+
+ const int required_length=
+ my_decimal_precision_to_length(intg + dec, dec,
+ item->unsigned_flag);
+
+ overflow= required_length - len;
+
+ if (overflow > 0)
+ dec= max(0, dec - overflow); // too long, discard fract
+ else
+ /* Corrected value fits. */
+ len= required_length;
+ }
+ return new Field_new_decimal(len, item->maybe_null, item->name,
+ dec, item->unsigned_flag);
+}
+
+
int Field_new_decimal::reset(void)
{
store_value(&decimal_zero);