~drizzle-trunk/drizzle/development

1999.6.1 by kalebral at gmail
update Copyright strings to a more common format to help with creating the master debian copyright file
1
/* Copyright (C) 2009 Sun Microsystems, Inc.
1054.1.7 by Brian Aker
Refactor TableList methods.
2
3
  This program is free software; you can redistribute it and/or modify
4
  it under the terms of the GNU General Public License as published by
5
  the Free Software Foundation; version 2 of the License.
6
7
  This program is distributed in the hope that it will be useful,
8
  but WITHOUT ANY WARRANTY; without even the implied warranty of
9
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10
  GNU General Public License for more details.
11
12
  You should have received a copy of the GNU General Public License
13
  along with this program; if not, write to the Free Software
1802.10.2 by Monty Taylor
Update all of the copyright headers to include the correct address.
14
  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA */
1054.1.7 by Brian Aker
Refactor TableList methods.
15
2173.2.1 by Monty Taylor
Fixes incorrect usage of include
16
#include <config.h>
1054.1.7 by Brian Aker
Refactor TableList methods.
17
18
#include <string>
19
2173.2.1 by Monty Taylor
Fixes incorrect usage of include
20
#include <drizzled/error.h>
21
#include <drizzled/table_list.h>
22
#include <drizzled/item.h>
23
#include <drizzled/item/field.h>
24
#include <drizzled/nested_join.h>
25
#include <drizzled/sql_lex.h>
26
#include <drizzled/sql_select.h>
1122.2.13 by Monty Taylor
Header cleanup.
27
1054.1.7 by Brian Aker
Refactor TableList methods.
28
using namespace std;
29
2252.1.18 by Olaf van der Spek
Common fwd
30
namespace drizzled {
1054.1.7 by Brian Aker
Refactor TableList methods.
31
2385.2.4 by Olaf van der Spek
cppcheck
32
void TableList::set_insert_values()
1054.1.7 by Brian Aker
Refactor TableList methods.
33
{
34
  if (table)
35
  {
1672.3.5 by Brian Aker
This replaces the allocation we do for insert/update.
36
    table->insert_values.resize(table->getShare()->rec_buff_length);
1054.1.7 by Brian Aker
Refactor TableList methods.
37
  }
38
}
39
2385.2.4 by Olaf van der Spek
cppcheck
40
bool TableList::is_leaf_for_name_resolution() const
1054.1.7 by Brian Aker
Refactor TableList methods.
41
{
2385.2.4 by Olaf van der Spek
cppcheck
42
  return is_natural_join || is_join_columns_complete || not nested_join;
1054.1.7 by Brian Aker
Refactor TableList methods.
43
}
44
45
TableList *TableList::find_underlying_table(Table *table_to_find)
46
{
47
  /* is this real table and table which we are looking for? */
48
  if (table == table_to_find)
49
    return this;
50
51
  return NULL;
52
}
53
1637.1.3 by Brian Aker
This fixes the parser to no longer do the bad syntax around the cross join
54
bool TableList::isCartesian() const
55
{
56
  return false;
57
}
58
1054.1.7 by Brian Aker
Refactor TableList methods.
59
bool TableList::placeholder()
60
{
1225.1.20 by Padraig O'Sullivan
Removed all remnants of schema_table from the TableList class. This cleans up a bunch of code.
61
  return derived || (create && !table->getDBStat()) || !table;
1054.1.7 by Brian Aker
Refactor TableList methods.
62
}
63
64
/*
1188.1.2 by Jay Pipes
Style and doxygen cleanup ONLY. Moves method documentation from source into header files. Removes TAB characters and cleans up indentation.
65
 * The right-most child of a nested table reference is the first
66
 * element in the list of children because the children are inserted
67
 * in reverse order.
68
 */
1054.1.7 by Brian Aker
Refactor TableList methods.
69
TableList *TableList::last_leaf_for_name_resolution()
70
{
71
  TableList *cur_table_ref= this;
2141.3.3 by vjsamuel1990 at gmail
Merge change nested_join_st to NestedJoin
72
  NestedJoin *cur_nested_join;
1054.1.7 by Brian Aker
Refactor TableList methods.
73
74
  if (is_leaf_for_name_resolution())
75
    return this;
76
  assert(nested_join);
77
78
  for (cur_nested_join= nested_join;
79
       cur_nested_join;
80
       cur_nested_join= cur_table_ref->nested_join)
81
  {
2183.2.21 by Olaf van der Spek
Use List::front()
82
    cur_table_ref= &cur_nested_join->join_list.front();
1054.1.7 by Brian Aker
Refactor TableList methods.
83
    /*
84
      If the current nested is a RIGHT JOIN, the operands in
85
      'join_list' are in reverse order, thus the last operand is in the
86
      end of the list.
87
    */
88
    if ((cur_table_ref->outer_join & JOIN_TYPE_RIGHT))
89
    {
2183.2.13 by Olaf van der Spek
Use List::begin()
90
      List<TableList>::iterator it(cur_nested_join->join_list.begin());
1054.1.7 by Brian Aker
Refactor TableList methods.
91
      TableList *next;
92
      cur_table_ref= it++;
93
      while ((next= it++))
94
        cur_table_ref= next;
95
    }
96
    if (cur_table_ref->is_leaf_for_name_resolution())
97
      break;
98
  }
99
  return cur_table_ref;
100
}
101
102
/*
1188.1.2 by Jay Pipes
Style and doxygen cleanup ONLY. Moves method documentation from source into header files. Removes TAB characters and cleans up indentation.
103
 * The left-most child of a nested table reference is the last element
104
 * in the list of children because the children are inserted in
105
 * reverse order.
106
 */
1054.1.7 by Brian Aker
Refactor TableList methods.
107
TableList *TableList::first_leaf_for_name_resolution()
108
{
109
  TableList *cur_table_ref= NULL;
2141.3.3 by vjsamuel1990 at gmail
Merge change nested_join_st to NestedJoin
110
  NestedJoin *cur_nested_join;
1054.1.7 by Brian Aker
Refactor TableList methods.
111
112
  if (is_leaf_for_name_resolution())
113
    return this;
114
  assert(nested_join);
115
116
  for (cur_nested_join= nested_join;
117
       cur_nested_join;
118
       cur_nested_join= cur_table_ref->nested_join)
119
  {
2183.2.13 by Olaf van der Spek
Use List::begin()
120
    List<TableList>::iterator it(cur_nested_join->join_list.begin());
1054.1.7 by Brian Aker
Refactor TableList methods.
121
    cur_table_ref= it++;
122
    /*
123
      If the current nested join is a RIGHT JOIN, the operands in
124
      'join_list' are in reverse order, thus the first operand is
125
      already at the front of the list. Otherwise the first operand
126
      is in the end of the list of join operands.
127
    */
128
    if (!(cur_table_ref->outer_join & JOIN_TYPE_RIGHT))
129
    {
130
      TableList *next;
131
      while ((next= it++))
132
        cur_table_ref= next;
133
    }
134
    if (cur_table_ref->is_leaf_for_name_resolution())
135
      break;
136
  }
137
  return cur_table_ref;
138
}
139
140
Item_subselect *TableList::containing_subselect()
141
{
142
  return (select_lex ? select_lex->master_unit()->item : 0);
143
}
144
145
bool TableList::process_index_hints(Table *tbl)
146
{
147
  /* initialize the result variables */
148
  tbl->keys_in_use_for_query= tbl->keys_in_use_for_group_by=
1574 by Brian Aker
Rollup patch for hiding tableshare.
149
    tbl->keys_in_use_for_order_by= tbl->getShare()->keys_in_use;
1054.1.7 by Brian Aker
Refactor TableList methods.
150
151
  /* index hint list processing */
152
  if (index_hints)
153
  {
154
    key_map index_join[INDEX_HINT_FORCE + 1];
155
    key_map index_order[INDEX_HINT_FORCE + 1];
156
    key_map index_group[INDEX_HINT_FORCE + 1];
157
    bool have_empty_use_join= false, have_empty_use_order= false,
158
         have_empty_use_group= false;
2183.2.13 by Olaf van der Spek
Use List::begin()
159
    List_iterator <Index_hint> iter(index_hints->begin());
1054.1.7 by Brian Aker
Refactor TableList methods.
160
161
    /* initialize temporary variables used to collect hints of each kind */
2318.8.9 by Olaf van der Spek
Use boost::to_upper
162
    for (int type= INDEX_HINT_IGNORE; type <= INDEX_HINT_FORCE; type++)
1054.1.7 by Brian Aker
Refactor TableList methods.
163
    {
164
      index_join[type].reset();
165
      index_order[type].reset();
166
      index_group[type].reset();
167
    }
168
169
    /* iterate over the hints list */
2318.8.9 by Olaf van der Spek
Use boost::to_upper
170
    while (Index_hint* hint= iter++)
1054.1.7 by Brian Aker
Refactor TableList methods.
171
    {
172
      /* process empty USE INDEX () */
173
      if (hint->type == INDEX_HINT_USE && !hint->key_name.str)
174
      {
175
        if (hint->clause & INDEX_HINT_MASK_JOIN)
176
        {
177
          index_join[hint->type].reset();
178
          have_empty_use_join= true;
179
        }
180
        if (hint->clause & INDEX_HINT_MASK_ORDER)
181
        {
182
          index_order[hint->type].reset();
183
          have_empty_use_order= true;
184
        }
185
        if (hint->clause & INDEX_HINT_MASK_GROUP)
186
        {
187
          index_group[hint->type].reset();
188
          have_empty_use_group= true;
189
        }
190
        continue;
191
      }
192
193
      /*
194
        Check if an index with the given name exists and get his offset in
195
        the keys bitmask for the table
196
      */
2318.8.9 by Olaf van der Spek
Use boost::to_upper
197
      uint32_t pos= 0;
1574 by Brian Aker
Rollup patch for hiding tableshare.
198
      if (not tbl->getShare()->doesKeyNameExist(hint->key_name.str, hint->key_name.length, pos))
1054.1.7 by Brian Aker
Refactor TableList methods.
199
      {
200
        my_error(ER_KEY_DOES_NOT_EXITS, MYF(0), hint->key_name.str, alias);
201
        return 1;
202
      }
203
      /* add to the appropriate clause mask */
204
      if (hint->clause & INDEX_HINT_MASK_JOIN)
205
        index_join[hint->type].set(pos);
206
      if (hint->clause & INDEX_HINT_MASK_ORDER)
207
        index_order[hint->type].set(pos);
208
      if (hint->clause & INDEX_HINT_MASK_GROUP)
209
        index_group[hint->type].set(pos);
210
    }
211
212
    /* cannot mix USE INDEX and FORCE INDEX */
213
    if ((index_join[INDEX_HINT_FORCE].any() ||
214
         index_order[INDEX_HINT_FORCE].any() ||
215
         index_group[INDEX_HINT_FORCE].any()) &&
216
        (index_join[INDEX_HINT_USE].any() ||  have_empty_use_join ||
217
         index_order[INDEX_HINT_USE].any() || have_empty_use_order ||
218
         index_group[INDEX_HINT_USE].any() || have_empty_use_group))
219
    {
220
      my_error(ER_WRONG_USAGE, MYF(0), index_hint_type_name[INDEX_HINT_USE],
221
               index_hint_type_name[INDEX_HINT_FORCE]);
222
      return 1;
223
    }
224
225
    /* process FORCE INDEX as USE INDEX with a flag */
226
    if (index_join[INDEX_HINT_FORCE].any() ||
227
        index_order[INDEX_HINT_FORCE].any() ||
228
        index_group[INDEX_HINT_FORCE].any())
229
    {
230
      tbl->force_index= true;
231
      index_join[INDEX_HINT_USE]|= index_join[INDEX_HINT_FORCE];
232
      index_order[INDEX_HINT_USE]|= index_order[INDEX_HINT_FORCE];
233
      index_group[INDEX_HINT_USE]|= index_group[INDEX_HINT_FORCE];
234
    }
235
236
    /* apply USE INDEX */
237
    if (index_join[INDEX_HINT_USE].any() || have_empty_use_join)
238
      tbl->keys_in_use_for_query&= index_join[INDEX_HINT_USE];
239
    if (index_order[INDEX_HINT_USE].any() || have_empty_use_order)
240
      tbl->keys_in_use_for_order_by&= index_order[INDEX_HINT_USE];
241
    if (index_group[INDEX_HINT_USE].any() || have_empty_use_group)
242
      tbl->keys_in_use_for_group_by&= index_group[INDEX_HINT_USE];
243
244
    /* apply IGNORE INDEX */
245
    key_map_subtract(tbl->keys_in_use_for_query, index_join[INDEX_HINT_IGNORE]);
246
    key_map_subtract(tbl->keys_in_use_for_order_by, index_order[INDEX_HINT_IGNORE]);
247
    key_map_subtract(tbl->keys_in_use_for_group_by, index_group[INDEX_HINT_IGNORE]);
248
  }
249
250
  /* make sure covering_keys don't include indexes disabled with a hint */
251
  tbl->covering_keys&= tbl->keys_in_use_for_query;
252
  return 0;
253
}
254
2215.2.1 by Stewart Smith
remove enum_query_type which was effectively unused. It was set to one value once, compared to it once (i.e. always true) and passed around everywhere doing nothing.
255
void TableList::print(Session *session, String *str)
1054.1.7 by Brian Aker
Refactor TableList methods.
256
{
257
  if (nested_join)
258
  {
259
    str->append('(');
2215.2.1 by Stewart Smith
remove enum_query_type which was effectively unused. It was set to one value once, compared to it once (i.e. always true) and passed around everywhere doing nothing.
260
    print_join(session, str, &nested_join->join_list);
1054.1.7 by Brian Aker
Refactor TableList methods.
261
    str->append(')');
262
  }
263
  else
264
  {
265
    const char *cmp_name;                         // Name to compare with alias
266
    if (derived)
267
    {
268
      // A derived table
269
      str->append('(');
2215.2.1 by Stewart Smith
remove enum_query_type which was effectively unused. It was set to one value once, compared to it once (i.e. always true) and passed around everywhere doing nothing.
270
      derived->print(str);
1054.1.7 by Brian Aker
Refactor TableList methods.
271
      str->append(')');
272
      cmp_name= "";                               // Force printing of alias
273
    }
274
    else
275
    {
276
      // A normal table
2385.1.8 by Olaf van der Spek
Refactor
277
      str->append_identifier(str_ref(schema));
2385.1.7 by Olaf van der Spek
Rename set_db to set_schema
278
      str->append('.');
2385.1.8 by Olaf van der Spek
Refactor
279
      str->append_identifier(str_ref(table_name));
280
      cmp_name= table_name;
1054.1.7 by Brian Aker
Refactor TableList methods.
281
    }
2385.1.7 by Olaf van der Spek
Rename set_db to set_schema
282
    if (my_strcasecmp(table_alias_charset, cmp_name, alias) && alias && alias[0])
1054.1.7 by Brian Aker
Refactor TableList methods.
283
    {
2385.1.7 by Olaf van der Spek
Rename set_db to set_schema
284
      str->append(' ');
285
      str->append_identifier(boost::to_lower_copy(string(alias)));
1054.1.7 by Brian Aker
Refactor TableList methods.
286
    }
287
288
    if (index_hints)
289
    {
2183.2.13 by Olaf van der Spek
Use List::begin()
290
      List<Index_hint>::iterator it(index_hints->begin());
2246.4.1 by Olaf van der Spek
Use BOOST_FOREACH
291
      while (Index_hint* hint= it++)
1054.1.7 by Brian Aker
Refactor TableList methods.
292
      {
2318.8.1 by Olaf van der Spek
Add data_ref.h
293
        str->append(STRING_WITH_LEN(" "));
294
        hint->print(session, str);
1054.1.7 by Brian Aker
Refactor TableList methods.
295
      }
296
    }
297
  }
298
}
1280.1.10 by Monty Taylor
Put everything in drizzled into drizzled namespace.
299
300
} /* namespace drizzled */