summaryrefslogtreecommitdiff
path: root/heap
diff options
context:
space:
mode:
Diffstat (limited to 'heap')
-rw-r--r--heap/Makefile.am3
-rw-r--r--heap/_check.c4
-rw-r--r--heap/heapdef.h4
-rw-r--r--heap/hp_create.c35
-rw-r--r--heap/hp_delete.c6
-rw-r--r--heap/hp_hash.c244
-rw-r--r--heap/hp_open.c4
-rw-r--r--heap/hp_rkey.c4
-rw-r--r--heap/hp_rrnd.c8
-rw-r--r--heap/hp_update.c6
-rw-r--r--heap/hp_write.c6
11 files changed, 283 insertions, 41 deletions
diff --git a/heap/Makefile.am b/heap/Makefile.am
index 9ce09757802..567c7774751 100644
--- a/heap/Makefile.am
+++ b/heap/Makefile.am
@@ -14,8 +14,7 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-INCLUDES = @MT_INCLUDES@ \
- -I$(top_builddir)/include -I$(top_srcdir)/include
+INCLUDES = -I$(top_builddir)/include -I$(top_srcdir)/include
LDADD = libheap.a ../mysys/libmysys.a ../dbug/libdbug.a \
../strings/libmystrings.a
pkglib_LIBRARIES = libheap.a
diff --git a/heap/_check.c b/heap/_check.c
index a745aee48bf..4316a9926f7 100644
--- a/heap/_check.c
+++ b/heap/_check.c
@@ -123,7 +123,7 @@ static int check_one_key(HP_KEYDEF *keydef, uint keynr, ulong records,
blength, records))
!= i)
{
- DBUG_PRINT("error",("Record in wrong link: Link %d Record: %lx Record-link %d", i,hash_info->ptr_to_rec,rec_link));
+ DBUG_PRINT("error",("Record in wrong link: Link %d Record: 0x%lx Record-link %d", i,hash_info->ptr_to_rec,rec_link));
error=1;
}
else
@@ -180,7 +180,7 @@ static int check_one_rb_key(HP_INFO *info, uint keynr, ulong records,
key_length, SEARCH_FIND | SEARCH_SAME, &not_used))
{
error= 1;
- DBUG_PRINT("error",("Record in wrong link: key: %d Record: %lx\n",
+ DBUG_PRINT("error",("Record in wrong link: key: %d Record: 0x%lx\n",
keynr, recpos));
}
else
diff --git a/heap/heapdef.h b/heap/heapdef.h
index 083765334ab..68d9405138f 100644
--- a/heap/heapdef.h
+++ b/heap/heapdef.h
@@ -86,7 +86,8 @@ extern ulong hp_mask(ulong hashnr,ulong buffmax,ulong maxlength);
extern void hp_movelink(HASH_INFO *pos,HASH_INFO *next_link,
HASH_INFO *newlink);
extern int hp_rec_key_cmp(HP_KEYDEF *keydef,const byte *rec1,
- const byte *rec2);
+ const byte *rec2,
+ my_bool diff_if_only_endspace_difference);
extern int hp_key_cmp(HP_KEYDEF *keydef,const byte *rec,
const byte *key);
extern void hp_make_key(HP_KEYDEF *keydef,byte *key,const byte *rec);
@@ -94,6 +95,7 @@ extern uint hp_rb_make_key(HP_KEYDEF *keydef, byte *key,
const byte *rec, byte *recpos);
extern uint hp_rb_key_length(HP_KEYDEF *keydef, const byte *key);
extern uint hp_rb_null_key_length(HP_KEYDEF *keydef, const byte *key);
+extern uint hp_rb_var_key_length(HP_KEYDEF *keydef, const byte *key);
extern my_bool hp_if_null_in_key(HP_KEYDEF *keyinfo, const byte *record);
extern int hp_close(register HP_INFO *info);
extern void hp_clear(HP_SHARE *info);
diff --git a/heap/hp_create.c b/heap/hp_create.c
index af32fefea1b..8fcf7dde000 100644
--- a/heap/hp_create.c
+++ b/heap/hp_create.c
@@ -76,9 +76,38 @@ int heap_create(const char *name, uint keys, HP_KEYDEF *keydef,
case HA_KEYTYPE_UINT24:
case HA_KEYTYPE_INT8:
keyinfo->seg[j].flag|= HA_SWAP_KEY;
+ break;
+ case HA_KEYTYPE_VARBINARY1:
+ /* Case-insensitiveness is handled in coll->hash_sort */
+ keyinfo->seg[j].type= HA_KEYTYPE_VARTEXT1;
+ /* fall_through */
+ case HA_KEYTYPE_VARTEXT1:
+ if (!my_binary_compare(keyinfo->seg[j].charset))
+ keyinfo->flag|= HA_END_SPACE_KEY;
+ keyinfo->flag|= HA_VAR_LENGTH_KEY;
+ /* Save number of bytes used to store length */
+ keyinfo->seg[j].bit_start= 1;
+ break;
+ case HA_KEYTYPE_VARBINARY2:
+ /* Case-insensitiveness is handled in coll->hash_sort */
+ /* fall_through */
+ case HA_KEYTYPE_VARTEXT2:
+ if (!my_binary_compare(keyinfo->seg[j].charset))
+ keyinfo->flag|= HA_END_SPACE_KEY;
+ keyinfo->flag|= HA_VAR_LENGTH_KEY;
+ /* Save number of bytes used to store length */
+ keyinfo->seg[j].bit_start= 2;
+ /*
+ Make future comparison simpler by only having to check for
+ one type
+ */
+ keyinfo->seg[j].type= HA_KEYTYPE_VARTEXT1;
+ break;
default:
break;
}
+ if (keyinfo->seg[j].flag & HA_END_SPACE_ARE_EQUAL)
+ keyinfo->flag|= HA_END_SPACE_KEY;
}
keyinfo->length= length;
length+= keyinfo->rb_tree.size_of_element +
@@ -89,7 +118,9 @@ int heap_create(const char *name, uint keys, HP_KEYDEF *keydef,
if (keyinfo->algorithm == HA_KEY_ALG_BTREE)
{
key_segs++; /* additional HA_KEYTYPE_END segment */
- if (keyinfo->flag & HA_NULL_PART_KEY)
+ if (keyinfo->flag & HA_VAR_LENGTH_KEY)
+ keyinfo->get_key_length= hp_rb_var_key_length;
+ else if (keyinfo->flag & HA_NULL_PART_KEY)
keyinfo->get_key_length= hp_rb_null_key_length;
else
keyinfo->get_key_length= hp_rb_key_length;
@@ -137,6 +168,8 @@ int heap_create(const char *name, uint keys, HP_KEYDEF *keydef,
keyinfo->write_key= hp_write_key;
keyinfo->hash_buckets= 0;
}
+ if ((keyinfo->flag & HA_AUTO_KEY) && create_info->with_auto_increment)
+ share->auto_key= i + 1;
}
share->min_records= min_records;
share->max_records= max_records;
diff --git a/heap/hp_delete.c b/heap/hp_delete.c
index 9cf8b8936b6..5287533ae0a 100644
--- a/heap/hp_delete.c
+++ b/heap/hp_delete.c
@@ -24,7 +24,7 @@ int heap_delete(HP_INFO *info, const byte *record)
HP_SHARE *share=info->s;
HP_KEYDEF *keydef, *end, *p_lastinx;
DBUG_ENTER("heap_delete");
- DBUG_PRINT("enter",("info: %lx record: %lx",info,record));
+ DBUG_PRINT("enter",("info: %lx record: 0x%lx",info,record));
test_active(info);
@@ -123,7 +123,7 @@ int hp_delete_key(HP_INFO *info, register HP_KEYDEF *keyinfo,
while (pos->ptr_to_rec != recpos)
{
- if (flag && !hp_rec_key_cmp(keyinfo, record, pos->ptr_to_rec))
+ if (flag && !hp_rec_key_cmp(keyinfo, record, pos->ptr_to_rec, 0))
last_ptr=pos; /* Previous same key */
gpos=pos;
if (!(pos=pos->next_key))
@@ -139,7 +139,7 @@ int hp_delete_key(HP_INFO *info, register HP_KEYDEF *keyinfo,
/* Save for heap_rnext/heap_rprev */
info->current_hash_ptr=last_ptr;
info->current_ptr = last_ptr ? last_ptr->ptr_to_rec : 0;
- DBUG_PRINT("info",("Corrected current_ptr to point at: %lx",
+ DBUG_PRINT("info",("Corrected current_ptr to point at: 0x%lx",
info->current_ptr));
}
empty=pos;
diff --git a/heap/hp_hash.c b/heap/hp_hash.c
index ee5b4958e62..9e4636ebdc0 100644
--- a/heap/hp_hash.c
+++ b/heap/hp_hash.c
@@ -255,6 +255,9 @@ ulong hp_hashnr(register HP_KEYDEF *keydef, register const byte *key)
if (*pos) /* Found null */
{
nr^= (nr << 1) | 1;
+ /* Add key pack length (2) to key for VARCHAR segments */
+ if (seg->type == HA_KEYTYPE_VARTEXT1)
+ key+= 2;
continue;
}
pos++;
@@ -262,14 +265,30 @@ ulong hp_hashnr(register HP_KEYDEF *keydef, register const byte *key)
if (seg->type == HA_KEYTYPE_TEXT)
{
CHARSET_INFO *cs= seg->charset;
- uint char_length= (uint) ((uchar*) key - pos);
+ uint length= seg->length;
if (cs->mbmaxlen > 1)
{
- uint length= char_length;
+ uint char_length;
char_length= my_charpos(cs, pos, pos + length, length/cs->mbmaxlen);
- set_if_smaller(char_length, length); /* QQ: ok to remove? */
+ set_if_smaller(length, char_length);
}
- cs->coll->hash_sort(cs, pos, char_length, &nr, &nr2);
+ cs->coll->hash_sort(cs, pos, length, &nr, &nr2);
+ }
+ else if (seg->type == HA_KEYTYPE_VARTEXT1) /* Any VARCHAR segments */
+ {
+ CHARSET_INFO *cs= seg->charset;
+ uint pack_length= 2; /* Key packing is constant */
+ uint length= uint2korr(pos);
+ if (cs->mbmaxlen > 1)
+ {
+ uint char_length;
+ char_length= my_charpos(cs, pos +pack_length,
+ pos +pack_length + length,
+ seg->length/cs->mbmaxlen);
+ set_if_smaller(length, char_length);
+ }
+ cs->coll->hash_sort(cs, pos+pack_length, length, &nr, &nr2);
+ key+= pack_length;
}
else
{
@@ -280,6 +299,7 @@ ulong hp_hashnr(register HP_KEYDEF *keydef, register const byte *key)
}
}
}
+ DBUG_PRINT("exit", ("hash: 0x%lx", nr));
return((ulong) nr);
}
@@ -287,7 +307,6 @@ ulong hp_hashnr(register HP_KEYDEF *keydef, register const byte *key)
ulong hp_rec_hashnr(register HP_KEYDEF *keydef, register const byte *rec)
{
- /*register*/
ulong nr=1, nr2=4;
HA_KEYSEG *seg,*endseg;
@@ -314,6 +333,21 @@ ulong hp_rec_hashnr(register HP_KEYDEF *keydef, register const byte *rec)
}
cs->coll->hash_sort(cs, pos, char_length, &nr, &nr2);
}
+ else if (seg->type == HA_KEYTYPE_VARTEXT1) /* Any VARCHAR segments */
+ {
+ CHARSET_INFO *cs= seg->charset;
+ uint pack_length= seg->bit_start;
+ uint length= (pack_length == 1 ? (uint) *(uchar*) pos : uint2korr(pos));
+ if (cs->mbmaxlen > 1)
+ {
+ uint char_length;
+ char_length= my_charpos(cs, pos + pack_length,
+ pos + pack_length + length,
+ seg->length/cs->mbmaxlen);
+ set_if_smaller(length, char_length);
+ }
+ cs->coll->hash_sort(cs, pos+pack_length, length, &nr, &nr2);
+ }
else
{
for (; pos < end ; pos++)
@@ -323,7 +357,8 @@ ulong hp_rec_hashnr(register HP_KEYDEF *keydef, register const byte *rec)
}
}
}
- return((ulong) nr);
+ DBUG_PRINT("exit", ("hash: 0x%lx", nr));
+ return(nr);
}
#else
@@ -358,6 +393,9 @@ ulong hp_hashnr(register HP_KEYDEF *keydef, register const byte *key)
if (*pos)
{
nr^= (nr << 1) | 1;
+ /* Add key pack length (2) to key for VARCHAR segments */
+ if (seg->type == HA_KEYTYPE_VARTEXT1)
+ key+= 2;
continue;
}
pos++;
@@ -366,6 +404,14 @@ ulong hp_hashnr(register HP_KEYDEF *keydef, register const byte *key)
{
seg->charset->hash_sort(seg->charset,pos,((uchar*)key)-pos,&nr,NULL);
}
+ else if (seg->type == HA_KEYTYPE_VARTEXT1) /* Any VARCHAR segments */
+ {
+ uint pack_length= 2; /* Key packing is constant */
+ uint length= uint2korr(pos);
+ seg->charset->hash_sort(seg->charset, pos+pack_length, length, &nr,
+ NULL);
+ key+= pack_length;
+ }
else
{
for ( ; pos < (uchar*) key ; pos++)
@@ -375,7 +421,8 @@ ulong hp_hashnr(register HP_KEYDEF *keydef, register const byte *key)
}
}
}
- return((ulong) nr);
+ DBUG_PRINT("exit", ("hash: 0x%lx", nr));
+ return(nr);
}
/* Calc hashvalue for a key in a record */
@@ -387,7 +434,7 @@ ulong hp_rec_hashnr(register HP_KEYDEF *keydef, register const byte *rec)
for (seg=keydef->seg,endseg=seg+keydef->keysegs ; seg < endseg ; seg++)
{
- uchar *pos=(uchar*) rec+seg->start,*end=pos+seg->length;
+ uchar *pos=(uchar*) rec+seg->start;
if (seg->null_bit)
{
if (rec[seg->null_pos] & seg->null_bit)
@@ -400,8 +447,16 @@ ulong hp_rec_hashnr(register HP_KEYDEF *keydef, register const byte *rec)
{
seg->charset->hash_sort(seg->charset,pos,((uchar*)key)-pos,&nr,NULL);
}
+ else if (seg->type == HA_KEYTYPE_VARTEXT1) /* Any VARCHAR segments */
+ {
+ uint pack_length= seg->bit_start;
+ uint length= (pack_length == 1 ? (uint) *(uchar*) pos : uint2korr(pos));
+ seg->charset->hash_sort(seg->charset, pos+pack_length,
+ length, &nr, NULL);
+ }
else
{
+ uchar *end= pos+seg->length;
for ( ; pos < end ; pos++)
{
nr *=16777619;
@@ -409,15 +464,35 @@ ulong hp_rec_hashnr(register HP_KEYDEF *keydef, register const byte *rec)
}
}
}
- return((ulong) nr);
+ DBUG_PRINT("exit", ("hash: 0x%lx", nr));
+ return(nr);
}
#endif
- /* Compare keys for two records. Returns 0 if they are identical */
+/*
+ Compare keys for two records. Returns 0 if they are identical
+
+ SYNOPSIS
+ hp_rec_key_cmp()
+ keydef Key definition
+ rec1 Record to compare
+ rec2 Other record to compare
+ diff_if_only_endspace_difference
+ Different number of end space is significant
+
+ NOTES
+ diff_if_only_endspace_difference is used to allow us to insert
+ 'a' and 'a ' when there is an an unique key.
-int hp_rec_key_cmp(HP_KEYDEF *keydef, const byte *rec1, const byte *rec2)
+ RETURN
+ 0 Key is identical
+ <> 0 Key differes
+*/
+
+int hp_rec_key_cmp(HP_KEYDEF *keydef, const byte *rec1, const byte *rec2,
+ my_bool diff_if_only_endspace_difference)
{
HA_KEYSEG *seg,*endseg;
@@ -442,9 +517,9 @@ int hp_rec_key_cmp(HP_KEYDEF *keydef, const byte *rec1, const byte *rec2)
{
uint char_length= seg->length / cs->mbmaxlen;
char_length1= my_charpos(cs, pos1, pos1 + seg->length, char_length);
- set_if_smaller(char_length1, seg->length); /* QQ: ok to remove? */
+ set_if_smaller(char_length1, seg->length);
char_length2= my_charpos(cs, pos2, pos2 + seg->length, char_length);
- set_if_smaller(char_length2, seg->length); /* QQ: ok to remove? */
+ set_if_smaller(char_length2, seg->length);
}
else
{
@@ -452,7 +527,42 @@ int hp_rec_key_cmp(HP_KEYDEF *keydef, const byte *rec1, const byte *rec2)
}
if (seg->charset->coll->strnncollsp(seg->charset,
pos1,char_length1,
- pos2,char_length2))
+ pos2,char_length2, 0))
+ return 1;
+ }
+ else if (seg->type == HA_KEYTYPE_VARTEXT1) /* Any VARCHAR segments */
+ {
+ uchar *pos1= (uchar*) rec1 + seg->start;
+ uchar *pos2= (uchar*) rec2 + seg->start;
+ uint char_length1, char_length2;
+ uint pack_length= seg->bit_start;
+ CHARSET_INFO *cs= seg->charset;
+ if (pack_length == 1)
+ {
+ char_length1= (uint) *(uchar*) pos1++;
+ char_length2= (uint) *(uchar*) pos2++;
+ }
+ else
+ {
+ char_length1= uint2korr(pos1);
+ char_length2= uint2korr(pos2);
+ pos1+= 2;
+ pos2+= 2;
+ }
+ if (cs->mbmaxlen > 1)
+ {
+ uint char_length= seg->length / cs->mbmaxlen;
+ char_length1= my_charpos(cs, pos1, pos1 + char_length1, char_length);
+ set_if_smaller(char_length1, seg->length);
+ char_length2= my_charpos(cs, pos2, pos2 + char_length2, char_length);
+ set_if_smaller(char_length2, seg->length);
+ }
+
+ if (cs->coll->strnncollsp(seg->charset,
+ pos1, char_length1,
+ pos2, char_length2,
+ seg->flag & HA_END_SPACE_ARE_EQUAL ?
+ 0 : diff_if_only_endspace_difference))
return 1;
}
else
@@ -480,7 +590,12 @@ int hp_key_cmp(HP_KEYDEF *keydef, const byte *rec, const byte *key)
if (found_null != (int) *key++)
return 1;
if (found_null)
+ {
+ /* Add key pack length (2) to key for VARCHAR segments */
+ if (seg->type == HA_KEYTYPE_VARTEXT1)
+ key+= 2;
continue;
+ }
}
if (seg->type == HA_KEYTYPE_TEXT)
{
@@ -504,7 +619,33 @@ int hp_key_cmp(HP_KEYDEF *keydef, const byte *rec, const byte *key)
if (seg->charset->coll->strnncollsp(seg->charset,
(uchar*) pos, char_length_rec,
- (uchar*) key, char_length_key))
+ (uchar*) key, char_length_key, 0))
+ return 1;
+ }
+ else if (seg->type == HA_KEYTYPE_VARTEXT1) /* Any VARCHAR segments */
+ {
+ uchar *pos= (uchar*) rec + seg->start;
+ CHARSET_INFO *cs= seg->charset;
+ uint pack_length= seg->bit_start;
+ uint char_length_rec= (pack_length == 1 ? (uint) *(uchar*) pos :
+ uint2korr(pos));
+ /* Key segments are always packed with 2 bytes */
+ uint char_length_key= uint2korr(key);
+ pos+= pack_length;
+ key+= 2; /* skip key pack length */
+ if (cs->mbmaxlen > 1)
+ {
+ uint char_length1, char_length2;
+ char_length1= char_length2= seg->length / cs->mbmaxlen;
+ char_length1= my_charpos(cs, key, key + char_length_key, char_length1);
+ set_if_smaller(char_length_key, char_length1);
+ char_length2= my_charpos(cs, pos, pos + char_length_rec, char_length2);
+ set_if_smaller(char_length_rec, char_length2);
+ }
+
+ if (cs->coll->strnncollsp(seg->charset,
+ (uchar*) pos, char_length_rec,
+ (uchar*) key, char_length_key, 0))
return 1;
}
else
@@ -536,11 +677,20 @@ void hp_make_key(HP_KEYDEF *keydef, byte *key, const byte *rec)
char_length / cs->mbmaxlen);
set_if_smaller(char_length, seg->length); /* QQ: ok to remove? */
}
+ if (seg->type == HA_KEYTYPE_VARTEXT1)
+ char_length+= seg->bit_start; /* Copy also length */
memcpy(key,rec+seg->start,(size_t) char_length);
key+= char_length;
}
}
+#define FIX_LENGTH(cs, pos, length, char_length) \
+ do { \
+ if (length > char_length) \
+ char_length= my_charpos(cs, pos, pos+length, char_length); \
+ set_if_smaller(char_length,length); \
+ } while(0)
+
uint hp_rb_make_key(HP_KEYDEF *keydef, byte *key,
const byte *rec, byte *recpos)
@@ -593,6 +743,26 @@ uint hp_rb_make_key(HP_KEYDEF *keydef, byte *key,
}
continue;
}
+
+ if (seg->flag & HA_VAR_LENGTH_PART)
+ {
+ uchar *pos= (uchar*) rec + seg->start;
+ uint length= seg->length;
+ uint pack_length= seg->bit_start;
+ uint tmp_length= (pack_length == 1 ? (uint) *(uchar*) pos :
+ uint2korr(pos));
+ CHARSET_INFO *cs= seg->charset;
+ char_length= length/cs->mbmaxlen;
+
+ pos+= pack_length; /* Skip VARCHAR length */
+ set_if_smaller(length,tmp_length);
+ FIX_LENGTH(cs, pos, length, char_length);
+ store_key_length_inc(key,char_length);
+ memcpy((byte*) key,(byte*) pos,(size_t) char_length);
+ key+= char_length;
+ continue;
+ }
+
char_length= seg->length;
if (seg->charset->mbmaxlen > 1)
{
@@ -608,7 +778,7 @@ uint hp_rb_make_key(HP_KEYDEF *keydef, byte *key,
key+= seg->length;
}
memcpy(key, &recpos, sizeof(byte*));
- return key - start_key;
+ return (uint) (key - start_key);
}
@@ -643,6 +813,23 @@ uint hp_rb_pack_key(HP_KEYDEF *keydef, uchar *key, const uchar *old,
}
continue;
}
+ if (seg->flag & (HA_VAR_LENGTH_PART | HA_BLOB_PART))
+ {
+ /* Length of key-part used with heap_rkey() always 2 */
+ uint tmp_length=uint2korr(old);
+ uint length= seg->length;
+ CHARSET_INFO *cs= seg->charset;
+ char_length= length/cs->mbmaxlen;
+
+ k_len-= 2+length;
+ old+= 2;
+ set_if_smaller(length,tmp_length); /* Safety */
+ FIX_LENGTH(cs, old, length, char_length);
+ store_key_length_inc(key,char_length);
+ memcpy((byte*) key, old,(size_t) char_length);
+ key+= char_length;
+ continue;
+ }
char_length= seg->length;
if (seg->charset->mbmaxlen > 1)
{
@@ -657,7 +844,7 @@ uint hp_rb_pack_key(HP_KEYDEF *keydef, uchar *key, const uchar *old,
key+= seg->length;
k_len-= seg->length;
}
- return key - start_key;
+ return (uint) (key - start_key);
}
@@ -679,9 +866,30 @@ uint hp_rb_null_key_length(HP_KEYDEF *keydef, const byte *key)
continue;
key+= seg->length;
}
- return key - start_key;
+ return (uint) (key - start_key);
}
+
+uint hp_rb_var_key_length(HP_KEYDEF *keydef, const byte *key)
+{
+ const byte *start_key= key;
+ HA_KEYSEG *seg, *endseg;
+
+ for (seg= keydef->seg, endseg= seg + keydef->keysegs; seg < endseg; seg++)
+ {
+ uint length= seg->length;
+ if (seg->null_bit && !*key++)
+ continue;
+ if (seg->flag & (HA_VAR_LENGTH_PART | HA_BLOB_PART))
+ {
+ get_key_length(length, key);
+ }
+ key+= length;
+ }
+ return (uint) (key - start_key);
+}
+
+
/*
Test if any of the key parts are NULL.
Return:
diff --git a/heap/hp_open.c b/heap/hp_open.c
index 1fa832208fb..fd937229b0d 100644
--- a/heap/hp_open.c
+++ b/heap/hp_open.c
@@ -63,7 +63,7 @@ HP_INFO *heap_open(const char *name, int mode)
#ifndef DBUG_OFF
info->opt_flag= READ_CHECK_USED; /* Check when changing */
#endif
- DBUG_PRINT("exit",("heap: %lx reclength: %d records_in_block: %d",
+ DBUG_PRINT("exit",("heap: 0x%lx reclength: %d records_in_block: %d",
info,share->reclength,share->block.records_in_block));
DBUG_RETURN(info);
}
@@ -82,7 +82,7 @@ HP_SHARE *hp_find_named_heap(const char *name)
info= (HP_SHARE*) pos->data;
if (!strcmp(name, info->name))
{
- DBUG_PRINT("exit", ("Old heap_database: %lx",info));
+ DBUG_PRINT("exit", ("Old heap_database: 0x%lx",info));
DBUG_RETURN(info);
}
}
diff --git a/heap/hp_rkey.c b/heap/hp_rkey.c
index 2c23d9d721e..f5f22a877a1 100644
--- a/heap/hp_rkey.c
+++ b/heap/hp_rkey.c
@@ -23,7 +23,7 @@ int heap_rkey(HP_INFO *info, byte *record, int inx, const byte *key,
HP_SHARE *share= info->s;
HP_KEYDEF *keyinfo= share->keydef + inx;
DBUG_ENTER("heap_rkey");
- DBUG_PRINT("enter",("base: %lx inx: %d",info,inx));
+ DBUG_PRINT("enter",("base: 0x%lx inx: %d",info,inx));
if ((uint) inx >= share->keys)
{
@@ -64,7 +64,7 @@ int heap_rkey(HP_INFO *info, byte *record, int inx, const byte *key,
info->update= 0;
DBUG_RETURN(my_errno);
}
- if (!(keyinfo->flag & HA_NOSAME))
+ if (!(keyinfo->flag & HA_NOSAME) || (keyinfo->flag & HA_END_SPACE_KEY))
memcpy(info->lastkey, key, (size_t) keyinfo->length);
}
memcpy(record, pos, (size_t) share->reclength);
diff --git a/heap/hp_rrnd.c b/heap/hp_rrnd.c
index cce3ce24e51..4daa3a06377 100644
--- a/heap/hp_rrnd.c
+++ b/heap/hp_rrnd.c
@@ -29,7 +29,7 @@ int heap_rrnd(register HP_INFO *info, byte *record, byte *pos)
{
HP_SHARE *share=info->s;
DBUG_ENTER("heap_rrnd");
- DBUG_PRINT("enter",("info: %lx pos: %lx",info,pos));
+ DBUG_PRINT("enter",("info: 0x%lx pos: %lx",info,pos));
info->lastinx= -1;
if (!(info->current_ptr= pos))
@@ -44,7 +44,7 @@ int heap_rrnd(register HP_INFO *info, byte *record, byte *pos)
}
info->update=HA_STATE_PREV_FOUND | HA_STATE_NEXT_FOUND | HA_STATE_AKTIV;
memcpy(record,info->current_ptr,(size_t) share->reclength);
- DBUG_PRINT("exit",("found record at %lx",info->current_ptr));
+ DBUG_PRINT("exit",("found record at 0x%lx",info->current_ptr));
info->current_hash_ptr=0; /* Can't use rnext */
DBUG_RETURN(0);
} /* heap_rrnd */
@@ -64,7 +64,7 @@ int heap_rrnd_old(register HP_INFO *info, byte *record, ulong pos)
{
HP_SHARE *share=info->s;
DBUG_ENTER("heap_rrnd");
- DBUG_PRINT("enter",("info: %lx pos: %ld",info,pos));
+ DBUG_PRINT("enter",("info: 0x%lx pos: %ld",info,pos));
info->lastinx= -1;
if (pos == (ulong) -1)
@@ -98,7 +98,7 @@ end:
}
info->update=HA_STATE_PREV_FOUND | HA_STATE_NEXT_FOUND | HA_STATE_AKTIV;
memcpy(record,info->current_ptr,(size_t) share->reclength);
- DBUG_PRINT("exit",("found record at %lx",info->current_ptr));
+ DBUG_PRINT("exit",("found record at 0x%lx",info->current_ptr));
info->current_hash_ptr=0; /* Can't use rnext */
DBUG_RETURN(0);
} /* heap_rrnd */
diff --git a/heap/hp_update.c b/heap/hp_update.c
index 2ed0edf08de..63ada225f06 100644
--- a/heap/hp_update.c
+++ b/heap/hp_update.c
@@ -37,7 +37,7 @@ int heap_update(HP_INFO *info, const byte *old, const byte *heap_new)
p_lastinx= share->keydef + info->lastinx;
for (keydef= share->keydef, end= keydef + share->keys; keydef < end; keydef++)
{
- if (hp_rec_key_cmp(keydef, old, heap_new))
+ if (hp_rec_key_cmp(keydef, old, heap_new, 0))
{
if ((*keydef->delete_key)(info, keydef, old, pos, keydef == p_lastinx) ||
(*keydef->write_key)(info, keydef, heap_new, pos))
@@ -60,7 +60,7 @@ int heap_update(HP_INFO *info, const byte *old, const byte *heap_new)
err:
if (my_errno == HA_ERR_FOUND_DUPP_KEY)
{
- info->errkey = keydef - share->keydef;
+ info->errkey = (int) (keydef - share->keydef);
if (keydef->algorithm == HA_KEY_ALG_BTREE)
{
/* we don't need to delete non-inserted key from rb-tree */
@@ -74,7 +74,7 @@ int heap_update(HP_INFO *info, const byte *old, const byte *heap_new)
}
while (keydef >= share->keydef)
{
- if (hp_rec_key_cmp(keydef, old, heap_new))
+ if (hp_rec_key_cmp(keydef, old, heap_new, 0))
{
if ((*keydef->delete_key)(info, keydef, heap_new, pos, 0) ||
(*keydef->write_key)(info, keydef, old, pos))
diff --git a/heap/hp_write.c b/heap/hp_write.c
index 808fe6608b1..a60d32eecb6 100644
--- a/heap/hp_write.c
+++ b/heap/hp_write.c
@@ -105,7 +105,7 @@ int hp_rb_write_key(HP_INFO *info, HP_KEYDEF *keyinfo, const byte *record,
custom_arg.key_length= hp_rb_make_key(keyinfo, info->recbuf, record, recpos);
if (keyinfo->flag & HA_NOSAME)
{
- custom_arg.search_flag= SEARCH_FIND | SEARCH_SAME;
+ custom_arg.search_flag= SEARCH_FIND | SEARCH_SAME | SEARCH_UPDATE;
keyinfo->rb_tree.flag= TREE_NO_DUPS;
}
else
@@ -138,7 +138,7 @@ static byte *next_free_record_pos(HP_SHARE *info)
pos=info->del_link;
info->del_link= *((byte**) pos);
info->deleted--;
- DBUG_PRINT("exit",("Used old position: %lx",pos));
+ DBUG_PRINT("exit",("Used old position: 0x%lx",pos));
DBUG_RETURN(pos);
}
if (!(block_pos=(info->records % info->block.records_in_block)))
@@ -370,7 +370,7 @@ int hp_write_key(HP_INFO *info, HP_KEYDEF *keyinfo,
pos=empty;
do
{
- if (! hp_rec_key_cmp(keyinfo, record, pos->ptr_to_rec))
+ if (! hp_rec_key_cmp(keyinfo, record, pos->ptr_to_rec, 1))
{
DBUG_RETURN(my_errno=HA_ERR_FOUND_DUPP_KEY);
}