1 /* 2 * Copyright (C) 2023 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 //! Fusion IPC delegator 17 18 #![allow(unused_variables)] 19 20 use std::cell::Cell; 21 use std::sync::Mutex; 22 use std::ffi::{ c_char, CString }; 23 use crate::hilog_rust::{ debug, info, error, hilog, HiLogLabel, LogType }; 24 use crate::ipc_rust::{ BorrowedMsgParcel, Deserialize, InterfaceToken, IRemoteBroker, IRemoteStub }; 25 use crate::fusion_data_rust::{ Intention, IPlugin, CallingContext, FusionResult }; 26 use crate::fusion_utils_rust::call_debug_enter; 27 use crate::fusion_ipc_service_rust::{ IDeviceStatus, FusionIpcStub }; 28 use crate::fusion_plugin_manager_rust::PluginManager; 29 30 const LOG_LABEL: HiLogLabel = HiLogLabel { 31 log_type: LogType::LogCore, 32 domain: 0xD002220, 33 tag: "FusionIpcDelegator" 34 }; 35 36 pub struct FusionIpcDelegator { 37 plugin_mgr: Mutex<Cell<PluginManager>>, 38 } 39 40 impl FusionIpcDelegator { new() -> Self41 pub fn new() -> Self { 42 Self { 43 plugin_mgr: Mutex::new(Cell::new(PluginManager::default())) 44 } 45 } 46 check_interface_token(&self, data: &BorrowedMsgParcel) -> FusionResult<i32>47 fn check_interface_token(&self, data: &BorrowedMsgParcel) -> FusionResult<i32> { 48 call_debug_enter!("FusionIpcDelegator::check_interface_token"); 49 match InterfaceToken::deserialize(data) { 50 Ok(token) => { 51 debug!(LOG_LABEL, "check interface token"); 52 if token.get_token() != FusionIpcStub::get_descriptor() { 53 error!(LOG_LABEL, "unexpected token"); 54 Err(-1) 55 } else { 56 Ok(0) 57 } 58 } 59 Err(_) => { 60 error!(LOG_LABEL, "Deserialization of interface token fail"); 61 Err(-1) 62 } 63 } 64 } 65 load_plugin(&self, intention: Intention) -> FusionResult<Box<dyn IPlugin>>66 fn load_plugin(&self, intention: Intention) -> FusionResult<Box<dyn IPlugin>> { 67 call_debug_enter!("FusionIpcDelegator::load_plugin"); 68 match self.plugin_mgr.lock() { 69 Ok(mut guard) => { 70 let plugin = guard.get_mut().load_plugin(intention); 71 match plugin { 72 Some(plugin) => { 73 debug!(LOG_LABEL, "Plugin loaded"); 74 Ok(plugin) 75 } 76 None => { 77 error!(LOG_LABEL, "Fail to load intention module"); 78 Err(-1) 79 } 80 } 81 } 82 Err(_) => { 83 error!(LOG_LABEL, "error locking"); 84 Err(-1) 85 } 86 } 87 } 88 } 89 90 impl IDeviceStatus for FusionIpcDelegator { enable(&self, intention: Intention, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>91 fn enable(&self, intention: Intention, data: &BorrowedMsgParcel, 92 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 93 call_debug_enter!("FusionIpcDelegator::enable"); 94 self.check_interface_token(data)?; 95 96 let plugin = self.load_plugin(intention)?; 97 let context = CallingContext::current(); 98 info!(LOG_LABEL, "call plugin.enable()"); 99 plugin.enable(&context, data, reply) 100 } 101 disable(&self, intention: Intention, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>102 fn disable(&self, intention: Intention, data: &BorrowedMsgParcel, 103 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 104 call_debug_enter!("FusionIpcDelegator::disable"); 105 self.check_interface_token(data)?; 106 107 let plugin = self.load_plugin(intention)?; 108 let context = CallingContext::current(); 109 info!(LOG_LABEL, "call plugin.disable()"); 110 plugin.disable(&context, data, reply) 111 } 112 start(&self, intention: Intention, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>113 fn start(&self, intention: Intention, data: &BorrowedMsgParcel, 114 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 115 call_debug_enter!("FusionIpcDelegator::start"); 116 self.check_interface_token(data)?; 117 118 let plugin = self.load_plugin(intention)?; 119 let context = CallingContext::current(); 120 info!(LOG_LABEL, "call plugin.start()"); 121 plugin.start(&context, data, reply) 122 } 123 stop(&self, intention: Intention, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>124 fn stop(&self, intention: Intention, data: &BorrowedMsgParcel, 125 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 126 call_debug_enter!("FusionIpcDelegator::stop"); 127 self.check_interface_token(data)?; 128 129 let plugin = self.load_plugin(intention)?; 130 let context = CallingContext::current(); 131 info!(LOG_LABEL, "call plugin.stop()"); 132 plugin.stop(&context, data, reply) 133 } 134 add_watch(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>135 fn add_watch(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, 136 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 137 call_debug_enter!("FusionIpcDelegator::add_watch"); 138 self.check_interface_token(data)?; 139 140 let plugin = self.load_plugin(intention)?; 141 let context = CallingContext::current(); 142 info!(LOG_LABEL, "call plugin.add_watch()"); 143 plugin.add_watch(&context, id, data, reply) 144 } 145 remove_watch(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>146 fn remove_watch(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, 147 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 148 call_debug_enter!("FusionIpcDelegator::remove_watch"); 149 self.check_interface_token(data)?; 150 151 let plugin = self.load_plugin(intention)?; 152 let context = CallingContext::current(); 153 info!(LOG_LABEL, "call plugin.remove_watch()"); 154 plugin.remove_watch(&context, id, data, reply) 155 } 156 set_param(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>157 fn set_param(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, 158 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 159 call_debug_enter!("FusionIpcDelegator::set_param"); 160 self.check_interface_token(data)?; 161 162 let plugin = self.load_plugin(intention)?; 163 let context = CallingContext::current(); 164 info!(LOG_LABEL, "call plugin.set_param()"); 165 plugin.set_param(&context, id, data, reply) 166 } 167 get_param(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>168 fn get_param(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, 169 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 170 call_debug_enter!("FusionIpcDelegator::get_param"); 171 self.check_interface_token(data)?; 172 173 let plugin = self.load_plugin(intention)?; 174 let context = CallingContext::current(); 175 info!(LOG_LABEL, "call plugin.get_param()"); 176 plugin.get_param(&context, id, data, reply) 177 } 178 control(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, reply: &mut BorrowedMsgParcel) -> FusionResult<i32>179 fn control(&self, intention: Intention, id: u32, data: &BorrowedMsgParcel, 180 reply: &mut BorrowedMsgParcel) -> FusionResult<i32> { 181 call_debug_enter!("FusionIpcDelegator::control"); 182 self.check_interface_token(data)?; 183 184 let plugin = self.load_plugin(intention)?; 185 let context = CallingContext::current(); 186 info!(LOG_LABEL, "call plugin.control()"); 187 plugin.control(&context, id, data, reply) 188 } 189 } 190 191 impl IRemoteBroker for FusionIpcDelegator {} 192