diff options
Diffstat (limited to 'media/libstagefright/foundation/AString.cpp')
-rw-r--r-- | media/libstagefright/foundation/AString.cpp | 331 |
1 files changed, 331 insertions, 0 deletions
diff --git a/media/libstagefright/foundation/AString.cpp b/media/libstagefright/foundation/AString.cpp new file mode 100644 index 0000000..61b76cf --- /dev/null +++ b/media/libstagefright/foundation/AString.cpp @@ -0,0 +1,331 @@ +/* + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include <ctype.h> +#include <stdarg.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include "ADebug.h" +#include "AString.h" + +namespace android { + +// static +const char *AString::kEmptyString = ""; + +AString::AString() + : mData((char *)kEmptyString), + mSize(0), + mAllocSize(1) { +} + +AString::AString(const char *s) + : mData(NULL), + mSize(0), + mAllocSize(1) { + setTo(s); +} + +AString::AString(const char *s, size_t size) + : mData(NULL), + mSize(0), + mAllocSize(1) { + setTo(s, size); +} + +AString::AString(const AString &from) + : mData(NULL), + mSize(0), + mAllocSize(1) { + setTo(from, 0, from.size()); +} + +AString::AString(const AString &from, size_t offset, size_t n) + : mData(NULL), + mSize(0), + mAllocSize(1) { + setTo(from, offset, n); +} + +AString::~AString() { + clear(); +} + +AString &AString::operator=(const AString &from) { + if (&from != this) { + setTo(from, 0, from.size()); + } + + return *this; +} + +size_t AString::size() const { + return mSize; +} + +const char *AString::c_str() const { + return mData; +} + +bool AString::empty() const { + return mSize == 0; +} + +void AString::setTo(const char *s) { + setTo(s, strlen(s)); +} + +void AString::setTo(const char *s, size_t size) { + clear(); + append(s, size); +} + +void AString::setTo(const AString &from, size_t offset, size_t n) { + CHECK(&from != this); + + clear(); + setTo(from.mData + offset, n); +} + +void AString::clear() { + if (mData && mData != kEmptyString) { + free(mData); + mData = NULL; + } + + mData = (char *)kEmptyString; + mSize = 0; + mAllocSize = 1; +} + +size_t AString::hash() const { + size_t x = 0; + for (size_t i = 0; i < mSize; ++i) { + x = (x * 31) + mData[i]; + } + + return x; +} + +bool AString::operator==(const AString &other) const { + return mSize == other.mSize && !memcmp(mData, other.mData, mSize); +} + +void AString::trim() { + makeMutable(); + + size_t i = 0; + while (i < mSize && isspace(mData[i])) { + ++i; + } + + size_t j = mSize; + while (j > i && isspace(mData[j - 1])) { + --j; + } + + memmove(mData, &mData[i], j - i); + mSize = j - i; + mData[mSize] = '\0'; +} + +void AString::erase(size_t start, size_t n) { + CHECK_LT(start, mSize); + CHECK_LE(start + n, mSize); + + makeMutable(); + + memmove(&mData[start], &mData[start + n], mSize - start - n); + mSize -= n; + mData[mSize] = '\0'; +} + +void AString::makeMutable() { + if (mData == kEmptyString) { + mData = strdup(kEmptyString); + } +} + +void AString::append(const char *s) { + append(s, strlen(s)); +} + +void AString::append(const char *s, size_t size) { + makeMutable(); + + if (mSize + size + 1 > mAllocSize) { + mAllocSize = (mAllocSize + size + 31) & -32; + mData = (char *)realloc(mData, mAllocSize); + CHECK(mData != NULL); + } + + memcpy(&mData[mSize], s, size); + mSize += size; + mData[mSize] = '\0'; +} + +void AString::append(const AString &from) { + append(from.c_str(), from.size()); +} + +void AString::append(const AString &from, size_t offset, size_t n) { + append(from.c_str() + offset, n); +} + +void AString::append(int x) { + char s[16]; + sprintf(s, "%d", x); + + append(s); +} + +void AString::append(unsigned x) { + char s[16]; + sprintf(s, "%u", x); + + append(s); +} + +void AString::append(long x) { + char s[16]; + sprintf(s, "%ld", x); + + append(s); +} + +void AString::append(unsigned long x) { + char s[16]; + sprintf(s, "%lu", x); + + append(s); +} + +void AString::append(long long x) { + char s[32]; + sprintf(s, "%lld", x); + + append(s); +} + +void AString::append(unsigned long long x) { + char s[32]; + sprintf(s, "%llu", x); + + append(s); +} + +void AString::append(float x) { + char s[16]; + sprintf(s, "%f", x); + + append(s); +} + +void AString::append(double x) { + char s[16]; + sprintf(s, "%f", x); + + append(s); +} + +void AString::append(void *x) { + char s[16]; + sprintf(s, "%p", x); + + append(s); +} + +ssize_t AString::find(const char *substring, size_t start) const { + CHECK_LE(start, size()); + + const char *match = strstr(mData + start, substring); + + if (match == NULL) { + return -1; + } + + return match - mData; +} + +void AString::insert(const AString &from, size_t insertionPos) { + insert(from.c_str(), from.size(), insertionPos); +} + +void AString::insert(const char *from, size_t size, size_t insertionPos) { + CHECK_GE(insertionPos, 0u); + CHECK_LE(insertionPos, mSize); + + makeMutable(); + + if (mSize + size + 1 > mAllocSize) { + mAllocSize = (mAllocSize + size + 31) & -32; + mData = (char *)realloc(mData, mAllocSize); + CHECK(mData != NULL); + } + + memmove(&mData[insertionPos + size], + &mData[insertionPos], mSize - insertionPos + 1); + + memcpy(&mData[insertionPos], from, size); + + mSize += size; +} + +bool AString::operator<(const AString &other) const { + return compare(other) < 0; +} + +bool AString::operator>(const AString &other) const { + return compare(other) > 0; +} + +int AString::compare(const AString &other) const { + return strcmp(mData, other.mData); +} + +void AString::tolower() { + makeMutable(); + + for (size_t i = 0; i < mSize; ++i) { + mData[i] = ::tolower(mData[i]); + } +} + +bool AString::startsWith(const char *prefix) const { + return !strncmp(mData, prefix, strlen(prefix)); +} + +AString StringPrintf(const char *format, ...) { + va_list ap; + va_start(ap, format); + + char *buffer; + vasprintf(&buffer, format, ap); + + va_end(ap); + + AString result(buffer); + + free(buffer); + buffer = NULL; + + return result; +} + +} // namespace android + |