@@ -616,7 +616,7 @@ impl<V: Vfs> Pager<V> {
616616 {
617617 let mut cache = self . inner . cache_for_key ( file) . lock ( ) ;
618618 if let Some ( page) = cache. get ( ( file, page_id) ) {
619- if page. realm_id_bytes != [ 0u8 ; 16 ] && page . realm_id_bytes != realm_id. 0 {
619+ if page. realm_id_bytes != Some ( realm_id. 0 ) {
620620 return Err ( PagedbError :: ChecksumFailure ) ;
621621 }
622622 self . inner . record_hit ( file) ;
@@ -1030,6 +1030,57 @@ mod tests {
10301030 assert ! ( matches!( err, PagedbError :: ChecksumFailure ) ) ;
10311031 }
10321032
1033+ #[ tokio:: test( flavor = "current_thread" ) ]
1034+ async fn cached_pages_require_an_exact_realm_match ( ) {
1035+ let pager = mk_pager ( ) . await ;
1036+ let zero_realm = RealmId ( [ 0 ; 16 ] ) ;
1037+ let nonzero_realm = RealmId ( [ 1 ; 16 ] ) ;
1038+ let body = vec ! [ 0u8 ; PAGE - ENVELOPE_OVERHEAD ] ;
1039+
1040+ pager
1041+ . write_main_page ( 1 , zero_realm, PageKind :: BTreeLeaf , & body)
1042+ . await
1043+ . unwrap ( ) ;
1044+ pager
1045+ . write_main_page ( 2 , nonzero_realm, PageKind :: BTreeLeaf , & body)
1046+ . await
1047+ . unwrap ( ) ;
1048+
1049+ {
1050+ let mut cache = pager. inner . buffer_pool . lock ( ) ;
1051+ assert_eq ! (
1052+ cache
1053+ . get( ( FileKey :: Main , 1 ) )
1054+ . map( |page| page. realm_id_bytes) ,
1055+ Some ( Some ( zero_realm. 0 ) )
1056+ ) ;
1057+ assert_eq ! (
1058+ cache
1059+ . get( ( FileKey :: Main , 2 ) )
1060+ . map( |page| page. realm_id_bytes) ,
1061+ Some ( Some ( nonzero_realm. 0 ) )
1062+ ) ;
1063+ }
1064+
1065+ for ( page_id, requested_realm) in [ ( 1 , nonzero_realm) , ( 2 , zero_realm) ] {
1066+ let misses_before = pager. inner . buffer_pool_misses . load ( AtomOrd :: Relaxed ) ;
1067+ let cache_len_before = pager. inner . buffer_pool . lock ( ) . len ( ) ;
1068+ let err = pager
1069+ . read_main_page ( page_id, requested_realm, PageKind :: BTreeLeaf )
1070+ . await
1071+ . err ( )
1072+ . unwrap ( ) ;
1073+
1074+ assert ! ( matches!( err, PagedbError :: ChecksumFailure ) ) ;
1075+ assert_eq ! (
1076+ pager. inner. buffer_pool_misses. load( AtomOrd :: Relaxed ) ,
1077+ misses_before,
1078+ "cached realm mismatch must not fall back to disk"
1079+ ) ;
1080+ assert_eq ! ( pager. inner. buffer_pool. lock( ) . len( ) , cache_len_before) ;
1081+ }
1082+ }
1083+
10331084 #[ tokio:: test( flavor = "current_thread" ) ]
10341085 async fn rejects_illegal_page_kind_on_main ( ) {
10351086 let pager = mk_pager ( ) . await ;
0 commit comments