1 //
2 // Copyright (C) 2016 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
17 #include "tpm_manager/server/binder_service.h"
18
19 #include <sysexits.h>
20
21 #include <base/bind.h>
22 #include <binderwrapper/binder_wrapper.h>
23
24 #include "tpm_manager/common/tpm_manager.pb.h"
25 #include "tpm_manager/common/tpm_manager_constants.h"
26
27 namespace {
28
29 // Sends a |response_proto| to |client| for an arbitrary protobuf type.
30 template <typename ResponseProtobufType>
ResponseHandler(const android::sp<android::tpm_manager::ITpmManagerClient> & client,const ResponseProtobufType & response_proto)31 void ResponseHandler(
32 const android::sp<android::tpm_manager::ITpmManagerClient>& client,
33 const ResponseProtobufType& response_proto) {
34 VLOG(2) << __func__;
35 std::vector<uint8_t> binder_response;
36 binder_response.resize(response_proto.ByteSize());
37 CHECK(response_proto.SerializeToArray(binder_response.data(),
38 binder_response.size()))
39 << "BinderService: Failed to serialize protobuf.";
40 android::binder::Status status = client->OnCommandResponse(binder_response);
41 if (!status.isOk()) {
42 LOG(ERROR) << "BinderService: Failed to send response to client: "
43 << status.toString8();
44 }
45 }
46
47 // Creates an error protobuf for NVRAM commands.
48 template <typename ResponseProtobufType>
CreateNvramErrorResponse(ResponseProtobufType * proto)49 void CreateNvramErrorResponse(ResponseProtobufType* proto) {
50 proto->set_result(tpm_manager::NVRAM_RESULT_IPC_ERROR);
51 }
52
53 // Creates an error protobuf for ownership commands.
54 template <typename ResponseProtobufType>
CreateOwnershipErrorResponse(ResponseProtobufType * proto)55 void CreateOwnershipErrorResponse(ResponseProtobufType* proto) {
56 proto->set_status(tpm_manager::STATUS_DEVICE_ERROR);
57 }
58
59 // Calls |method| with a protobuf decoded from |request| using ResponseHandler()
60 // and |client| to handle the response. On error, uses |get_error_response| to
61 // construct a response and sends that to |client|.
62 template <typename RequestProtobufType, typename ResponseProtobufType>
RequestHandler(const std::vector<uint8_t> & request,const base::Callback<void (const RequestProtobufType &,const base::Callback<void (const ResponseProtobufType &)> &)> & method,const base::Callback<void (ResponseProtobufType *)> & get_error_response,const android::sp<android::tpm_manager::ITpmManagerClient> & client)63 void RequestHandler(
64 const std::vector<uint8_t>& request,
65 const base::Callback<
66 void(const RequestProtobufType&,
67 const base::Callback<void(const ResponseProtobufType&)>&)>& method,
68 const base::Callback<void(ResponseProtobufType*)>& get_error_response,
69 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
70 VLOG(2) << __func__;
71 base::Callback<void(const ResponseProtobufType&)> callback =
72 base::Bind(ResponseHandler<ResponseProtobufType>, client);
73 RequestProtobufType request_proto;
74 if (!request_proto.ParseFromArray(request.data(), request.size())) {
75 LOG(ERROR) << "BinderService: Bad request data.";
76 // Send an error response.
77 ResponseProtobufType response_proto;
78 get_error_response.Run(&response_proto);
79 callback.Run(response_proto);
80 return;
81 }
82 method.Run(request_proto, callback);
83 }
84
85 } // namespace
86
87 namespace tpm_manager {
88
BinderService(TpmNvramInterface * nvram_service,TpmOwnershipInterface * ownership_service)89 BinderService::BinderService(TpmNvramInterface* nvram_service,
90 TpmOwnershipInterface* ownership_service)
91 : nvram_service_(nvram_service), ownership_service_(ownership_service) {}
92
InitForTesting()93 void BinderService::InitForTesting() {
94 nvram_binder_ = new NvramServiceInternal(nvram_service_);
95 ownership_binder_ = new OwnershipServiceInternal(ownership_service_);
96 }
97
OnInit()98 int BinderService::OnInit() {
99 if (!watcher_.Init()) {
100 LOG(ERROR) << "BinderService: BinderWatcher::Init failed.";
101 return EX_UNAVAILABLE;
102 }
103 nvram_binder_ = new NvramServiceInternal(nvram_service_);
104 ownership_binder_ = new OwnershipServiceInternal(ownership_service_);
105 if (!android::BinderWrapper::GetOrCreateInstance()->RegisterService(
106 kTpmNvramBinderName, android::IInterface::asBinder(nvram_binder_))) {
107 LOG(ERROR) << "BinderService: RegisterService failed (nvram).";
108 return EX_UNAVAILABLE;
109 }
110 if (!android::BinderWrapper::GetOrCreateInstance()->RegisterService(
111 kTpmOwnershipBinderName,
112 android::IInterface::asBinder(ownership_binder_))) {
113 LOG(ERROR) << "BinderService: RegisterService failed (ownership).";
114 return EX_UNAVAILABLE;
115 }
116 LOG(INFO) << "TpmManager: Binder services registered.";
117 return brillo::Daemon::OnInit();
118 }
119
GetITpmNvram()120 android::tpm_manager::ITpmNvram* BinderService::GetITpmNvram() {
121 return nvram_binder_.get();
122 }
123
GetITpmOwnership()124 android::tpm_manager::ITpmOwnership* BinderService::GetITpmOwnership() {
125 return ownership_binder_.get();
126 }
127
NvramServiceInternal(TpmNvramInterface * nvram_service)128 BinderService::NvramServiceInternal::NvramServiceInternal(
129 TpmNvramInterface* nvram_service)
130 : nvram_service_(nvram_service) {}
131
DefineSpace(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)132 android::binder::Status BinderService::NvramServiceInternal::DefineSpace(
133 const std::vector<uint8_t>& command_proto,
134 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
135 RequestHandler<DefineSpaceRequest, DefineSpaceReply>(
136 command_proto, base::Bind(&TpmNvramInterface::DefineSpace,
137 base::Unretained(nvram_service_)),
138 base::Bind(CreateNvramErrorResponse<DefineSpaceReply>), client);
139 return android::binder::Status::ok();
140 }
141
DestroySpace(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)142 android::binder::Status BinderService::NvramServiceInternal::DestroySpace(
143 const std::vector<uint8_t>& command_proto,
144 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
145 RequestHandler<DestroySpaceRequest, DestroySpaceReply>(
146 command_proto, base::Bind(&TpmNvramInterface::DestroySpace,
147 base::Unretained(nvram_service_)),
148 base::Bind(CreateNvramErrorResponse<DestroySpaceReply>), client);
149 return android::binder::Status::ok();
150 }
151
WriteSpace(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)152 android::binder::Status BinderService::NvramServiceInternal::WriteSpace(
153 const std::vector<uint8_t>& command_proto,
154 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
155 RequestHandler<WriteSpaceRequest, WriteSpaceReply>(
156 command_proto, base::Bind(&TpmNvramInterface::WriteSpace,
157 base::Unretained(nvram_service_)),
158 base::Bind(CreateNvramErrorResponse<WriteSpaceReply>), client);
159 return android::binder::Status::ok();
160 }
161
ReadSpace(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)162 android::binder::Status BinderService::NvramServiceInternal::ReadSpace(
163 const std::vector<uint8_t>& command_proto,
164 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
165 RequestHandler<ReadSpaceRequest, ReadSpaceReply>(
166 command_proto, base::Bind(&TpmNvramInterface::ReadSpace,
167 base::Unretained(nvram_service_)),
168 base::Bind(CreateNvramErrorResponse<ReadSpaceReply>), client);
169 return android::binder::Status::ok();
170 }
171
LockSpace(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)172 android::binder::Status BinderService::NvramServiceInternal::LockSpace(
173 const std::vector<uint8_t>& command_proto,
174 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
175 RequestHandler<LockSpaceRequest, LockSpaceReply>(
176 command_proto, base::Bind(&TpmNvramInterface::LockSpace,
177 base::Unretained(nvram_service_)),
178 base::Bind(CreateNvramErrorResponse<LockSpaceReply>), client);
179 return android::binder::Status::ok();
180 }
181
ListSpaces(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)182 android::binder::Status BinderService::NvramServiceInternal::ListSpaces(
183 const std::vector<uint8_t>& command_proto,
184 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
185 RequestHandler<ListSpacesRequest, ListSpacesReply>(
186 command_proto, base::Bind(&TpmNvramInterface::ListSpaces,
187 base::Unretained(nvram_service_)),
188 base::Bind(CreateNvramErrorResponse<ListSpacesReply>), client);
189 return android::binder::Status::ok();
190 }
191
GetSpaceInfo(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)192 android::binder::Status BinderService::NvramServiceInternal::GetSpaceInfo(
193 const std::vector<uint8_t>& command_proto,
194 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
195 RequestHandler<GetSpaceInfoRequest, GetSpaceInfoReply>(
196 command_proto, base::Bind(&TpmNvramInterface::GetSpaceInfo,
197 base::Unretained(nvram_service_)),
198 base::Bind(CreateNvramErrorResponse<GetSpaceInfoReply>), client);
199 return android::binder::Status::ok();
200 }
201
OwnershipServiceInternal(TpmOwnershipInterface * ownership_service)202 BinderService::OwnershipServiceInternal::OwnershipServiceInternal(
203 TpmOwnershipInterface* ownership_service)
204 : ownership_service_(ownership_service) {}
205
GetTpmStatus(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)206 android::binder::Status BinderService::OwnershipServiceInternal::GetTpmStatus(
207 const std::vector<uint8_t>& command_proto,
208 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
209 RequestHandler<GetTpmStatusRequest, GetTpmStatusReply>(
210 command_proto, base::Bind(&TpmOwnershipInterface::GetTpmStatus,
211 base::Unretained(ownership_service_)),
212 base::Bind(CreateOwnershipErrorResponse<GetTpmStatusReply>), client);
213 return android::binder::Status::ok();
214 }
215
TakeOwnership(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)216 android::binder::Status BinderService::OwnershipServiceInternal::TakeOwnership(
217 const std::vector<uint8_t>& command_proto,
218 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
219 RequestHandler<TakeOwnershipRequest, TakeOwnershipReply>(
220 command_proto, base::Bind(&TpmOwnershipInterface::TakeOwnership,
221 base::Unretained(ownership_service_)),
222 base::Bind(CreateOwnershipErrorResponse<TakeOwnershipReply>), client);
223 return android::binder::Status::ok();
224 }
225
226 android::binder::Status
RemoveOwnerDependency(const std::vector<uint8_t> & command_proto,const android::sp<android::tpm_manager::ITpmManagerClient> & client)227 BinderService::OwnershipServiceInternal::RemoveOwnerDependency(
228 const std::vector<uint8_t>& command_proto,
229 const android::sp<android::tpm_manager::ITpmManagerClient>& client) {
230 RequestHandler<RemoveOwnerDependencyRequest, RemoveOwnerDependencyReply>(
231 command_proto, base::Bind(&TpmOwnershipInterface::RemoveOwnerDependency,
232 base::Unretained(ownership_service_)),
233 base::Bind(CreateOwnershipErrorResponse<RemoveOwnerDependencyReply>),
234 client);
235 return android::binder::Status::ok();
236 }
237
238 } // namespace tpm_manager
239