1 /*
2 * Copyright 2019 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16 #include "security/facade.h"
17
18 #include "grpc/grpc_event_queue.h"
19 #include "hci/address_with_type.h"
20 #include "hci/le_address_manager.h"
21 #include "l2cap/classic/security_policy.h"
22 #include "l2cap/le/l2cap_le_module.h"
23 #include "os/handler.h"
24 #include "security/facade.grpc.pb.h"
25 #include "security/pairing/oob_data.h"
26 #include "security/security_manager_listener.h"
27 #include "security/security_module.h"
28 #include "security/ui.h"
29
30 using bluetooth::l2cap::le::L2capLeModule;
31
32 namespace bluetooth {
33 namespace security {
34
35 namespace {
36 constexpr uint8_t AUTH_REQ_NO_BOND = 0x01;
37 constexpr uint8_t AUTH_REQ_BOND = 0x01;
38 constexpr uint8_t AUTH_REQ_MITM_MASK = 0x04;
39 constexpr uint8_t AUTH_REQ_SECURE_CONNECTIONS_MASK = 0x08;
40 constexpr uint8_t AUTH_REQ_KEYPRESS_MASK = 0x10;
41 constexpr uint8_t AUTH_REQ_CT2_MASK = 0x20;
42 constexpr uint8_t AUTH_REQ_RFU_MASK = 0xC0;
43
ToFacadeAddressWithType(hci::AddressWithType address)44 facade::BluetoothAddressWithType ToFacadeAddressWithType(hci::AddressWithType address) {
45 facade::BluetoothAddressWithType ret;
46
47 ret.mutable_address()->set_address(address.GetAddress().ToString());
48 ret.set_type(static_cast<facade::BluetoothAddressTypeEnum>(address.GetAddressType()));
49
50 return ret;
51 }
52
53 } // namespace
54
55 class SecurityModuleFacadeService : public SecurityModuleFacade::Service, public ISecurityManagerListener, public UI {
56 public:
SecurityModuleFacadeService(SecurityModule * security_module,L2capLeModule * l2cap_le_module,::bluetooth::os::Handler * security_handler)57 SecurityModuleFacadeService(
58 SecurityModule* security_module, L2capLeModule* l2cap_le_module, ::bluetooth::os::Handler* security_handler)
59 : security_module_(security_module), l2cap_le_module_(l2cap_le_module), security_handler_(security_handler) {
60 security_module_->GetSecurityManager()->RegisterCallbackListener(this, security_handler_);
61 security_module_->GetSecurityManager()->SetUserInterfaceHandler(this, security_handler_);
62
63 /* In order to receive connect/disconenct event, we must register service */
64 l2cap_le_module_->GetFixedChannelManager()->RegisterService(
65 bluetooth::l2cap::kLastFixedChannel - 2,
66 common::BindOnce(&SecurityModuleFacadeService::OnL2capRegistrationCompleteLe, common::Unretained(this)),
67 common::Bind(&SecurityModuleFacadeService::OnConnectionOpenLe, common::Unretained(this)),
68 security_handler_);
69 }
70
OnL2capRegistrationCompleteLe(l2cap::le::FixedChannelManager::RegistrationResult result,std::unique_ptr<l2cap::le::FixedChannelService> le_smp_service)71 void OnL2capRegistrationCompleteLe(
72 l2cap::le::FixedChannelManager::RegistrationResult result,
73 std::unique_ptr<l2cap::le::FixedChannelService> le_smp_service) {
74 ASSERT_LOG(
75 result == bluetooth::l2cap::le::FixedChannelManager::RegistrationResult::SUCCESS,
76 "Failed to register to LE SMP Fixed Channel Service");
77 }
78
OnConnectionOpenLe(std::unique_ptr<l2cap::le::FixedChannel> channel)79 void OnConnectionOpenLe(std::unique_ptr<l2cap::le::FixedChannel> channel) {
80 channel->RegisterOnCloseCallback(
81 security_handler_,
82 common::BindOnce(
83 &SecurityModuleFacadeService::OnConnectionClosedLe, common::Unretained(this), channel->GetDevice()));
84 }
85
OnConnectionClosedLe(hci::AddressWithType address,hci::ErrorCode error_code)86 void OnConnectionClosedLe(hci::AddressWithType address, hci::ErrorCode error_code) {
87 SecurityHelperMsg disconnected;
88 *disconnected.mutable_peer() = ToFacadeAddressWithType(address);
89 disconnected.set_message_type(HelperMsgType::DEVICE_DISCONNECTED);
90 helper_events_.OnIncomingEvent(disconnected);
91 }
92
CreateBond(::grpc::ServerContext * context,const facade::BluetoothAddressWithType * request,::google::protobuf::Empty * response)93 ::grpc::Status CreateBond(::grpc::ServerContext* context, const facade::BluetoothAddressWithType* request,
94 ::google::protobuf::Empty* response) override {
95 hci::Address peer;
96 ASSERT(hci::Address::FromString(request->address().address(), peer));
97 hci::AddressType peer_type = static_cast<hci::AddressType>(request->type());
98 security_module_->GetSecurityManager()->CreateBond(hci::AddressWithType(peer, peer_type));
99 return ::grpc::Status::OK;
100 }
101
CreateBondOutOfBand(::grpc::ServerContext * context,const::bluetooth::security::OobDataBondMessage * request,::google::protobuf::Empty * response)102 ::grpc::Status CreateBondOutOfBand(
103 ::grpc::ServerContext* context,
104 const ::bluetooth::security::OobDataBondMessage* request,
105 ::google::protobuf::Empty* response) override {
106 hci::Address peer;
107 ASSERT(hci::Address::FromString(request->address().address().address(), peer));
108 hci::AddressType peer_type = static_cast<hci::AddressType>(request->address().type());
109 pairing::SimplePairingHash c;
110 pairing::SimplePairingRandomizer r;
111 std::copy(
112 std::begin(request->p192_data().confirmation_value()),
113 std::end(request->p192_data().confirmation_value()),
114 c.data());
115 std::copy(std::begin(request->p192_data().random_value()), std::end(request->p192_data().random_value()), r.data());
116 pairing::OobData p192_data(c, r);
117 std::copy(
118 std::begin(request->p256_data().confirmation_value()),
119 std::end(request->p256_data().confirmation_value()),
120 c.data());
121 std::copy(std::begin(request->p256_data().random_value()), std::end(request->p256_data().random_value()), r.data());
122 pairing::OobData p256_data(c, r);
123 security_module_->GetSecurityManager()->CreateBondOutOfBand(
124 hci::AddressWithType(peer, peer_type), p192_data, p256_data);
125 return ::grpc::Status::OK;
126 }
127
GetOutOfBandData(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::google::protobuf::Empty * response)128 ::grpc::Status GetOutOfBandData(
129 ::grpc::ServerContext* context,
130 const ::google::protobuf::Empty* request,
131 ::google::protobuf::Empty* response) override {
132 security_module_->GetSecurityManager()->GetOutOfBandData(
133 security_handler_->BindOnceOn(this, &SecurityModuleFacadeService::OobDataEventOccurred));
134 return ::grpc::Status::OK;
135 }
136
FetchGetOutOfBandDataEvents(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::grpc::ServerWriter<OobDataBondMessage> * writer)137 ::grpc::Status FetchGetOutOfBandDataEvents(
138 ::grpc::ServerContext* context,
139 const ::google::protobuf::Empty* request,
140 ::grpc::ServerWriter<OobDataBondMessage>* writer) override {
141 return oob_events_.RunLoop(context, writer);
142 }
143
CreateBondLe(::grpc::ServerContext * context,const facade::BluetoothAddressWithType * request,::google::protobuf::Empty * response)144 ::grpc::Status CreateBondLe(::grpc::ServerContext* context, const facade::BluetoothAddressWithType* request,
145 ::google::protobuf::Empty* response) override {
146 hci::Address peer;
147 ASSERT(hci::Address::FromString(request->address().address(), peer));
148 hci::AddressType peer_type = static_cast<hci::AddressType>(request->type());
149 security_module_->GetSecurityManager()->CreateBondLe(hci::AddressWithType(peer, peer_type));
150 return ::grpc::Status::OK;
151 }
152
CancelBond(::grpc::ServerContext * context,const facade::BluetoothAddressWithType * request,::google::protobuf::Empty * response)153 ::grpc::Status CancelBond(::grpc::ServerContext* context, const facade::BluetoothAddressWithType* request,
154 ::google::protobuf::Empty* response) override {
155 hci::Address peer;
156 ASSERT(hci::Address::FromString(request->address().address(), peer));
157 hci::AddressType peer_type = hci::AddressType::PUBLIC_DEVICE_ADDRESS;
158 security_module_->GetSecurityManager()->CancelBond(hci::AddressWithType(peer, peer_type));
159 return ::grpc::Status::OK;
160 }
161
RemoveBond(::grpc::ServerContext * context,const facade::BluetoothAddressWithType * request,::google::protobuf::Empty * response)162 ::grpc::Status RemoveBond(::grpc::ServerContext* context, const facade::BluetoothAddressWithType* request,
163 ::google::protobuf::Empty* response) override {
164 hci::Address peer;
165 ASSERT(hci::Address::FromString(request->address().address(), peer));
166 hci::AddressType peer_type = hci::AddressType::PUBLIC_DEVICE_ADDRESS;
167 security_module_->GetSecurityManager()->RemoveBond(hci::AddressWithType(peer, peer_type));
168 return ::grpc::Status::OK;
169 }
170
FetchUiEvents(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::grpc::ServerWriter<UiMsg> * writer)171 ::grpc::Status FetchUiEvents(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
172 ::grpc::ServerWriter<UiMsg>* writer) override {
173 return ui_events_.RunLoop(context, writer);
174 }
175
SendUiCallback(::grpc::ServerContext * context,const UiCallbackMsg * request,::google::protobuf::Empty * response)176 ::grpc::Status SendUiCallback(::grpc::ServerContext* context, const UiCallbackMsg* request,
177 ::google::protobuf::Empty* response) override {
178 hci::Address peer;
179 ASSERT(hci::Address::FromString(request->address().address().address(), peer));
180 hci::AddressType remote_type = static_cast<hci::AddressType>(request->address().type());
181
182 switch (request->message_type()) {
183 case UiCallbackType::PASSKEY:
184 security_module_->GetSecurityManager()->OnPasskeyEntry(
185 hci::AddressWithType(peer, remote_type), request->numeric_value());
186 break;
187 case UiCallbackType::YES_NO:
188 security_module_->GetSecurityManager()->OnConfirmYesNo(hci::AddressWithType(peer, remote_type),
189 request->boolean());
190 break;
191 case UiCallbackType::PAIRING_PROMPT:
192 security_module_->GetSecurityManager()->OnPairingPromptAccepted(
193 hci::AddressWithType(peer, remote_type), request->boolean());
194 break;
195 case UiCallbackType::PIN:
196 LOG_INFO("PIN Callback");
197 security_module_->GetSecurityManager()->OnPinEntry(
198 hci::AddressWithType(peer, remote_type),
199 std::vector<uint8_t>(request->pin().cbegin(), request->pin().cend()));
200 break;
201 default:
202 LOG_ERROR("Unknown UiCallbackType %d", static_cast<int>(request->message_type()));
203 return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Unknown UiCallbackType");
204 }
205 return ::grpc::Status::OK;
206 }
207
FetchBondEvents(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::grpc::ServerWriter<BondMsg> * writer)208 ::grpc::Status FetchBondEvents(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
209 ::grpc::ServerWriter<BondMsg>* writer) override {
210 return bond_events_.RunLoop(context, writer);
211 }
212
FetchHelperEvents(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::grpc::ServerWriter<SecurityHelperMsg> * writer)213 ::grpc::Status FetchHelperEvents(
214 ::grpc::ServerContext* context,
215 const ::google::protobuf::Empty* request,
216 ::grpc::ServerWriter<SecurityHelperMsg>* writer) override {
217 return helper_events_.RunLoop(context, writer);
218 }
SetIoCapability(::grpc::ServerContext * context,const IoCapabilityMessage * request,::google::protobuf::Empty * response)219 ::grpc::Status SetIoCapability(::grpc::ServerContext* context, const IoCapabilityMessage* request,
220 ::google::protobuf::Empty* response) override {
221 security_module_->GetFacadeConfigurationApi()->SetIoCapability(
222 static_cast<hci::IoCapability>(request->capability()));
223 return ::grpc::Status::OK;
224 }
225
SetLeIoCapability(::grpc::ServerContext * context,const LeIoCapabilityMessage * request,::google::protobuf::Empty * response)226 ::grpc::Status SetLeIoCapability(
227 ::grpc::ServerContext* context,
228 const LeIoCapabilityMessage* request,
229 ::google::protobuf::Empty* response) override {
230 security_module_->GetFacadeConfigurationApi()->SetLeIoCapability(
231 static_cast<security::IoCapability>(request->capabilities()));
232 return ::grpc::Status::OK;
233 }
234
SetAuthenticationRequirements(::grpc::ServerContext * context,const AuthenticationRequirementsMessage * request,::google::protobuf::Empty * response)235 ::grpc::Status SetAuthenticationRequirements(::grpc::ServerContext* context,
236 const AuthenticationRequirementsMessage* request,
237 ::google::protobuf::Empty* response) override {
238 security_module_->GetFacadeConfigurationApi()->SetAuthenticationRequirements(
239 static_cast<hci::AuthenticationRequirements>(request->requirement()));
240 return ::grpc::Status::OK;
241 }
242
SetLeAuthRequirements(::grpc::ServerContext * context,const LeAuthRequirementsMessage * request,::google::protobuf::Empty * response)243 ::grpc::Status SetLeAuthRequirements(
244 ::grpc::ServerContext* context,
245 const LeAuthRequirementsMessage* request,
246 ::google::protobuf::Empty* response) override {
247 uint8_t auth_req = request->bond() ? AUTH_REQ_BOND : AUTH_REQ_NO_BOND;
248
249 if (request->mitm()) auth_req |= AUTH_REQ_MITM_MASK;
250 if (request->secure_connections()) auth_req |= AUTH_REQ_SECURE_CONNECTIONS_MASK;
251 if (request->keypress()) auth_req |= AUTH_REQ_KEYPRESS_MASK;
252 if (request->ct2()) auth_req |= AUTH_REQ_CT2_MASK;
253 if (request->reserved_bits()) auth_req |= (((request->reserved_bits()) << 6) & AUTH_REQ_RFU_MASK);
254
255 security_module_->GetFacadeConfigurationApi()->SetLeAuthRequirements(auth_req);
256 return ::grpc::Status::OK;
257 }
258
SetLeMaximumEncryptionKeySize(::grpc::ServerContext * context,const LeMaximumEncryptionKeySizeMessage * request,::google::protobuf::Empty * response)259 ::grpc::Status SetLeMaximumEncryptionKeySize(
260 ::grpc::ServerContext* context,
261 const LeMaximumEncryptionKeySizeMessage* request,
262 ::google::protobuf::Empty* response) override {
263 security_module_->GetFacadeConfigurationApi()->SetLeMaximumEncryptionKeySize(
264 request->maximum_encryption_key_size());
265 return ::grpc::Status::OK;
266 }
267
SetLeOobDataPresent(::grpc::ServerContext * context,const LeOobDataPresentMessage * request,::google::protobuf::Empty * response)268 ::grpc::Status SetLeOobDataPresent(
269 ::grpc::ServerContext* context,
270 const LeOobDataPresentMessage* request,
271 ::google::protobuf::Empty* response) override {
272 security_module_->GetFacadeConfigurationApi()->SetLeOobDataPresent(
273 static_cast<OobDataFlag>(request->data_present()));
274 return ::grpc::Status::OK;
275 }
276
SetLeInitiatorAddressPolicy(::grpc::ServerContext * context,const hci::PrivacyPolicy * request,::google::protobuf::Empty * response)277 ::grpc::Status SetLeInitiatorAddressPolicy(
278 ::grpc::ServerContext* context, const hci::PrivacyPolicy* request, ::google::protobuf::Empty* response) override {
279 Address address = Address::kEmpty;
280 hci::LeAddressManager::AddressPolicy address_policy =
281 static_cast<hci::LeAddressManager::AddressPolicy>(request->address_policy());
282 if (address_policy == hci::LeAddressManager::AddressPolicy::USE_STATIC_ADDRESS ||
283 address_policy == hci::LeAddressManager::AddressPolicy::USE_PUBLIC_ADDRESS) {
284 ASSERT(Address::FromString(request->address_with_type().address().address(), address));
285 }
286 hci::AddressWithType address_with_type(address, static_cast<hci::AddressType>(request->address_with_type().type()));
287 crypto_toolbox::Octet16 irk = {};
288 auto request_irk_length = request->rotation_irk().end() - request->rotation_irk().begin();
289 if (request_irk_length == crypto_toolbox::OCTET16_LEN) {
290 std::vector<uint8_t> irk_data(request->rotation_irk().begin(), request->rotation_irk().end());
291 std::copy_n(irk_data.begin(), crypto_toolbox::OCTET16_LEN, irk.begin());
292 } else {
293 ASSERT(request_irk_length == 0);
294 }
295 auto minimum_rotation_time = std::chrono::milliseconds(request->minimum_rotation_time());
296 auto maximum_rotation_time = std::chrono::milliseconds(request->maximum_rotation_time());
297 security_module_->GetSecurityManager()->SetLeInitiatorAddressPolicyForTest(
298 address_policy, address_with_type, irk, minimum_rotation_time, maximum_rotation_time);
299 return ::grpc::Status::OK;
300 }
301
FetchEnforceSecurityPolicyEvents(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::grpc::ServerWriter<EnforceSecurityPolicyMsg> * writer)302 ::grpc::Status FetchEnforceSecurityPolicyEvents(
303 ::grpc::ServerContext* context,
304 const ::google::protobuf::Empty* request,
305 ::grpc::ServerWriter<EnforceSecurityPolicyMsg>* writer) override {
306 return enforce_security_policy_events_.RunLoop(context, writer);
307 }
308
EnforceSecurityPolicy(::grpc::ServerContext * context,const SecurityPolicyMessage * request,::google::protobuf::Empty * response)309 ::grpc::Status EnforceSecurityPolicy(
310 ::grpc::ServerContext* context,
311 const SecurityPolicyMessage* request,
312 ::google::protobuf::Empty* response) override {
313 hci::Address peer;
314 ASSERT(hci::Address::FromString(request->address().address().address(), peer));
315 hci::AddressType peer_type = static_cast<hci::AddressType>(request->address().type());
316 hci::AddressWithType peer_with_type(peer, peer_type);
317 l2cap::classic::SecurityEnforcementInterface::ResultCallback callback =
318 security_handler_->BindOnceOn(this, &SecurityModuleFacadeService::EnforceSecurityPolicyEvent);
319 security_module_->GetFacadeConfigurationApi()->EnforceSecurityPolicy(
320 peer_with_type, static_cast<l2cap::classic::SecurityPolicy>(request->policy()), std::move(callback));
321 return ::grpc::Status::OK;
322 }
323
GetLeOutOfBandData(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::bluetooth::security::OobDataMessage * response)324 ::grpc::Status GetLeOutOfBandData(
325 ::grpc::ServerContext* context,
326 const ::google::protobuf::Empty* request,
327 ::bluetooth::security::OobDataMessage* response) override {
328 std::array<uint8_t, 16> le_sc_c;
329 std::array<uint8_t, 16> le_sc_r;
330 security_module_->GetFacadeConfigurationApi()->GetLeOutOfBandData(&le_sc_c, &le_sc_r);
331
332 std::string le_sc_c_str(17, '\0');
333 std::copy(le_sc_c.begin(), le_sc_c.end(), le_sc_c_str.data());
334 response->set_confirmation_value(le_sc_c_str);
335
336 std::string le_sc_r_str(17, '\0');
337 std::copy(le_sc_r.begin(), le_sc_r.end(), le_sc_r_str.data());
338 response->set_random_value(le_sc_r_str);
339
340 return ::grpc::Status::OK;
341 }
342
SetOutOfBandData(::grpc::ServerContext * context,const::bluetooth::security::OobDataMessage * request,::google::protobuf::Empty * response)343 ::grpc::Status SetOutOfBandData(
344 ::grpc::ServerContext* context,
345 const ::bluetooth::security::OobDataMessage* request,
346 ::google::protobuf::Empty* response) override {
347 hci::Address peer;
348 ASSERT(hci::Address::FromString(request->address().address().address(), peer));
349 hci::AddressType peer_type = static_cast<hci::AddressType>(request->address().type());
350 hci::AddressWithType peer_with_type(peer, peer_type);
351
352 // We can't simply iterate till end of string, because we have an empty byte added at the end. We know confirm and
353 // random are fixed size, 16 bytes
354 std::array<uint8_t, 16> le_sc_c;
355 auto req_le_sc_c = request->confirmation_value();
356 std::copy(req_le_sc_c.begin(), req_le_sc_c.begin() + 16, le_sc_c.data());
357
358 std::array<uint8_t, 16> le_sc_r;
359 auto req_le_sc_r = request->random_value();
360 std::copy(req_le_sc_r.begin(), req_le_sc_r.begin() + 16, le_sc_r.data());
361
362 security_module_->GetFacadeConfigurationApi()->SetOutOfBandData(peer_with_type, le_sc_c, le_sc_r);
363 return ::grpc::Status::OK;
364 }
365
FetchDisconnectEvents(::grpc::ServerContext * context,const::google::protobuf::Empty * request,::grpc::ServerWriter<DisconnectMsg> * writer)366 ::grpc::Status FetchDisconnectEvents(
367 ::grpc::ServerContext* context,
368 const ::google::protobuf::Empty* request,
369 ::grpc::ServerWriter<DisconnectMsg>* writer) override {
370 security_module_->GetFacadeConfigurationApi()->SetDisconnectCallback(
371 common::Bind(&SecurityModuleFacadeService::DisconnectEventOccurred, common::Unretained(this)));
372 return disconnect_events_.RunLoop(context, writer);
373 }
374
OobDataEventOccurred(bluetooth::hci::CommandCompleteView packet)375 void OobDataEventOccurred(bluetooth::hci::CommandCompleteView packet) {
376 LOG_INFO("Got OOB Data event");
377 ASSERT(packet.IsValid());
378 auto cc = bluetooth::hci::ReadLocalOobDataCompleteView::Create(packet);
379 ASSERT(cc.IsValid());
380 OobDataBondMessage msg;
381 OobDataMessage p192;
382 // Just need this to satisfy the proto message
383 bluetooth::hci::AddressWithType peer;
384 *p192.mutable_address() = ToFacadeAddressWithType(peer);
385
386 auto c = cc.GetC();
387 p192.set_confirmation_value(c.data(), c.size());
388
389 auto r = cc.GetR();
390 p192.set_random_value(r.data(), r.size());
391
392 // Only the Extended version returns 256 also.
393 // The API has a parameter for both, so we set it
394 // empty and the module and test suite will ignore it.
395 OobDataMessage p256;
396 *p256.mutable_address() = ToFacadeAddressWithType(peer);
397
398 std::array<uint8_t, 16> empty_val;
399 p256.set_confirmation_value(empty_val.data(), empty_val.size());
400 p256.set_random_value(empty_val.data(), empty_val.size());
401
402 *msg.mutable_address() = ToFacadeAddressWithType(peer);
403 *msg.mutable_p192_data() = p192;
404 *msg.mutable_p256_data() = p256;
405 oob_events_.OnIncomingEvent(msg);
406 }
407
DisconnectEventOccurred(bluetooth::hci::AddressWithType peer)408 void DisconnectEventOccurred(bluetooth::hci::AddressWithType peer) {
409 LOG_INFO("%s", peer.ToString().c_str());
410 DisconnectMsg msg;
411 *msg.mutable_address() = ToFacadeAddressWithType(peer);
412 disconnect_events_.OnIncomingEvent(msg);
413 }
414
DisplayPairingPrompt(const bluetooth::hci::AddressWithType & peer,std::string name)415 void DisplayPairingPrompt(const bluetooth::hci::AddressWithType& peer, std::string name) {
416 LOG_INFO("%s", peer.ToString().c_str());
417 UiMsg display_yes_no;
418 *display_yes_no.mutable_peer() = ToFacadeAddressWithType(peer);
419 display_yes_no.set_message_type(UiMsgType::DISPLAY_PAIRING_PROMPT);
420 display_yes_no.set_unique_id(unique_id++);
421 ui_events_.OnIncomingEvent(display_yes_no);
422 }
423
DisplayConfirmValue(ConfirmationData data)424 virtual void DisplayConfirmValue(ConfirmationData data) {
425 const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
426 std::string name = data.GetName();
427 uint32_t numeric_value = data.GetNumericValue();
428 LOG_INFO("%s value = 0x%x", peer.ToString().c_str(), numeric_value);
429 UiMsg display_with_value;
430 *display_with_value.mutable_peer() = ToFacadeAddressWithType(peer);
431 display_with_value.set_message_type(UiMsgType::DISPLAY_YES_NO_WITH_VALUE);
432 display_with_value.set_numeric_value(numeric_value);
433 display_with_value.set_unique_id(unique_id++);
434 ui_events_.OnIncomingEvent(display_with_value);
435 }
436
DisplayYesNoDialog(ConfirmationData data)437 void DisplayYesNoDialog(ConfirmationData data) override {
438 const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
439 std::string name = data.GetName();
440 LOG_INFO("%s", peer.ToString().c_str());
441 UiMsg display_yes_no;
442 *display_yes_no.mutable_peer() = ToFacadeAddressWithType(peer);
443 display_yes_no.set_message_type(UiMsgType::DISPLAY_YES_NO);
444 display_yes_no.set_unique_id(unique_id++);
445 ui_events_.OnIncomingEvent(display_yes_no);
446 }
447
DisplayPasskey(ConfirmationData data)448 void DisplayPasskey(ConfirmationData data) override {
449 const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
450 std::string name = data.GetName();
451 uint32_t passkey = data.GetNumericValue();
452 LOG_INFO("%s value = 0x%x", peer.ToString().c_str(), passkey);
453 UiMsg display_passkey;
454 *display_passkey.mutable_peer() = ToFacadeAddressWithType(peer);
455 display_passkey.set_message_type(UiMsgType::DISPLAY_PASSKEY);
456 display_passkey.set_numeric_value(passkey);
457 display_passkey.set_unique_id(unique_id++);
458 ui_events_.OnIncomingEvent(display_passkey);
459 }
460
DisplayEnterPasskeyDialog(ConfirmationData data)461 void DisplayEnterPasskeyDialog(ConfirmationData data) override {
462 const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
463 std::string name = data.GetName();
464 LOG_INFO("%s", peer.ToString().c_str());
465 UiMsg display_passkey_input;
466 *display_passkey_input.mutable_peer() = ToFacadeAddressWithType(peer);
467 display_passkey_input.set_message_type(UiMsgType::DISPLAY_PASSKEY_ENTRY);
468 display_passkey_input.set_unique_id(unique_id++);
469 ui_events_.OnIncomingEvent(display_passkey_input);
470 }
471
DisplayEnterPinDialog(ConfirmationData data)472 void DisplayEnterPinDialog(ConfirmationData data) override {
473 const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
474 std::string name = data.GetName();
475 LOG_INFO("%s", peer.ToString().c_str());
476 UiMsg display_pin_input;
477 *display_pin_input.mutable_peer() = ToFacadeAddressWithType(peer);
478 display_pin_input.set_message_type(UiMsgType::DISPLAY_PIN_ENTRY);
479 display_pin_input.set_unique_id(unique_id++);
480 ui_events_.OnIncomingEvent(display_pin_input);
481 }
482
Cancel(const bluetooth::hci::AddressWithType & peer)483 void Cancel(const bluetooth::hci::AddressWithType& peer) override {
484 LOG_INFO("%s", peer.ToString().c_str());
485 UiMsg display_cancel;
486 *display_cancel.mutable_peer() = ToFacadeAddressWithType(peer);
487 display_cancel.set_message_type(UiMsgType::DISPLAY_CANCEL);
488 display_cancel.set_unique_id(unique_id++);
489 ui_events_.OnIncomingEvent(display_cancel);
490 }
491
OnDeviceBonded(hci::AddressWithType peer)492 void OnDeviceBonded(hci::AddressWithType peer) override {
493 LOG_INFO("%s", peer.ToString().c_str());
494 BondMsg bonded;
495 *bonded.mutable_peer() = ToFacadeAddressWithType(peer);
496 bonded.set_message_type(BondMsgType::DEVICE_BONDED);
497 bond_events_.OnIncomingEvent(bonded);
498 }
499
OnEncryptionStateChanged(hci::EncryptionChangeView encryption_change_view)500 void OnEncryptionStateChanged(hci::EncryptionChangeView encryption_change_view) override {}
501
OnDeviceUnbonded(hci::AddressWithType peer)502 void OnDeviceUnbonded(hci::AddressWithType peer) override {
503 LOG_INFO("%s", peer.ToString().c_str());
504 BondMsg unbonded;
505 *unbonded.mutable_peer() = ToFacadeAddressWithType(peer);
506 unbonded.set_message_type(BondMsgType::DEVICE_UNBONDED);
507 bond_events_.OnIncomingEvent(unbonded);
508 }
509
OnDeviceBondFailed(hci::AddressWithType peer,PairingFailure status)510 void OnDeviceBondFailed(hci::AddressWithType peer, PairingFailure status) override {
511 LOG_INFO("%s", peer.ToString().c_str());
512 BondMsg bond_failed;
513 *bond_failed.mutable_peer() = ToFacadeAddressWithType(peer);
514 bond_failed.set_message_type(BondMsgType::DEVICE_BOND_FAILED);
515 bond_failed.set_reason(static_cast<uint8_t>(status.reason));
516 bond_events_.OnIncomingEvent(bond_failed);
517 }
518
EnforceSecurityPolicyEvent(bool result)519 void EnforceSecurityPolicyEvent(bool result) {
520 EnforceSecurityPolicyMsg msg;
521 msg.set_result(result);
522 enforce_security_policy_events_.OnIncomingEvent(msg);
523 }
524
525 private:
526 SecurityModule* security_module_;
527 L2capLeModule* l2cap_le_module_;
528 ::bluetooth::os::Handler* security_handler_;
529 ::bluetooth::grpc::GrpcEventQueue<UiMsg> ui_events_{"UI events"};
530 ::bluetooth::grpc::GrpcEventQueue<BondMsg> bond_events_{"Bond events"};
531 ::bluetooth::grpc::GrpcEventQueue<SecurityHelperMsg> helper_events_{"Events that don't fit any other category"};
532 ::bluetooth::grpc::GrpcEventQueue<EnforceSecurityPolicyMsg> enforce_security_policy_events_{
533 "Enforce Security Policy Events"};
534 ::bluetooth::grpc::GrpcEventQueue<DisconnectMsg> disconnect_events_{"Disconnect events"};
535 ::bluetooth::grpc::GrpcEventQueue<OobDataBondMessage> oob_events_{"OOB Data events"};
536 uint32_t unique_id{1};
537 std::map<uint32_t, common::OnceCallback<void(bool)>> user_yes_no_callbacks_;
538 std::map<uint32_t, common::OnceCallback<void(uint32_t)>> user_passkey_callbacks_;
539 };
540
ListDependencies(ModuleList * list)541 void SecurityModuleFacadeModule::ListDependencies(ModuleList* list) {
542 ::bluetooth::grpc::GrpcFacadeModule::ListDependencies(list);
543 list->add<SecurityModule>();
544 list->add<L2capLeModule>();
545 }
546
Start()547 void SecurityModuleFacadeModule::Start() {
548 ::bluetooth::grpc::GrpcFacadeModule::Start();
549 service_ =
550 new SecurityModuleFacadeService(GetDependency<SecurityModule>(), GetDependency<L2capLeModule>(), GetHandler());
551 }
552
Stop()553 void SecurityModuleFacadeModule::Stop() {
554 delete service_;
555 ::bluetooth::grpc::GrpcFacadeModule::Stop();
556 }
557
GetService() const558 ::grpc::Service* SecurityModuleFacadeModule::GetService() const {
559 return service_;
560 }
561
562 const ModuleFactory SecurityModuleFacadeModule::Factory =
__anonb20831cd0202() 563 ::bluetooth::ModuleFactory([]() { return new SecurityModuleFacadeModule(); });
564
565 } // namespace security
566 } // namespace bluetooth
567