@@ -411,12 +411,7 @@ impl ImageProxy {
411
411
} ) ;
412
412
}
413
413
let fdret = match ( fdret, reply. pipeid ) {
414
- ( Some ( fd) , n) => {
415
- if n == 0 {
416
- return Err ( Error :: Other ( "got fd but no pipeid" . into ( ) ) ) ;
417
- }
418
- Some ( ( fd, n) )
419
- }
414
+ ( Some ( fd) , n) => Some ( ( fd, n) ) ,
420
415
( None , n) => {
421
416
if n != 0 {
422
417
return Err ( Error :: Other ( format ! ( "got no fd with pipeid {}" , n) . into ( ) ) ) ;
@@ -458,6 +453,7 @@ impl ImageProxy {
458
453
#[ instrument]
459
454
async fn finish_pipe ( & self , pipeid : u32 ) -> Result < ( ) > {
460
455
tracing:: debug!( "closing pipe" ) ;
456
+ debug_assert ! ( pipeid > 0 ) ;
461
457
let ( r, fd) = self . impl_request ( "FinishPipe" , [ pipeid] ) . await ?;
462
458
if fd. is_some ( ) {
463
459
return Err ( Error :: Other ( "Unexpected fd in finish_pipe reply" . into ( ) ) ) ;
@@ -496,6 +492,9 @@ impl ImageProxy {
496
492
497
493
async fn read_all_fd ( & self , fd : Option < ( OwnedFd , u32 ) > ) -> Result < Vec < u8 > > {
498
494
let ( fd, pipeid) = fd. ok_or_else ( || Error :: Other ( "Missing fd from reply" . into ( ) ) ) ?;
495
+ if pipeid == 0 {
496
+ return Err ( Error :: Other ( "got fd but no pipeid" . into ( ) ) ) ;
497
+ }
499
498
let fd = tokio:: fs:: File :: from_std ( std:: fs:: File :: from ( fd) ) ;
500
499
let mut fd = tokio:: io:: BufReader :: new ( fd) ;
501
500
let mut r = Vec :: new ( ) ;
@@ -570,12 +569,33 @@ impl ImageProxy {
570
569
vec ! [ img. 0 . into( ) , digest. to_string( ) . into( ) , size. into( ) ] ;
571
570
let ( _bloblen, fd) = self . impl_request :: < i64 , _ , _ > ( "GetBlob" , args) . await ?;
572
571
let ( fd, pipeid) = fd. ok_or_else ( || Error :: new_other ( "Missing fd from reply" ) ) ?;
572
+ if pipeid == 0 {
573
+ return Err ( Error :: Other ( "got fd but no pipeid" . into ( ) ) ) ;
574
+ }
573
575
let fd = tokio:: fs:: File :: from_std ( std:: fs:: File :: from ( fd) ) ;
574
576
let fd = tokio:: io:: BufReader :: new ( fd) ;
575
577
let finish = Box :: pin ( self . finish_pipe ( pipeid) ) ;
576
578
Ok ( ( fd, finish) )
577
579
}
578
580
581
+ /// Fetch a blob identified by e.g. `sha256:<digest>`; does not perform
582
+ /// any verification that the blob matches the digest. The size of the
583
+ /// blob and a pipe file descriptor are returned.
584
+ #[ instrument]
585
+ pub async fn get_raw_blob (
586
+ & self ,
587
+ img : & OpenedImage ,
588
+ digest : & Digest ,
589
+ ) -> Result < ( u64 , tokio:: fs:: File ) > {
590
+ tracing:: debug!( "fetching blob" ) ;
591
+ let args: Vec < serde_json:: Value > = vec ! [ img. 0 . into( ) , digest. to_string( ) . into( ) ] ;
592
+ let ( bloblen, fd) = self . impl_request :: < u64 , _ , _ > ( "GetRawBlob" , args) . await ?;
593
+ let ( fd, pipeid) = fd. ok_or_else ( || Error :: new_other ( "Missing fd from reply" ) ) ?;
594
+ debug_assert_eq ! ( pipeid, 0 ) ;
595
+ let fd = tokio:: fs:: File :: from_std ( std:: fs:: File :: from ( fd) ) ;
596
+ Ok ( ( bloblen, fd) )
597
+ }
598
+
579
599
/// Fetch a descriptor. The requested size and digest are verified (by the proxy process).
580
600
#[ instrument]
581
601
pub async fn get_descriptor (
0 commit comments