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

Commit 040424fd authored by Christopher Wiley's avatar Christopher Wiley Committed by android-build-merger
Browse files

Merge "Add support for decoding UTF16 to UTF8" am: ac4728f8 am: 7b0c8479

am: 4ab1dbe5

* commit '4ab1dbe5':
  Add support for decoding UTF16 to UTF8
parents 1d52ba38 4ab1dbe5
Loading
Loading
Loading
Loading
+15 −0
Original line number Diff line number Diff line
@@ -17,6 +17,7 @@
#ifndef ANDROID_PARCEL_H
#define ANDROID_PARCEL_H

#include <string>
#include <vector>

#include <cutils/native_handle.h>
@@ -119,6 +120,10 @@ public:
    status_t            writeChar(char16_t val);
    status_t            writeByte(int8_t val);

    // Take a UTF8 encoded string, convert to UTF16, write it to the parcel.
    status_t            writeUtf8AsUtf16(const std::string& str);
    status_t            writeUtf8AsUtf16(const std::unique_ptr<std::string>& str);

    status_t            writeByteVector(const std::unique_ptr<std::vector<int8_t>>& val);
    status_t            writeByteVector(const std::vector<int8_t>& val);
    status_t            writeInt32Vector(const std::unique_ptr<std::vector<int32_t>>& val);
@@ -136,6 +141,9 @@ public:
    status_t            writeString16Vector(
                            const std::unique_ptr<std::vector<std::unique_ptr<String16>>>& val);
    status_t            writeString16Vector(const std::vector<String16>& val);
    status_t            writeUtf8VectorAsUtf16Vector(
                            const std::unique_ptr<std::vector<std::unique_ptr<std::string>>>& val);
    status_t            writeUtf8VectorAsUtf16Vector(const std::vector<std::string>& val);

    status_t            writeStrongBinderVector(const std::unique_ptr<std::vector<sp<IBinder>>>& val);
    status_t            writeStrongBinderVector(const std::vector<sp<IBinder>>& val);
@@ -230,6 +238,10 @@ public:
    int8_t              readByte() const;
    status_t            readByte(int8_t *pArg) const;

    // Read a UTF16 encoded string, convert to UTF8
    status_t            readUtf8FromUtf16(std::string* str) const;
    status_t            readUtf8FromUtf16(std::unique_ptr<std::string>* str) const;

    const char*         readCString() const;
    String8             readString8() const;
    String16            readString16() const;
@@ -274,6 +286,9 @@ public:
    status_t            readString16Vector(
                            std::unique_ptr<std::vector<std::unique_ptr<String16>>>* val) const;
    status_t            readString16Vector(std::vector<String16>* val) const;
    status_t            readUtf8VectorFromUtf16Vector(
                            std::unique_ptr<std::vector<std::unique_ptr<std::string>>>* val) const;
    status_t            readUtf8VectorFromUtf16Vector(std::vector<std::string>* val) const;

    template<typename T>
    status_t            read(Flattenable<T>& val) const;
+88 −0
Original line number Diff line number Diff line
@@ -749,6 +749,37 @@ restart_write:
    return NULL;
}

status_t Parcel::writeUtf8AsUtf16(const std::string& str) {
    const uint8_t* strData = (uint8_t*)str.data();
    const size_t strLen= str.length();
    const ssize_t utf16Len = utf8_to_utf16_length(strData, strLen);
    if (utf16Len < 0 || utf16Len> std::numeric_limits<int32_t>::max()) {
        return BAD_VALUE;
    }

    status_t err = writeInt32(utf16Len);
    if (err) {
        return err;
    }

    // Allocate enough bytes to hold our converted string and its terminating NULL.
    void* dst = writeInplace((utf16Len + 1) * sizeof(char16_t));
    if (!dst) {
        return NO_MEMORY;
    }

    utf8_to_utf16(strData, strLen, (char16_t*)dst);

    return NO_ERROR;
}

status_t Parcel::writeUtf8AsUtf16(const std::unique_ptr<std::string>& str) {
  if (!str) {
    return writeInt32(-1);
  }
  return writeUtf8AsUtf16(*str);
}

status_t Parcel::writeByteVector(const std::unique_ptr<std::vector<int8_t>>& val)
{
    if (!val) {
@@ -852,6 +883,15 @@ status_t Parcel::writeString16Vector(
    return writeNullableTypedVector(val, &Parcel::writeString16);
}

status_t Parcel::writeUtf8VectorAsUtf16Vector(
                        const std::unique_ptr<std::vector<std::unique_ptr<std::string>>>& val) {
    return writeNullableTypedVector(val, &Parcel::writeUtf8AsUtf16);
}

status_t Parcel::writeUtf8VectorAsUtf16Vector(const std::vector<std::string>& val) {
    return writeTypedVector(val, &Parcel::writeUtf8AsUtf16);
}

status_t Parcel::writeInt32(int32_t val)
{
    return writeAligned(val);
@@ -1491,6 +1531,14 @@ status_t Parcel::readString16Vector(std::vector<String16>* val) const {
    return readTypedVector(val, &Parcel::readString16);
}

status_t Parcel::readUtf8VectorFromUtf16Vector(
        std::unique_ptr<std::vector<std::unique_ptr<std::string>>>* val) const {
    return readNullableTypedVector(val, &Parcel::readUtf8FromUtf16);
}

status_t Parcel::readUtf8VectorFromUtf16Vector(std::vector<std::string>* val) const {
    return readTypedVector(val, &Parcel::readUtf8FromUtf16);
}

status_t Parcel::readInt32(int32_t *pArg) const
{
@@ -1649,6 +1697,46 @@ int8_t Parcel::readByte() const
    return int8_t(readInt32());
}

status_t Parcel::readUtf8FromUtf16(std::string* str) const {
    size_t utf16Size = 0;
    const char16_t* src = readString16Inplace(&utf16Size);
    if (!src) {
        return UNEXPECTED_NULL;
    }

    // Save ourselves the trouble, we're done.
    if (utf16Size == 0u) {
        str->clear();
       return NO_ERROR;
    }

    ssize_t utf8Size = utf16_to_utf8_length(src, utf16Size);
    if (utf8Size < 0) {
        return BAD_VALUE;
    }
    // Note that while it is probably safe to assume string::resize keeps a
    // spare byte around for the trailing null, we're going to be explicit.
    str->resize(utf8Size + 1);
    utf16_to_utf8(src, utf16Size, &((*str)[0]));
    str->resize(utf8Size);
    return NO_ERROR;
}

status_t Parcel::readUtf8FromUtf16(std::unique_ptr<std::string>* str) const {
    const int32_t start = dataPosition();
    int32_t size;
    status_t status = readInt32(&size);
    str->reset();

    if (status != OK || size < 0) {
        return status;
    }

    setDataPosition(start);
    str->reset(new std::string());
    return readUtf8FromUtf16(str->get());
}

const char* Parcel::readCString() const
{
    const size_t avail = mDataSize-mDataPos;