@@ -3,7 +3,10 @@ use std::{
33 io:: { Read as _, Seek as _, SeekFrom , Write as _} ,
44 os:: unix:: fs:: PermissionsExt as _,
55 path:: { Path , PathBuf } ,
6- sync:: { Arc , Mutex } ,
6+ sync:: {
7+ atomic:: { AtomicU64 , Ordering } ,
8+ Arc , Mutex ,
9+ } ,
710 thread,
811} ;
912
@@ -532,7 +535,7 @@ impl OciDownload {
532535 layers : & [ & OciLayer ] ,
533536 output_dir : & Path ,
534537 ) -> Result < Vec < PathBuf > , DownloadError > {
535- let downloaded = Arc :: new ( Mutex :: new ( 0u64 ) ) ;
538+ let downloaded = Arc :: new ( AtomicU64 :: new ( 0 ) ) ;
536539 let paths = Arc :: new ( Mutex :: new ( Vec :: new ( ) ) ) ;
537540 let errors = Arc :: new ( Mutex :: new ( Vec :: new ( ) ) ) ;
538541
@@ -568,16 +571,14 @@ impl OciDownload {
568571 if path. is_file ( ) {
569572 if let Ok ( metadata) = path. metadata ( ) {
570573 if metadata. len ( ) == layer. size {
571- {
572- let mut shared = downloaded. lock ( ) . unwrap ( ) ;
573- * shared += layer. size ;
574- let current = * shared;
575- if let Some ( ref cb) = on_progress {
576- cb ( Progress :: Chunk {
577- current,
578- total : total_size,
579- } ) ;
580- }
574+ let current = downloaded
575+ . fetch_add ( layer. size , Ordering :: Relaxed )
576+ + layer. size ;
577+ if let Some ( ref cb) = on_progress {
578+ cb ( Progress :: Chunk {
579+ current,
580+ total : total_size,
581+ } ) ;
581582 }
582583 paths. lock ( ) . unwrap ( ) . push ( path) ;
583584 continue ;
@@ -795,7 +796,7 @@ impl OciDownload {
795796 path,
796797 downloaded,
797798 self . on_progress . as_ref ( ) ,
798- & Arc :: new ( Mutex :: new ( 0u64 ) ) ,
799+ & Arc :: new ( AtomicU64 :: new ( 0 ) ) ,
799800 total_size,
800801 )
801802 }
@@ -819,7 +820,7 @@ fn download_layer_impl(
819820 path : & Path ,
820821 local_downloaded : & mut u64 ,
821822 on_progress : Option < & Arc < dyn Fn ( Progress ) + Send + Sync > > ,
822- shared_downloaded : & Arc < Mutex < u64 > > ,
823+ shared_downloaded : & Arc < AtomicU64 > ,
823824 total_size : u64 ,
824825) -> Result < ( ) , DownloadError > {
825826 let url = format ! (
@@ -901,8 +902,7 @@ fn download_layer_impl(
901902
902903 // Add resume offset to shared counter so progress shows correct cumulative total
903904 if is_resuming {
904- let mut shared = shared_downloaded. lock ( ) . unwrap ( ) ;
905- * shared += resume_offset;
905+ shared_downloaded. fetch_add ( resume_offset, Ordering :: Relaxed ) ;
906906 }
907907
908908 loop {
@@ -914,11 +914,7 @@ fn download_layer_impl(
914914 file. write_all ( & buffer[ ..n] ) ?;
915915 * local_downloaded += n as u64 ;
916916
917- let current_total = {
918- let mut shared = shared_downloaded. lock ( ) . unwrap ( ) ;
919- * shared += n as u64 ;
920- * shared
921- } ;
917+ let current_total = { shared_downloaded. fetch_add ( n as u64 , Ordering :: Relaxed ) + n as u64 } ;
922918
923919 let checkpoint = * local_downloaded / ( 1024 * 1024 ) ;
924920 if checkpoint > last_checkpoint {
0 commit comments