@@ -617,13 +617,15 @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
617
617
int nb_sectors , QEMUIOVector * qiov )
618
618
{
619
619
BDRVQcowState * s = bs -> opaque ;
620
- int index_in_cluster ;
620
+ int offset_in_cluster ;
621
621
int ret = 0 , n ;
622
622
uint64_t cluster_offset ;
623
623
struct iovec hd_iov ;
624
624
QEMUIOVector hd_qiov ;
625
625
uint8_t * buf ;
626
626
void * orig_buf ;
627
+ int64_t offset = sector_num * BDRV_SECTOR_SIZE ;
628
+ int64_t bytes = nb_sectors * BDRV_SECTOR_SIZE ;
627
629
628
630
if (qiov -> niov > 1 ) {
629
631
buf = orig_buf = qemu_try_blockalign (bs , qiov -> size );
@@ -637,77 +639,73 @@ static coroutine_fn int qcow_co_readv(BlockDriverState *bs, int64_t sector_num,
637
639
638
640
qemu_co_mutex_lock (& s -> lock );
639
641
640
- while (nb_sectors != 0 ) {
642
+ while (bytes != 0 ) {
641
643
/* prepare next request */
642
- ret = get_cluster_offset (bs , sector_num << 9 ,
643
- 0 , 0 , 0 , 0 , & cluster_offset );
644
+ ret = get_cluster_offset (bs , offset , 0 , 0 , 0 , 0 , & cluster_offset );
644
645
if (ret < 0 ) {
645
646
break ;
646
647
}
647
- index_in_cluster = sector_num & (s -> cluster_sectors - 1 );
648
- n = s -> cluster_sectors - index_in_cluster ;
649
- if (n > nb_sectors ) {
650
- n = nb_sectors ;
648
+ offset_in_cluster = offset & (s -> cluster_size - 1 );
649
+ n = s -> cluster_size - offset_in_cluster ;
650
+ if (n > bytes ) {
651
+ n = bytes ;
651
652
}
652
653
653
654
if (!cluster_offset ) {
654
655
if (bs -> backing ) {
655
656
/* read from the base image */
656
657
hd_iov .iov_base = (void * )buf ;
657
- hd_iov .iov_len = n * 512 ;
658
+ hd_iov .iov_len = n ;
658
659
qemu_iovec_init_external (& hd_qiov , & hd_iov , 1 );
659
660
qemu_co_mutex_unlock (& s -> lock );
660
661
/* qcow2 emits this on bs->file instead of bs->backing */
661
662
BLKDBG_EVENT (bs -> file , BLKDBG_READ_BACKING_AIO );
662
- ret = bdrv_co_readv (bs -> backing , sector_num , n , & hd_qiov );
663
+ ret = bdrv_co_preadv (bs -> backing , offset , n , & hd_qiov , 0 );
663
664
qemu_co_mutex_lock (& s -> lock );
664
665
if (ret < 0 ) {
665
666
break ;
666
667
}
667
668
} else {
668
669
/* Note: in this case, no need to wait */
669
- memset (buf , 0 , 512 * n );
670
+ memset (buf , 0 , n );
670
671
}
671
672
} else if (cluster_offset & QCOW_OFLAG_COMPRESSED ) {
672
673
/* add AIO support for compressed blocks ? */
673
674
if (decompress_cluster (bs , cluster_offset ) < 0 ) {
674
675
ret = - EIO ;
675
676
break ;
676
677
}
677
- memcpy (buf ,
678
- s -> cluster_cache + index_in_cluster * 512 , 512 * n );
678
+ memcpy (buf , s -> cluster_cache + offset_in_cluster , n );
679
679
} else {
680
680
if ((cluster_offset & 511 ) != 0 ) {
681
681
ret = - EIO ;
682
682
break ;
683
683
}
684
684
hd_iov .iov_base = (void * )buf ;
685
- hd_iov .iov_len = n * 512 ;
685
+ hd_iov .iov_len = n ;
686
686
qemu_iovec_init_external (& hd_qiov , & hd_iov , 1 );
687
687
qemu_co_mutex_unlock (& s -> lock );
688
688
BLKDBG_EVENT (bs -> file , BLKDBG_READ_AIO );
689
- ret = bdrv_co_readv (bs -> file ,
690
- (cluster_offset >> 9 ) + index_in_cluster ,
691
- n , & hd_qiov );
689
+ ret = bdrv_co_preadv (bs -> file , cluster_offset + offset_in_cluster ,
690
+ n , & hd_qiov , 0 );
692
691
qemu_co_mutex_lock (& s -> lock );
693
692
if (ret < 0 ) {
694
693
break ;
695
694
}
696
695
if (bs -> encrypted ) {
697
696
assert (s -> crypto );
698
697
if (qcrypto_block_decrypt (s -> crypto ,
699
- sector_num * BDRV_SECTOR_SIZE , buf ,
700
- n * BDRV_SECTOR_SIZE , NULL ) < 0 ) {
698
+ offset , buf , n , NULL ) < 0 ) {
701
699
ret = - EIO ;
702
700
break ;
703
701
}
704
702
}
705
703
}
706
704
ret = 0 ;
707
705
708
- nb_sectors -= n ;
709
- sector_num += n ;
710
- buf += n * 512 ;
706
+ bytes -= n ;
707
+ offset += n ;
708
+ buf += n ;
711
709
}
712
710
713
711
qemu_co_mutex_unlock (& s -> lock );
0 commit comments