Repository navigation
Expand file tree
/
Copy pathinterpreter.rs
More file actions
138 lines (122 loc) · 4.63 KB
/
Copy pathinterpreter.rs
File metadata and controls
138 lines (122 loc) · 4.63 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
use rustpython_vm::InterpreterBuilder;
/// Extension trait for InterpreterBuilder to add rustpython-specific functionality.
pub trait InterpreterBuilderExt {
/// Initialize the Python standard library.
///
/// Requires the `stdlib` feature to be enabled.
#[cfg(feature = "stdlib")]
#[must_use]
fn init_stdlib(self) -> Self;
}
impl InterpreterBuilderExt for InterpreterBuilder {
#[cfg(feature = "stdlib")]
fn init_stdlib(self) -> Self {
let defs = rustpython_stdlib::stdlib_module_defs(&self.ctx);
let builder = self.add_native_modules(&defs);
#[cfg(all(feature = "ssl-rustls-aws-lc", not(target_arch = "wasm32")))]
let builder = builder.init_hook(install_default_tls_provider);
cfg_select! {
feature = "freeze-stdlib" => builder
.add_frozen_modules(rustpython_pylib::FROZEN_STDLIB)
.init_hook(set_frozen_stdlib_dir),
_ => builder.init_hook(setup_dynamic_stdlib),
}
}
}
#[cfg(all(feature = "ssl-rustls-aws-lc", not(target_arch = "wasm32")))]
fn install_default_tls_provider(_vm: &mut crate::VirtualMachine) {
use rustls::crypto::aws_lc_rs;
use rustpython_stdlib::ssl::providers::CryptoExt;
#[cfg(feature = "ssl-rustls-aws-lc-fips")]
let (all_cipher_suites, all_kx_groups) = (None, None);
#[cfg(not(feature = "ssl-rustls-aws-lc-fips"))]
let (all_cipher_suites, all_kx_groups) = (
Some(aws_lc_rs::ALL_CIPHER_SUITES),
Some(aws_lc_rs::ALL_KX_GROUPS),
);
let ext = CryptoExt {
all_cipher_suites,
default_cipher_suites: Some(aws_lc_rs::DEFAULT_CIPHER_SUITES),
all_kx_groups,
any_supported_key: Some(aws_lc_rs::sign::any_supported_type),
ticketer: aws_lc_rs::Ticketer::new,
};
let _ = CryptoExt::set_provider(aws_lc_rs::default_provider(), ext);
}
/// Set stdlib_dir for frozen standard library
#[cfg(all(feature = "stdlib", feature = "freeze-stdlib"))]
fn set_frozen_stdlib_dir(vm: &mut crate::VirtualMachine) {
use rustpython_vm::common::rc::PyRc;
if !vm.state.config.settings.use_frozen_modules {
setup_dynamic_stdlib(vm);
return;
}
if use_build_stdlib(vm) {
let state = PyRc::get_mut(&mut vm.state).unwrap();
state.config.paths.stdlib_dir =
Some(canonical_stdlib_path(rustpython_pylib::LIB_PATH.to_owned()));
}
}
/// Setup dynamic standard library loading from filesystem
#[cfg(feature = "stdlib")]
fn setup_dynamic_stdlib(vm: &mut crate::VirtualMachine) {
use rustpython_vm::common::rc::PyRc;
if !use_build_stdlib(vm) {
return;
}
let state = PyRc::get_mut(&mut vm.state).unwrap();
let paths: Vec<String> = collect_stdlib_paths()
.into_iter()
.map(canonical_stdlib_path)
.collect();
// Set stdlib_dir to the first stdlib path if available
if let Some(first_path) = paths.first() {
state.config.paths.stdlib_dir = Some(first_path.clone());
}
rustpython_vm::getpath::add_build_time_paths(
&state.config.settings,
&mut state.config.paths,
paths,
);
}
// Preserve a discovered library. Only an explicit nonempty prefix half of
// PYTHONHOME forbids falling back to the build-tree pure-Python library.
#[cfg(feature = "stdlib")]
fn use_build_stdlib(vm: &crate::VirtualMachine) -> bool {
vm.state.config.paths.stdlib_dir.is_none()
&& vm.state.config.settings.home.as_deref().is_none_or(|home| {
let (prefix, _) = home
.split_once(if cfg!(windows) { ';' } else { ':' })
.unwrap_or((home, home));
prefix.is_empty()
})
}
/// Resolve the build-tree library link consistently for both backends.
#[cfg(feature = "stdlib")]
fn canonical_stdlib_path(path: String) -> String {
std::fs::canonicalize(&path)
.map(|canonical| {
let value = canonical.to_string_lossy();
#[cfg(windows)]
if let Some(stripped) = value.strip_prefix(r"\\?\") {
return stripped.to_owned();
}
value.into_owned()
})
.unwrap_or(path)
}
/// Collect standard library paths from build-time configuration
#[cfg(feature = "stdlib")]
fn collect_stdlib_paths() -> Vec<String> {
// BUILDTIME_RUSTPYTHONPATH should be set when distributing
if let Some(paths) = option_env!("BUILDTIME_RUSTPYTHONPATH") {
crate::settings::split_paths(paths)
.map(|path| path.into_os_string().into_string().unwrap())
.collect()
} else {
vec![
#[cfg(feature = "rustpython-pylib")]
rustpython_pylib::LIB_PATH.to_owned(),
]
}
}