109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley/* 209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * Copyright (C) 2015 The Android Open Source Project 309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * 409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * Licensed under the Apache License, Version 2.0 (the "License"); 509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * you may not use this file except in compliance with the License. 609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * You may obtain a copy of the License at 709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * 809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * http://www.apache.org/licenses/LICENSE-2.0 909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * 1009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * Unless required by applicable law or agreed to in writing, software 1109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * distributed under the License is distributed on an "AS IS" BASIS, 1209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * See the License for the specific language governing permissions and 1409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley * limitations under the License. 1509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley */ 1609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 1709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley#ifndef ANDROID_BINDER_STATUS_H 1809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley#define ANDROID_BINDER_STATUS_H 1909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 2009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley#include <cstdint> 2109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 2209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley#include <binder/Parcel.h> 2309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley#include <utils/String8.h> 2409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 2509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wileynamespace android { 2609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wileynamespace binder { 2709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 2809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// An object similar in function to a status_t except that it understands 2909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// how exceptions are encoded in the prefix of a Parcel. Used like: 3009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// 3109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// Parcel data; 3209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// Parcel reply; 3309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// status_t status; 3409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// binder::Status remote_exception; 3509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// if ((status = data.writeInterfaceToken(interface_descriptor)) != OK || 3609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// (status = data.writeInt32(function_input)) != OK) { 3709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// // We failed to write into the memory of our local parcel? 3809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// } 3909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// if ((status = remote()->transact(transaction, data, &reply)) != OK) { 4009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// // Something has gone wrong in the binder driver or libbinder. 4109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// } 4209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// if ((status = remote_exception.readFromParcel(reply)) != OK) { 4309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// // The remote didn't correctly write the exception header to the 4409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// // reply. 4509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// } 4609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// if (!remote_exception.isOk()) { 4709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// // The transaction went through correctly, but the remote reported an 4809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// // exception during handling. 4909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// } 5009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley// 5109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wileyclass Status final { 5209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wileypublic: 5309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // Keep the exception codes in sync with android/os/Parcel.java. 5409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley enum Exception { 5509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_NONE = 0, 5609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_SECURITY = -1, 5709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_BAD_PARCELABLE = -2, 5809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_ILLEGAL_ARGUMENT = -3, 5909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_NULL_POINTER = -4, 6009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_ILLEGAL_STATE = -5, 6109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_NETWORK_MAIN_THREAD = -6, 6209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_UNSUPPORTED_OPERATION = -7, 63c1e491d5a4923298b612de919537d4293574b443Christopher Wiley EX_SERVICE_SPECIFIC = -8, 6409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 6509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // This is special and Java specific; see Parcel.java. 6609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley EX_HAS_REPLY_HEADER = -128, 67cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // This is special, and indicates to C++ binder proxies that the 68cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // transaction has failed at a low level. 69cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley EX_TRANSACTION_FAILED = -129, 7009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley }; 7109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 72cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // A more readable alias for the default constructor. 73cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley static Status ok(); 74c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // Authors should explicitly pick whether their integer is: 75c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // - an exception code (EX_* above) 76c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // - service specific error code 77c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // - status_t 78c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // 79c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // Prefer a generic exception code when possible, then a service specific 80c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // code, and finally a status_t for low level failures or legacy support. 81c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // Exception codes and service specific errors map to nicer exceptions for 82c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // Java clients. 83cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley static Status fromExceptionCode(int32_t exceptionCode); 84cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley static Status fromExceptionCode(int32_t exceptionCode, 85cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley const String8& message); 86c1e491d5a4923298b612de919537d4293574b443Christopher Wiley static Status fromServiceSpecificError(int32_t serviceSpecificErrorCode); 87c1e491d5a4923298b612de919537d4293574b443Christopher Wiley static Status fromServiceSpecificError(int32_t serviceSpecificErrorCode, 88c1e491d5a4923298b612de919537d4293574b443Christopher Wiley const String8& message); 8909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley static Status fromStatusT(status_t status); 9009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 9109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley Status() = default; 92cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley ~Status() = default; 9309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 9409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // Status objects are copyable and contain just simple data. 9509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley Status(const Status& status) = default; 9609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley Status(Status&& status) = default; 9709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley Status& operator=(const Status& status) = default; 9809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 9909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // Bear in mind that if the client or service is a Java endpoint, this 10009eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // is not the logic which will provide/interpret the data here. 10109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley status_t readFromParcel(const Parcel& parcel); 10209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley status_t writeToParcel(Parcel* parcel) const; 10309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 10409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // Set one of the pre-defined exception types defined above. 10509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley void setException(int32_t ex, const String8& message); 106c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // Set a service specific exception with error code. 107c1e491d5a4923298b612de919537d4293574b443Christopher Wiley void setServiceSpecificError(int32_t errorCode, const String8& message); 108cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // Setting a |status| != OK causes generated code to return |status| 109cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // from Binder transactions, rather than writing an exception into the 110c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // reply Parcel. This is the least preferable way of reporting errors. 11109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley void setFromStatusT(status_t status); 11209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 11309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // Get information about an exception. 11409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley int32_t exceptionCode() const { return mException; } 11509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley const String8& exceptionMessage() const { return mMessage; } 116cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley status_t transactionError() const { 117cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley return mException == EX_TRANSACTION_FAILED ? mErrorCode : OK; 118cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley } 119c1e491d5a4923298b612de919537d4293574b443Christopher Wiley int32_t serviceSpecificErrorCode() const { 120c1e491d5a4923298b612de919537d4293574b443Christopher Wiley return mException == EX_SERVICE_SPECIFIC ? mErrorCode : 0; 121c1e491d5a4923298b612de919537d4293574b443Christopher Wiley } 12209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 12309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley bool isOk() const { return mException == EX_NONE; } 12409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 12509eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley // For logging. 12609eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley String8 toString8() const; 12709eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 12809eb749704afd9e226e1347cb20c90be2016cd21Christopher Wileyprivate: 129c1e491d5a4923298b612de919537d4293574b443Christopher Wiley Status(int32_t exceptionCode, int32_t errorCode); 130c1e491d5a4923298b612de919537d4293574b443Christopher Wiley Status(int32_t exceptionCode, int32_t errorCode, const String8& message); 131cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley 132cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // If |mException| == EX_TRANSACTION_FAILED, generated code will return 133cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // |mErrorCode| as the result of the transaction rather than write an 134cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // exception to the reply parcel. 135cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // 136cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // Otherwise, we always write |mException| to the parcel. 137cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley // If |mException| != EX_NONE, we write |mMessage| as well. 138c1e491d5a4923298b612de919537d4293574b443Christopher Wiley // If |mException| == EX_SERVICE_SPECIFIC we write |mErrorCode| as well. 13909eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley int32_t mException = EX_NONE; 140cff7f175c1a4f790fdc64a56695c5b4b08b6bb6eChristopher Wiley int32_t mErrorCode = 0; 14109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley String8 mMessage; 14209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley}; // class Status 14309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 144bbab196fe58e5657d90f6f40a19fb93c2a91a8acEino-Ville Talvala// For gtest output logging 145bbab196fe58e5657d90f6f40a19fb93c2a91a8acEino-Ville Talvalatemplate<typename T> 146bbab196fe58e5657d90f6f40a19fb93c2a91a8acEino-Ville TalvalaT& operator<< (T& stream, const Status& s) { 147bbab196fe58e5657d90f6f40a19fb93c2a91a8acEino-Ville Talvala stream << s.toString8().string(); 148bbab196fe58e5657d90f6f40a19fb93c2a91a8acEino-Ville Talvala return stream; 149bbab196fe58e5657d90f6f40a19fb93c2a91a8acEino-Ville Talvala} 150bbab196fe58e5657d90f6f40a19fb93c2a91a8acEino-Ville Talvala 15109eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley} // namespace binder 15209eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley} // namespace android 15309eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley 15409eb749704afd9e226e1347cb20c90be2016cd21Christopher Wiley#endif // ANDROID_BINDER_STATUS_H 155