mirror of
https://github.com/clash-verge-rev/clash-verge-rev.git
synced 2026-04-13 13:30:31 +08:00
fix: memory leak when switching profiles
This commit is contained in:
parent
c57a962109
commit
bd338cb5de
@ -6,6 +6,7 @@
|
|||||||
- 修复无网络时无限请求 IP 归属查询
|
- 修复无网络时无限请求 IP 归属查询
|
||||||
- 修复 WebDAV 页面重试逻辑
|
- 修复 WebDAV 页面重试逻辑
|
||||||
- 修复 Linux 通过 GUI 安装服务模式权限不符合预期
|
- 修复 Linux 通过 GUI 安装服务模式权限不符合预期
|
||||||
|
- 修复切换订阅所导致的内存持续增长
|
||||||
|
|
||||||
<details>
|
<details>
|
||||||
<summary><strong> ✨ 新增功能 </strong></summary>
|
<summary><strong> ✨ 新增功能 </strong></summary>
|
||||||
|
|||||||
@ -189,6 +189,10 @@ impl Config {
|
|||||||
pub async fn generate() -> Result<()> {
|
pub async fn generate() -> Result<()> {
|
||||||
let (config, exists_keys, logs) = enhance::enhance().await;
|
let (config, exists_keys, logs) = enhance::enhance().await;
|
||||||
|
|
||||||
|
Self::runtime().await.edit_draft(|d| {
|
||||||
|
d.clean_all();
|
||||||
|
});
|
||||||
|
|
||||||
Self::runtime().await.edit_draft(|d| {
|
Self::runtime().await.edit_draft(|d| {
|
||||||
*d = IRuntime {
|
*d = IRuntime {
|
||||||
config: Some(config),
|
config: Some(config),
|
||||||
|
|||||||
@ -22,6 +22,13 @@ impl IRuntime {
|
|||||||
Self::default()
|
Self::default()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
pub fn clean_all(&mut self) {
|
||||||
|
self.config = None;
|
||||||
|
self.exists_keys.clear();
|
||||||
|
self.chain_logs.clear();
|
||||||
|
}
|
||||||
|
|
||||||
// 这里只更改 allow-lan | ipv6 | log-level | tun
|
// 这里只更改 allow-lan | ipv6 | log-level | tun
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn patch_config(&mut self, patch: &Mapping) {
|
pub fn patch_config(&mut self, patch: &Mapping) {
|
||||||
|
|||||||
@ -13,6 +13,7 @@ use self::{
|
|||||||
seq::{SeqMap, use_seq},
|
seq::{SeqMap, use_seq},
|
||||||
tun::use_tun,
|
tun::use_tun,
|
||||||
};
|
};
|
||||||
|
use crate::process::AsyncHandler;
|
||||||
use crate::utils::dirs;
|
use crate::utils::dirs;
|
||||||
use crate::{config::Config, utils::tmpl};
|
use crate::{config::Config, utils::tmpl};
|
||||||
use crate::{config::IVerge, constants};
|
use crate::{config::IVerge, constants};
|
||||||
@ -33,6 +34,7 @@ struct ConfigValues {
|
|||||||
socks_enabled: bool,
|
socks_enabled: bool,
|
||||||
http_enabled: bool,
|
http_enabled: bool,
|
||||||
enable_dns_settings: bool,
|
enable_dns_settings: bool,
|
||||||
|
enable_external_controller: bool,
|
||||||
#[cfg(not(target_os = "windows"))]
|
#[cfg(not(target_os = "windows"))]
|
||||||
redir_enabled: bool,
|
redir_enabled: bool,
|
||||||
#[cfg(target_os = "linux")]
|
#[cfg(target_os = "linux")]
|
||||||
@ -108,13 +110,22 @@ async fn get_config_values() -> ConfigValues {
|
|||||||
..
|
..
|
||||||
} = *verge_arc;
|
} = *verge_arc;
|
||||||
|
|
||||||
let (clash_core, enable_tun, enable_builtin, socks_enabled, http_enabled, enable_dns_settings) = (
|
let (
|
||||||
|
clash_core,
|
||||||
|
enable_tun,
|
||||||
|
enable_builtin,
|
||||||
|
socks_enabled,
|
||||||
|
http_enabled,
|
||||||
|
enable_dns_settings,
|
||||||
|
enable_external_controller,
|
||||||
|
) = (
|
||||||
Some(verge_arc.get_valid_clash_core()),
|
Some(verge_arc.get_valid_clash_core()),
|
||||||
enable_tun_mode.unwrap_or(false),
|
enable_tun_mode.unwrap_or(false),
|
||||||
enable_builtin_enhanced.unwrap_or(true),
|
enable_builtin_enhanced.unwrap_or(true),
|
||||||
verge_socks_enabled.unwrap_or(false),
|
verge_socks_enabled.unwrap_or(false),
|
||||||
verge_http_enabled.unwrap_or(false),
|
verge_http_enabled.unwrap_or(false),
|
||||||
enable_dns_settings.unwrap_or(false),
|
enable_dns_settings.unwrap_or(false),
|
||||||
|
verge_arc.enable_external_controller.unwrap_or(false),
|
||||||
);
|
);
|
||||||
|
|
||||||
#[cfg(not(target_os = "windows"))]
|
#[cfg(not(target_os = "windows"))]
|
||||||
@ -134,6 +145,7 @@ async fn get_config_values() -> ConfigValues {
|
|||||||
socks_enabled,
|
socks_enabled,
|
||||||
http_enabled,
|
http_enabled,
|
||||||
enable_dns_settings,
|
enable_dns_settings,
|
||||||
|
enable_external_controller,
|
||||||
#[cfg(not(target_os = "windows"))]
|
#[cfg(not(target_os = "windows"))]
|
||||||
redir_enabled,
|
redir_enabled,
|
||||||
#[cfg(target_os = "linux")]
|
#[cfg(target_os = "linux")]
|
||||||
@ -378,11 +390,12 @@ fn process_profile_items(
|
|||||||
(config, exists_keys, result_map)
|
(config, exists_keys, result_map)
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn merge_default_config(
|
fn merge_default_config(
|
||||||
mut config: Mapping,
|
mut config: Mapping,
|
||||||
clash_config: Mapping,
|
clash_config: Mapping,
|
||||||
socks_enabled: bool,
|
socks_enabled: bool,
|
||||||
http_enabled: bool,
|
http_enabled: bool,
|
||||||
|
enable_external_controller: bool,
|
||||||
#[cfg(not(target_os = "windows"))] redir_enabled: bool,
|
#[cfg(not(target_os = "windows"))] redir_enabled: bool,
|
||||||
#[cfg(target_os = "linux")] tproxy_enabled: bool,
|
#[cfg(target_os = "linux")] tproxy_enabled: bool,
|
||||||
) -> Mapping {
|
) -> Mapping {
|
||||||
@ -433,19 +446,8 @@ async fn merge_default_config(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
// 处理 external-controller 键的开关逻辑
|
// 处理 external-controller 键的开关逻辑
|
||||||
if key.as_str() == Some("external-controller") {
|
if key.as_str() == Some("external-controller") && !enable_external_controller {
|
||||||
let enable_external_controller = Config::verge()
|
config.insert(key, "".into());
|
||||||
.await
|
|
||||||
.latest_arc()
|
|
||||||
.enable_external_controller
|
|
||||||
.unwrap_or(false);
|
|
||||||
|
|
||||||
if enable_external_controller {
|
|
||||||
config.insert(key, value);
|
|
||||||
} else {
|
|
||||||
// 如果禁用了外部控制器,设置为空字符串
|
|
||||||
config.insert(key, "".into());
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
config.insert(key, value);
|
config.insert(key, value);
|
||||||
}
|
}
|
||||||
@ -602,6 +604,7 @@ pub async fn enhance() -> (Mapping, HashSet<String>, HashMap<String, ResultLog>)
|
|||||||
socks_enabled,
|
socks_enabled,
|
||||||
http_enabled,
|
http_enabled,
|
||||||
enable_dns_settings,
|
enable_dns_settings,
|
||||||
|
enable_external_controller,
|
||||||
#[cfg(not(target_os = "windows"))]
|
#[cfg(not(target_os = "windows"))]
|
||||||
redir_enabled,
|
redir_enabled,
|
||||||
#[cfg(target_os = "linux")]
|
#[cfg(target_os = "linux")]
|
||||||
@ -620,48 +623,58 @@ pub async fn enhance() -> (Mapping, HashSet<String>, HashMap<String, ResultLog>)
|
|||||||
let global_script = profile.global_script;
|
let global_script = profile.global_script;
|
||||||
let profile_name = profile.profile_name;
|
let profile_name = profile.profile_name;
|
||||||
|
|
||||||
// process globals
|
let (config, exists_keys_set, result_map) = AsyncHandler::spawn_blocking(move || {
|
||||||
let (config, exists_keys, result_map) = process_global_items(config, global_merge, global_script, &profile_name);
|
// process globals
|
||||||
|
let (config, exists_keys, result_map) =
|
||||||
|
process_global_items(config, global_merge, global_script, &profile_name);
|
||||||
|
|
||||||
// process profile-specific items
|
// process profile-specific items
|
||||||
let (config, exists_keys, result_map) = process_profile_items(
|
let (config, exists_keys, result_map) = process_profile_items(
|
||||||
config,
|
config,
|
||||||
exists_keys,
|
exists_keys,
|
||||||
result_map,
|
result_map,
|
||||||
rules_item,
|
rules_item,
|
||||||
proxies_item,
|
proxies_item,
|
||||||
groups_item,
|
groups_item,
|
||||||
merge_item,
|
merge_item,
|
||||||
script_item,
|
script_item,
|
||||||
&profile_name,
|
&profile_name,
|
||||||
);
|
);
|
||||||
|
|
||||||
// merge default clash config
|
// merge default clash config
|
||||||
let config = merge_default_config(
|
let config = merge_default_config(
|
||||||
config,
|
config,
|
||||||
clash_config,
|
clash_config,
|
||||||
socks_enabled,
|
socks_enabled,
|
||||||
http_enabled,
|
http_enabled,
|
||||||
#[cfg(not(target_os = "windows"))]
|
enable_external_controller,
|
||||||
redir_enabled,
|
#[cfg(not(target_os = "windows"))]
|
||||||
#[cfg(target_os = "linux")]
|
redir_enabled,
|
||||||
tproxy_enabled,
|
#[cfg(target_os = "linux")]
|
||||||
)
|
tproxy_enabled,
|
||||||
.await;
|
);
|
||||||
|
|
||||||
// builtin scripts
|
// builtin scripts
|
||||||
let mut config = apply_builtin_scripts(config, clash_core, enable_builtin);
|
let mut config = apply_builtin_scripts(config, clash_core.clone(), enable_builtin);
|
||||||
|
|
||||||
config = cleanup_proxy_groups(config);
|
config = cleanup_proxy_groups(config);
|
||||||
|
|
||||||
config = use_tun(config, enable_tun);
|
config = use_tun(config, enable_tun);
|
||||||
config = use_sort(config);
|
config = use_sort(config);
|
||||||
|
|
||||||
|
let mut exists_keys_set = HashSet::new();
|
||||||
|
exists_keys_set.extend(exists_keys);
|
||||||
|
|
||||||
|
(config, exists_keys_set, result_map)
|
||||||
|
})
|
||||||
|
.await
|
||||||
|
.unwrap_or_else(|e| {
|
||||||
|
logging!(error, Type::Core, "enhance task join error: {}", e);
|
||||||
|
(Mapping::new(), HashSet::new(), HashMap::new())
|
||||||
|
});
|
||||||
|
|
||||||
// dns settings
|
// dns settings
|
||||||
config = apply_dns_settings(config, enable_dns_settings).await;
|
let config = apply_dns_settings(config, enable_dns_settings).await;
|
||||||
|
|
||||||
let mut exists_keys_set = HashSet::new();
|
|
||||||
exists_keys_set.extend(exists_keys);
|
|
||||||
|
|
||||||
(config, exists_keys_set, result_map)
|
(config, exists_keys_set, result_map)
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user