1a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood/*
2a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * Copyright (C) 2010 The Android Open Source Project
3a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood *
4a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * Licensed under the Apache License, Version 2.0 (the "License");
5a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * you may not use this file except in compliance with the License.
6a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * You may obtain a copy of the License at
7a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood *
8a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood *      http://www.apache.org/licenses/LICENSE-2.0
9a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood *
10a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * Unless required by applicable law or agreed to in writing, software
11a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * distributed under the License is distributed on an "AS IS" BASIS,
12a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * See the License for the specific language governing permissions and
14a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood * limitations under the License.
15a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood */
16a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
17a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood#define LOG_TAG "MtpProperty"
18a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
19377b2ec9a2885f9b6405b07ba900a9e3f4349c38Kévin PETIT#include <inttypes.h>
20eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar#include <cutils/compiler.h>
21a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood#include "MtpDataPacket.h"
220c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood#include "MtpDebug.h"
23a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood#include "MtpProperty.h"
24a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood#include "MtpStringBuffer.h"
25a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood#include "MtpUtils.h"
26a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
27a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwoodnamespace android {
28a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
29a6c490b8b2d96ebaab632286029463f932ae3b6bMike LockwoodMtpProperty::MtpProperty()
30a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    :   mCode(0),
31a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mType(0),
32a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mWriteable(false),
33a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mDefaultArrayLength(0),
34a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mDefaultArrayValues(NULL),
35a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mCurrentArrayLength(0),
36a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mCurrentArrayValues(NULL),
372bb8c0e7c4e4093f4161ff5e98cef51c87193859Mike Lockwood        mGroupCode(0),
38a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mFormFlag(kFormNone),
39a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mEnumLength(0),
40a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mEnumValues(NULL)
41a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood{
42dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    memset(&mDefaultValue, 0, sizeof(mDefaultValue));
43dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    memset(&mCurrentValue, 0, sizeof(mCurrentValue));
44dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    memset(&mMinimumValue, 0, sizeof(mMinimumValue));
45dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    memset(&mMaximumValue, 0, sizeof(mMaximumValue));
46a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood}
47a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
4821ef7d0e70c5ad599bc2602cb484f8cd647055caMike LockwoodMtpProperty::MtpProperty(MtpPropertyCode propCode,
4921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                         MtpDataType type,
5021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                         bool writeable,
5121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                         int defaultValue)
5221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    :   mCode(propCode),
5321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mType(type),
5421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mWriteable(writeable),
5521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mDefaultArrayLength(0),
5621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mDefaultArrayValues(NULL),
5721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mCurrentArrayLength(0),
5821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mCurrentArrayValues(NULL),
5940ce1f262cc4edbc8b7c470830325466263acaecMike Lockwood        mGroupCode(0),
6021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mFormFlag(kFormNone),
6121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mEnumLength(0),
6221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        mEnumValues(NULL)
6321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood{
6421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    memset(&mDefaultValue, 0, sizeof(mDefaultValue));
6521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    memset(&mCurrentValue, 0, sizeof(mCurrentValue));
6621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    memset(&mMinimumValue, 0, sizeof(mMinimumValue));
6721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    memset(&mMaximumValue, 0, sizeof(mMaximumValue));
6821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood
6921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    if (defaultValue) {
7021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        switch (type) {
7121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_INT8:
72dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.i8 = defaultValue;
7321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
7421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_UINT8:
75dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.u8 = defaultValue;
7621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
7721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_INT16:
78dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.i16 = defaultValue;
7921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
8021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_UINT16:
81dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.u16 = defaultValue;
8221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
8321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_INT32:
84dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.i32 = defaultValue;
8521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
8621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_UINT32:
87dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.u32 = defaultValue;
8821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
8921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_INT64:
90dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.i64 = defaultValue;
9121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
9221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            case MTP_TYPE_UINT64:
93dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood                mDefaultValue.u.u64 = defaultValue;
9421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood                break;
9521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            default:
9629357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block                ALOGE("unknown type %04X in MtpProperty::MtpProperty", type);
9721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        }
9821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    }
9921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood}
10021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood
101a6c490b8b2d96ebaab632286029463f932ae3b6bMike LockwoodMtpProperty::~MtpProperty() {
102a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    if (mType == MTP_TYPE_STR) {
103a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        // free all strings
104a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        free(mDefaultValue.str);
105a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        free(mCurrentValue.str);
106a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        free(mMinimumValue.str);
107a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        free(mMaximumValue.str);
108a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        if (mDefaultArrayValues) {
109ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            for (uint32_t i = 0; i < mDefaultArrayLength; i++)
110a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood                free(mDefaultArrayValues[i].str);
111a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        }
112a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        if (mCurrentArrayValues) {
113ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            for (uint32_t i = 0; i < mCurrentArrayLength; i++)
114a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood                free(mCurrentArrayValues[i].str);
115a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        }
116a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        if (mEnumValues) {
117ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            for (uint16_t i = 0; i < mEnumLength; i++)
118a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood                free(mEnumValues[i].str);
119a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        }
120a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    }
121a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    delete[] mDefaultArrayValues;
122a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    delete[] mCurrentArrayValues;
123a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    delete[] mEnumValues;
124a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood}
125a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
126ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwoodbool MtpProperty::read(MtpDataPacket& packet) {
127ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    uint8_t temp8;
128ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood
129ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    if (!packet.getUInt16(mCode)) return false;
1305da864845e024833c4c7f641acd7c88187a6bc1eMike Lockwood    bool deviceProp = isDeviceProperty();
131ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    if (!packet.getUInt16(mType)) return false;
132ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    if (!packet.getUInt8(temp8)) return false;
133ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    mWriteable = (temp8 == 1);
134a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    switch (mType) {
135a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AINT8:
136a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AUINT8:
137a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AINT16:
138a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AUINT16:
139a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AINT32:
140a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AUINT32:
141a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AINT64:
142a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AUINT64:
143a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AINT128:
144a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_AUINT128:
145a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            mDefaultArrayValues = readArrayValues(packet, mDefaultArrayLength);
146ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!mDefaultArrayValues) return false;
147ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (deviceProp) {
1487cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood                mCurrentArrayValues = readArrayValues(packet, mCurrentArrayLength);
149ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood                if (!mCurrentArrayValues) return false;
150ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            }
151a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
152a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        default:
153ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!readValue(packet, mDefaultValue)) return false;
154ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (deviceProp) {
155ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood                if (!readValue(packet, mCurrentValue)) return false;
156ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            }
157a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    }
158ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    if (!deviceProp) {
159ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood        if (!packet.getUInt32(mGroupCode)) return false;
160ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    }
161ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    if (!packet.getUInt8(mFormFlag)) return false;
162a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
163a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    if (mFormFlag == kFormRange) {
164ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!readValue(packet, mMinimumValue)) return false;
165ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!readValue(packet, mMaximumValue)) return false;
166ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!readValue(packet, mStepSize)) return false;
167a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    } else if (mFormFlag == kFormEnum) {
168ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood        if (!packet.getUInt16(mEnumLength)) return false;
169a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        mEnumValues = new MtpPropertyValue[mEnumLength];
170ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood        for (int i = 0; i < mEnumLength; i++) {
171ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!readValue(packet, mEnumValues[i])) return false;
172ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood        }
173a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    }
174ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood
175ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    return true;
176a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood}
177a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
17821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwoodvoid MtpProperty::write(MtpDataPacket& packet) {
1797cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood    bool deviceProp = isDeviceProperty();
1807cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood
18121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    packet.putUInt16(mCode);
18221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    packet.putUInt16(mType);
18321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    packet.putUInt8(mWriteable ? 1 : 0);
18421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood
18521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    switch (mType) {
18621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AINT8:
18721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AUINT8:
18821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AINT16:
18921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AUINT16:
19021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AINT32:
19121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AUINT32:
19221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AINT64:
19321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AUINT64:
19421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AINT128:
19521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_AUINT128:
19621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            writeArrayValues(packet, mDefaultArrayValues, mDefaultArrayLength);
1977cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood            if (deviceProp)
1987cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood                writeArrayValues(packet, mCurrentArrayValues, mCurrentArrayLength);
19921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
20021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        default:
20121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            writeValue(packet, mDefaultValue);
2027cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood            if (deviceProp)
2037cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood                writeValue(packet, mCurrentValue);
20421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    }
2057cee5d3c3673d9a325d8096eea0ba48258fc656cMike Lockwood    if (!deviceProp)
2060fa848d780cf990a2860637f40432d28594c85a3Mike Lockwood        packet.putUInt32(mGroupCode);
2070fa848d780cf990a2860637f40432d28594c85a3Mike Lockwood    packet.putUInt8(mFormFlag);
20821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    if (mFormFlag == kFormRange) {
20921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            writeValue(packet, mMinimumValue);
21021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            writeValue(packet, mMaximumValue);
21121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            writeValue(packet, mStepSize);
21221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    } else if (mFormFlag == kFormEnum) {
21321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        packet.putUInt16(mEnumLength);
21421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        for (int i = 0; i < mEnumLength; i++)
21521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            writeValue(packet, mEnumValues[i]);
21621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    }
21721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood}
21821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood
219dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwoodvoid MtpProperty::setDefaultValue(const uint16_t* string) {
220dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    free(mDefaultValue.str);
221dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    if (string) {
222dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood        MtpStringBuffer buffer(string);
223dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood        mDefaultValue.str = strdup(buffer);
224dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    }
225dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    else
226dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood        mDefaultValue.str = NULL;
227dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood}
228dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood
229dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwoodvoid MtpProperty::setCurrentValue(const uint16_t* string) {
230dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    free(mCurrentValue.str);
231dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    if (string) {
232dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood        MtpStringBuffer buffer(string);
233dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood        mCurrentValue.str = strdup(buffer);
234dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    }
235dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood    else
236dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood        mCurrentValue.str = NULL;
237dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood}
238dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood
2390181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwoodvoid MtpProperty::setFormRange(int min, int max, int step) {
2400181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood    mFormFlag = kFormRange;
2410181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood    switch (mType) {
2420181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_INT8:
2430181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.i8 = min;
2440181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.i8 = max;
2450181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.i8 = step;
2460181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2470181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_UINT8:
2480181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.u8 = min;
2490181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.u8 = max;
2500181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.u8 = step;
2510181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2520181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_INT16:
2530181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.i16 = min;
2540181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.i16 = max;
2550181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.i16 = step;
2560181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2570181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_UINT16:
2580181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.u16 = min;
2590181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.u16 = max;
2600181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.u16 = step;
2610181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2620181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_INT32:
2630181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.i32 = min;
2640181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.i32 = max;
2650181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.i32 = step;
2660181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2670181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_UINT32:
2680181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.u32 = min;
2690181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.u32 = max;
2700181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.u32 = step;
2710181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2720181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_INT64:
2730181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.i64 = min;
2740181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.i64 = max;
2750181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.i64 = step;
2760181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2770181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        case MTP_TYPE_UINT64:
2780181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMinimumValue.u.u64 = min;
2790181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mMaximumValue.u.u64 = max;
2800181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            mStepSize.u.u64 = step;
2810181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2820181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        default:
28329357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("unsupported type for MtpProperty::setRange");
2840181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            break;
2850181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood    }
2860181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood}
2870181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood
2880181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwoodvoid MtpProperty::setFormEnum(const int* values, int count) {
2890181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood     mFormFlag = kFormEnum;
2900181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood     delete[] mEnumValues;
2910181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood     mEnumValues = new MtpPropertyValue[count];
2920181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood     mEnumLength = count;
2930181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood
2940181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood    for (int i = 0; i < count; i++) {
2950181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        int value = *values++;
2960181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood            switch (mType) {
2970181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_INT8:
2980181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.i8 = value;
2990181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3000181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_UINT8:
3010181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.u8 = value;
3020181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3030181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_INT16:
3040181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.i16 = value;
3050181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3060181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_UINT16:
3070181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.u16 = value;
3080181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3090181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_INT32:
3100181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.i32 = value;
3110181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3120181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_UINT32:
3130181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.u32 = value;
3140181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3150181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_INT64:
3160181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.i64 = value;
3170181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3180181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                case MTP_TYPE_UINT64:
3190181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    mEnumValues[i].u.u64 = value;
3200181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3210181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                default:
32229357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block                    ALOGE("unsupported type for MtpProperty::setEnum");
3230181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood                    break;
3240181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood        }
3250181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood    }
3260181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood}
3270181726d0cc2d0fc6f6a53b6479dcf0fc41b9499Mike Lockwood
328b892d0e5556ed6ded3e0548f75ab16fc2e3d92c3Mike Lockwoodvoid MtpProperty::setFormDateTime() {
329b892d0e5556ed6ded3e0548f75ab16fc2e3d92c3Mike Lockwood     mFormFlag = kFormDateTime;
330b892d0e5556ed6ded3e0548f75ab16fc2e3d92c3Mike Lockwood}
331b892d0e5556ed6ded3e0548f75ab16fc2e3d92c3Mike Lockwood
332a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwoodvoid MtpProperty::print() {
3330c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    MtpString buffer;
3340c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    bool deviceProp = isDeviceProperty();
3350c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    if (deviceProp)
336df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block        ALOGI("    %s (%04X)", MtpDebug::getDevicePropCodeName(mCode), mCode);
3370c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    else
338df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block        ALOGI("    %s (%04X)", MtpDebug::getObjectPropCodeName(mCode), mCode);
339df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block    ALOGI("    type %04X", mType);
340df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block    ALOGI("    writeable %s", (mWriteable ? "true" : "false"));
3410c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    buffer = "    default value: ";
3420c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    print(mDefaultValue, buffer);
343df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block    ALOGI("%s", (const char *)buffer);
3440c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    if (deviceProp) {
3450c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        buffer = "    current value: ";
3460c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        print(mCurrentValue, buffer);
347df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block        ALOGI("%s", (const char *)buffer);
3480c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    }
3490c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    switch (mFormFlag) {
3500c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case kFormNone:
3510c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3520c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case kFormRange:
3530c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer = "    Range (";
3540c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            print(mMinimumValue, buffer);
3550c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer += ", ";
3560c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            print(mMaximumValue, buffer);
3570c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer += ", ";
3580c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            print(mStepSize, buffer);
359fd34626771a63d3a835863e1b4bf71dcb26e28d8Mike Lockwood            buffer += ")";
360df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block            ALOGI("%s", (const char *)buffer);
3610c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3620c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case kFormEnum:
3630c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer = "    Enum { ";
3640c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            for (int i = 0; i < mEnumLength; i++) {
3650c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood                print(mEnumValues[i], buffer);
3660c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood                buffer += " ";
3670c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            }
3680c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer += "}";
369df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block            ALOGI("%s", (const char *)buffer);
3700c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3710c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case kFormDateTime:
372df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block            ALOGI("    DateTime\n");
3730c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3740c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        default:
375df64d15042bbd5e0e4933ac49bf3c177dd94752cSteve Block            ALOGI("    form %d\n", mFormFlag);
3760c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3770c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    }
3780c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood}
3790c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood
3800c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwoodvoid MtpProperty::print(MtpPropertyValue& value, MtpString& buffer) {
3810c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    switch (mType) {
3820c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_INT8:
3830c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%d", value.u.i8);
3840c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3850c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_UINT8:
3860c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%d", value.u.u8);
3870c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3880c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_INT16:
3890c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%d", value.u.i16);
3900c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3910c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_UINT16:
3920c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%d", value.u.u16);
3930c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3940c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_INT32:
3950c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%d", value.u.i32);
3960c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
3970c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_UINT32:
3980c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%d", value.u.u32);
3990c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
4000c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_INT64:
401377b2ec9a2885f9b6405b07ba900a9e3f4349c38Kévin PETIT            buffer.appendFormat("%" PRId64, value.u.i64);
4020c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
4030c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_UINT64:
404377b2ec9a2885f9b6405b07ba900a9e3f4349c38Kévin PETIT            buffer.appendFormat("%" PRIu64, value.u.u64);
4050c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
4060c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_INT128:
4070c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%08X%08X%08X%08X", value.u.i128[0], value.u.i128[1],
4080c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood                    value.u.i128[2], value.u.i128[3]);
4090c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
4100c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_UINT128:
4110c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%08X%08X%08X%08X", value.u.u128[0], value.u.u128[1],
4120c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood                    value.u.u128[2], value.u.u128[3]);
4130c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
4140c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        case MTP_TYPE_STR:
4150c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            buffer.appendFormat("%s", value.str);
4160c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
4170c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood        default:
41829357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("unsupported type for MtpProperty::print\n");
4190c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood            break;
4200c7c7c76a96a82ec728a2d5c091941c4057ffb25Mike Lockwood    }
421a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood}
422a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
423ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwoodbool MtpProperty::readValue(MtpDataPacket& packet, MtpPropertyValue& value) {
4245cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood    MtpStringBuffer stringBuffer;
4255cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood
426a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    switch (mType) {
427a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_INT8:
4285cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT8:
429ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getInt8(value.u.i8)) return false;
430a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
431a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_UINT8:
4325cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT8:
433ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getUInt8(value.u.u8)) return false;
434a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
435a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_INT16:
4365cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT16:
437ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getInt16(value.u.i16)) return false;
438a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
439a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_UINT16:
4405cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT16:
441ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getUInt16(value.u.u16)) return false;
442a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
443a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_INT32:
4445cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT32:
445ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getInt32(value.u.i32)) return false;
446a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
447a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_UINT32:
4485cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT32:
449ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getUInt32(value.u.u32)) return false;
450a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
451a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_INT64:
4525cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT64:
453ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getInt64(value.u.i64)) return false;
454a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
455a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_UINT64:
4565cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT64:
457ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getUInt64(value.u.u64)) return false;
458a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
459a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_INT128:
4605cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT128:
461ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getInt128(value.u.i128)) return false;
462a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
463a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        case MTP_TYPE_UINT128:
4645cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT128:
465ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getUInt128(value.u.u128)) return false;
466a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood            break;
4675cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_STR:
468ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            if (!packet.getString(stringBuffer)) return false;
4695cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood            value.str = strdup(stringBuffer);
4705cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood            break;
471a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        default:
47229357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("unknown type %04X in MtpProperty::readValue", mType);
473ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            return false;
474a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    }
475ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    return true;
476a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood}
477a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
47821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwoodvoid MtpProperty::writeValue(MtpDataPacket& packet, MtpPropertyValue& value) {
4795cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood    MtpStringBuffer stringBuffer;
4805cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood
48121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    switch (mType) {
48221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_INT8:
4835cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT8:
484dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putInt8(value.u.i8);
48521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
48621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_UINT8:
4875cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT8:
488dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putUInt8(value.u.u8);
48921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
49021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_INT16:
4915cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT16:
492dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putInt16(value.u.i16);
49321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
49421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_UINT16:
4955cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT16:
496dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putUInt16(value.u.u16);
49721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
49821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_INT32:
4995cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT32:
500dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putInt32(value.u.i32);
50121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
50221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_UINT32:
5035cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT32:
504dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putUInt32(value.u.u32);
50521ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
50621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_INT64:
5075cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT64:
508dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putInt64(value.u.i64);
50921ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
51021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_UINT64:
5115cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT64:
512dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putUInt64(value.u.u64);
51321ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
51421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_INT128:
5155cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AINT128:
516dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putInt128(value.u.i128);
51721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
51821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        case MTP_TYPE_UINT128:
5195cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_AUINT128:
520dde372033b4da75ebde7ea2afdec1c1b86ab5a42Mike Lockwood            packet.putUInt128(value.u.u128);
52121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood            break;
5225cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood        case MTP_TYPE_STR:
5235cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood            if (value.str)
5245cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood                packet.putString(value.str);
5255cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood            else
5265cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood                packet.putEmptyString();
5275cdceca217319bf6a22caf1acadc38c8dc259316Mike Lockwood            break;
52821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        default:
52929357bc2c0dd7c43ad3bd0c8e3efa4e6fd9bfd47Steve Block            ALOGE("unknown type %04X in MtpProperty::writeValue", mType);
53021ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    }
53121ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood}
53221ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood
533ab063847e6e893740749029a04cce1f6b7345ed5Mike LockwoodMtpPropertyValue* MtpProperty::readArrayValues(MtpDataPacket& packet, uint32_t& length) {
534ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    if (!packet.getUInt32(length)) return NULL;
535ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood
536eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar    // Fail if resulting array is over 2GB.  This is because the maximum array
537eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar    // size may be less than SIZE_MAX on some platforms.
538eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar    if ( CC_UNLIKELY(
539eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar            length == 0 ||
540eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar            length >= INT32_MAX / sizeof(MtpPropertyValue)) ) {
541eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar        length = 0;
542a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood        return NULL;
543eb5d7f2f1cc049ea7f95a4f089ce2113d7683ddaLajos Molnar    }
544a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    MtpPropertyValue* result = new MtpPropertyValue[length];
545ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    for (uint32_t i = 0; i < length; i++)
546ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood        if (!readValue(packet, result[i])) {
547ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            delete result;
548ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood            return NULL;
549ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood        }
550a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood    return result;
551a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood}
552a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood
553ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwoodvoid MtpProperty::writeArrayValues(MtpDataPacket& packet, MtpPropertyValue* values, uint32_t length) {
55421ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood    packet.putUInt32(length);
555ab063847e6e893740749029a04cce1f6b7345ed5Mike Lockwood    for (uint32_t i = 0; i < length; i++)
55621ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood        writeValue(packet, values[i]);
55721ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood}
55821ef7d0e70c5ad599bc2602cb484f8cd647055caMike Lockwood
559a6c490b8b2d96ebaab632286029463f932ae3b6bMike Lockwood}  // namespace android
560