@@ -1444,18 +1444,19 @@ static int hash_blob_stream(struct odb_write_stream *stream,
14441444}
14451445
14461446/*
1447- * Read the contents from fd for size bytes , streaming it to the
1447+ * Read the contents from the stream provided , streaming it to the
14481448 * packfile in state while updating the hash in ctx.
14491449 */
14501450static void stream_blob_to_pack (struct transaction_packfile * state ,
1451- struct git_hash_ctx * ctx , int fd , size_t size ,
1452- const char * path )
1451+ struct git_hash_ctx * ctx , size_t size ,
1452+ struct odb_write_stream * stream )
14531453{
14541454 git_zstream s ;
14551455 unsigned char ibuf [16384 ];
14561456 unsigned char obuf [16384 ];
14571457 unsigned hdrlen ;
14581458 int status = Z_OK ;
1459+ size_t total = 0 ;
14591460
14601461 git_deflate_init (& s , pack_compression_level );
14611462
@@ -1464,23 +1465,20 @@ static void stream_blob_to_pack(struct transaction_packfile *state,
14641465 s .avail_out = sizeof (obuf ) - hdrlen ;
14651466
14661467 while (status != Z_STREAM_END ) {
1467- if (size && !s .avail_in ) {
1468- size_t rsize = size < sizeof (ibuf ) ? size : sizeof (ibuf );
1469- ssize_t read_result = read_in_full (fd , ibuf , rsize );
1470- if (read_result < 0 )
1471- die_errno ("failed to read from '%s'" , path );
1472- if ((size_t )read_result != rsize )
1473- die ("failed to read %u bytes from '%s'" ,
1474- (unsigned )rsize , path );
1468+ if (!stream -> is_finished && !s .avail_in ) {
1469+ ssize_t rsize = stream -> read (stream , ibuf , sizeof (ibuf ));
1470+
1471+ if (rsize < 0 )
1472+ die ("failed to read blob data" );
14751473
14761474 git_hash_update (ctx , ibuf , rsize );
14771475
14781476 s .next_in = ibuf ;
14791477 s .avail_in = rsize ;
1480- size - = rsize ;
1478+ total + = rsize ;
14811479 }
14821480
1483- status = git_deflate (& s , size ? 0 : Z_FINISH );
1481+ status = git_deflate (& s , stream -> is_finished ? Z_FINISH : 0 );
14841482
14851483 if (!s .avail_out || status == Z_STREAM_END ) {
14861484 size_t written = s .next_out - obuf ;
@@ -1500,6 +1498,11 @@ static void stream_blob_to_pack(struct transaction_packfile *state,
15001498 die ("unexpected deflate failure: %d" , status );
15011499 }
15021500 }
1501+
1502+ if (total != size )
1503+ die ("read %" PRIuMAX " bytes of blob data, but expected %" PRIuMAX " bytes" ,
1504+ (uintmax_t )total , (uintmax_t )size );
1505+
15031506 git_deflate_end (& s );
15041507}
15051508
@@ -1571,10 +1574,13 @@ static void flush_packfile_transaction(struct odb_transaction_files *transaction
15711574 * binary blobs, they generally do not want to get any conversion, and
15721575 * callers should avoid this code path when filters are requested.
15731576 */
1574- static int index_blob_packfile_transaction (struct odb_transaction_files * transaction ,
1575- struct object_id * result_oid , int fd ,
1576- size_t size , const char * path )
1577+ static int index_blob_packfile_transaction (struct odb_transaction * base ,
1578+ struct odb_write_stream * stream ,
1579+ size_t size , struct object_id * result_oid )
15771580{
1581+ struct odb_transaction_files * transaction = container_of (base ,
1582+ struct odb_transaction_files ,
1583+ base );
15781584 struct transaction_packfile * state = & transaction -> packfile ;
15791585 struct git_hash_ctx ctx ;
15801586 unsigned char obuf [16384 ];
@@ -1608,7 +1614,7 @@ static int index_blob_packfile_transaction(struct odb_transaction_files *transac
16081614 hashfile_checkpoint (state -> f , & checkpoint );
16091615 idx -> offset = state -> offset ;
16101616 crc32_begin (state -> f );
1611- stream_blob_to_pack (state , & ctx , fd , size , path );
1617+ stream_blob_to_pack (state , & ctx , size , stream );
16121618 git_hash_final_oid (result_oid , & ctx );
16131619
16141620 idx -> crc32 = crc32_end (state -> f );
@@ -1652,15 +1658,12 @@ int index_fd(struct index_state *istate, struct object_id *oid,
16521658
16531659 if (flags & INDEX_WRITE_OBJECT ) {
16541660 struct object_database * odb = the_repository -> objects ;
1655- struct odb_transaction_files * files_transaction ;
1656- struct odb_transaction * transaction ;
1657-
1658- transaction = odb_transaction_begin (odb );
1659- files_transaction = container_of (odb -> transaction ,
1660- struct odb_transaction_files ,
1661- base );
1662- ret = index_blob_packfile_transaction (files_transaction , oid , fd ,
1663- xsize_t (st -> st_size ), path );
1661+ struct odb_transaction * transaction = odb_transaction_begin (odb );
1662+
1663+ ret = index_blob_packfile_transaction (odb -> transaction ,
1664+ & stream ,
1665+ xsize_t (st -> st_size ),
1666+ oid );
16641667 odb_transaction_commit (transaction );
16651668 } else {
16661669 ret = hash_blob_stream (& stream ,
0 commit comments