Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 32fcd900 authored by Steven Moreland's avatar Steven Moreland Committed by android-build-merger
Browse files

Merge "libbinder_ndk: nullable primitive arrays" am: 01f7eeab am: 164022cd

am: 260b5855

Change-Id: I70a0aae10a91f84f0d6e0db9d1dc6e6d82f2ac0d
parents c9a0ab69 260b5855
Loading
Loading
Loading
Loading
+77 −53
Original line number Diff line number Diff line
@@ -132,109 +132,127 @@ typedef const char* (*AParcel_stringArrayElementGetter)(const void* arrayData, s
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readInt32Array
 *
 * \param arrayData some external representation of an array of int32_t.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of int32_t of size 'length' (if length is >= 0, if length is 0, this
 * may be nullptr).
 *
 * \return a buffer of int32_t of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef int32_t* (*AParcel_int32ArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_int32ArrayAllocator)(void* arrayData, int32_t length, int32_t** outBuffer);

/**
 * This is called to get the underlying data from an arrayData object.
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readUint32Array
 *
 * \param arrayData some external representation of an array of uint32_t.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of uint32_t of size 'length' (if length is >= 0, if length is 0, this
 * may be nullptr).
 *
 * \return a buffer of uint32_t of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef uint32_t* (*AParcel_uint32ArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_uint32ArrayAllocator)(void* arrayData, int32_t length, uint32_t** outBuffer);

/**
 * This is called to get the underlying data from an arrayData object.
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readInt64Array
 *
 * \param arrayData some external representation of an array of int64_t.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of int64_t of size 'length' (if length is >= 0, if length is 0, this
 * may be nullptr).
 *
 * \return a buffer of int64_t of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef int64_t* (*AParcel_int64ArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_int64ArrayAllocator)(void* arrayData, int32_t length, int64_t** outBuffer);

/**
 * This is called to get the underlying data from an arrayData object.
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readUint64Array
 *
 * \param arrayData some external representation of an array of uint64_t.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of uint64_t of size 'length' (if length is >= 0, if length is 0, this
 * may be nullptr).
 *
 * \return a buffer of uint64_t of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef uint64_t* (*AParcel_uint64ArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_uint64ArrayAllocator)(void* arrayData, int32_t length, uint64_t** outBuffer);

/**
 * This is called to get the underlying data from an arrayData object.
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readFloatArray
 *
 * \param arrayData some external representation of an array of float.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of float of size 'length' (if length is >= 0, if length is 0, this may
 * be nullptr).
 *
 * \return a buffer of float of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef float* (*AParcel_floatArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_floatArrayAllocator)(void* arrayData, int32_t length, float** outBuffer);

/**
 * This is called to get the underlying data from an arrayData object.
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readDoubleArray
 *
 * \param arrayData some external representation of an array of double.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of double of size 'length' (if length is >= 0, if length is 0, this may
 * be nullptr).
 *
 * \return a buffer of double of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef double* (*AParcel_doubleArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_doubleArrayAllocator)(void* arrayData, int32_t length, double** outBuffer);

/**
 * This allocates an array of size 'length' inside of arrayData and returns whether or not there was
 * a success.
 * a success. If length is -1, then this should allocate some representation of a null array.
 *
 * See also AParcel_readBoolArray
 *
 * \param arrayData some external representation of an array of bool.
 * \param length the length to allocate arrayData to.
 * \param length the length to allocate arrayData to (or -1 if this represents a null array).
 *
 * \return whether the allocation succeeded.
 */
typedef bool (*AParcel_boolArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_boolArrayAllocator)(void* arrayData, int32_t length);

/**
 * This is called to get the underlying data from an arrayData object at index.
@@ -264,32 +282,38 @@ typedef void (*AParcel_boolArraySetter)(void* arrayData, size_t index, bool valu
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readCharArray
 *
 * \param arrayData some external representation of an array of char16_t.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of char16_t of size 'length' (if length is >= 0, if length is 0, this
 * may be nullptr).
 *
 * \return a buffer of char16_t of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef char16_t* (*AParcel_charArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_charArrayAllocator)(void* arrayData, int32_t length, char16_t** outBuffer);

/**
 * This is called to get the underlying data from an arrayData object.
 *
 * The implementation of this function should allocate a contiguous array of size 'length' and
 * return that underlying buffer to be filled out. If there is an error or length is 0, null may be
 * returned.
 * returned. If length is -1, this should allocate some representation of a null array.
 *
 * See also AParcel_readByteArray
 *
 * \param arrayData some external representation of an array of int8_t.
 * \param length the length to allocate arrayData to.
 * \param outBuffer a buffer of int8_t of size 'length' (if length is >= 0, if length is 0, this may
 * be nullptr).
 *
 * \return a buffer of int8_t of size 'length'.
 * \return whether or not the allocation was successful (or whether a null array is represented when
 * length is -1).
 */
typedef int8_t* (*AParcel_byteArrayAllocator)(void* arrayData, size_t length);
typedef bool (*AParcel_byteArrayAllocator)(void* arrayData, int32_t length, int8_t** outBuffer);

// @END-PRIMITIVE-VECTOR-GETTERS

@@ -632,72 +656,72 @@ binder_status_t AParcel_readByte(const AParcel* parcel, int8_t* value) __INTRODU
 * Writes an array of int32_t to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeInt32Array(AParcel* parcel, const int32_t* arrayData, size_t length)
binder_status_t AParcel_writeInt32Array(AParcel* parcel, const int32_t* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
 * Writes an array of uint32_t to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeUint32Array(AParcel* parcel, const uint32_t* arrayData, size_t length)
binder_status_t AParcel_writeUint32Array(AParcel* parcel, const uint32_t* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
 * Writes an array of int64_t to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeInt64Array(AParcel* parcel, const int64_t* arrayData, size_t length)
binder_status_t AParcel_writeInt64Array(AParcel* parcel, const int64_t* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
 * Writes an array of uint64_t to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeUint64Array(AParcel* parcel, const uint64_t* arrayData, size_t length)
binder_status_t AParcel_writeUint64Array(AParcel* parcel, const uint64_t* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
 * Writes an array of float to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeFloatArray(AParcel* parcel, const float* arrayData, size_t length)
binder_status_t AParcel_writeFloatArray(AParcel* parcel, const float* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
 * Writes an array of double to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeDoubleArray(AParcel* parcel, const double* arrayData, size_t length)
binder_status_t AParcel_writeDoubleArray(AParcel* parcel, const double* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
@@ -708,36 +732,36 @@ binder_status_t AParcel_writeDoubleArray(AParcel* parcel, const double* arrayDat
 *
 * \param parcel the parcel to write to.
 * \param arrayData some external representation of an array.
 * \param length the length of arrayData.
 * \param length the length of arrayData (or -1 if this represents a null array).
 * \param getter the callback to retrieve data at specific locations in the array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeBoolArray(AParcel* parcel, const void* arrayData, size_t length,
binder_status_t AParcel_writeBoolArray(AParcel* parcel, const void* arrayData, int32_t length,
                                       AParcel_boolArrayGetter getter) __INTRODUCED_IN(29);

/**
 * Writes an array of char16_t to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeCharArray(AParcel* parcel, const char16_t* arrayData, size_t length)
binder_status_t AParcel_writeCharArray(AParcel* parcel, const char16_t* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
 * Writes an array of int8_t to the next location in a non-null parcel.
 *
 * \param parcel the parcel to write to.
 * \param arrayData an array of size 'length'.
 * \param length the length of arrayData.
 * \param arrayData an array of size 'length' (or null if length is -1, may be null if length is 0).
 * \param length the length of arrayData or -1 if this represents a null array.
 *
 * \return STATUS_OK on successful write.
 */
binder_status_t AParcel_writeByteArray(AParcel* parcel, const int8_t* arrayData, size_t length)
binder_status_t AParcel_writeByteArray(AParcel* parcel, const int8_t* arrayData, int32_t length)
        __INTRODUCED_IN(29);

/**
+198 −16

File changed.

Preview size limit exceeded, changes collapsed.

+63 −48
Original line number Diff line number Diff line
@@ -36,28 +36,46 @@ using ::android::base::unique_fd;
using ::android::os::ParcelFileDescriptor;

template <typename T>
using ContiguousArrayAllocator = T* (*)(void* arrayData, size_t length);
using ContiguousArrayAllocator = bool (*)(void* arrayData, int32_t length, T** outBuffer);

template <typename T>
using ArrayAllocator = bool (*)(void* arrayData, size_t length);
using ArrayAllocator = bool (*)(void* arrayData, int32_t length);
template <typename T>
using ArrayGetter = T (*)(const void* arrayData, size_t index);
template <typename T>
using ArraySetter = void (*)(void* arrayData, size_t index, T value);

template <typename T>
binder_status_t WriteArray(AParcel* parcel, const T* array, size_t length) {
    if (length > std::numeric_limits<int32_t>::max()) return STATUS_BAD_VALUE;
binder_status_t WriteAndValidateArraySize(AParcel* parcel, bool isNullArray, int32_t length) {
    // only -1 can be used to represent a null array
    if (length < -1) return STATUS_BAD_VALUE;

    if (!isNullArray && length < 0) {
        LOG(ERROR) << __func__ << ": null array must be used with length == -1.";
        return STATUS_BAD_VALUE;
    }
    if (isNullArray && length > 0) {
        LOG(ERROR) << __func__ << ": null buffer cannot be for size " << length << " array.";
        return STATUS_BAD_VALUE;
    }

    Parcel* rawParcel = parcel->get();

    status_t status = rawParcel->writeInt32(static_cast<int32_t>(length));
    if (status != STATUS_OK) return PruneStatusT(status);

    return STATUS_OK;
}

template <typename T>
binder_status_t WriteArray(AParcel* parcel, const T* array, int32_t length) {
    binder_status_t status = WriteAndValidateArraySize(parcel, array == nullptr, length);
    if (status != STATUS_OK) return status;
    if (length <= 0) return STATUS_OK;

    int32_t size = 0;
    if (__builtin_smul_overflow(sizeof(T), length, &size)) return STATUS_NO_MEMORY;

    void* const data = rawParcel->writeInplace(size);
    void* const data = parcel->get()->writeInplace(size);
    if (data == nullptr) return STATUS_NO_MEMORY;

    memcpy(data, array, size);
@@ -67,17 +85,16 @@ binder_status_t WriteArray(AParcel* parcel, const T* array, size_t length) {

// Each element in a char16_t array is converted to an int32_t (not packed).
template <>
binder_status_t WriteArray<char16_t>(AParcel* parcel, const char16_t* array, size_t length) {
    if (length > std::numeric_limits<int32_t>::max()) return STATUS_BAD_VALUE;

    Parcel* rawParcel = parcel->get();

    status_t status = rawParcel->writeInt32(static_cast<int32_t>(length));
    if (status != STATUS_OK) return PruneStatusT(status);
binder_status_t WriteArray<char16_t>(AParcel* parcel, const char16_t* array, int32_t length) {
    binder_status_t status = WriteAndValidateArraySize(parcel, array == nullptr, length);
    if (status != STATUS_OK) return status;
    if (length <= 0) return STATUS_OK;

    int32_t size = 0;
    if (__builtin_smul_overflow(sizeof(char16_t), length, &size)) return STATUS_NO_MEMORY;

    Parcel* rawParcel = parcel->get();

    for (int32_t i = 0; i < length; i++) {
        status = rawParcel->writeChar(array[i]);

@@ -96,10 +113,12 @@ binder_status_t ReadArray(const AParcel* parcel, void* arrayData,
    status_t status = rawParcel->readInt32(&length);

    if (status != STATUS_OK) return PruneStatusT(status);
    if (length < 0) return STATUS_UNEXPECTED_NULL;
    if (length < -1) return STATUS_BAD_VALUE;

    T* array = allocator(arrayData, length);
    if (length == 0) return STATUS_OK;
    T* array;
    if (!allocator(arrayData, length, &array)) return STATUS_NO_MEMORY;

    if (length <= 0) return STATUS_OK;
    if (array == nullptr) return STATUS_NO_MEMORY;

    int32_t size = 0;
@@ -123,10 +142,12 @@ binder_status_t ReadArray<char16_t>(const AParcel* parcel, void* arrayData,
    status_t status = rawParcel->readInt32(&length);

    if (status != STATUS_OK) return PruneStatusT(status);
    if (length < 0) return STATUS_UNEXPECTED_NULL;
    if (length < -1) return STATUS_BAD_VALUE;

    char16_t* array;
    if (!allocator(arrayData, length, &array)) return STATUS_NO_MEMORY;

    char16_t* array = allocator(arrayData, length);
    if (length == 0) return STATUS_OK;
    if (length <= 0) return STATUS_OK;
    if (array == nullptr) return STATUS_NO_MEMORY;

    int32_t size = 0;
@@ -142,15 +163,16 @@ binder_status_t ReadArray<char16_t>(const AParcel* parcel, void* arrayData,
}

template <typename T>
binder_status_t WriteArray(AParcel* parcel, const void* arrayData, size_t length,
binder_status_t WriteArray(AParcel* parcel, const void* arrayData, int32_t length,
                           ArrayGetter<T> getter, status_t (Parcel::*write)(T)) {
    if (length > std::numeric_limits<int32_t>::max()) return STATUS_BAD_VALUE;
    // we have no clue if arrayData represents a null object or not, we can only infer from length
    bool arrayIsNull = length < 0;
    binder_status_t status = WriteAndValidateArraySize(parcel, arrayIsNull, length);
    if (status != STATUS_OK) return status;
    if (length <= 0) return STATUS_OK;

    Parcel* rawParcel = parcel->get();

    status_t status = rawParcel->writeInt32(static_cast<int32_t>(length));
    if (status != STATUS_OK) return PruneStatusT(status);

    for (size_t i = 0; i < length; i++) {
        status = (rawParcel->*write)(getter(arrayData, i));

@@ -169,10 +191,12 @@ binder_status_t ReadArray(const AParcel* parcel, void* arrayData, ArrayAllocator
    status_t status = rawParcel->readInt32(&length);

    if (status != STATUS_OK) return PruneStatusT(status);
    if (length < 0) return STATUS_UNEXPECTED_NULL;
    if (length < -1) return STATUS_BAD_VALUE;

    if (!allocator(arrayData, length)) return STATUS_NO_MEMORY;

    if (length <= 0) return STATUS_OK;

    for (size_t i = 0; i < length; i++) {
        T readTarget;
        status = (rawParcel->*read)(&readTarget);
@@ -317,20 +341,11 @@ binder_status_t AParcel_readString(const AParcel* parcel, void* stringData,

binder_status_t AParcel_writeStringArray(AParcel* parcel, const void* arrayData, int32_t length,
                                         AParcel_stringArrayElementGetter getter) {
    Parcel* rawParcel = parcel->get();

    if (length < 0) {
        if (length != -1) {
            LOG(WARNING) << __func__ << ": null array must be used with length == -1.";
            return STATUS_BAD_VALUE;
        }

        status_t status = rawParcel->writeInt32(-1);
        return PruneStatusT(status);
    }

    status_t status = rawParcel->writeInt32(static_cast<int32_t>(length));
    if (status != STATUS_OK) return PruneStatusT(status);
    // we have no clue if arrayData represents a null object or not, we can only infer from length
    bool arrayIsNull = length < 0;
    binder_status_t status = WriteAndValidateArraySize(parcel, arrayIsNull, length);
    if (status != STATUS_OK) return status;
    if (length <= 0) return STATUS_OK;

    for (size_t i = 0; i < length; i++) {
        size_t length = 0;
@@ -482,42 +497,42 @@ binder_status_t AParcel_readByte(const AParcel* parcel, int8_t* value) {
    return PruneStatusT(status);
}

binder_status_t AParcel_writeInt32Array(AParcel* parcel, const int32_t* arrayData, size_t length) {
binder_status_t AParcel_writeInt32Array(AParcel* parcel, const int32_t* arrayData, int32_t length) {
    return WriteArray<int32_t>(parcel, arrayData, length);
}

binder_status_t AParcel_writeUint32Array(AParcel* parcel, const uint32_t* arrayData,
                                         size_t length) {
                                         int32_t length) {
    return WriteArray<uint32_t>(parcel, arrayData, length);
}

binder_status_t AParcel_writeInt64Array(AParcel* parcel, const int64_t* arrayData, size_t length) {
binder_status_t AParcel_writeInt64Array(AParcel* parcel, const int64_t* arrayData, int32_t length) {
    return WriteArray<int64_t>(parcel, arrayData, length);
}

binder_status_t AParcel_writeUint64Array(AParcel* parcel, const uint64_t* arrayData,
                                         size_t length) {
                                         int32_t length) {
    return WriteArray<uint64_t>(parcel, arrayData, length);
}

binder_status_t AParcel_writeFloatArray(AParcel* parcel, const float* arrayData, size_t length) {
binder_status_t AParcel_writeFloatArray(AParcel* parcel, const float* arrayData, int32_t length) {
    return WriteArray<float>(parcel, arrayData, length);
}

binder_status_t AParcel_writeDoubleArray(AParcel* parcel, const double* arrayData, size_t length) {
binder_status_t AParcel_writeDoubleArray(AParcel* parcel, const double* arrayData, int32_t length) {
    return WriteArray<double>(parcel, arrayData, length);
}

binder_status_t AParcel_writeBoolArray(AParcel* parcel, const void* arrayData, size_t length,
binder_status_t AParcel_writeBoolArray(AParcel* parcel, const void* arrayData, int32_t length,
                                       AParcel_boolArrayGetter getter) {
    return WriteArray<bool>(parcel, arrayData, length, getter, &Parcel::writeBool);
}

binder_status_t AParcel_writeCharArray(AParcel* parcel, const char16_t* arrayData, size_t length) {
binder_status_t AParcel_writeCharArray(AParcel* parcel, const char16_t* arrayData, int32_t length) {
    return WriteArray<char16_t>(parcel, arrayData, length);
}

binder_status_t AParcel_writeByteArray(AParcel* parcel, const int8_t* arrayData, size_t length) {
binder_status_t AParcel_writeByteArray(AParcel* parcel, const int8_t* arrayData, int32_t length) {
    return WriteArray<int8_t>(parcel, arrayData, length);
}

+39 −11

File changed.

Preview size limit exceeded, changes collapsed.