• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2022 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 #include "base_obj.h"
17 
18 #include <cstdio>
19 
20 #include "securec.h"
21 
22 namespace OHOS {
23 namespace AAFwk {
24 const InterfaceID g_IID_IObject = {
25     0x8321f710, 0xa0c0, 0x4cbe, 0xbfbc, {0x5, 0xa, 0x7, 0x8, 0xf, 0x1, 0x3, 0x1, 0x2, 0xb, 0x1, 0xb}
26 };
27 
28 const InterfaceID g_IID_IWeakReference = {
29     0x26ab1978, 0x1d11, 0x4a4f, 0x826d, {0x6, 0x1, 0x7, 0x8, 0x5, 0xc, 0x0, 0x4, 0x8, 0xc, 0xc, 0xa}
30 };
31 
32 const InterfaceID g_IID_IWeakReferenceSource = {
33     0xbc3f5250, 0x34d7, 0x42d2, 0x9b40, {0xf, 0xf, 0xc, 0xe, 0x8, 0x3, 0xf, 0xd, 0x4, 0x0, 0x6, 0x1}
34 };
35 
36 class WeakReferenceImpl final : public RefCounter, public IWeakReference {
37 public:
WeakReferenceImpl(IInterface * object,WeakRefCounter * wkRef)38     WeakReferenceImpl(IInterface *object, WeakRefCounter *wkRef) : object_(object), wkRef_(wkRef)
39     {}
40 
~WeakReferenceImpl()41     virtual ~WeakReferenceImpl()
42     {}
43 
44     void IncStrongRef(const void *id = nullptr) override;
45 
46     void DecStrongRef(const void *id = nullptr) override;
47 
48     IInterface *Query(const InterfaceID &iid) override;
49 
50     InterfaceID GetInterfaceID(IInterface *object) override;
51 
52     ErrCode Resolve(const InterfaceID &iid, IInterface **object) override;
53 
54 private:
55     IInterface *object_ = nullptr;
56     WeakRefCounter *wkRef_ = nullptr;
57 };
58 
IncStrongRef(const void * id)59 void WeakReferenceImpl::IncStrongRef(const void *id)
60 {
61     RefCounter::IncStrongRefCount(id);
62 }
63 
DecStrongRef(const void * id)64 void WeakReferenceImpl::DecStrongRef(const void *id)
65 {
66     RefCounter::DecStrongRefCount(id);
67 }
68 
Query(const InterfaceID & iid)69 IInterface *WeakReferenceImpl::Query(const InterfaceID &iid)
70 {
71     if ((iid == g_IID_IWeakReference) || (iid == g_IID_IInterface)) {
72         return static_cast<IWeakReference *>(this);
73     }
74     return nullptr;
75 }
76 
GetInterfaceID(IInterface * object)77 InterfaceID WeakReferenceImpl::GetInterfaceID(IInterface *object)
78 {
79     if (object == static_cast<IWeakReference *>(this)) {
80         return g_IID_IWeakReference;
81     }
82     return InterfaceID::Empty;
83 }
84 
Resolve(const InterfaceID & iid,IInterface ** object)85 ErrCode WeakReferenceImpl::Resolve(const InterfaceID &iid, IInterface **object)
86 {
87     VALIDATE_NOT_NULL(object);
88 
89     if ((object_ != nullptr) && wkRef_->AttemptIncStrongRef(this)) {
90         *object = object_->Query(iid);
91         if (*object == nullptr) {
92             object_->DecStrongRef(this);
93         }
94     } else {
95         *object = nullptr;
96     }
97     return ERR_OK;
98 }
99 
IncStrongRef(const void * id)100 void Object::IncStrongRef(const void *id)
101 {
102     RefBase::IncStrongRef(id);
103 }
104 
DecStrongRef(const void * id)105 void Object::DecStrongRef(const void *id)
106 {
107     RefBase::DecStrongRef(id);
108 }
109 
Query(const InterfaceID & iid)110 IInterface *Object::Query(const InterfaceID &iid)
111 {
112     if (iid == g_IID_IObject) {
113         return static_cast<IObject *>(this);
114     }
115     if (iid == g_IID_IWeakReferenceSource) {
116         return static_cast<IWeakReferenceSource *>(this);
117     }
118     if (iid == g_IID_IInterface) {
119         return static_cast<IWeakReferenceSource *>(this);
120     }
121     return nullptr;
122 }
123 
GetInterfaceID(IInterface * object)124 InterfaceID Object::GetInterfaceID(IInterface *object)
125 {
126     if (object == static_cast<IObject *>(this)) {
127         return g_IID_IObject;
128     }
129     if (object == static_cast<IWeakReferenceSource *>(this)) {
130         return g_IID_IWeakReferenceSource;
131     }
132     return InterfaceID::Empty;
133 }
134 
GetClassID()135 ClassID Object::GetClassID()
136 {
137     return ClassID::Empty;
138 }
139 
GetHashCode()140 int Object::GetHashCode()
141 {
142     return reinterpret_cast<HANDLE>(this);
143 }
144 
Equals(IObject & other)145 bool Object::Equals(IObject &other)
146 {
147     Object *otherObj = nullptr;
148     otherObj = static_cast<Object *>(&other);
149     return this == otherObj;
150 }
151 
GetWeakReference(sptr<IWeakReference> & weakRef)152 ErrCode Object::GetWeakReference(sptr<IWeakReference> &weakRef)
153 {
154     void *addr = calloc(sizeof(WeakReferenceImpl), 1);
155     if (addr == nullptr) {
156         return ERR_NO_MEMORY;
157     }
158     weakRef = new (addr) WeakReferenceImpl(static_cast<IObject *>(this), CreateWeakRef(addr));
159     return ERR_OK;
160 }
161 
ToString()162 std::string Object::ToString()
163 {
164     static constexpr int BUFFER_MAX = 1024;
165     std::string str("");
166     char *buf = new (std::nothrow) char[BUFFER_MAX];
167     if (buf != nullptr) {
168         int ret = snprintf_s(buf, BUFFER_MAX, BUFFER_MAX - 1, "[Object %p]", this);
169         if (ret >= 0) {
170             str = buf;
171         }
172         delete[] buf;
173         buf = nullptr;
174     }
175     return str;
176 }
177 
Equals(IInterface & obj1,IInterface & obj2)178 bool Object::Equals(IInterface &obj1, IInterface &obj2)
179 {
180     if (IInterface::Query(&obj1) == IInterface::Query(&obj2)) {
181         return true;
182     }
183 
184     IObject *o1 = IObject::Query(obj1);
185     if (o1 == nullptr) {
186         return false;
187     }
188     return o1->Equals(*(IObject::Query(obj2)));
189 }
190 
ToString(IInterface & object)191 std::string Object::ToString(IInterface &object)
192 {
193     IObject *obj = IObject::Query(object);
194     return ((obj != nullptr) ? obj->ToString() : "");
195 }
196 }  // namespace AAFwk
197 }  // namespace OHOS
198