1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "remoting/protocol/pairing_host_authenticator.h"
8 #include "base/logging.h"
9 #include "remoting/base/constants.h"
10 #include "remoting/base/rsa_key_pair.h"
11 #include "remoting/protocol/channel_authenticator.h"
12 #include "remoting/protocol/v2_authenticator.h"
13 #include "third_party/libjingle/source/talk/xmllite/xmlelement.h"
18 PairingHostAuthenticator::PairingHostAuthenticator(
19 scoped_refptr
<PairingRegistry
> pairing_registry
,
20 const std::string
& local_cert
,
21 scoped_refptr
<RsaKeyPair
> key_pair
,
22 const std::string
& pin
)
23 : pairing_registry_(pairing_registry
),
24 local_cert_(local_cert
),
27 protocol_error_(false),
28 waiting_for_paired_secret_(false),
32 PairingHostAuthenticator::~PairingHostAuthenticator() {
35 Authenticator::State
PairingHostAuthenticator::state() const {
36 if (protocol_error_
) {
38 } else if (waiting_for_paired_secret_
) {
39 return PROCESSING_MESSAGE
;
40 } else if (!v2_authenticator_
) {
41 return WAITING_MESSAGE
;
43 return PairingAuthenticatorBase::state();
46 Authenticator::RejectionReason
47 PairingHostAuthenticator::rejection_reason() const {
48 if (protocol_error_
) {
49 return PROTOCOL_ERROR
;
51 return PairingAuthenticatorBase::rejection_reason();
54 void PairingHostAuthenticator::CreateV2AuthenticatorWithPIN(
56 const SetAuthenticatorCallback
& callback
) {
57 callback
.Run(V2Authenticator::CreateForHost(
58 local_cert_
, key_pair_
, pin_
, initial_state
));
61 void PairingHostAuthenticator::ProcessMessage(
62 const buzz::XmlElement
* message
,
63 const base::Closure
& resume_callback
) {
64 if (!v2_authenticator_
) {
65 std::string client_id
;
67 const buzz::XmlElement
* pairing_tag
= message
->FirstNamed(kPairingInfoTag
);
69 client_id
= pairing_tag
->Attr(kClientIdAttribute
);
72 if (client_id
.empty()) {
73 LOG(ERROR
) << "No client id specified.";
74 protocol_error_
= true;
76 waiting_for_paired_secret_
= true;
77 pairing_registry_
->GetPairing(
79 base::Bind(&PairingHostAuthenticator::ProcessMessageWithPairing
,
80 weak_factory_
.GetWeakPtr(),
81 base::Owned(new buzz::XmlElement(*message
)),
87 PairingAuthenticatorBase::ProcessMessage(message
, resume_callback
);
90 void PairingHostAuthenticator::AddPairingElements(buzz::XmlElement
* message
) {
94 void PairingHostAuthenticator::ProcessMessageWithPairing(
95 const buzz::XmlElement
* message
,
96 const base::Closure
& resume_callback
,
97 PairingRegistry::Pairing pairing
) {
98 waiting_for_paired_secret_
= false;
99 std::string paired_secret
= pairing
.shared_secret();
100 if (paired_secret
.empty()) {
101 VLOG(0) << "Unknown client id";
102 error_message_
= "unknown-client-id";
105 using_paired_secret_
= !paired_secret
.empty();
106 if (using_paired_secret_
) {
107 v2_authenticator_
= V2Authenticator::CreateForHost(
108 local_cert_
, key_pair_
, paired_secret
, WAITING_MESSAGE
);
109 PairingAuthenticatorBase::ProcessMessage(message
, resume_callback
);
111 v2_authenticator_
= V2Authenticator::CreateForHost(
112 local_cert_
, key_pair_
, pin_
, MESSAGE_READY
);
113 // The client's optimistic SPAKE message is using a Paired Secret to
114 // which the host doesn't have access, so don't bother processing it.
115 resume_callback
.Run();
119 } // namespace protocol
120 } // namespace remoting