mod.rs 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324
  1. /* This file is part of DarkFi (https://dark.fi)
  2. *
  3. * Copyright (C) 2020-2026 Dyne.org foundation
  4. *
  5. * This program is free software: you can redistribute it and/or modify
  6. * it under the terms of the GNU Affero General Public License as
  7. * published by the Free Software Foundation, either version 3 of the
  8. * License, or (at your option) any later version.
  9. *
  10. * This program is distributed in the hope that it will be useful,
  11. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. * GNU Affero General Public License for more details.
  14. *
  15. * You should have received a copy of the GNU Affero General Public License
  16. * along with this program. If not, see <https://www.gnu.org/licenses/>.
  17. */
  18. use sled_overlay::sled;
  19. use std::{array::TryFromSliceError, string::FromUtf8Error, sync::Arc};
  20. pub mod darkirc;
  21. pub use darkirc::DarkIrcPtr;
  22. pub mod fud;
  23. pub use fud::FudPluginPtr as FudPtr;
  24. pub mod drk;
  25. pub use drk::DrkPluginPtr as DrkPtr;
  26. pub use darkirc::DarkIrc;
  27. pub use fud::FudPlugin;
  28. pub use drk::DrkPlugin;
  29. use darkfi::net::Settings as NetSettings;
  30. use crate::{
  31. prop::{Property, PropertyAtomicGuard, PropertySubType, PropertyType, PropertyValue, Role},
  32. scene::{SceneNode, SceneNodePtr, SceneNodeType},
  33. };
  34. pub struct PluginSettings {
  35. pub setting_root: SceneNodePtr,
  36. pub sled_tree: sled::Tree,
  37. }
  38. impl PluginSettings {
  39. pub fn add_setting(&self, name: &str, default: PropertyValue) -> Option<SceneNodePtr> {
  40. let atom = &mut PropertyAtomicGuard::none();
  41. let node = match default {
  42. PropertyValue::Bool(b) => {
  43. let mut node = SceneNode::new(name, SceneNodeType::Setting);
  44. let prop = Property::new("value", PropertyType::Bool, PropertySubType::Null);
  45. node.add_property(prop).unwrap();
  46. let prop = Property::new("default", PropertyType::Bool, PropertySubType::Null);
  47. node.add_property(prop).unwrap();
  48. node.set_property_bool(atom, Role::User, "value", b.clone()).unwrap();
  49. node.set_property_bool(atom, Role::App, "default", b.clone()).unwrap();
  50. Some(node)
  51. }
  52. PropertyValue::Uint32(u) => {
  53. let mut node = SceneNode::new(name, SceneNodeType::Setting);
  54. let prop = Property::new("value", PropertyType::Uint32, PropertySubType::Null);
  55. node.add_property(prop).unwrap();
  56. let prop = Property::new("default", PropertyType::Uint32, PropertySubType::Null);
  57. node.add_property(prop).unwrap();
  58. node.set_property_u32(atom, Role::User, "value", u.clone()).unwrap();
  59. node.set_property_u32(atom, Role::App, "default", u.clone()).unwrap();
  60. Some(node)
  61. }
  62. PropertyValue::Float32(f) => {
  63. let mut node = SceneNode::new(name, SceneNodeType::Setting);
  64. let prop = Property::new("value", PropertyType::Float32, PropertySubType::Null);
  65. node.add_property(prop).unwrap();
  66. let prop = Property::new("default", PropertyType::Float32, PropertySubType::Null);
  67. node.add_property(prop).unwrap();
  68. node.set_property_f32(atom, Role::User, "value", f.clone()).unwrap();
  69. node.set_property_f32(atom, Role::App, "default", f.clone()).unwrap();
  70. Some(node)
  71. }
  72. PropertyValue::Str(s) => {
  73. let mut node = SceneNode::new(name, SceneNodeType::Setting);
  74. let prop = Property::new("value", PropertyType::Str, PropertySubType::Null);
  75. node.add_property(prop).unwrap();
  76. let prop = Property::new("default", PropertyType::Str, PropertySubType::Null);
  77. node.add_property(prop).unwrap();
  78. node.set_property_str(atom, Role::User, "value", s.clone()).unwrap();
  79. node.set_property_str(atom, Role::App, "default", s.clone()).unwrap();
  80. Some(node)
  81. }
  82. _ => None,
  83. };
  84. match node {
  85. Some(n) => {
  86. let node_ptr = Arc::new(n);
  87. self.setting_root.link(node_ptr.clone().into());
  88. Some(node_ptr)
  89. }
  90. None => None,
  91. }
  92. }
  93. // For all settings, copy the value from sled into the setting node's value property
  94. pub fn load_settings(&self) {
  95. let atom = &mut PropertyAtomicGuard::none();
  96. for setting_node in self.setting_root.get_children().iter() {
  97. if setting_node.typ != SceneNodeType::Setting {
  98. continue
  99. }
  100. let value = setting_node.get_property("value").clone().unwrap();
  101. match value.typ {
  102. PropertyType::Bool => {
  103. let sled_result = self.sled_tree.get(setting_node.name.as_str());
  104. if let Ok(Some(sled_value)) = sled_result {
  105. setting_node
  106. .set_property_bool(atom, Role::User, "value", sled_value[0] != 0)
  107. .unwrap();
  108. }
  109. }
  110. PropertyType::Uint32 => {
  111. let sled_result = self.sled_tree.get(setting_node.name.as_str());
  112. if let Ok(Some(sled_value)) = sled_result {
  113. if sled_value.len() == 4 {
  114. let bytes: Result<[u8; 4], TryFromSliceError> =
  115. sled_value.as_ref().try_into();
  116. if let Ok(b) = bytes {
  117. setting_node
  118. .set_property_u32(
  119. atom,
  120. Role::User,
  121. "value",
  122. u32::from_le_bytes(b),
  123. )
  124. .unwrap();
  125. }
  126. }
  127. }
  128. }
  129. PropertyType::Float32 => {
  130. let sled_result = self.sled_tree.get(setting_node.name.as_str());
  131. if let Ok(Some(sled_value)) = sled_result {
  132. if sled_value.len() == 4 {
  133. let bytes: Result<[u8; 4], TryFromSliceError> =
  134. sled_value.as_ref().try_into();
  135. if let Ok(b) = bytes {
  136. setting_node
  137. .set_property_f32(
  138. atom,
  139. Role::User,
  140. "value",
  141. f32::from_le_bytes(b),
  142. )
  143. .unwrap();
  144. }
  145. }
  146. }
  147. }
  148. PropertyType::Str => {
  149. let sled_result = self.sled_tree.get(setting_node.name.as_str());
  150. if let Ok(Some(sled_value)) = sled_result {
  151. let string: Result<String, FromUtf8Error> =
  152. String::from_utf8(sled_value.to_vec());
  153. if let Ok(s) = string {
  154. setting_node.set_property_str(atom, Role::User, "value", s).unwrap();
  155. }
  156. }
  157. }
  158. _ => {}
  159. }
  160. }
  161. }
  162. // Save all settings to sled
  163. pub fn save_settings(&self) {
  164. for setting_node in self.setting_root.get_children().iter() {
  165. if setting_node.typ != SceneNodeType::Setting {
  166. continue
  167. }
  168. let value = setting_node.get_property("value").clone().unwrap();
  169. match value.typ {
  170. PropertyType::Bool => {
  171. let value_bytes = if value.get_bool(0).unwrap() { 1u8 } else { 0u8 };
  172. self.sled_tree
  173. .insert(setting_node.name.as_str(), sled::IVec::from(vec![value_bytes]))
  174. .unwrap();
  175. }
  176. PropertyType::Uint32 => {
  177. self.sled_tree
  178. .insert(
  179. setting_node.name.as_str(),
  180. sled::IVec::from(value.get_u32(0).unwrap().to_le_bytes().as_ref()),
  181. )
  182. .unwrap();
  183. }
  184. PropertyType::Float32 => {
  185. self.sled_tree
  186. .insert(
  187. setting_node.name.as_str(),
  188. sled::IVec::from(value.get_f32(0).unwrap().to_le_bytes().as_ref()),
  189. )
  190. .unwrap();
  191. }
  192. PropertyType::Str => {
  193. self.sled_tree
  194. .insert(
  195. setting_node.name.as_str(),
  196. sled::IVec::from(value.get_str(0).unwrap().as_bytes()),
  197. )
  198. .unwrap();
  199. }
  200. _ => {}
  201. }
  202. }
  203. }
  204. pub fn get_setting(&self, name: &str) -> Option<SceneNodePtr> {
  205. self.setting_root
  206. .clone()
  207. .get_children()
  208. .iter()
  209. .find(|node| node.typ == SceneNodeType::Setting && node.name == name)
  210. .cloned()
  211. }
  212. pub fn add_p2p_settings(&self, p2p_settings: &NetSettings) {
  213. self.add_setting(
  214. "net.outbound_connections",
  215. PropertyValue::Uint32(p2p_settings.outbound_connections as u32),
  216. );
  217. self.add_setting(
  218. "net.inbound_connections",
  219. PropertyValue::Uint32(p2p_settings.inbound_connections as u32),
  220. );
  221. //TODO: Update this when multiple active_profiles at a time is supported
  222. self.add_setting(
  223. "net.outbound_connect_timeout",
  224. PropertyValue::Uint32(
  225. p2p_settings
  226. .outbound_connect_timeout(&p2p_settings.active_profiles.first().unwrap())
  227. as u32,
  228. ),
  229. );
  230. self.add_setting(
  231. "net.channel_handshake_timeout",
  232. PropertyValue::Uint32(
  233. p2p_settings
  234. .channel_handshake_timeout(&p2p_settings.active_profiles.first().unwrap())
  235. as u32,
  236. ),
  237. );
  238. self.add_setting(
  239. "net.channel_heartbeat_interval",
  240. PropertyValue::Uint32(
  241. p2p_settings
  242. .channel_heartbeat_interval(&p2p_settings.active_profiles.first().unwrap())
  243. as u32,
  244. ),
  245. );
  246. self.add_setting(
  247. "net.outbound_peer_discovery_cooloff_time",
  248. PropertyValue::Uint32(p2p_settings.outbound_peer_discovery_cooloff_time as u32),
  249. );
  250. self.add_setting("net.localnet", PropertyValue::Bool(p2p_settings.localnet));
  251. self.add_setting(
  252. "net.greylist_refinery_interval",
  253. PropertyValue::Uint32(p2p_settings.greylist_refinery_interval as u32),
  254. );
  255. self.add_setting(
  256. "net.time_with_no_connections",
  257. PropertyValue::Uint32(p2p_settings.time_with_no_connections as u32),
  258. );
  259. }
  260. // Update a NetSettings from settings in the node tree
  261. pub fn update_p2p_settings(&self, p2p_settings: &mut NetSettings) {
  262. p2p_settings.outbound_connections = self
  263. .get_setting("net.outbound_connections")
  264. .unwrap()
  265. .get_property_u32("value")
  266. .unwrap() as usize;
  267. p2p_settings.inbound_connections =
  268. self.get_setting("net.inbound_connections").unwrap().get_property_u32("value").unwrap()
  269. as usize;
  270. //TODO: Update this when multiple active_profiles at a time is supported
  271. if let Some(profile) =
  272. p2p_settings.profiles.get_mut(p2p_settings.active_profiles.first().unwrap())
  273. {
  274. profile.outbound_connect_timeout = self
  275. .get_setting("net.outbound_connect_timeout")
  276. .unwrap()
  277. .get_property_u32("value")
  278. .unwrap() as u64;
  279. profile.channel_handshake_timeout = self
  280. .get_setting("net.channel_handshake_timeout")
  281. .unwrap()
  282. .get_property_u32("value")
  283. .unwrap() as u64;
  284. profile.channel_heartbeat_interval = self
  285. .get_setting("net.channel_heartbeat_interval")
  286. .unwrap()
  287. .get_property_u32("value")
  288. .unwrap() as u64;
  289. }
  290. p2p_settings.outbound_peer_discovery_cooloff_time = self
  291. .get_setting("net.outbound_peer_discovery_cooloff_time")
  292. .unwrap()
  293. .get_property_u32("value")
  294. .unwrap() as u64;
  295. p2p_settings.localnet =
  296. self.get_setting("net.localnet").unwrap().get_property_bool("value").unwrap();
  297. p2p_settings.greylist_refinery_interval = self
  298. .get_setting("net.greylist_refinery_interval")
  299. .unwrap()
  300. .get_property_u32("value")
  301. .unwrap() as u64;
  302. p2p_settings.time_with_no_connections = self
  303. .get_setting("net.time_with_no_connections")
  304. .unwrap()
  305. .get_property_u32("value")
  306. .unwrap() as u64;
  307. }
  308. }