@@ -12,6 +12,7 @@ use crate::ffi::{
12
12
ext_php_rs_sapi_globals, php_core_globals, sapi_globals_struct, sapi_header_struct,
13
13
sapi_headers_struct, sapi_request_info, zend_is_auto_global, TRACK_VARS_COOKIE , TRACK_VARS_ENV ,
14
14
TRACK_VARS_FILES , TRACK_VARS_GET , TRACK_VARS_POST , TRACK_VARS_REQUEST , TRACK_VARS_SERVER ,
15
+ php_file_globals, file_globals
15
16
} ;
16
17
17
18
use crate :: types:: { ZendHashTable , ZendObject , ZendStr } ;
@@ -358,13 +359,53 @@ impl SapiRequestInfo {
358
359
}
359
360
}
360
361
362
+ /// Stores global variables used in the SAPI.
363
+ pub type FileGlobals = php_file_globals ;
364
+
365
+ impl FileGlobals {
366
+ /// Returns a reference to the PHP process globals.
367
+ ///
368
+ /// The process globals are guarded by a RwLock. There can be multiple
369
+ /// immutable references at one time but only ever one mutable reference.
370
+ /// Attempting to retrieve the globals while already holding the global
371
+ /// guard will lead to a deadlock. Dropping the globals guard will release
372
+ /// the lock.
373
+ pub fn get ( ) -> GlobalReadGuard < Self > {
374
+ // SAFETY: PHP executor globals are statically declared therefore should never
375
+ // return an invalid pointer.
376
+ let globals = unsafe { & file_globals } ;
377
+ let guard = FILE_GLOBALS_LOCK . read ( ) ;
378
+ GlobalReadGuard { globals, guard }
379
+ }
380
+
381
+ /// Returns a mutable reference to the PHP executor globals.
382
+ ///
383
+ /// The executor globals are guarded by a RwLock. There can be multiple
384
+ /// immutable references at one time but only ever one mutable reference.
385
+ /// Attempting to retrieve the globals while already holding the global
386
+ /// guard will lead to a deadlock. Dropping the globals guard will release
387
+ /// the lock.
388
+ pub fn get_mut ( ) -> GlobalWriteGuard < Self > {
389
+ // SAFETY: PHP executor globals are statically declared therefore should never
390
+ // return an invalid pointer.
391
+ let globals = unsafe { & mut file_globals } ;
392
+ let guard = SAPI_GLOBALS_LOCK . write ( ) ;
393
+ GlobalWriteGuard { globals, guard }
394
+ }
395
+
396
+ pub fn stream_wrappers ( & self ) -> Option < & ' static ZendHashTable > {
397
+ unsafe { self . stream_wrappers . as_ref ( ) }
398
+ }
399
+ }
400
+
361
401
/// Executor globals rwlock.
362
402
///
363
403
/// PHP provides no indication if the executor globals are being accessed so
364
404
/// this is only effective on the Rust side.
365
405
static GLOBALS_LOCK : RwLock < ( ) > = const_rwlock ( ( ) ) ;
366
406
static PROCESS_GLOBALS_LOCK : RwLock < ( ) > = const_rwlock ( ( ) ) ;
367
407
static SAPI_GLOBALS_LOCK : RwLock < ( ) > = const_rwlock ( ( ) ) ;
408
+ static FILE_GLOBALS_LOCK : RwLock < ( ) > = const_rwlock ( ( ) ) ;
368
409
369
410
/// Wrapper guard that contains a reference to a given type `T`. Dropping a
370
411
/// guard releases the lock on the relevant rwlock.
0 commit comments