1 /*
2  * Copyright (c) 2020 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 #include "remote_register.h"
16 #include <ohos_errno.h>
17 #include <ohos_init.h>
18 #include <liteipc_adapter.h>
19 #include <log.h>
20 #include "policy_define.h"
21 #include "samgr_lite.h"
22 #include "memory_adapter.h"
23 #include "thread_adapter.h"
24 #include "iproxy_client.h"
25 #include "default_client.h"
26 
27 #undef LOG_TAG
28 #undef LOG_DOMAIN
29 #define LOG_TAG "Samgr"
30 #define LOG_DOMAIN 0xD001800
31 
32 #define RETRY_INTERVAL 2
33 #define MAX_RETRY_TIMES 10
34 #define ABILITY_UID_START 100
35 static void InitializeRegistry(void);
36 static RemoteRegister g_remoteRegister;
37 static BOOL g_isAbilityInited = FALSE;
38 
SAMGR_RegisterServiceApi(const char * service,const char * feature,const Identity * identity,IUnknown * iUnknown)39 int SAMGR_RegisterServiceApi(const char *service, const char *feature, const Identity *identity, IUnknown *iUnknown)
40 {
41     if (service == NULL) {
42         return EC_INVALID;
43     }
44     InitializeRegistry();
45     MUTEX_Lock(g_remoteRegister.mtx);
46     SaName saName = {service, feature};
47     int32 token = SAMGR_AddRouter(g_remoteRegister.endpoint, &saName, identity, iUnknown);
48     MUTEX_Unlock(g_remoteRegister.mtx);
49     if (token < 0 || !g_remoteRegister.endpoint->running) {
50         return token;
51     }
52     return SAMGR_ProcPolicy(g_remoteRegister.endpoint, &saName, token);
53 }
54 
SAMGR_FindServiceApi(const char * service,const char * feature)55 IUnknown *SAMGR_FindServiceApi(const char *service, const char *feature)
56 {
57     if (service == NULL) {
58         return NULL;
59     }
60     InitializeRegistry();
61     SaName key = {service, feature};
62     // the proxy already exits.
63     int index = VECTOR_FindByKey(&g_remoteRegister.clients, &key);
64     if (index != INVALID_INDEX) {
65         return VECTOR_At(&g_remoteRegister.clients, index);
66     }
67     IUnknown *proxy = SAMGR_CreateIProxy(g_remoteRegister.endpoint->context, service, feature);
68     if (proxy == NULL) {
69         return NULL;
70     }
71     MUTEX_Lock(g_remoteRegister.mtx);
72     index = VECTOR_FindByKey(&g_remoteRegister.clients, &key);
73     if (index != INVALID_INDEX) {
74         MUTEX_Unlock(g_remoteRegister.mtx);
75         proxy->Release(proxy);
76         return VECTOR_At(&g_remoteRegister.clients, index);
77     }
78     VECTOR_Add(&g_remoteRegister.clients, proxy);
79     MUTEX_Unlock(g_remoteRegister.mtx);
80     HILOG_INFO(HILOG_MODULE_SAMGR, "Create remote sa proxy<%s, %s>!", service, feature);
81     return proxy;
82 }
83 
SAMGR_RegisterSystemCapabilityApi(const char * sysCap,BOOL isReg)84 int32 SAMGR_RegisterSystemCapabilityApi(const char *sysCap, BOOL isReg)
85 {
86     InitializeRegistry();
87     return SAMGR_AddSysCap(g_remoteRegister.endpoint, sysCap, isReg);
88 }
89 
SAMGR_QuerySystemCapabilityApi(const char * sysCap)90 BOOL SAMGR_QuerySystemCapabilityApi(const char *sysCap)
91 {
92     InitializeRegistry();
93     BOOL isReg = FALSE;
94     if (SAMGR_GetSysCap(g_remoteRegister.endpoint, sysCap, &isReg) != EC_SUCCESS) {
95         return FALSE;
96     }
97     return isReg;
98 }
99 
SAMGR_GetSystemCapabilitiesApi(char sysCaps[MAX_SYSCAP_NUM][MAX_SYSCAP_NAME_LEN],int32 * size)100 int32 SAMGR_GetSystemCapabilitiesApi(char sysCaps[MAX_SYSCAP_NUM][MAX_SYSCAP_NAME_LEN], int32 *size)
101 {
102     InitializeRegistry();
103     return SAMGR_GetSystemCapabilities(g_remoteRegister.endpoint, sysCaps, size);
104 }
105 
ClearRegistry(void)106 static void ClearRegistry(void)
107 {
108     if (g_remoteRegister.endpoint == NULL) {
109         return;
110     }
111     HILOG_INFO(HILOG_MODULE_SAMGR, "Clear Client Registry!");
112     SAMGR_Free(g_remoteRegister.mtx);
113     g_remoteRegister.mtx = NULL;
114     VECTOR_Clear(&(g_remoteRegister.clients));
115     VECTOR_Clear(&(g_remoteRegister.endpoint->routers));
116     CloseLiteIpc(g_remoteRegister.endpoint->context);
117     SAMGR_Free(g_remoteRegister.endpoint);
118     g_remoteRegister.endpoint = NULL;
119 }
120 
InitializeRegistry(void)121 static void InitializeRegistry(void)
122 {
123     if (getuid() >= ABILITY_UID_START && !g_isAbilityInited) {
124         ClearRegistry();
125         g_isAbilityInited = TRUE;
126     }
127     if (g_remoteRegister.endpoint != NULL) {
128         return;
129     }
130     HILOG_INFO(HILOG_MODULE_SAMGR, "Initialize Client Registry!");
131     MUTEX_GlobalLock();
132     if (g_remoteRegister.endpoint == NULL) {
133         g_remoteRegister.mtx = MUTEX_InitValue();
134         g_remoteRegister.clients = VECTOR_Make((VECTOR_Key)SAMGR_GetSAName, (VECTOR_Compare)SAMGR_CompareSAName);
135         g_remoteRegister.endpoint = SAMGR_CreateEndpoint("ipc client", NULL);
136     }
137     MUTEX_GlobalUnlock();
138 }
139