~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/time_functions.h

  • Committer: Stewart Smith
  • Date: 2010-08-12 16:48:46 UTC
  • mto: This revision was merged to the branch mainline in revision 1707.
  • Revision ID: stewart@flamingspork.com-20100812164846-s9bhy47g60bvqs41
bug lp:611379 Equivalent queries with Impossible where return different results

The following two equivalent queries return different results in maria 5.2 and 5.3 (and identical results in mysql 5.5.5) :

SELECT SUM( DISTINCT table1 .`pk` ) FROM B table1 STRAIGHT_JOIN ( BB table2 JOIN CC ON table2 .`col_varchar_key` ) ON table2 .`pk` ;

SELECT * FROM ( SELECT SUM( DISTINCT table1 .`pk` ) FROM B table1 STRAIGHT_JOIN ( BB table2 JOIN CC ON table2 .`col_varchar_key` ) ON table2 .`pk` );

MariaDB returns 0 on the second query and NULL on the first, whereas MySQL returns NULL on both. In MariaDB, both EXPLAIN plans agree that "Impossible WHERE noticed after reading const tables"



We have some slightly different output in drizzle:

main.bug_lp611379 [ fail ]
drizzletest: At line 9: query 'explain select * from (select sum(distinct t1.a) from t1,t2 where t1.a=t2.a)
as t' failed: 1048: Column 'sum(distinct t1.a)' cannot be null

but the fix gets us the correct query results, although with slightly different execution plans.



This fix is directly ported from MariaDB.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/* -*- mode: c++; c-basic-offset: 2; indent-tabs-mode: nil; -*-
2
2
 *  vim:expandtab:shiftwidth=2:tabstop=2:smarttab:
3
3
 *
4
 
 *  Copyright (C) 2008-2009 Sun Microsystems, Inc.
 
4
 *  Copyright (C) 2008-2009 Sun Microsystems
5
5
 *
6
6
 *  This program is free software; you can redistribute it and/or modify
7
7
 *  it under the terms of the GNU General Public License as published by
20
20
#ifndef DRIZZLED_TIME_FUNCTIONS_H
21
21
#define DRIZZLED_TIME_FUNCTIONS_H
22
22
 
23
 
#include <drizzled/sql_error.h>
24
 
#include <drizzled/type/time.h>
 
23
#include "drizzled/sql_error.h"
 
24
#include "drizzled/drizzle_time.h"
25
25
 
26
26
namespace drizzled
27
27
{
 
28
 
 
29
typedef struct st_drizzle_time DRIZZLE_TIME;
 
30
 
28
31
/* Calc weekday from daynr */
29
32
/* Returns 0 for monday, 1 for tuesday .... */
30
33
int calc_weekday(long daynr, bool sunday_first_day_of_week);
57
60
        Otherwise it is the last week of the previous year, and the
58
61
        next week is week 1.
59
62
*/
60
 
uint32_t calc_week(type::Time *l_time, uint32_t week_behaviour, uint32_t *year);
 
63
uint32_t calc_week(DRIZZLE_TIME *l_time, uint32_t week_behaviour, uint32_t *year);
61
64
 
62
65
/* Change a daynr to year, month and day */
63
66
/* Daynr 0 is returned as date 00.00.00 */
67
70
                         uint32_t *day);
68
71
 
69
72
/*
70
 
  Convert a timestamp string to a type::Time value and produce a warning
 
73
  Convert a timestamp string to a DRIZZLE_TIME value and produce a warning
71
74
  if string was truncated during conversion.
72
75
 
73
76
  NOTE
74
77
    See description of str_to_datetime() for more information.
75
78
*/
76
 
type::timestamp_t str_to_datetime_with_warn(Session *session,
77
 
                                            const char *str, 
78
 
                                            uint32_t length,
79
 
                                            type::Time *l_time, 
80
 
                                            uint32_t flags);
 
79
enum enum_drizzle_timestamp_type str_to_datetime_with_warn(const char *str, 
 
80
                                                           uint32_t length,
 
81
                                                           DRIZZLE_TIME *l_time, 
 
82
                                                           uint32_t flags);
81
83
 
82
84
/*
83
 
  Convert a time string to a type::Time struct and produce a warning
 
85
  Convert a time string to a DRIZZLE_TIME struct and produce a warning
84
86
  if string was cut during conversion.
85
87
 
86
88
  NOTE
87
89
    See str_to_time() for more info.
88
90
*/
89
 
bool str_to_time_with_warn(Session *session, const char *str, uint32_t length, type::Time *l_time);
 
91
bool str_to_time_with_warn(const char *str, uint32_t length, DRIZZLE_TIME *l_time);
 
92
 
 
93
/*
 
94
  Convert a system time structure to TIME
 
95
*/
 
96
void localtime_to_TIME(DRIZZLE_TIME *to, struct tm *from);
 
97
 
 
98
void make_date(const DRIZZLE_TIME *l_time, String *str);
 
99
 
 
100
void make_datetime(const DRIZZLE_TIME *l_time, String *str);
90
101
 
91
102
void make_truncated_value_warning(Session *session, 
92
103
                                  DRIZZLE_ERROR::enum_warning_level level,
93
104
                                  const char *str_val,
94
105
                                  uint32_t str_length, 
95
 
                                  type::timestamp_t time_type,
 
106
                                  enum enum_drizzle_timestamp_type time_type,
96
107
                                  const char *field_name);
97
108
 
98
109
/*
112
123
  NOTE
113
124
    This function calculates difference between l_time1 and l_time2 absolute
114
125
    values. So one should set l_sign and correct result if he want to take
115
 
    signs into account (i.e. for type::Time values).
 
126
    signs into account (i.e. for DRIZZLE_TIME values).
116
127
 
117
128
  RETURN VALUES
118
129
    Returns sign of difference.
120
131
    0 means positive result
121
132
 
122
133
*/
123
 
bool calc_time_diff(type::Time *l_time1, 
124
 
                    type::Time *l_time2, 
 
134
bool calc_time_diff(DRIZZLE_TIME *l_time1, 
 
135
                    DRIZZLE_TIME *l_time2, 
125
136
                    int l_sign,
126
137
                    int64_t *seconds_out, 
127
138
                    long *microseconds_out);