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 "StringType.h" 18 19 #include "HidlTypeAssertion.h" 20 21 #include <hidl-util/Formatter.h> 22 23 namespace android { 24 25 StringType::StringType(Scope* parent) : Type(parent, "string") {} 26 27 bool StringType::isString() const { 28 return true; 29 } 30 31 bool StringType::deepCanCheckEquality(std::unordered_set<const Type*>* /* visited */) const { 32 return true; 33 } 34 35 std::string StringType::typeName() const { 36 return "string"; 37 } 38 39 std::string StringType::getCppType(StorageMode mode, 40 bool specifyNamespaces) const { 41 const std::string base = 42 std::string(specifyNamespaces ? "::android::hardware::" : "") 43 + "hidl_string"; 44 45 switch (mode) { 46 case StorageMode_Stack: 47 return base; 48 49 case StorageMode_Argument: 50 return "const " + base + "&"; 51 52 case StorageMode_Result: 53 return "const " + base + "*"; 54 } 55 } 56 57 std::string StringType::getJavaType(bool /* forInitializer */) const { 58 return "String"; 59 } 60 61 std::string StringType::getJavaSuffix() const { 62 return "String"; 63 } 64 65 std::string StringType::getVtsType() const { 66 return "TYPE_STRING"; 67 } 68 69 void StringType::emitReaderWriter( 70 Formatter &out, 71 const std::string &name, 72 const std::string &parcelObj, 73 bool parcelObjIsPointer, 74 bool isReader, 75 ErrorMode mode) const { 76 const std::string parentName = "_hidl_" + name + "_parent"; 77 out << "size_t " << parentName << ";\n\n"; 78 79 const std::string parcelObjDeref = 80 parcelObj + (parcelObjIsPointer ? "->" : "."); 81 82 if (isReader) { 83 out << "_hidl_err = " 84 << parcelObjDeref 85 << "readBuffer(" 86 << "sizeof(*" 87 << name 88 << "), &" 89 << parentName 90 << ", " 91 << " reinterpret_cast<const void **>(" 92 << "&" << name 93 << "));\n\n"; 94 95 handleError(out, mode); 96 } else { 97 out << "_hidl_err = " 98 << parcelObjDeref 99 << "writeBuffer(&" 100 << name 101 << ", sizeof(" 102 << name 103 << "), &" 104 << parentName 105 << ");\n"; 106 107 handleError(out, mode); 108 } 109 110 emitReaderWriterEmbedded( 111 out, 112 0 /* depth */, 113 name, 114 name /* sanitizedName */, 115 isReader /* nameIsPointer */, 116 parcelObj, 117 parcelObjIsPointer, 118 isReader, 119 mode, 120 parentName, 121 "0 /* parentOffset */"); 122 } 123 124 void StringType::emitReaderWriterEmbedded( 125 Formatter &out, 126 size_t /* depth */, 127 const std::string &name, 128 const std::string & /*sanitizedName*/, 129 bool nameIsPointer, 130 const std::string &parcelObj, 131 bool parcelObjIsPointer, 132 bool isReader, 133 ErrorMode mode, 134 const std::string &parentName, 135 const std::string &offsetText) const { 136 emitReaderWriterEmbeddedForTypeName( 137 out, 138 name, 139 nameIsPointer, 140 parcelObj, 141 parcelObjIsPointer, 142 isReader, 143 mode, 144 parentName, 145 offsetText, 146 "::android::hardware::hidl_string", 147 "" /* childName */, 148 "::android::hardware"); 149 } 150 151 void StringType::emitJavaFieldInitializer( 152 Formatter &out, const std::string &fieldName) const { 153 emitJavaFieldDefaultInitialValue(out, "String " + fieldName); 154 } 155 156 void StringType::emitJavaFieldDefaultInitialValue( 157 Formatter &out, const std::string &declaredFieldName) const { 158 out << declaredFieldName << " = new String();\n"; 159 } 160 161 void StringType::emitJavaFieldReaderWriter( 162 Formatter &out, 163 size_t /* depth */, 164 const std::string &parcelName, 165 const std::string &blobName, 166 const std::string &fieldName, 167 const std::string &offset, 168 bool isReader) const { 169 if (isReader) { 170 out << fieldName 171 << " = " 172 << blobName 173 << ".getString(" 174 << offset 175 << ");\n"; 176 177 out << "\n" 178 << parcelName 179 << ".readEmbeddedBuffer(\n"; 180 181 out.indent(); 182 out.indent(); 183 184 // hidl_string's embedded buffer is never null(able), because it defaults to a 185 // buffer containing an empty string. 186 out << "(" << getJavaTypeCast(fieldName) << ").getBytes().length + 1,\n" 187 << blobName 188 << ".handle(),\n" 189 << offset 190 << " + 0 /* offsetof(hidl_string, mBuffer) */," 191 << "false /* nullable */);\n\n"; 192 193 out.unindent(); 194 out.unindent(); 195 196 return; 197 } 198 199 out << blobName 200 << ".putString(" 201 << offset 202 << ", " 203 << fieldName 204 << ");\n"; 205 } 206 207 bool StringType::needsEmbeddedReadWrite() const { 208 return true; 209 } 210 211 bool StringType::resultNeedsDeref() const { 212 return true; 213 } 214 215 void StringType::emitVtsTypeDeclarations(Formatter& out) const { 216 out << "type: " << getVtsType() << "\n"; 217 } 218 219 static HidlTypeAssertion assertion("hidl_string", 16 /* size */); 220 void StringType::getAlignmentAndSize(size_t *align, size_t *size) const { 221 *align = 8; // hidl_string 222 *size = assertion.size(); 223 } 224 225 } // namespace android 226 227