32 #include <drizzled/sql_select.h>
33 #include <drizzled/field/blob.h>
34 #include <drizzled/drizzled.h>
35 #include <drizzled/internal/my_sys.h>
36 #include <drizzled/table.h>
37 #include <drizzled/session.h>
38 #include <drizzled/system_variables.h>
46 static uint32_t used_blob_length(CacheField **ptr)
48 uint32_t length,blob_length;
49 for (length=0 ; *ptr ; ptr++)
51 (*ptr)->blob_length=blob_length=(*ptr)->blob_field->get_length();
53 (*ptr)->str= (*ptr)->blob_field->get_ptr();
64 int join_init_cache(Session *session, JoinTable *tables, uint32_t table_count)
66 unsigned int length, blobs;
68 CacheField *copy,**blob_ptr;
72 cache= &tables[table_count].cache;
73 cache->fields=blobs=0;
76 for (
unsigned int i= 0; i < table_count ; i++, join_tab++)
78 if (!join_tab->used_fieldlength)
80 cache->fields+=join_tab->used_fields;
81 blobs+=join_tab->used_blobs;
84 if (join_tab->rowid_keep_flags & JoinTable::KEEP_ROWID)
87 join_tab->used_fieldlength += join_tab->table->cursor->ref_length;
90 if (!(cache->field=(CacheField*)
91 memory::sql_alloc(
sizeof(CacheField)*(cache->fields+table_count*2)+(blobs+1)*
sizeof(CacheField*))))
93 size= cache->end - cache->buff;
94 global_join_buffer.sub(size);
95 free((
unsigned char*) cache->buff);
100 blob_ptr=cache->blob_ptr=(CacheField**)
101 (cache->field+cache->fields+table_count*2);
104 for (
unsigned int i= 0 ; i < table_count ; i++)
106 uint32_t null_fields=0, used_fields;
107 Field **f_ptr,*field;
108 for (f_ptr= tables[i].table->getFields(), used_fields= tables[i].used_fields; used_fields; f_ptr++)
111 if (field->isReadSet())
114 length+=field->fill_cache_field(copy);
115 if (copy->blob_field)
117 if (field->maybe_null())
119 copy->get_rowid= NULL;
124 if (null_fields && tables[i].table->getNullFields())
126 copy->str= tables[i].table->null_flags;
127 copy->length= tables[i].table->getShare()->null_bytes;
130 copy->get_rowid= NULL;
131 length+=copy->length;
136 if (tables[i].table->maybe_null)
138 copy->str= (
unsigned char*) &tables[i].table->null_row;
139 copy->length=
sizeof(tables[i].table->null_row);
142 copy->get_rowid= NULL;
143 length+=copy->length;
148 if (tables[i].rowid_keep_flags & JoinTable::KEEP_ROWID)
150 copy->str= tables[i].table->cursor->ref;
151 copy->length= tables[i].table->cursor->ref_length;
154 copy->get_rowid= NULL;
155 if (tables[i].rowid_keep_flags & JoinTable::CALL_POSITION)
158 copy->get_rowid= tables[i].table;
160 tables[i].rowid_keep_flags&= ~((int)JoinTable::CALL_POSITION);
166 cache->length= length+blobs*
sizeof(
char*);
169 size= max((
size_t) session->variables.join_buff_size, (
size_t)cache->length);
170 if (not global_join_buffer.add(size))
172 my_error(ER_OUT_OF_GLOBAL_JOINMEMORY, MYF(ME_ERROR+ME_WAITTANG));
175 cache->buff= (
unsigned char*) malloc(size);
176 cache->end= cache->buff+size;
177 cache->reset_cache_write();
182 bool JoinCache::store_record_in_cache()
184 JoinCache *cache=
this;
185 unsigned char *local_pos;
186 CacheField *copy,*end_field;
189 local_pos= cache->pos;
190 end_field= cache->field+cache->fields;
193 uint32_t local_length;
195 local_length= cache->length;
198 local_length+= used_blob_length(cache->blob_ptr);
201 if ((last_record= (local_length + cache->length > (
size_t) (cache->end - local_pos))))
203 cache->ptr_record= cache->records;
211 for (copy= cache->field; copy < end_field; copy++)
213 if (copy->blob_field)
217 copy->blob_field->get_image(local_pos, copy->length+
sizeof(
char*), copy->blob_field->charset());
218 local_pos+= copy->length+
sizeof(
char*);
222 copy->blob_field->get_image(local_pos, copy->length,
223 copy->blob_field->charset());
224 memcpy(local_pos + copy->length,copy->str,copy->blob_length);
225 local_pos+= copy->length+copy->blob_length;
232 copy->get_rowid->cursor->position(copy->get_rowid->getInsertRecord());
236 unsigned char *str, *local_end;
237 for (str= copy->str,local_end= str+copy->length; local_end > str && local_end[-1] ==
' '; local_end--) {}
239 uint32_t local_length= (uint32_t) (local_end - str);
240 memcpy(local_pos+2, str, local_length);
241 int2store(local_pos, local_length);
242 local_pos+= local_length+2;
246 memcpy(local_pos, copy->str, copy->length);
247 local_pos+= copy->length;
251 cache->pos= local_pos;
252 return last_record || (size_t) (cache->end - local_pos) < cache->length;
255 void JoinCache::reset_cache_read()
261 void JoinCache::reset_cache_write()
265 ptr_record= UINT32_MAX;
void calc_used_field_length(Session *, JoinTable *join_tab)