Susumu Yata
null+****@clear*****
Mon Dec 7 12:29:09 JST 2015
Susumu Yata 2015-12-07 12:29:09 +0900 (Mon, 07 Dec 2015) New Revision: 7c338c60159262a0a60f8c5c480b48df6f7f56e8 https://github.com/groonga/groonga/commit/7c338c60159262a0a60f8c5c480b48df6f7f56e8 Message: grn_ja_reader: support Zlib compressed values GitHub: #441 Modified files: lib/grn_store.h lib/store.c Modified: lib/grn_store.h (+1 -1) =================================================================== --- lib/grn_store.h 2015-12-07 12:38:18 +0900 (f9fb86e) +++ lib/grn_store.h 2015-12-07 12:29:09 +0900 (c5da1b1) @@ -104,7 +104,6 @@ void grn_ja_check(grn_ctx *ctx, grn_ja *ja); /* * grn_ja_reader is designed to improve the performance of sequential access. - * FIXME: Compressed values are not supported yet. */ typedef struct { grn_ja *ja; @@ -150,6 +149,7 @@ grn_rc grn_ja_reader_read(grn_ctx *ctx, grn_ja_reader *reader, void *buf); /* * grn_ja_reader_pread() reads a part of the current value to `buf`. * If `offset` and `size` are invalid, the behavior is undefined. + * FIXME: Compressed values are not supported yet. */ grn_rc grn_ja_reader_pread(grn_ctx *ctx, grn_ja_reader *reader, size_t offset, size_t size, void *buf); Modified: lib/store.c (+61 -16) =================================================================== --- lib/store.c 2015-12-07 12:38:18 +0900 (4adb024) +++ lib/store.c 2015-12-07 12:29:09 +0900 (b99fe46) @@ -1621,18 +1621,9 @@ grn_ja_reader_close(grn_ctx *ctx, grn_ja_reader *reader) return GRN_SUCCESS; } -#ifdef GRN_WITH_ZLIB -static grn_rc -grn_ja_reader_seek_zlib(grn_ctx *ctx, grn_ja_reader *reader, grn_id id) -{ - // TODO - return GRN_FUNCTION_NOT_IMPLEMENTED; -} -#endif /* GRN_WITH_ZLIB */ - -#ifdef GRN_WITH_LZ4 +#if defined(GRN_WITH_ZLIB) || defined(GRN_WITH_LZ4) static grn_rc -grn_ja_reader_seek_lz4(grn_ctx *ctx, grn_ja_reader *reader, grn_id id) +grn_ja_reader_seek_compressed(grn_ctx *ctx, grn_ja_reader *reader, grn_id id) { grn_ja_einfo *einfo; void *seg_addr; @@ -1676,7 +1667,7 @@ grn_ja_reader_seek_lz4(grn_ctx *ctx, grn_ja_reader *reader, grn_id id) reader->value_size = (uint32_t)*(uint64_t *)seg_addr; return GRN_SUCCESS; } -#endif /* GRN_WITH_LZ4 */ +#endif /* defined(GRN_WITH_ZLIB) || defined(GRN_WITH_LZ4) */ static grn_rc grn_ja_reader_seek_raw(grn_ctx *ctx, grn_ja_reader *reader, grn_id id) @@ -1725,12 +1716,12 @@ grn_ja_reader_seek(grn_ctx *ctx, grn_ja_reader *reader, grn_id id) { #ifdef GRN_WITH_ZLIB if (reader->ja->header->flags & GRN_OBJ_COMPRESS_ZLIB) { - return grn_ja_reader_seek_zlib(ctx, reader, id); + return grn_ja_reader_seek_compressed(ctx, reader, id); } #endif /* GRN_WITH_ZLIB */ #ifdef GRN_WITH_LZ4 if (reader->ja->header->flags & GRN_OBJ_COMPRESS_LZ4) { - return grn_ja_reader_seek_lz4(ctx, reader, id); + return grn_ja_reader_seek_compressed(ctx, reader, id); } #endif /* GRN_WITH_LZ4 */ return grn_ja_reader_seek_raw(ctx, reader, id); @@ -1740,8 +1731,62 @@ grn_ja_reader_seek(grn_ctx *ctx, grn_ja_reader *reader, grn_id id) static grn_rc grn_ja_reader_read_zlib(grn_ctx *ctx, grn_ja_reader *reader, void *buf) { - // TODO - return GRN_FUNCTION_NOT_IMPLEMENTED; + uLong dest_size = reader->value_size; + grn_ja_einfo *einfo = (grn_ja_einfo *)reader->einfo; + if (EHUGE_P(einfo)) { + /* TODO: Use z_stream to avoid copy. */ + grn_io *io = reader->ja->io; + void *seg_addr; + char *packed_ptr; + uint32_t size, seg_id; + if (reader->packed_size > reader->packed_buf_size) { + void *new_buf = GRN_REALLOC(reader->packed_buf, reader->packed_size); + if (!new_buf) { + return GRN_NO_MEMORY_AVAILABLE; + } + reader->packed_buf = new_buf; + reader->packed_buf_size = reader->packed_size; + } + packed_ptr = (char *)reader->packed_buf; + grn_memcpy(packed_ptr, (char *)reader->body_seg_addr + sizeof(uint64_t), + io->header->segment_size - sizeof(uint64_t)); + packed_ptr += io->header->segment_size - sizeof(uint64_t); + size = reader->packed_size - (io->header->segment_size - sizeof(uint64_t)); + seg_id = reader->body_seg_id + 1; + while (size > io->header->segment_size) { + GRN_IO_SEG_REF(io, seg_id, seg_addr); + if (!seg_addr) { + return GRN_UNKNOWN_ERROR; + } + grn_memcpy(packed_ptr, seg_addr, io->header->segment_size); + GRN_IO_SEG_UNREF(io, seg_id); + seg_id++; + size -= io->header->segment_size; + packed_ptr += io->header->segment_size; + } + GRN_IO_SEG_REF(io, seg_id, seg_addr); + if (!seg_addr) { + return GRN_UNKNOWN_ERROR; + } + grn_memcpy(packed_ptr, seg_addr, size); + GRN_IO_SEG_UNREF(io, seg_id); + seg_id++; + if (uncompress((Bytef *)buf, &dest_size, (const Bytef *)reader->packed_buf, + reader->packed_size - sizeof(uint64_t)) != Z_OK) { + return GRN_UNKNOWN_ERROR; + } + } else { + char *packed_addr = (char *)reader->body_seg_addr; + packed_addr += reader->body_seg_offset + sizeof(uint64_t); + if (uncompress((Bytef *)buf, &dest_size, (const Bytef *)packed_addr, + reader->packed_size - sizeof(uint64_t)) != Z_OK) { + return GRN_UNKNOWN_ERROR; + } + } + if (dest_size != reader->value_size) { + return GRN_UNKNOWN_ERROR; + } + return GRN_SUCCESS; } #endif /* GRN_WITH_ZLIB */ -------------- next part -------------- HTML����������������������������... Descargar