From cf7d5b774fcd0c71348acb660216c6bce8dccc71 Mon Sep 17 00:00:00 2001 From: marko Date: Thu, 29 Nov 2007 10:07:47 +0000 Subject: [PATCH] branches/zip: trx_undo_rec_get_partial_row(): Set up the row_ext cache only for those externally stored columns that occur in the ordering columns of indexes. Prefetch the prefixes of those columns, because the clustered index record and the BLOBs may have been deleted by the time when the purge thread needs to read the BLOB prefixes. row_ext_create(): Add the debug assertion ut_ad(ut_is_2pow(zip_size)). --- include/row0ext.ic | 2 ++ trx/trx0rec.c | 48 ++++++++++++++++++++++++++++++++++++++-------- 2 files changed, 42 insertions(+), 8 deletions(-) diff --git a/include/row0ext.ic b/include/row0ext.ic index 78f3ef10700..eedc83552f8 100644 --- a/include/row0ext.ic +++ b/include/row0ext.ic @@ -42,6 +42,8 @@ row_ext_create( row_ext_t* ret = mem_heap_alloc(heap, (sizeof *ret) + (n_ext - 1) * sizeof ret->len); + ut_ad(ut_is_2pow(zip_size)); + ret->n_ext = n_ext; ret->ext = ext; ret->zip_size = zip_size; diff --git a/trx/trx0rec.c b/trx/trx0rec.c index df32afc351d..faf11431a6f 100644 --- a/trx/trx0rec.c +++ b/trx/trx0rec.c @@ -894,7 +894,11 @@ trx_undo_rec_get_partial_row( ulint n_ext_cols; ulint* ext_cols; - ut_ad(index && ptr && row && ext && heap); + ut_ad(index); + ut_ad(ptr); + ut_ad(row); + ut_ad(heap); + ut_ad(dict_index_is_clust(index)); row_len = dict_table_get_n_cols(index->table); n_ext_cols = 0; @@ -908,15 +912,17 @@ trx_undo_rec_get_partial_row( ptr += 2; while (ptr != end_ptr) { - dfield_t* dfield; - byte* field; - ulint field_no; - ulint col_no; - ulint len; + dfield_t* dfield; + byte* field; + ulint field_no; + const dict_col_t* col; + ulint col_no; + ulint len; ptr = trx_undo_update_rec_get_field_no(ptr, &field_no); - col_no = dict_index_get_nth_col_no(index, field_no); + col = dict_index_get_nth_col(index, field_no); + col_no = dict_col_get_no(col); ptr = trx_undo_rec_get_col_val(ptr, &field, &len); @@ -929,14 +935,40 @@ trx_undo_rec_get_partial_row( dfield_set_len(dfield, len - UNIV_EXTERN_STORAGE_FIELD); dfield_set_ext(dfield); - ext_cols[n_ext_cols++] = col_no; + if (col->ord_part) { + /* We will have to fetch prefixes of + externally stored columns that are + referenced by column prefixes. */ + ext_cols[n_ext_cols++] = col_no; + } } } if (n_ext_cols) { + ulint i; + *ext = row_ext_create(n_ext_cols, ext_cols, dict_table_zip_size(index->table), heap); + + /* Fetch the BLOB prefixes, because the clustered + index record (and the BLOBs) may have been deleted by + the time row_ext_lookup() is called later in the purge + thread. */ + for (i = 0; i < n_ext_cols; i++) { + const dfield_t* dfield; + ulint len; + byte* b; + + dfield = dtuple_get_nth_field(*row, ext_cols[i]); + + b = row_ext_lookup_ith(*ext, i, + dfield_get_data(dfield), + dfield_get_len(dfield), + &len); + ut_a(b); + ut_a(b != field_ref_zero); + } } else { *ext = NULL; }