1 /* 2 * Copyright (C) 2015, 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 "type_java.h" 18 19 #include <sys/types.h> 20 21 #include <android-base/strings.h> 22 23 #include "aidl_language.h" 24 #include "logging.h" 25 26 using std::string; 27 using android::base::Split; 28 using android::base::Join; 29 using android::base::Trim; 30 31 namespace android { 32 namespace aidl { 33 namespace java { 34 35 Expression* NULL_VALUE; 36 Expression* THIS_VALUE; 37 Expression* SUPER_VALUE; 38 Expression* TRUE_VALUE; 39 Expression* FALSE_VALUE; 40 41 // ================================================================ 42 43 Type::Type(const JavaTypeNamespace* types, const string& name, int kind, 44 bool canWriteToParcel, bool canBeOut) 45 : Type(types, "", name, kind, canWriteToParcel, canBeOut, "", -1) {} 46 47 Type::Type(const JavaTypeNamespace* types, const string& package, 48 const string& name, int kind, bool canWriteToParcel, 49 bool canBeOut, const string& declFile, int declLine) 50 : ValidatableType(kind, package, name, declFile, declLine), 51 m_types(types), 52 m_javaType((package.empty()) ? name : package + "." + name), 53 m_canWriteToParcel(canWriteToParcel), 54 m_canBeOut(canBeOut) { 55 } 56 57 string Type::CreatorName() const { return ""; } 58 59 string Type::InstantiableName() const { return JavaType(); } 60 61 void Type::WriteToParcel(StatementBlock* addTo, Variable* v, Variable* parcel, 62 int flags) const { 63 fprintf(stderr, "aidl:internal error %s:%d qualifiedName=%sn", __FILE__, 64 __LINE__, m_javaType.c_str()); 65 addTo->Add(new LiteralExpression("/* WriteToParcel error " + m_javaType + 66 " */")); 67 } 68 69 void Type::CreateFromParcel(StatementBlock* addTo, Variable* v, 70 Variable* parcel, Variable**) const { 71 fprintf(stderr, "aidl:internal error %s:%d qualifiedName=%s\n", __FILE__, 72 __LINE__, m_javaType.c_str()); 73 addTo->Add(new LiteralExpression("/* CreateFromParcel error " + 74 m_javaType + " */")); 75 } 76 77 void Type::ReadFromParcel(StatementBlock* addTo, Variable* v, Variable* parcel, 78 Variable**) const { 79 fprintf(stderr, "aidl:internal error %s:%d qualifiedName=%s\n", __FILE__, 80 __LINE__, m_javaType.c_str()); 81 addTo->Add(new LiteralExpression("/* ReadFromParcel error " + 82 m_javaType + " */")); 83 } 84 85 Expression* Type::BuildWriteToParcelFlags(int flags) const { 86 if (flags == 0) { 87 return new LiteralExpression("0"); 88 } 89 if ((flags & PARCELABLE_WRITE_RETURN_VALUE) != 0) { 90 return new FieldVariable(m_types->ParcelableInterfaceType(), 91 "PARCELABLE_WRITE_RETURN_VALUE"); 92 } 93 return new LiteralExpression("0"); 94 } 95 96 // ================================================================ 97 98 BasicType::BasicType(const JavaTypeNamespace* types, const string& name, 99 const string& marshallParcel, 100 const string& unmarshallParcel, 101 const string& writeArrayParcel, 102 const string& createArrayParcel, 103 const string& readArrayParcel) 104 : Type(types, name, ValidatableType::KIND_BUILT_IN, true, false), 105 m_marshallParcel(marshallParcel), 106 m_unmarshallParcel(unmarshallParcel) { 107 m_array_type.reset(new BasicArrayType(types, name, writeArrayParcel, 108 createArrayParcel, readArrayParcel)); 109 } 110 111 void BasicType::WriteToParcel(StatementBlock* addTo, Variable* v, 112 Variable* parcel, int flags) const { 113 addTo->Add(new MethodCall(parcel, m_marshallParcel, 1, v)); 114 } 115 116 void BasicType::CreateFromParcel(StatementBlock* addTo, Variable* v, 117 Variable* parcel, Variable**) const { 118 addTo->Add(new Assignment(v, new MethodCall(parcel, m_unmarshallParcel))); 119 } 120 121 BasicArrayType::BasicArrayType(const JavaTypeNamespace* types, 122 const string& name, 123 const string& writeArrayParcel, 124 const string& createArrayParcel, 125 const string& readArrayParcel) 126 : Type(types, name, ValidatableType::KIND_BUILT_IN, true, true), 127 m_writeArrayParcel(writeArrayParcel), 128 m_createArrayParcel(createArrayParcel), 129 m_readArrayParcel(readArrayParcel) {} 130 131 132 void BasicArrayType::WriteToParcel(StatementBlock* addTo, Variable* v, 133 Variable* parcel, int flags) const { 134 addTo->Add(new MethodCall(parcel, m_writeArrayParcel, 1, v)); 135 } 136 137 void BasicArrayType::CreateFromParcel(StatementBlock* addTo, Variable* v, 138 Variable* parcel, Variable**) const { 139 addTo->Add(new Assignment(v, new MethodCall(parcel, m_createArrayParcel))); 140 } 141 142 void BasicArrayType::ReadFromParcel(StatementBlock* addTo, Variable* v, 143 Variable* parcel, Variable**) const { 144 addTo->Add(new MethodCall(parcel, m_readArrayParcel, 1, v)); 145 } 146 147 // ================================================================ 148 149 FileDescriptorType::FileDescriptorType(const JavaTypeNamespace* types) 150 : Type(types, "java.io", "FileDescriptor", ValidatableType::KIND_BUILT_IN, 151 true, false) { 152 m_array_type.reset(new FileDescriptorArrayType(types)); 153 } 154 155 void FileDescriptorType::WriteToParcel(StatementBlock* addTo, Variable* v, 156 Variable* parcel, int flags) const { 157 addTo->Add(new MethodCall(parcel, "writeRawFileDescriptor", 1, v)); 158 } 159 160 void FileDescriptorType::CreateFromParcel(StatementBlock* addTo, Variable* v, 161 Variable* parcel, Variable**) const { 162 addTo->Add(new Assignment(v, new MethodCall(parcel, "readRawFileDescriptor"))); 163 } 164 165 FileDescriptorArrayType::FileDescriptorArrayType(const JavaTypeNamespace* types) 166 : Type(types, "java.io", "FileDescriptor", ValidatableType::KIND_BUILT_IN, 167 true, true) {} 168 169 void FileDescriptorArrayType::WriteToParcel(StatementBlock* addTo, Variable* v, 170 Variable* parcel, int flags) const { 171 addTo->Add(new MethodCall(parcel, "writeRawFileDescriptorArray", 1, v)); 172 } 173 174 void FileDescriptorArrayType::CreateFromParcel(StatementBlock* addTo, Variable* v, 175 Variable* parcel, Variable**) const { 176 addTo->Add(new Assignment(v, new MethodCall(parcel, "createRawFileDescriptorArray"))); 177 } 178 179 void FileDescriptorArrayType::ReadFromParcel(StatementBlock* addTo, Variable* v, 180 Variable* parcel, Variable**) const { 181 addTo->Add(new MethodCall(parcel, "readRawFileDescriptorArray", 1, v)); 182 } 183 184 // ================================================================ 185 186 BooleanType::BooleanType(const JavaTypeNamespace* types) 187 : Type(types, "boolean", ValidatableType::KIND_BUILT_IN, true, false) { 188 m_array_type.reset(new BooleanArrayType(types)); 189 } 190 191 void BooleanType::WriteToParcel(StatementBlock* addTo, Variable* v, 192 Variable* parcel, int flags) const { 193 addTo->Add(new MethodCall( 194 parcel, "writeInt", 1, 195 new Ternary(v, new LiteralExpression("1"), new LiteralExpression("0")))); 196 } 197 198 void BooleanType::CreateFromParcel(StatementBlock* addTo, Variable* v, 199 Variable* parcel, Variable**) const { 200 addTo->Add( 201 new Assignment(v, new Comparison(new LiteralExpression("0"), "!=", 202 new MethodCall(parcel, "readInt")))); 203 } 204 205 BooleanArrayType::BooleanArrayType(const JavaTypeNamespace* types) 206 : Type(types, "boolean", ValidatableType::KIND_BUILT_IN, true, true) {} 207 208 void BooleanArrayType::WriteToParcel(StatementBlock* addTo, Variable* v, 209 Variable* parcel, int flags) const { 210 addTo->Add(new MethodCall(parcel, "writeBooleanArray", 1, v)); 211 } 212 213 void BooleanArrayType::CreateFromParcel(StatementBlock* addTo, Variable* v, 214 Variable* parcel, Variable**) const { 215 addTo->Add(new Assignment(v, new MethodCall(parcel, "createBooleanArray"))); 216 } 217 218 void BooleanArrayType::ReadFromParcel(StatementBlock* addTo, Variable* v, 219 Variable* parcel, Variable**) const { 220 addTo->Add(new MethodCall(parcel, "readBooleanArray", 1, v)); 221 } 222 223 // ================================================================ 224 225 CharType::CharType(const JavaTypeNamespace* types) 226 : Type(types, "char", ValidatableType::KIND_BUILT_IN, true, false) { 227 m_array_type.reset(new CharArrayType(types)); 228 } 229 230 void CharType::WriteToParcel(StatementBlock* addTo, Variable* v, 231 Variable* parcel, int flags) const { 232 addTo->Add( 233 new MethodCall(parcel, "writeInt", 1, new Cast(m_types->IntType(), v))); 234 } 235 236 void CharType::CreateFromParcel(StatementBlock* addTo, Variable* v, 237 Variable* parcel, Variable**) const { 238 addTo->Add(new Assignment(v, new MethodCall(parcel, "readInt"), this)); 239 } 240 241 CharArrayType::CharArrayType(const JavaTypeNamespace* types) 242 : Type(types, "char", ValidatableType::KIND_BUILT_IN, true, true) {} 243 244 void CharArrayType::WriteToParcel(StatementBlock* addTo, Variable* v, 245 Variable* parcel, int flags) const { 246 addTo->Add(new MethodCall(parcel, "writeCharArray", 1, v)); 247 } 248 249 void CharArrayType::CreateFromParcel(StatementBlock* addTo, Variable* v, 250 Variable* parcel, Variable**) const { 251 addTo->Add(new Assignment(v, new MethodCall(parcel, "createCharArray"))); 252 } 253 254 void CharArrayType::ReadFromParcel(StatementBlock* addTo, Variable* v, 255 Variable* parcel, Variable**) const { 256 addTo->Add(new MethodCall(parcel, "readCharArray", 1, v)); 257 } 258 259 // ================================================================ 260 261 StringType::StringType(const JavaTypeNamespace* types, 262 const std::string& package, 263 const std::string& class_name) 264 : Type(types, package, class_name, 265 ValidatableType::KIND_BUILT_IN, true, false) { 266 m_array_type.reset(new StringArrayType(types)); 267 } 268 269 string StringType::CreatorName() const { 270 return "android.os.Parcel.STRING_CREATOR"; 271 } 272 273 void StringType::WriteToParcel(StatementBlock* addTo, Variable* v, 274 Variable* parcel, int flags) const { 275 addTo->Add(new MethodCall(parcel, "writeString", 1, v)); 276 } 277 278 void StringType::CreateFromParcel(StatementBlock* addTo, Variable* v, 279 Variable* parcel, Variable**) const { 280 addTo->Add(new Assignment(v, new MethodCall(parcel, "readString"))); 281 } 282 283 StringArrayType::StringArrayType(const JavaTypeNamespace* types) 284 : Type(types, "java.lang", "String", ValidatableType::KIND_BUILT_IN, 285 true, true) {} 286 287 string StringArrayType::CreatorName() const { 288 return "android.os.Parcel.STRING_CREATOR"; 289 } 290 291 void StringArrayType::WriteToParcel(StatementBlock* addTo, Variable* v, 292 Variable* parcel, int flags) const { 293 addTo->Add(new MethodCall(parcel, "writeStringArray", 1, v)); 294 } 295 296 void StringArrayType::CreateFromParcel(StatementBlock* addTo, Variable* v, 297 Variable* parcel, Variable**) const { 298 addTo->Add(new Assignment(v, new MethodCall(parcel, "createStringArray"))); 299 } 300 301 void StringArrayType::ReadFromParcel(StatementBlock* addTo, Variable* v, 302 Variable* parcel, Variable**) const { 303 addTo->Add(new MethodCall(parcel, "readStringArray", 1, v)); 304 } 305 306 // ================================================================ 307 308 CharSequenceType::CharSequenceType(const JavaTypeNamespace* types) 309 : Type(types, "java.lang", "CharSequence", ValidatableType::KIND_BUILT_IN, 310 true, false) {} 311 312 string CharSequenceType::CreatorName() const { 313 return "android.os.Parcel.STRING_CREATOR"; 314 } 315 316 void CharSequenceType::WriteToParcel(StatementBlock* addTo, Variable* v, 317 Variable* parcel, int flags) const { 318 // if (v != null) { 319 // parcel.writeInt(1); 320 // v.writeToParcel(parcel); 321 // } else { 322 // parcel.writeInt(0); 323 // } 324 IfStatement* elsepart = new IfStatement(); 325 elsepart->statements->Add( 326 new MethodCall(parcel, "writeInt", 1, new LiteralExpression("0"))); 327 IfStatement* ifpart = new IfStatement; 328 ifpart->expression = new Comparison(v, "!=", NULL_VALUE); 329 ifpart->elseif = elsepart; 330 ifpart->statements->Add( 331 new MethodCall(parcel, "writeInt", 1, new LiteralExpression("1"))); 332 ifpart->statements->Add(new MethodCall(m_types->TextUtilsType(), 333 "writeToParcel", 3, v, parcel, 334 BuildWriteToParcelFlags(flags))); 335 336 addTo->Add(ifpart); 337 } 338 339 void CharSequenceType::CreateFromParcel(StatementBlock* addTo, Variable* v, 340 Variable* parcel, Variable**) const { 341 // if (0 != parcel.readInt()) { 342 // v = TextUtils.createFromParcel(parcel) 343 // } else { 344 // v = null; 345 // } 346 IfStatement* elsepart = new IfStatement(); 347 elsepart->statements->Add(new Assignment(v, NULL_VALUE)); 348 349 IfStatement* ifpart = new IfStatement(); 350 ifpart->expression = new Comparison(new LiteralExpression("0"), "!=", 351 new MethodCall(parcel, "readInt")); 352 ifpart->elseif = elsepart; 353 ifpart->statements->Add(new Assignment( 354 v, new MethodCall(m_types->TextUtilsType(), 355 "CHAR_SEQUENCE_CREATOR.createFromParcel", 1, parcel))); 356 357 addTo->Add(ifpart); 358 } 359 360 // ================================================================ 361 362 RemoteExceptionType::RemoteExceptionType(const JavaTypeNamespace* types) 363 : Type(types, "android.os", "RemoteException", 364 ValidatableType::KIND_BUILT_IN, false, false) {} 365 366 void RemoteExceptionType::WriteToParcel(StatementBlock* addTo, Variable* v, 367 Variable* parcel, int flags) const { 368 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 369 } 370 371 void RemoteExceptionType::CreateFromParcel(StatementBlock* addTo, Variable* v, 372 Variable* parcel, Variable**) const { 373 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 374 } 375 376 // ================================================================ 377 378 RuntimeExceptionType::RuntimeExceptionType(const JavaTypeNamespace* types) 379 : Type(types, "java.lang", "RuntimeException", 380 ValidatableType::KIND_BUILT_IN, false, false) {} 381 382 void RuntimeExceptionType::WriteToParcel(StatementBlock* addTo, Variable* v, 383 Variable* parcel, int flags) const { 384 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 385 } 386 387 void RuntimeExceptionType::CreateFromParcel(StatementBlock* addTo, Variable* v, 388 Variable* parcel, 389 Variable**) const { 390 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 391 } 392 393 // ================================================================ 394 395 IBinderType::IBinderType(const JavaTypeNamespace* types) 396 : Type(types, "android.os", "IBinder", ValidatableType::KIND_BUILT_IN, 397 true, false) { 398 m_array_type.reset(new IBinderArrayType(types)); 399 } 400 401 void IBinderType::WriteToParcel(StatementBlock* addTo, Variable* v, 402 Variable* parcel, int flags) const { 403 addTo->Add(new MethodCall(parcel, "writeStrongBinder", 1, v)); 404 } 405 406 void IBinderType::CreateFromParcel(StatementBlock* addTo, Variable* v, 407 Variable* parcel, Variable**) const { 408 addTo->Add(new Assignment(v, new MethodCall(parcel, "readStrongBinder"))); 409 } 410 411 IBinderArrayType::IBinderArrayType(const JavaTypeNamespace* types) 412 : Type(types, "android.os", "IBinder", ValidatableType::KIND_BUILT_IN, 413 true, true) {} 414 415 void IBinderArrayType::WriteToParcel(StatementBlock* addTo, Variable* v, 416 Variable* parcel, int flags) const { 417 addTo->Add(new MethodCall(parcel, "writeBinderArray", 1, v)); 418 } 419 420 void IBinderArrayType::CreateFromParcel(StatementBlock* addTo, Variable* v, 421 Variable* parcel, Variable**) const { 422 addTo->Add(new Assignment(v, new MethodCall(parcel, "createBinderArray"))); 423 } 424 425 void IBinderArrayType::ReadFromParcel(StatementBlock* addTo, Variable* v, 426 Variable* parcel, Variable**) const { 427 addTo->Add(new MethodCall(parcel, "readBinderArray", 1, v)); 428 } 429 430 // ================================================================ 431 432 IInterfaceType::IInterfaceType(const JavaTypeNamespace* types) 433 : Type(types, "android.os", "IInterface", ValidatableType::KIND_BUILT_IN, 434 false, false) {} 435 436 void IInterfaceType::WriteToParcel(StatementBlock* addTo, Variable* v, 437 Variable* parcel, int flags) const { 438 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 439 } 440 441 void IInterfaceType::CreateFromParcel(StatementBlock* addTo, Variable* v, 442 Variable* parcel, Variable**) const { 443 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 444 } 445 446 // ================================================================ 447 448 BinderType::BinderType(const JavaTypeNamespace* types) 449 : Type(types, "android.os", "Binder", ValidatableType::KIND_BUILT_IN, 450 false, false) {} 451 452 void BinderType::WriteToParcel(StatementBlock* addTo, Variable* v, 453 Variable* parcel, int flags) const { 454 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 455 } 456 457 void BinderType::CreateFromParcel(StatementBlock* addTo, Variable* v, 458 Variable* parcel, Variable**) const { 459 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 460 } 461 462 // ================================================================ 463 464 BinderProxyType::BinderProxyType(const JavaTypeNamespace* types) 465 : Type(types, "android.os", "BinderProxy", ValidatableType::KIND_BUILT_IN, 466 false, false) {} 467 468 void BinderProxyType::WriteToParcel(StatementBlock* addTo, Variable* v, 469 Variable* parcel, int flags) const { 470 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 471 } 472 473 void BinderProxyType::CreateFromParcel(StatementBlock* addTo, Variable* v, 474 Variable* parcel, Variable**) const { 475 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 476 } 477 478 // ================================================================ 479 480 ParcelType::ParcelType(const JavaTypeNamespace* types) 481 : Type(types, "android.os", "Parcel", ValidatableType::KIND_BUILT_IN, 482 false, false) {} 483 484 void ParcelType::WriteToParcel(StatementBlock* addTo, Variable* v, 485 Variable* parcel, int flags) const { 486 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 487 } 488 489 void ParcelType::CreateFromParcel(StatementBlock* addTo, Variable* v, 490 Variable* parcel, Variable**) const { 491 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 492 } 493 494 // ================================================================ 495 496 ParcelableInterfaceType::ParcelableInterfaceType(const JavaTypeNamespace* types) 497 : Type(types, "android.os", "Parcelable", ValidatableType::KIND_BUILT_IN, 498 false, false) {} 499 500 void ParcelableInterfaceType::WriteToParcel(StatementBlock* addTo, Variable* v, 501 Variable* parcel, int flags) const { 502 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 503 } 504 505 void ParcelableInterfaceType::CreateFromParcel(StatementBlock* addTo, 506 Variable* v, Variable* parcel, 507 Variable**) const { 508 fprintf(stderr, "aidl:internal error %s:%d\n", __FILE__, __LINE__); 509 } 510 511 // ================================================================ 512 513 MapType::MapType(const JavaTypeNamespace* types) 514 : Type(types, "java.util", "Map", ValidatableType::KIND_BUILT_IN, 515 true, true) {} 516 517 void MapType::WriteToParcel(StatementBlock* addTo, Variable* v, 518 Variable* parcel, int flags) const { 519 addTo->Add(new MethodCall(parcel, "writeMap", 1, v)); 520 } 521 522 static void EnsureClassLoader(StatementBlock* addTo, Variable** cl, 523 const JavaTypeNamespace* types) { 524 // We don't want to look up the class loader once for every 525 // collection argument, so ensure we do it at most once per method. 526 if (*cl == NULL) { 527 *cl = new Variable(types->ClassLoaderType(), "cl"); 528 addTo->Add(new VariableDeclaration( 529 *cl, new LiteralExpression("this.getClass().getClassLoader()"), 530 types->ClassLoaderType())); 531 } 532 } 533 534 void MapType::CreateFromParcel(StatementBlock* addTo, Variable* v, 535 Variable* parcel, Variable** cl) const { 536 EnsureClassLoader(addTo, cl, m_types); 537 addTo->Add(new Assignment(v, new MethodCall(parcel, "readHashMap", 1, *cl))); 538 } 539 540 void MapType::ReadFromParcel(StatementBlock* addTo, Variable* v, 541 Variable* parcel, Variable** cl) const { 542 EnsureClassLoader(addTo, cl, m_types); 543 addTo->Add(new MethodCall(parcel, "readMap", 2, v, *cl)); 544 } 545 546 // ================================================================ 547 548 ListType::ListType(const JavaTypeNamespace* types) 549 : Type(types, "java.util", "List", ValidatableType::KIND_BUILT_IN, 550 true, true) {} 551 552 string ListType::InstantiableName() const { return "java.util.ArrayList"; } 553 554 void ListType::WriteToParcel(StatementBlock* addTo, Variable* v, 555 Variable* parcel, int flags) const { 556 addTo->Add(new MethodCall(parcel, "writeList", 1, v)); 557 } 558 559 void ListType::CreateFromParcel(StatementBlock* addTo, Variable* v, 560 Variable* parcel, Variable** cl) const { 561 EnsureClassLoader(addTo, cl, m_types); 562 addTo->Add( 563 new Assignment(v, new MethodCall(parcel, "readArrayList", 1, *cl))); 564 } 565 566 void ListType::ReadFromParcel(StatementBlock* addTo, Variable* v, 567 Variable* parcel, Variable** cl) const { 568 EnsureClassLoader(addTo, cl, m_types); 569 addTo->Add(new MethodCall(parcel, "readList", 2, v, *cl)); 570 } 571 572 // ================================================================ 573 574 UserDataType::UserDataType(const JavaTypeNamespace* types, 575 const string& package, const string& name, 576 bool builtIn, bool canWriteToParcel, 577 const string& declFile, int declLine) 578 : Type(types, package, name, 579 builtIn ? ValidatableType::KIND_BUILT_IN 580 : ValidatableType::KIND_PARCELABLE, 581 canWriteToParcel, true, declFile, declLine) { 582 m_array_type.reset(new UserDataArrayType(types, package, name, builtIn, 583 canWriteToParcel, declFile, 584 declLine)); 585 } 586 587 string UserDataType::CreatorName() const { 588 return JavaType() + ".CREATOR"; 589 } 590 591 void UserDataType::WriteToParcel(StatementBlock* addTo, Variable* v, 592 Variable* parcel, int flags) const { 593 // if (v != null) { 594 // parcel.writeInt(1); 595 // v.writeToParcel(parcel); 596 // } else { 597 // parcel.writeInt(0); 598 // } 599 IfStatement* elsepart = new IfStatement(); 600 elsepart->statements->Add( 601 new MethodCall(parcel, "writeInt", 1, new LiteralExpression("0"))); 602 IfStatement* ifpart = new IfStatement; 603 ifpart->expression = new Comparison(v, "!=", NULL_VALUE); 604 ifpart->elseif = elsepart; 605 ifpart->statements->Add( 606 new MethodCall(parcel, "writeInt", 1, new LiteralExpression("1"))); 607 ifpart->statements->Add(new MethodCall(v, "writeToParcel", 2, parcel, 608 BuildWriteToParcelFlags(flags))); 609 610 addTo->Add(ifpart); 611 } 612 613 void UserDataType::CreateFromParcel(StatementBlock* addTo, Variable* v, 614 Variable* parcel, Variable**) const { 615 // if (0 != parcel.readInt()) { 616 // v = CLASS.CREATOR.createFromParcel(parcel) 617 // } else { 618 // v = null; 619 // } 620 IfStatement* elsepart = new IfStatement(); 621 elsepart->statements->Add(new Assignment(v, NULL_VALUE)); 622 623 IfStatement* ifpart = new IfStatement(); 624 ifpart->expression = new Comparison(new LiteralExpression("0"), "!=", 625 new MethodCall(parcel, "readInt")); 626 ifpart->elseif = elsepart; 627 ifpart->statements->Add(new Assignment( 628 v, new MethodCall(v->type, "CREATOR.createFromParcel", 1, parcel))); 629 630 addTo->Add(ifpart); 631 } 632 633 void UserDataType::ReadFromParcel(StatementBlock* addTo, Variable* v, 634 Variable* parcel, Variable**) const { 635 // TODO: really, we don't need to have this extra check, but we 636 // don't have two separate marshalling code paths 637 // if (0 != parcel.readInt()) { 638 // v.readFromParcel(parcel) 639 // } 640 IfStatement* ifpart = new IfStatement(); 641 ifpart->expression = new Comparison(new LiteralExpression("0"), "!=", 642 new MethodCall(parcel, "readInt")); 643 ifpart->statements->Add(new MethodCall(v, "readFromParcel", 1, parcel)); 644 addTo->Add(ifpart); 645 } 646 647 UserDataArrayType::UserDataArrayType(const JavaTypeNamespace* types, 648 const string& package, const string& name, 649 bool builtIn, bool canWriteToParcel, 650 const string& declFile, int declLine) 651 : Type(types, package, name, 652 builtIn ? ValidatableType::KIND_BUILT_IN 653 : ValidatableType::KIND_PARCELABLE, 654 canWriteToParcel, true, declFile, declLine) {} 655 656 string UserDataArrayType::CreatorName() const { 657 return JavaType() + ".CREATOR"; 658 } 659 660 void UserDataArrayType::WriteToParcel(StatementBlock* addTo, Variable* v, 661 Variable* parcel, int flags) const { 662 addTo->Add(new MethodCall(parcel, "writeTypedArray", 2, v, 663 BuildWriteToParcelFlags(flags))); 664 } 665 666 void UserDataArrayType::CreateFromParcel(StatementBlock* addTo, Variable* v, 667 Variable* parcel, Variable**) const { 668 string creator = v->type->JavaType() + ".CREATOR"; 669 addTo->Add(new Assignment(v, new MethodCall(parcel, "createTypedArray", 1, 670 new LiteralExpression(creator)))); 671 } 672 673 void UserDataArrayType::ReadFromParcel(StatementBlock* addTo, Variable* v, 674 Variable* parcel, Variable**) const { 675 string creator = v->type->JavaType() + ".CREATOR"; 676 addTo->Add(new MethodCall(parcel, "readTypedArray", 2, v, 677 new LiteralExpression(creator))); 678 } 679 680 // ================================================================ 681 682 InterfaceType::InterfaceType(const JavaTypeNamespace* types, 683 const string& package, const string& name, 684 bool builtIn, bool oneway, const string& declFile, 685 int declLine, const Type* stub, const Type* proxy) 686 : Type(types, package, name, builtIn ? ValidatableType::KIND_BUILT_IN 687 : ValidatableType::KIND_INTERFACE, 688 true, false, declFile, declLine), 689 m_oneway(oneway), 690 stub_(stub), 691 proxy_(proxy) {} 692 693 bool InterfaceType::OneWay() const { return m_oneway; } 694 695 void InterfaceType::WriteToParcel(StatementBlock* addTo, Variable* v, 696 Variable* parcel, int flags) const { 697 // parcel.writeStrongBinder(v != null ? v.asBinder() : null); 698 addTo->Add( 699 new MethodCall(parcel, "writeStrongBinder", 1, 700 new Ternary(new Comparison(v, "!=", NULL_VALUE), 701 new MethodCall(v, "asBinder"), NULL_VALUE))); 702 } 703 704 void InterfaceType::CreateFromParcel(StatementBlock* addTo, Variable* v, 705 Variable* parcel, Variable**) const { 706 // v = Interface.asInterface(parcel.readStrongBinder()); 707 addTo->Add(new Assignment( 708 v, new MethodCall(stub_, "asInterface", 1, 709 new MethodCall(parcel, "readStrongBinder")))); 710 } 711 712 // ================================================================ 713 714 GenericListType::GenericListType(const JavaTypeNamespace* types, 715 const Type* contained_type) 716 : Type(types, "java.util", "List<" + contained_type->CanonicalName() + ">", 717 ValidatableType::KIND_BUILT_IN, true, true), 718 m_contained_type(contained_type), 719 m_creator(contained_type->CreatorName()) {} 720 721 string GenericListType::CreatorName() const { 722 return "android.os.Parcel.arrayListCreator"; 723 } 724 725 string GenericListType::InstantiableName() const { 726 return "java.util.ArrayList<" + m_contained_type->JavaType() + ">"; 727 } 728 729 void GenericListType::WriteToParcel(StatementBlock* addTo, Variable* v, 730 Variable* parcel, int flags) const { 731 if (m_creator == m_types->StringType()->CreatorName()) { 732 addTo->Add(new MethodCall(parcel, "writeStringList", 1, v)); 733 } else if (m_creator == m_types->IBinderType()->CreatorName()) { 734 addTo->Add(new MethodCall(parcel, "writeBinderList", 1, v)); 735 } else { 736 // parcel.writeTypedListXX(arg); 737 addTo->Add(new MethodCall(parcel, "writeTypedList", 1, v)); 738 } 739 } 740 741 void GenericListType::CreateFromParcel(StatementBlock* addTo, Variable* v, 742 Variable* parcel, Variable**) const { 743 if (m_creator == m_types->StringType()->CreatorName()) { 744 addTo->Add( 745 new Assignment(v, new MethodCall(parcel, "createStringArrayList", 0))); 746 } else if (m_creator == m_types->IBinderType()->CreatorName()) { 747 addTo->Add( 748 new Assignment(v, new MethodCall(parcel, "createBinderArrayList", 0))); 749 } else { 750 // v = _data.readTypedArrayList(XXX.creator); 751 addTo->Add( 752 new Assignment(v, new MethodCall(parcel, "createTypedArrayList", 1, 753 new LiteralExpression(m_creator)))); 754 } 755 } 756 757 void GenericListType::ReadFromParcel(StatementBlock* addTo, Variable* v, 758 Variable* parcel, Variable**) const { 759 if (m_creator == m_types->StringType()->CreatorName()) { 760 addTo->Add(new MethodCall(parcel, "readStringList", 1, v)); 761 } else if (m_creator == m_types->IBinderType()->CreatorName()) { 762 addTo->Add(new MethodCall(parcel, "readBinderList", 1, v)); 763 } else { 764 // v = _data.readTypedList(v, XXX.creator); 765 addTo->Add(new MethodCall(parcel, "readTypedList", 2, v, 766 new LiteralExpression(m_creator))); 767 } 768 } 769 770 // ================================================================ 771 772 ClassLoaderType::ClassLoaderType(const JavaTypeNamespace* types) 773 : Type(types, "java.lang", "ClassLoader", ValidatableType::KIND_BUILT_IN, 774 false, false) {} 775 776 // ================================================================ 777 778 void JavaTypeNamespace::Init() { 779 Add(new BasicType(this, "void", "XXX", "XXX", "XXX", "XXX", "XXX")); 780 781 m_bool_type = new BooleanType(this); 782 Add(m_bool_type); 783 784 Add(new BasicType(this, "byte", "writeByte", "readByte", "writeByteArray", 785 "createByteArray", "readByteArray")); 786 787 Add(new CharType(this)); 788 789 m_int_type = new BasicType(this, "int", "writeInt", "readInt", 790 "writeIntArray", "createIntArray", "readIntArray"); 791 Add(m_int_type); 792 793 Add(new BasicType(this, "long", "writeLong", "readLong", "writeLongArray", 794 "createLongArray", "readLongArray")); 795 796 Add(new BasicType(this, "float", "writeFloat", "readFloat", "writeFloatArray", 797 "createFloatArray", "readFloatArray")); 798 799 Add(new BasicType(this, "double", "writeDouble", "readDouble", 800 "writeDoubleArray", "createDoubleArray", 801 "readDoubleArray")); 802 803 m_string_type = new class StringType(this, "java.lang", "String"); 804 Add(m_string_type); 805 Add(new class StringType(this, ::android::aidl::kAidlReservedTypePackage, 806 ::android::aidl::kUtf8InCppStringClass)); 807 808 Add(new Type(this, "java.lang", "Object", ValidatableType::KIND_BUILT_IN, 809 false, false)); 810 811 Add(new FileDescriptorType(this)); 812 813 Add(new CharSequenceType(this)); 814 815 Add(new MapType(this)); 816 817 Add(new ListType(this)); 818 819 m_text_utils_type = 820 new Type(this, "android.text", "TextUtils", 821 ValidatableType::KIND_BUILT_IN, false, false); 822 Add(m_text_utils_type); 823 824 m_remote_exception_type = new class RemoteExceptionType(this); 825 Add(m_remote_exception_type); 826 827 m_runtime_exception_type = new class RuntimeExceptionType(this); 828 Add(m_runtime_exception_type); 829 830 m_ibinder_type = new class IBinderType(this); 831 Add(m_ibinder_type); 832 833 m_iinterface_type = new class IInterfaceType(this); 834 Add(m_iinterface_type); 835 836 m_binder_native_type = new class BinderType(this); 837 Add(m_binder_native_type); 838 839 m_binder_proxy_type = new class BinderProxyType(this); 840 Add(m_binder_proxy_type); 841 842 m_parcel_type = new class ParcelType(this); 843 Add(m_parcel_type); 844 845 m_parcelable_interface_type = new class ParcelableInterfaceType(this); 846 Add(m_parcelable_interface_type); 847 848 m_context_type = new class Type(this, "android.content", "Context", 849 ValidatableType::KIND_BUILT_IN, false, false); 850 Add(m_context_type); 851 852 m_classloader_type = new class ClassLoaderType(this); 853 Add(m_classloader_type); 854 855 NULL_VALUE = new LiteralExpression("null"); 856 THIS_VALUE = new LiteralExpression("this"); 857 SUPER_VALUE = new LiteralExpression("super"); 858 TRUE_VALUE = new LiteralExpression("true"); 859 FALSE_VALUE = new LiteralExpression("false"); 860 } 861 862 bool JavaTypeNamespace::AddParcelableType(const AidlParcelable& p, 863 const std::string& filename) { 864 Type* type = 865 new UserDataType(this, p.GetPackage(), p.GetName(), false, 866 true, filename, p.GetLine()); 867 return Add(type); 868 } 869 870 bool JavaTypeNamespace::AddBinderType(const AidlInterface& b, 871 const std::string& filename) { 872 // for interfaces, add the stub, proxy, and interface types. 873 Type* stub = new Type(this, b.GetPackage(), 874 b.GetName() + ".Stub", ValidatableType::KIND_GENERATED, 875 false, false, filename, b.GetLine()); 876 Type* proxy = new Type(this, b.GetPackage(), 877 b.GetName() + ".Stub.Proxy", 878 ValidatableType::KIND_GENERATED, 879 false, false, filename, b.GetLine()); 880 Type* type = 881 new InterfaceType(this, b.GetPackage(), b.GetName(), false, 882 b.IsOneway(), filename, b.GetLine(), stub, proxy); 883 884 bool success = true; 885 success &= Add(type); 886 success &= Add(stub); 887 success &= Add(proxy); 888 return success; 889 } 890 891 bool JavaTypeNamespace::AddListType(const std::string& contained_type_name) { 892 const Type* contained_type = FindTypeByCanonicalName(contained_type_name); 893 if (!contained_type) { 894 return false; 895 } 896 Add(new GenericListType(this, contained_type)); 897 return true; 898 } 899 900 bool JavaTypeNamespace::AddMapType(const string& key_type_name, 901 const string& value_type_name) { 902 LOG(ERROR) << "Don't know how to create a Map<K,V> container."; 903 return false; 904 } 905 906 } // namespace java 907 } // namespace aidl 908 } // namespace android 909