Support @nullable(heap) for recursive types

@nullable(heap=true) marks a parcelable field to be held in a heap
allocated wrapper like unique_ptr<T> in C++ and Box<T> in Rust.

This enables recursive parcelable types like following:

  parcelable Recursive {
    @nullable(heap=true) Recursive r;
  }

Note `r` is represented in Option<Box<Recursive>> in Rust because Box<T>
should hold a value always.

Bug: 188690695
Test: aidl_integration_test
Change-Id: Ic9b209da73c1395785c078aeecd34fda74e42e7d
diff --git a/aidl_to_ndk.cpp b/aidl_to_ndk.cpp
index b3ab6d6..f535d10 100644
--- a/aidl_to_ndk.cpp
+++ b/aidl_to_ndk.cpp
@@ -159,6 +159,7 @@
     }
     clazz += base::StringPrintf("<%s>", base::Join(type_params, ", ").c_str());
   }
+  const std::string nullable = typeSpec.IsHeapNullable() ? "std::unique_ptr" : "std::optional";
   return TypeInfo{
       .raw =
           TypeInfo::Aspect{
@@ -174,7 +175,7 @@
           .write_func = StandardWrite("::ndk::AParcel_writeVector"),
       }),
       .nullable = std::shared_ptr<TypeInfo::Aspect>(new TypeInfo::Aspect{
-          .cpp_name = "std::optional<" + clazz + ">",
+          .cpp_name = nullable + "<" + clazz + ">",
           .value_is_cheap = false,
           .read_func = StandardRead("::ndk::AParcel_readNullableParcelable"),
           .write_func = StandardWrite("::ndk::AParcel_writeNullableParcelable"),