~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/field_conv.cc

  • Committer: Brian Aker
  • Date: 2008-10-06 06:47:29 UTC
  • Revision ID: brian@tangent.org-20081006064729-2i9mhjkzyvow9xsm
RemoveĀ uint.

Show diffs side-by-side

added added

removed removed

Lines of Context:
24
24
    gives much more speed.
25
25
*/
26
26
 
27
 
#include "config.h"
28
 
#include <drizzled/error.h>
29
 
#include <drizzled/table.h>
30
 
#include <drizzled/session.h>
31
 
 
32
 
#include <drizzled/field/str.h>
33
 
#include <drizzled/field/num.h>
34
 
#include <drizzled/field/blob.h>
35
 
#include <drizzled/field/enum.h>
36
 
#include <drizzled/field/null.h>
37
 
#include <drizzled/field/date.h>
38
 
#include <drizzled/field/decimal.h>
39
 
#include <drizzled/field/real.h>
40
 
#include <drizzled/field/double.h>
41
 
#include <drizzled/field/long.h>
42
 
#include <drizzled/field/int64_t.h>
43
 
#include <drizzled/field/num.h>
44
 
#include <drizzled/field/timestamp.h>
45
 
#include <drizzled/field/datetime.h>
46
 
#include <drizzled/field/varstring.h>
47
 
 
48
 
namespace drizzled
49
 
{
50
 
 
51
 
static void do_field_eq(CopyField *copy)
52
 
{
53
 
  memcpy(copy->to_ptr, copy->from_ptr, copy->from_length);
54
 
}
55
 
 
56
 
static void do_field_1(CopyField *copy)
57
 
{
58
 
  copy->to_ptr[0]= copy->from_ptr[0];
59
 
}
60
 
 
61
 
static void do_field_2(CopyField *copy)
62
 
{
63
 
  copy->to_ptr[0]= copy->from_ptr[0];
64
 
  copy->to_ptr[1]= copy->from_ptr[1];
65
 
}
66
 
 
67
 
static void do_field_3(CopyField *copy)
68
 
{
69
 
  copy->to_ptr[0]= copy->from_ptr[0];
70
 
  copy->to_ptr[1]= copy->from_ptr[1];
71
 
  copy->to_ptr[2]= copy->from_ptr[2];
72
 
}
73
 
 
74
 
static void do_field_4(CopyField *copy)
75
 
{
76
 
  copy->to_ptr[0]= copy->from_ptr[0];
77
 
  copy->to_ptr[1]= copy->from_ptr[1];
78
 
  copy->to_ptr[2]= copy->from_ptr[2];
79
 
  copy->to_ptr[3]= copy->from_ptr[3];
80
 
}
81
 
 
82
 
static void do_field_6(CopyField *copy)
83
 
{                  // For blob field
84
 
  copy->to_ptr[0]= copy->from_ptr[0];
85
 
  copy->to_ptr[1]= copy->from_ptr[1];
86
 
  copy->to_ptr[2]= copy->from_ptr[2];
87
 
  copy->to_ptr[3]= copy->from_ptr[3];
88
 
  copy->to_ptr[4]= copy->from_ptr[4];
89
 
  copy->to_ptr[5]= copy->from_ptr[5];
90
 
}
91
 
 
92
 
static void do_field_8(CopyField *copy)
93
 
{
94
 
  copy->to_ptr[0]= copy->from_ptr[0];
95
 
  copy->to_ptr[1]= copy->from_ptr[1];
96
 
  copy->to_ptr[2]= copy->from_ptr[2];
97
 
  copy->to_ptr[3]= copy->from_ptr[3];
98
 
  copy->to_ptr[4]= copy->from_ptr[4];
99
 
  copy->to_ptr[5]= copy->from_ptr[5];
100
 
  copy->to_ptr[6]= copy->from_ptr[6];
101
 
  copy->to_ptr[7]= copy->from_ptr[7];
102
 
}
103
 
 
104
 
 
105
 
static void do_field_to_null_str(CopyField *copy)
 
27
#include <drizzled/server_includes.h>
 
28
 
 
29
static void do_field_eq(Copy_field *copy)
 
30
{
 
31
  memcpy(copy->to_ptr,copy->from_ptr,copy->from_length);
 
32
}
 
33
 
 
34
static void do_field_1(Copy_field *copy)
 
35
{
 
36
  copy->to_ptr[0]=copy->from_ptr[0];
 
37
}
 
38
 
 
39
static void do_field_2(Copy_field *copy)
 
40
{
 
41
  copy->to_ptr[0]=copy->from_ptr[0];
 
42
  copy->to_ptr[1]=copy->from_ptr[1];
 
43
}
 
44
 
 
45
static void do_field_3(Copy_field *copy)
 
46
{
 
47
  copy->to_ptr[0]=copy->from_ptr[0];
 
48
  copy->to_ptr[1]=copy->from_ptr[1];
 
49
  copy->to_ptr[2]=copy->from_ptr[2];
 
50
}
 
51
 
 
52
static void do_field_4(Copy_field *copy)
 
53
{
 
54
  copy->to_ptr[0]=copy->from_ptr[0];
 
55
  copy->to_ptr[1]=copy->from_ptr[1];
 
56
  copy->to_ptr[2]=copy->from_ptr[2];
 
57
  copy->to_ptr[3]=copy->from_ptr[3];
 
58
}
 
59
 
 
60
static void do_field_6(Copy_field *copy)
 
61
{                                               // For blob field
 
62
  copy->to_ptr[0]=copy->from_ptr[0];
 
63
  copy->to_ptr[1]=copy->from_ptr[1];
 
64
  copy->to_ptr[2]=copy->from_ptr[2];
 
65
  copy->to_ptr[3]=copy->from_ptr[3];
 
66
  copy->to_ptr[4]=copy->from_ptr[4];
 
67
  copy->to_ptr[5]=copy->from_ptr[5];
 
68
}
 
69
 
 
70
static void do_field_8(Copy_field *copy)
 
71
{
 
72
  copy->to_ptr[0]=copy->from_ptr[0];
 
73
  copy->to_ptr[1]=copy->from_ptr[1];
 
74
  copy->to_ptr[2]=copy->from_ptr[2];
 
75
  copy->to_ptr[3]=copy->from_ptr[3];
 
76
  copy->to_ptr[4]=copy->from_ptr[4];
 
77
  copy->to_ptr[5]=copy->from_ptr[5];
 
78
  copy->to_ptr[6]=copy->from_ptr[6];
 
79
  copy->to_ptr[7]=copy->from_ptr[7];
 
80
}
 
81
 
 
82
 
 
83
static void do_field_to_null_str(Copy_field *copy)
106
84
{
107
85
  if (*copy->from_null_ptr & copy->from_bit)
108
86
  {
109
87
    memset(copy->to_ptr, 0, copy->from_length);
110
 
    copy->to_null_ptr[0]= 1;  // Always bit 1
 
88
    copy->to_null_ptr[0]=1;                     // Always bit 1
111
89
  }
112
90
  else
113
91
  {
114
 
    copy->to_null_ptr[0]= 0;
115
 
    memcpy(copy->to_ptr, copy->from_ptr, copy->from_length);
 
92
    copy->to_null_ptr[0]=0;
 
93
    memcpy(copy->to_ptr,copy->from_ptr,copy->from_length);
116
94
  }
117
95
}
118
96
 
119
97
 
120
 
static void do_outer_field_to_null_str(CopyField *copy)
 
98
static void do_outer_field_to_null_str(Copy_field *copy)
121
99
{
122
100
  if (*copy->null_row ||
123
101
      (copy->from_null_ptr && (*copy->from_null_ptr & copy->from_bit)))
124
102
  {
125
103
    memset(copy->to_ptr, 0, copy->from_length);
126
 
    copy->to_null_ptr[0]= 1;  // Always bit 1
 
104
    copy->to_null_ptr[0]=1;                     // Always bit 1
127
105
  }
128
106
  else
129
107
  {
130
 
    copy->to_null_ptr[0]= 0;
131
 
    memcpy(copy->to_ptr, copy->from_ptr, copy->from_length);
 
108
    copy->to_null_ptr[0]=0;
 
109
    memcpy(copy->to_ptr,copy->from_ptr,copy->from_length);
132
110
  }
133
111
}
134
112
 
210
188
}
211
189
 
212
190
 
213
 
static void do_skip(CopyField *)
 
191
static void do_skip(Copy_field *copy __attribute__((unused)))
214
192
{
215
193
}
216
194
 
217
195
 
218
 
static void do_copy_null(CopyField *copy)
 
196
static void do_copy_null(Copy_field *copy)
219
197
{
220
198
  if (*copy->from_null_ptr & copy->from_bit)
221
199
  {
222
 
    *copy->to_null_ptr|= copy->to_bit;
 
200
    *copy->to_null_ptr|=copy->to_bit;
223
201
    copy->to_field->reset();
224
202
  }
225
203
  else
230
208
}
231
209
 
232
210
 
233
 
static void do_outer_field_null(CopyField *copy)
 
211
static void do_outer_field_null(Copy_field *copy)
234
212
{
235
213
  if (*copy->null_row ||
236
214
      (copy->from_null_ptr && (*copy->from_null_ptr & copy->from_bit)))
246
224
}
247
225
 
248
226
 
249
 
static void do_copy_not_null(CopyField *copy)
 
227
static void do_copy_not_null(Copy_field *copy)
250
228
{
251
229
  if (*copy->from_null_ptr & copy->from_bit)
252
230
  {
259
237
}
260
238
 
261
239
 
262
 
static void do_copy_maybe_null(CopyField *copy)
 
240
static void do_copy_maybe_null(Copy_field *copy)
263
241
{
264
242
  *copy->to_null_ptr&= ~copy->to_bit;
265
243
  (copy->do_copy2)(copy);
267
245
 
268
246
/* timestamp and next_number has special handling in case of NULL values */
269
247
 
270
 
static void do_copy_timestamp(CopyField *copy)
 
248
static void do_copy_timestamp(Copy_field *copy)
271
249
{
272
250
  if (*copy->from_null_ptr & copy->from_bit)
273
251
  {
279
257
}
280
258
 
281
259
 
282
 
static void do_copy_next_number(CopyField *copy)
 
260
static void do_copy_next_number(Copy_field *copy)
283
261
{
284
262
  if (*copy->from_null_ptr & copy->from_bit)
285
263
  {
292
270
}
293
271
 
294
272
 
295
 
static void do_copy_blob(CopyField *copy)
 
273
static void do_copy_blob(Copy_field *copy)
296
274
{
297
 
  ulong length= ((Field_blob*) copy->from_field)->get_length();
 
275
  ulong length=((Field_blob*) copy->from_field)->get_length();
298
276
  ((Field_blob*) copy->to_field)->store_length(length);
299
 
  memcpy(copy->to_ptr, copy->from_ptr, sizeof(char*));
 
277
  memcpy(copy->to_ptr,copy->from_ptr,sizeof(char*));
300
278
}
301
279
 
302
 
static void do_conv_blob(CopyField *copy)
 
280
static void do_conv_blob(Copy_field *copy)
303
281
{
304
282
  copy->from_field->val_str(&copy->tmp);
305
283
  ((Field_blob *) copy->to_field)->store(copy->tmp.ptr(),
306
 
                                         copy->tmp.length(),
307
 
                                         copy->tmp.charset());
 
284
                                         copy->tmp.length(),
 
285
                                         copy->tmp.charset());
308
286
}
309
287
 
310
288
/** Save blob in copy->tmp for GROUP BY. */
311
289
 
312
 
static void do_save_blob(CopyField *copy)
 
290
static void do_save_blob(Copy_field *copy)
313
291
{
314
292
  char buff[MAX_FIELD_WIDTH];
315
 
  String res(buff, sizeof(buff), copy->tmp.charset());
 
293
  String res(buff,sizeof(buff),copy->tmp.charset());
316
294
  copy->from_field->val_str(&res);
317
295
  copy->tmp.copy(res);
318
296
  ((Field_blob *) copy->to_field)->store(copy->tmp.ptr(),
319
 
                                         copy->tmp.length(),
320
 
                                         copy->tmp.charset());
 
297
                                         copy->tmp.length(),
 
298
                                         copy->tmp.charset());
321
299
}
322
300
 
323
301
 
324
 
static void do_field_string(CopyField *copy)
 
302
static void do_field_string(Copy_field *copy)
325
303
{
326
304
  char buff[MAX_FIELD_WIDTH];
327
305
  copy->tmp.set_quick(buff,sizeof(buff),copy->tmp.charset());
331
309
}
332
310
 
333
311
 
334
 
static void do_field_enum(CopyField *copy)
 
312
static void do_field_enum(Copy_field *copy)
335
313
{
336
314
  if (copy->from_field->val_int() == 0)
337
315
    ((Field_enum *) copy->to_field)->store_type((uint64_t) 0);
340
318
}
341
319
 
342
320
 
343
 
static void do_field_int(CopyField *copy)
 
321
static void do_field_int(Copy_field *copy)
344
322
{
345
323
  int64_t value= copy->from_field->val_int();
346
324
  copy->to_field->store(value,
347
325
                        test(copy->from_field->flags & UNSIGNED_FLAG));
348
326
}
349
327
 
350
 
static void do_field_real(CopyField *copy)
 
328
static void do_field_real(Copy_field *copy)
351
329
{
352
330
  double value=copy->from_field->val_real();
353
331
  copy->to_field->store(value);
354
332
}
355
333
 
356
334
 
357
 
static void do_field_decimal(CopyField *copy)
 
335
static void do_field_decimal(Copy_field *copy)
358
336
{
359
337
  my_decimal value;
360
338
  copy->to_field->store_decimal(copy->from_field->val_decimal(&value));
366
344
  from string.
367
345
*/
368
346
 
369
 
static void do_cut_string(CopyField *copy)
 
347
static void do_cut_string(Copy_field *copy)
370
348
{
371
349
  const CHARSET_INFO * const cs= copy->from_field->charset();
372
350
  memcpy(copy->to_ptr,copy->from_ptr,copy->to_length);
388
366
  from string.
389
367
*/
390
368
 
391
 
static void do_cut_string_complex(CopyField *copy)
 
369
static void do_cut_string_complex(Copy_field *copy)
392
370
{                                               // Shorter string field
393
371
  int well_formed_error;
394
372
  const CHARSET_INFO * const cs= copy->from_field->charset();
395
373
  const unsigned char *from_end= copy->from_ptr + copy->from_length;
396
374
  uint32_t copy_length= cs->cset->well_formed_len(cs,
397
375
                                              (char*) copy->from_ptr,
398
 
                                              (char*) from_end,
 
376
                                              (char*) from_end, 
399
377
                                              copy->to_length / cs->mbmaxlen,
400
378
                                              &well_formed_error);
401
379
  if (copy->to_length < copy_length)
420
398
 
421
399
 
422
400
 
423
 
static void do_expand_binary(CopyField *copy)
424
 
{
425
 
  const CHARSET_INFO * const cs= copy->from_field->charset();
426
 
  memcpy(copy->to_ptr, copy->from_ptr, copy->from_length);
427
 
  cs->cset->fill(cs, (char*) copy->to_ptr+copy->from_length,
428
 
                 copy->to_length-copy->from_length, '\0');
429
 
}
430
 
 
431
 
 
432
 
 
433
 
static void do_expand_string(CopyField *copy)
434
 
{
435
 
  const CHARSET_INFO * const cs= copy->from_field->charset();
436
 
  memcpy(copy->to_ptr,copy->from_ptr,copy->from_length);
437
 
  cs->cset->fill(cs, (char*) copy->to_ptr+copy->from_length,
438
 
                 copy->to_length-copy->from_length, ' ');
439
 
}
440
 
 
441
 
 
442
 
static void do_varstring1(CopyField *copy)
443
 
{
444
 
  uint32_t length= (uint32_t) *(unsigned char*) copy->from_ptr;
 
401
static void do_expand_binary(Copy_field *copy)
 
402
{
 
403
  const CHARSET_INFO * const cs= copy->from_field->charset();
 
404
  memcpy(copy->to_ptr,copy->from_ptr,copy->from_length);
 
405
  cs->cset->fill(cs, (char*) copy->to_ptr+copy->from_length,
 
406
                     copy->to_length-copy->from_length, '\0');
 
407
}
 
408
 
 
409
 
 
410
 
 
411
static void do_expand_string(Copy_field *copy)
 
412
{
 
413
  const CHARSET_INFO * const cs= copy->from_field->charset();
 
414
  memcpy(copy->to_ptr,copy->from_ptr,copy->from_length);
 
415
  cs->cset->fill(cs, (char*) copy->to_ptr+copy->from_length,
 
416
                     copy->to_length-copy->from_length, ' ');
 
417
}
 
418
 
 
419
 
 
420
static void do_varstring1(Copy_field *copy)
 
421
{
 
422
  uint32_t length= (uint) *(unsigned char*) copy->from_ptr;
445
423
  if (length > copy->to_length- 1)
446
424
  {
447
 
    length= copy->to_length - 1;
 
425
    length=copy->to_length - 1;
448
426
    if (copy->from_field->table->in_use->count_cuted_fields)
449
427
      copy->to_field->set_warning(DRIZZLE_ERROR::WARN_LEVEL_WARN,
450
428
                                  ER_WARN_DATA_TRUNCATED, 1);
454
432
}
455
433
 
456
434
 
457
 
static void do_varstring1_mb(CopyField *copy)
 
435
static void do_varstring1_mb(Copy_field *copy)
458
436
{
459
437
  int well_formed_error;
460
438
  const CHARSET_INFO * const cs= copy->from_field->charset();
461
 
  uint32_t from_length= (uint32_t) *(unsigned char*) copy->from_ptr;
 
439
  uint32_t from_length= (uint) *(unsigned char*) copy->from_ptr;
462
440
  const unsigned char *from_ptr= copy->from_ptr + 1;
463
441
  uint32_t to_char_length= (copy->to_length - 1) / cs->mbmaxlen;
464
442
  uint32_t length= cs->cset->well_formed_len(cs, (char*) from_ptr,
466
444
                                         to_char_length, &well_formed_error);
467
445
  if (length < from_length)
468
446
  {
469
 
    if (current_session->count_cuted_fields)
 
447
    if (current_thd->count_cuted_fields)
470
448
      copy->to_field->set_warning(DRIZZLE_ERROR::WARN_LEVEL_WARN,
471
449
                                  ER_WARN_DATA_TRUNCATED, 1);
472
450
  }
475
453
}
476
454
 
477
455
 
478
 
static void do_varstring2(CopyField *copy)
 
456
static void do_varstring2(Copy_field *copy)
479
457
{
480
 
  uint32_t length= uint2korr(copy->from_ptr);
 
458
  uint32_t length=uint2korr(copy->from_ptr);
481
459
  if (length > copy->to_length- HA_KEY_BLOB_LENGTH)
482
460
  {
483
461
    length=copy->to_length-HA_KEY_BLOB_LENGTH;
491
469
}
492
470
 
493
471
 
494
 
static void do_varstring2_mb(CopyField *copy)
 
472
static void do_varstring2_mb(Copy_field *copy)
495
473
{
496
474
  int well_formed_error;
497
475
  const CHARSET_INFO * const cs= copy->from_field->charset();
499
477
  uint32_t from_length= uint2korr(copy->from_ptr);
500
478
  const unsigned char *from_beg= copy->from_ptr + HA_KEY_BLOB_LENGTH;
501
479
  uint32_t length= cs->cset->well_formed_len(cs, (char*) from_beg,
502
 
                                             (char*) from_beg + from_length,
503
 
                                             char_length, &well_formed_error);
 
480
                                         (char*) from_beg + from_length,
 
481
                                         char_length, &well_formed_error);
504
482
  if (length < from_length)
505
483
  {
506
 
    if (current_session->count_cuted_fields)
 
484
    if (current_thd->count_cuted_fields)
507
485
      copy->to_field->set_warning(DRIZZLE_ERROR::WARN_LEVEL_WARN,
508
486
                                  ER_WARN_DATA_TRUNCATED, 1);
509
 
  }
 
487
  }  
510
488
  int2store(copy->to_ptr, length);
511
489
  memcpy(copy->to_ptr+HA_KEY_BLOB_LENGTH, from_beg, length);
512
490
}
513
 
 
 
491
 
514
492
 
515
493
/***************************************************************************
516
 
** The different functions that fills in a CopyField class
 
494
** The different functions that fills in a Copy_field class
517
495
***************************************************************************/
518
496
 
519
497
/**
524
502
  The 'to' buffer should have a size of field->pack_length()+1
525
503
*/
526
504
 
527
 
void CopyField::set(unsigned char *to,Field *from)
 
505
void Copy_field::set(unsigned char *to,Field *from)
528
506
{
529
 
  from_ptr= from->ptr;
530
 
  to_ptr= to;
531
 
  from_length= from->pack_length();
 
507
  from_ptr=from->ptr;
 
508
  to_ptr=to;
 
509
  from_length=from->pack_length();
532
510
  if (from->maybe_null())
533
511
  {
534
 
    from_null_ptr= from->null_ptr;
535
 
    from_bit= from->null_bit;
536
 
    to_ptr[0]= 1;                             // Null as default value
537
 
    to_null_ptr= (unsigned char*) to_ptr++;
538
 
    to_bit= 1;
 
512
    from_null_ptr=from->null_ptr;
 
513
    from_bit=     from->null_bit;
 
514
    to_ptr[0]=    1;                            // Null as default value
 
515
    to_null_ptr=  (unsigned char*) to_ptr++;
 
516
    to_bit=       1;
539
517
    if (from->table->maybe_null)
540
518
    {
541
 
      null_row= &from->table->null_row;
542
 
      do_copy= do_outer_field_to_null_str;
 
519
      null_row=   &from->table->null_row;
 
520
      do_copy=    do_outer_field_to_null_str;
543
521
    }
544
522
    else
545
 
      do_copy= do_field_to_null_str;
 
523
      do_copy=    do_field_to_null_str;
546
524
  }
547
525
  else
548
526
  {
549
 
    to_null_ptr= 0;                           // For easy debugging
550
 
    do_copy= do_field_eq;
 
527
    to_null_ptr=  0;                            // For easy debugging
 
528
    do_copy=      do_field_eq;
551
529
  }
552
530
}
553
531
 
554
532
 
555
533
/*
556
 
  To do:
 
534
  To do: 
557
535
 
558
536
  If 'save\ is set to true and the 'from' is a blob field, do_copy is set to
559
537
  do_save_blob rather than do_conv_blob.  The only differences between them
560
538
  appears to be:
561
539
 
562
 
  - do_save_blob allocates and uses an intermediate buffer before calling
563
 
    Field_blob::store. Is this in order to trigger the call to
 
540
  - do_save_blob allocates and uses an intermediate buffer before calling 
 
541
    Field_blob::store. Is this in order to trigger the call to 
564
542
    well_formed_copy_nchars, by changing the pointer copy->tmp.ptr()?
565
543
    That call will take place anyway in all known cases.
566
544
 
567
 
  - The above causes a truncation to MAX_FIELD_WIDTH. Is this the intended
 
545
  - The above causes a truncation to MAX_FIELD_WIDTH. Is this the intended 
568
546
    effect? Truncation is handled by well_formed_copy_nchars anyway.
569
547
 */
570
 
void CopyField::set(Field *to,Field *from,bool save)
 
548
void Copy_field::set(Field *to,Field *from,bool save)
571
549
{
572
550
  if (to->type() == DRIZZLE_TYPE_NULL)
573
551
  {
574
 
    to_null_ptr= 0;           // For easy debugging
575
 
    to_ptr= 0;
576
 
    do_copy= do_skip;
 
552
    to_null_ptr=0;                              // For easy debugging
 
553
    to_ptr=0;
 
554
    do_copy=do_skip;
577
555
    return;
578
556
  }
579
 
  from_field= from;
580
 
  to_field= to;
581
 
  from_ptr= from->ptr;
582
 
  from_length= from->pack_length();
583
 
  to_ptr= to->ptr;
584
 
  to_length= to_field->pack_length();
 
557
  from_field=from;
 
558
  to_field=to;
 
559
  from_ptr=from->ptr;
 
560
  from_length=from->pack_length();
 
561
  to_ptr=  to->ptr;
 
562
  to_length=to_field->pack_length();
585
563
 
586
564
  // set up null handling
587
 
  from_null_ptr= to_null_ptr= 0;
 
565
  from_null_ptr=to_null_ptr=0;
588
566
  if (from->maybe_null())
589
567
  {
590
 
    from_null_ptr= from->null_ptr;
591
 
    from_bit= from->null_bit;
 
568
    from_null_ptr=      from->null_ptr;
 
569
    from_bit=           from->null_bit;
592
570
    if (to_field->real_maybe_null())
593
571
    {
594
 
      to_null_ptr= to->null_ptr;
595
 
      to_bit= to->null_bit;
 
572
      to_null_ptr=      to->null_ptr;
 
573
      to_bit=           to->null_bit;
596
574
      if (from_null_ptr)
597
 
        do_copy= do_copy_null;
 
575
        do_copy=        do_copy_null;
598
576
      else
599
577
      {
600
 
        null_row= &from->table->null_row;
601
 
        do_copy= do_outer_field_null;
 
578
        null_row=       &from->table->null_row;
 
579
        do_copy=        do_outer_field_null;
602
580
      }
603
581
    }
604
582
    else
613
591
  }
614
592
  else if (to_field->real_maybe_null())
615
593
  {
616
 
    to_null_ptr= to->null_ptr;
617
 
    to_bit= to->null_bit;
 
594
    to_null_ptr=        to->null_ptr;
 
595
    to_bit=             to->null_bit;
618
596
    do_copy= do_copy_maybe_null;
619
597
  }
620
598
  else
621
 
   do_copy= 0;
 
599
   do_copy=0;
622
600
 
623
601
  if ((to->flags & BLOB_FLAG) && save)
624
602
    do_copy2= do_save_blob;
625
603
  else
626
604
    do_copy2= get_copy_func(to,from);
627
 
  if (!do_copy)         // Not null
628
 
    do_copy= do_copy2;
 
605
  if (!do_copy)                                 // Not null
 
606
    do_copy=do_copy2;
629
607
}
630
608
 
631
609
 
632
 
CopyField::Copy_func *
633
 
CopyField::get_copy_func(Field *to,Field *from)
 
610
Copy_field::Copy_func *
 
611
Copy_field::get_copy_func(Field *to,Field *from)
634
612
{
635
613
  bool compatible_db_low_byte_first= (to->table->s->db_low_byte_first ==
636
614
                                     from->table->s->db_low_byte_first);
641
619
    if (from_length != to_length || !compatible_db_low_byte_first)
642
620
    {
643
621
      // Correct pointer to point at char pointer
644
 
      to_ptr+= to_length - to->table->s->blob_ptr_size;
 
622
      to_ptr+=   to_length - to->table->s->blob_ptr_size;
645
623
      from_ptr+= from_length- from->table->s->blob_ptr_size;
646
624
      return do_copy_blob;
647
625
    }
650
628
  {
651
629
    if (to->result_type() == DECIMAL_RESULT)
652
630
      return do_field_decimal;
653
 
      
654
631
    // Check if identical fields
655
632
    if (from->result_type() == STRING_RESULT)
656
633
    {
660
637
      */
661
638
      if (to->real_type() != from->real_type() ||
662
639
          !compatible_db_low_byte_first ||
663
 
          (((to->table->in_use->variables.sql_mode & (MODE_NO_ZERO_DATE | MODE_INVALID_DATES)) && to->type() == DRIZZLE_TYPE_DATE) || to->type() == DRIZZLE_TYPE_DATETIME))
 
640
          (((to->table->in_use->variables.sql_mode & (MODE_NO_ZERO_DATE | MODE_INVALID_DATES)) && to->type() == DRIZZLE_TYPE_NEWDATE) || to->type() == DRIZZLE_TYPE_DATETIME))
664
641
      {
665
 
        if (from->real_type() == DRIZZLE_TYPE_ENUM)
666
 
        {
667
 
          if (to->result_type() != STRING_RESULT)
668
 
          {
669
 
            return do_field_int;  // Convert SET to number
670
 
          }
671
 
          
672
 
          return do_field_string;
673
 
        }
 
642
        if (from->real_type() == DRIZZLE_TYPE_ENUM)
 
643
          if (to->result_type() != STRING_RESULT)
 
644
            return do_field_int;                // Convert SET to number
 
645
        return do_field_string;
674
646
      }
675
 
      
676
647
      if (to->real_type() == DRIZZLE_TYPE_ENUM)
677
648
      {
678
 
        if (!to->eq_def(from))
 
649
        if (!to->eq_def(from))
679
650
        {
680
651
          if (from->real_type() == DRIZZLE_TYPE_ENUM &&
681
652
              to->real_type() == DRIZZLE_TYPE_ENUM)
685
656
        }
686
657
      }
687
658
      else if (to->charset() != from->charset())
688
 
        return do_field_string;
 
659
        return do_field_string;
689
660
      else if (to->real_type() == DRIZZLE_TYPE_VARCHAR)
690
661
      {
691
662
        if (((Field_varstring*) to)->length_bytes !=
692
663
            ((Field_varstring*) from)->length_bytes)
693
 
        {
694
664
          return do_field_string;
695
 
        }
696
 
        
697
665
        if (to_length != from_length)
698
 
        {
699
666
          return (((Field_varstring*) to)->length_bytes == 1 ?
700
667
                  (from->charset()->mbmaxlen == 1 ? do_varstring1 :
701
668
                                                    do_varstring1_mb) :
702
669
                  (from->charset()->mbmaxlen == 1 ? do_varstring2 :
703
670
                                                    do_varstring2_mb));
704
 
        }
705
671
      }
706
672
      else if (to_length < from_length)
707
 
      {
708
 
        return (from->charset()->mbmaxlen == 1 ?
 
673
        return (from->charset()->mbmaxlen == 1 ?
709
674
                do_cut_string : do_cut_string_complex);
710
 
      }
711
675
      else if (to_length > from_length)
712
676
      {
713
677
        if (to->charset() == &my_charset_bin)
715
679
        else
716
680
          return do_expand_string;
717
681
      }
 
682
 
718
683
    }
719
684
    else if (to->real_type() != from->real_type() ||
720
 
             to_length != from_length ||
 
685
             to_length != from_length ||
721
686
             !compatible_db_low_byte_first)
722
687
    {
723
688
      if (to->result_type() == STRING_RESULT)
724
 
        return do_field_string;
 
689
        return do_field_string;
725
690
      if (to->result_type() == INT_RESULT)
726
 
        return do_field_int;
727
 
 
 
691
        return do_field_int;
728
692
      return do_field_real;
729
693
    }
730
694
    else
731
695
    {
732
696
      if (!to->eq_def(from) || !compatible_db_low_byte_first)
733
697
      {
734
 
        if (to->result_type() == INT_RESULT)
735
 
          return do_field_int;
736
 
        else
737
 
          return do_field_real;
 
698
        if (to->result_type() == INT_RESULT)
 
699
          return do_field_int;
 
700
        else
 
701
          return do_field_real;
738
702
      }
739
703
    }
740
704
  }
741
 
  
742
705
    /* Eq fields */
743
 
  switch (to_length)
744
 
  {
 
706
  switch (to_length) {
745
707
  case 1: return do_field_1;
746
708
  case 2: return do_field_2;
747
709
  case 3: return do_field_3;
749
711
  case 6: return do_field_6;
750
712
  case 8: return do_field_8;
751
713
  }
752
 
  
753
714
  return do_field_eq;
754
715
}
755
716
 
762
723
      !(to->type() == DRIZZLE_TYPE_BLOB && to->table->copy_blobs))
763
724
  {
764
725
    /* Please god, will someone rewrite this to be readable :( */
765
 
    if (to->pack_length() == from->pack_length() &&
766
 
        !(to->flags & UNSIGNED_FLAG && !(from->flags & UNSIGNED_FLAG)) &&
767
 
        to->real_type() != DRIZZLE_TYPE_ENUM &&
768
 
        (to->real_type() != DRIZZLE_TYPE_DECIMAL || (to->field_length == from->field_length && (((Field_num*)to)->dec == ((Field_num*)from)->dec))) &&
 
726
    if (to->pack_length() == from->pack_length() && 
 
727
        !(to->flags & UNSIGNED_FLAG && !(from->flags & UNSIGNED_FLAG)) && 
 
728
        to->real_type() != DRIZZLE_TYPE_ENUM && 
 
729
        (to->real_type() != DRIZZLE_TYPE_NEWDECIMAL || (to->field_length == from->field_length && (((Field_num*)to)->dec == ((Field_num*)from)->dec))) &&
769
730
        from->charset() == to->charset() &&
770
731
        to->table->s->db_low_byte_first == from->table->s->db_low_byte_first &&
771
 
        (!(to->table->in_use->variables.sql_mode & (MODE_NO_ZERO_DATE | MODE_INVALID_DATES)) || (to->type() != DRIZZLE_TYPE_DATE && to->type() != DRIZZLE_TYPE_DATETIME)) &&
 
732
        (!(to->table->in_use->variables.sql_mode & (MODE_NO_ZERO_DATE | MODE_INVALID_DATES)) || (to->type() != DRIZZLE_TYPE_NEWDATE && to->type() != DRIZZLE_TYPE_DATETIME)) && 
772
733
        (from->real_type() != DRIZZLE_TYPE_VARCHAR || ((Field_varstring*)from)->length_bytes == ((Field_varstring*)to)->length_bytes))
773
734
    {                                           // Identical fields
 
735
#ifdef HAVE_purify
774
736
      /* This may happen if one does 'UPDATE ... SET x=x' */
775
737
      if (to->ptr != from->ptr)
 
738
#endif
776
739
        memcpy(to->ptr,from->ptr,to->pack_length());
777
740
      return 0;
778
741
    }
823
786
  else
824
787
    return to->store(from->val_int(), test(from->flags & UNSIGNED_FLAG));
825
788
}
826
 
 
827
 
} /* namespace drizzled */