Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Skip to content

Commit e30d03c

Browse files
author
Nikita Glukhov
committed
WIP: versioned TOAST chunks
1 parent 70bd424 commit e30d03c

File tree

13 files changed

+314
-161
lines changed

13 files changed

+314
-161
lines changed

src/backend/access/common/detoast.c

Lines changed: 36 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ detoast_external_attr(struct varlena *attr)
4646
{
4747
struct varlena *result;
4848

49-
if (VARATT_IS_EXTERNAL_ONDISK(attr) || VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
49+
if (VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
5050
{
5151
/*
5252
* This is an external stored plain value
@@ -115,7 +115,7 @@ detoast_external_attr(struct varlena *attr)
115115
struct varlena *
116116
detoast_attr(struct varlena *attr)
117117
{
118-
if (VARATT_IS_EXTERNAL_ONDISK(attr) || VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
118+
if (VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
119119
{
120120
/*
121121
* This is an externally stored datum --- fetch it back from there
@@ -226,15 +226,14 @@ detoast_attr_slice(struct varlena *attr,
226226
//if (VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
227227
// elog(ERROR, "slicing of chunked attributes is not yet supported"); /* FIXME */
228228

229-
if (VARATT_IS_EXTERNAL_ONDISK(attr) ||
230-
VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
229+
if (VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
231230
{
232-
struct varatt_external toast_pointer;
231+
struct varatt_external_versioned toast_pointer;
233232

234233
VARATT_EXTERNAL_INLINE_GET_POINTER(toast_pointer, attr);
235234

236235
/* fast path for non-compressed external datums */
237-
if (!VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer))
236+
if (!VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer.va_external))
238237
return toast_fetch_datum_slice(attr, sliceoffset, slicelength);
239238

240239
/*
@@ -244,7 +243,7 @@ detoast_attr_slice(struct varlena *attr,
244243
*/
245244
if (slicelimit >= 0)
246245
{
247-
int32 max_size = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer);
246+
int32 max_size = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer.va_external);
248247

249248
/*
250249
* Determine maximum amount of compressed data needed for a prefix
@@ -255,7 +254,7 @@ detoast_attr_slice(struct varlena *attr,
255254
* determine how much compressed data we need to be sure of being
256255
* able to decompress the required slice.
257256
*/
258-
if (VARATT_EXTERNAL_GET_COMPRESS_METHOD(toast_pointer) ==
257+
if (VARATT_EXTERNAL_GET_COMPRESS_METHOD(toast_pointer.va_external) ==
259258
TOAST_PGLZ_COMPRESSION_ID)
260259
max_size = pglz_maximum_compressed_size(slicelimit, max_size);
261260

@@ -346,9 +345,9 @@ detoast_attr_slice(struct varlena *attr,
346345
DetoastIterator
347346
create_detoast_iterator(struct varlena *attr)
348347
{
349-
struct varatt_external toast_pointer;
348+
struct varatt_external_versioned toast_pointer;
350349
DetoastIterator iter;
351-
if (VARATT_IS_EXTERNAL_ONDISK(attr) || VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
350+
if (VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
352351
{
353352
FetchDatumIterator fetch_iter;
354353
int32 inlineSize;
@@ -363,13 +362,13 @@ create_detoast_iterator(struct varlena *attr)
363362
/* Must copy to access aligned fields */
364363
inlineSize = VARATT_EXTERNAL_INLINE_GET_POINTER(toast_pointer, attr);
365364

366-
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer))
365+
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer.va_external))
367366
{
368367
iter->compressed = true;
369-
iter->compression_method = VARATT_EXTERNAL_GET_COMPRESS_METHOD(toast_pointer);
368+
iter->compression_method = VARATT_EXTERNAL_GET_COMPRESS_METHOD(toast_pointer.va_external);
370369

371370
/* prepare buffer to received decompressed data */
372-
iter->buf = create_toast_buffer(toast_pointer.va_rawsize, false);
371+
iter->buf = create_toast_buffer(toast_pointer.va_external.va_rawsize, false);
373372
}
374373
else
375374
{
@@ -472,21 +471,21 @@ toast_fetch_datum(struct varlena *attr)
472471
{
473472
Relation toastrel;
474473
struct varlena *result;
475-
struct varatt_external toast_pointer;
474+
struct varatt_external_versioned toast_pointer;
476475
int32 attrsize;
477476
int32 inline_size;
478477
char *detoast_ptr;
479478

480-
if (!VARATT_IS_EXTERNAL_ONDISK(attr) && !VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
479+
if (!VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
481480
elog(ERROR, "toast_fetch_datum shouldn't be called for non-ondisk datums");
482481

483482
/* Must copy to access aligned fields */
484483
inline_size = VARATT_EXTERNAL_INLINE_GET_POINTER(toast_pointer, attr);
485-
attrsize = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer);
484+
attrsize = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer.va_external);
486485

487486
result = (struct varlena *) palloc(attrsize + VARHDRSZ);
488487

489-
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer))
488+
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer.va_external))
490489
SET_VARSIZE_COMPRESSED(result, attrsize + VARHDRSZ);
491490
else
492491
SET_VARSIZE(result, attrsize + VARHDRSZ);
@@ -511,10 +510,12 @@ toast_fetch_datum(struct varlena *attr)
511510
/*
512511
* Open the toast relation and its indexes
513512
*/
514-
toastrel = table_open(toast_pointer.va_toastrelid, AccessShareLock);
513+
toastrel = table_open(toast_pointer.va_external.va_toastrelid, AccessShareLock);
515514

516515
/* Fetch all chunks */
517-
table_relation_fetch_toast_slice(toastrel, toast_pointer.va_valueid,
516+
table_relation_fetch_toast_slice(toastrel,
517+
toast_pointer.va_external.va_valueid,
518+
toast_pointer.va_version,
518519
attrsize - inline_size, 0, attrsize - inline_size,
519520
(struct varlena *) detoast_ptr);
520521

@@ -541,12 +542,11 @@ toast_fetch_datum_slice(struct varlena *attr, int32 sliceoffset,
541542
{
542543
Relation toastrel;
543544
struct varlena *result;
544-
struct varatt_external toast_pointer;
545+
struct varatt_external_versioned toast_pointer;
545546
int32 attrsize;
546547
int32 inline_size;
547548

548-
if (!VARATT_IS_EXTERNAL_ONDISK(attr) &&
549-
!VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
549+
if (!VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
550550
elog(ERROR, "toast_fetch_datum_slice shouldn't be called for non-ondisk datums");
551551

552552
/* Must copy to access aligned fields */
@@ -557,9 +557,9 @@ toast_fetch_datum_slice(struct varlena *attr, int32 sliceoffset,
557557
* prefix -- this isn't lo_* we can't return a compressed datum which is
558558
* meaningful to toast later.
559559
*/
560-
Assert(!VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer) || 0 == sliceoffset);
560+
Assert(!VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer.va_external) || 0 == sliceoffset);
561561

562-
attrsize = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer);
562+
attrsize = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer.va_external);
563563

564564
if (sliceoffset >= attrsize)
565565
{
@@ -572,7 +572,7 @@ toast_fetch_datum_slice(struct varlena *attr, int32 sliceoffset,
572572
* space required by va_tcinfo, which is stored at the beginning as an
573573
* int32 value.
574574
*/
575-
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer) && slicelength > 0)
575+
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer.va_external) && slicelength > 0)
576576
slicelength = slicelength + sizeof(int32);
577577

578578
/*
@@ -585,7 +585,7 @@ toast_fetch_datum_slice(struct varlena *attr, int32 sliceoffset,
585585

586586
result = (struct varlena *) palloc(slicelength + VARHDRSZ);
587587

588-
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer))
588+
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer.va_external))
589589
SET_VARSIZE_COMPRESSED(result, slicelength + VARHDRSZ);
590590
else
591591
SET_VARSIZE(result, slicelength + VARHDRSZ);
@@ -619,10 +619,12 @@ toast_fetch_datum_slice(struct varlena *attr, int32 sliceoffset,
619619
return result; /* Can save a lot of work at this point! */
620620

621621
/* Open the toast relation */
622-
toastrel = table_open(toast_pointer.va_toastrelid, AccessShareLock);
622+
toastrel = table_open(toast_pointer.va_external.va_toastrelid, AccessShareLock);
623623

624624
/* Fetch all chunks */
625-
table_relation_fetch_toast_slice(toastrel, toast_pointer.va_valueid,
625+
table_relation_fetch_toast_slice(toastrel,
626+
toast_pointer.va_external.va_valueid,
627+
toast_pointer.va_version,
626628
attrsize - inline_size, sliceoffset, slicelength,
627629
result);
628630

@@ -717,13 +719,13 @@ toast_raw_datum_size(Datum value)
717719
struct varlena *attr = (struct varlena *) DatumGetPointer(value);
718720
Size result;
719721

720-
if (VARATT_IS_EXTERNAL_ONDISK(attr) || VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
722+
if (VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
721723
{
722724
/* va_rawsize is the size of the original datum -- including header */
723-
struct varatt_external toast_pointer;
725+
struct varatt_external_versioned toast_pointer;
724726

725727
VARATT_EXTERNAL_INLINE_GET_POINTER(toast_pointer, attr);
726-
result = toast_pointer.va_rawsize;
728+
result = toast_pointer.va_external.va_rawsize;
727729
}
728730
else if (VARATT_IS_EXTERNAL_INDIRECT(attr))
729731
{
@@ -773,18 +775,17 @@ toast_datum_size(Datum value)
773775
struct varlena *attr = (struct varlena *) DatumGetPointer(value);
774776
Size result;
775777

776-
if (VARATT_IS_EXTERNAL_ONDISK(attr) ||
777-
VARATT_IS_EXTERNAL_ONDISK_INLINE(attr))
778+
if (VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
778779
{
779780
/*
780781
* Attribute is stored externally - return the extsize whether
781782
* compressed or not. We do not count the size of the toast pointer
782783
* ... should we?
783784
*/
784-
struct varatt_external toast_pointer;
785+
struct varatt_external_versioned toast_pointer;
785786

786787
VARATT_EXTERNAL_INLINE_GET_POINTER(toast_pointer, attr);
787-
result = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer); /* FIXME inlineSize */
788+
result = VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer.va_external); /* FIXME inlineSize */
788789
}
789790
else if (VARATT_IS_EXTERNAL_INDIRECT(attr))
790791
{

src/backend/access/common/toast_compression.c

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -339,14 +339,14 @@ toast_get_compression_id(struct varlena *attr)
339339
* external toast pointer. If compressed inline, fetch it from the toast
340340
* compression header.
341341
*/
342-
if (VARATT_IS_EXTERNAL_ONDISK(attr))
342+
if (VARATT_IS_EXTERNAL_ONDISK_ANY(attr))
343343
{
344-
struct varatt_external toast_pointer;
344+
struct varatt_external_versioned toast_pointer;
345345

346-
VARATT_EXTERNAL_GET_POINTER(toast_pointer, attr);
346+
VARATT_EXTERNAL_INLINE_GET_POINTER(toast_pointer, attr);
347347

348-
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer))
349-
cmid = VARATT_EXTERNAL_GET_COMPRESS_METHOD(toast_pointer);
348+
if (VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer.va_external))
349+
cmid = VARATT_EXTERNAL_GET_COMPRESS_METHOD(toast_pointer.va_external);
350350
}
351351
else if (VARATT_IS_COMPRESSED(attr))
352352
cmid = VARDATA_COMPRESSED_GET_COMPRESS_METHOD(attr);

0 commit comments

Comments
 (0)