Merge "MTP: Skip runtime thumbnail generation for Android Host" into sc-dev
This commit is contained in:
@@ -101,6 +101,8 @@ public class MtpDatabase implements AutoCloseable {
|
||||
private int mBatteryLevel;
|
||||
private int mBatteryScale;
|
||||
private int mDeviceType;
|
||||
private String mHostType;
|
||||
private boolean mSkipThumbForHost = false;
|
||||
|
||||
private MtpServer mServer;
|
||||
private MtpStorageManager mManager;
|
||||
@@ -192,6 +194,7 @@ public class MtpDatabase implements AutoCloseable {
|
||||
MtpConstants.DEVICE_PROPERTY_IMAGE_SIZE,
|
||||
MtpConstants.DEVICE_PROPERTY_BATTERY_LEVEL,
|
||||
MtpConstants.DEVICE_PROPERTY_PERCEIVED_DEVICE_TYPE,
|
||||
MtpConstants.DEVICE_PROPERTY_SESSION_INITIATOR_VERSION_INFO,
|
||||
};
|
||||
|
||||
@VisibleForNative
|
||||
@@ -408,6 +411,8 @@ public class MtpDatabase implements AutoCloseable {
|
||||
}
|
||||
context.deleteDatabase(devicePropertiesName);
|
||||
}
|
||||
mHostType = "";
|
||||
mSkipThumbForHost = false;
|
||||
}
|
||||
|
||||
@VisibleForNative
|
||||
@@ -672,12 +677,24 @@ public class MtpDatabase implements AutoCloseable {
|
||||
|
||||
@VisibleForNative
|
||||
private int getDeviceProperty(int property, long[] outIntValue, char[] outStringValue) {
|
||||
int length;
|
||||
String value;
|
||||
|
||||
switch (property) {
|
||||
case MtpConstants.DEVICE_PROPERTY_SYNCHRONIZATION_PARTNER:
|
||||
case MtpConstants.DEVICE_PROPERTY_DEVICE_FRIENDLY_NAME:
|
||||
// writable string properties kept in shared preferences
|
||||
String value = mDeviceProperties.getString(Integer.toString(property), "");
|
||||
int length = value.length();
|
||||
value = mDeviceProperties.getString(Integer.toString(property), "");
|
||||
length = value.length();
|
||||
if (length > 255) {
|
||||
length = 255;
|
||||
}
|
||||
value.getChars(0, length, outStringValue, 0);
|
||||
outStringValue[length] = 0;
|
||||
return MtpConstants.RESPONSE_OK;
|
||||
case MtpConstants.DEVICE_PROPERTY_SESSION_INITIATOR_VERSION_INFO:
|
||||
value = mHostType;
|
||||
length = value.length();
|
||||
if (length > 255) {
|
||||
length = 255;
|
||||
}
|
||||
@@ -717,6 +734,14 @@ public class MtpDatabase implements AutoCloseable {
|
||||
e.putString(Integer.toString(property), stringValue);
|
||||
return (e.commit() ? MtpConstants.RESPONSE_OK
|
||||
: MtpConstants.RESPONSE_GENERAL_ERROR);
|
||||
case MtpConstants.DEVICE_PROPERTY_SESSION_INITIATOR_VERSION_INFO:
|
||||
mHostType = stringValue;
|
||||
if (stringValue.startsWith("Android/")) {
|
||||
Log.d(TAG, "setDeviceProperty." + Integer.toHexString(property)
|
||||
+ "=" + stringValue);
|
||||
mSkipThumbForHost = true;
|
||||
}
|
||||
return MtpConstants.RESPONSE_OK;
|
||||
}
|
||||
|
||||
return MtpConstants.RESPONSE_DEVICE_PROP_NOT_SUPPORTED;
|
||||
@@ -838,6 +863,10 @@ public class MtpDatabase implements AutoCloseable {
|
||||
outLongs[0] = thumbOffsetAndSize != null ? thumbOffsetAndSize[1] : 0;
|
||||
outLongs[1] = exif.getAttributeInt(ExifInterface.TAG_PIXEL_X_DIMENSION, 0);
|
||||
outLongs[2] = exif.getAttributeInt(ExifInterface.TAG_PIXEL_Y_DIMENSION, 0);
|
||||
if (mSkipThumbForHost) {
|
||||
Log.d(TAG, "getThumbnailInfo: Skip runtime thumbnail.");
|
||||
return true;
|
||||
}
|
||||
if (exif.getThumbnailRange() != null) {
|
||||
if ((outLongs[0] == 0) || (outLongs[1] == 0) || (outLongs[2] == 0)) {
|
||||
Log.d(TAG, "getThumbnailInfo: check thumb info:"
|
||||
@@ -880,6 +909,10 @@ public class MtpDatabase implements AutoCloseable {
|
||||
try {
|
||||
ExifInterface exif = new ExifInterface(path);
|
||||
|
||||
if (mSkipThumbForHost) {
|
||||
Log.d(TAG, "getThumbnailData: Skip runtime thumbnail.");
|
||||
return exif.getThumbnail();
|
||||
}
|
||||
if (exif.getThumbnailRange() != null)
|
||||
return exif.getThumbnail();
|
||||
} catch (IOException e) {
|
||||
|
||||
@@ -169,6 +169,18 @@ public final class MtpDevice {
|
||||
return native_get_device_info();
|
||||
}
|
||||
|
||||
/**
|
||||
* Set device property SESSION_INITIATOR_VERSION_INFO
|
||||
*
|
||||
* @param propertyStr string value for device property SESSION_INITIATOR_VERSION_INFO
|
||||
* @return -1 for error, 0 for success
|
||||
*
|
||||
* {@hide}
|
||||
*/
|
||||
public int setDevicePropertyInitVersion(@NonNull String propertyStr) {
|
||||
return native_set_device_property_init_version(propertyStr);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the list of IDs for all storage units on this device
|
||||
* Information about each storage unit can be accessed via {@link #getStorageInfo}.
|
||||
@@ -421,6 +433,7 @@ public final class MtpDevice {
|
||||
private native boolean native_open(String deviceName, int fd);
|
||||
private native void native_close();
|
||||
private native MtpDeviceInfo native_get_device_info();
|
||||
private native int native_set_device_property_init_version(String propertyStr);
|
||||
private native int[] native_get_storage_ids();
|
||||
private native MtpStorageInfo native_get_storage_info(int storageId);
|
||||
private native int[] native_get_object_handles(int storageId, int format, int objectHandle);
|
||||
|
||||
@@ -31,6 +31,7 @@ public class MtpDeviceInfo {
|
||||
private String mSerialNumber;
|
||||
private int[] mOperationsSupported;
|
||||
private int[] mEventsSupported;
|
||||
private int[] mDevicePropertySupported;
|
||||
|
||||
// only instantiated via JNI
|
||||
private MtpDeviceInfo() {
|
||||
@@ -143,6 +144,21 @@ public class MtpDeviceInfo {
|
||||
return mEventsSupported;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns Device property code supported by the device.
|
||||
*
|
||||
* @return supported Device property code. Can be null if device does not provide the property.
|
||||
*
|
||||
* @see MtpConstants#DEVICE_PROPERTY_SYNCHRONIZATION_PARTNER
|
||||
* @see MtpConstants#DEVICE_PROPERTY_DEVICE_FRIENDLY_NAME
|
||||
* @see MtpConstants#DEVICE_PROPERTY_SESSION_INITIATOR_VERSION_INFO
|
||||
*
|
||||
* {@hide}
|
||||
*/
|
||||
public final @NonNull int[] getDevicePropertySupported() {
|
||||
return mDevicePropertySupported;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns if the given operation is supported by the device or not.
|
||||
* @param code Operation code.
|
||||
@@ -161,6 +177,17 @@ public class MtpDeviceInfo {
|
||||
return isSupported(mEventsSupported, code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns if the given Device property is supported by the device or not.
|
||||
* @param code Device property code.
|
||||
* @return If the given Device property is supported by the device or not.
|
||||
*
|
||||
* {@hide}
|
||||
*/
|
||||
public boolean isDevicePropertySupported(int code) {
|
||||
return isSupported(mDevicePropertySupported, code);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns if the code set contains code.
|
||||
* @hide
|
||||
|
||||
@@ -1131,6 +1131,7 @@ static const PropertyTableEntry kDevicePropertyTable[] = {
|
||||
{ MTP_DEVICE_PROPERTY_IMAGE_SIZE, MTP_TYPE_STR },
|
||||
{ MTP_DEVICE_PROPERTY_BATTERY_LEVEL, MTP_TYPE_UINT8 },
|
||||
{ MTP_DEVICE_PROPERTY_PERCEIVED_DEVICE_TYPE, MTP_TYPE_UINT32 },
|
||||
{ MTP_DEVICE_PROPERTY_SESSION_INITIATOR_VERSION_INFO, MTP_TYPE_STR },
|
||||
};
|
||||
|
||||
bool MtpDatabase::getObjectPropertyInfo(MtpObjectProperty property, int& type) {
|
||||
@@ -1289,6 +1290,7 @@ MtpProperty* MtpDatabase::getDevicePropertyDesc(MtpDeviceProperty property) {
|
||||
switch (property) {
|
||||
case MTP_DEVICE_PROPERTY_SYNCHRONIZATION_PARTNER:
|
||||
case MTP_DEVICE_PROPERTY_DEVICE_FRIENDLY_NAME:
|
||||
case MTP_DEVICE_PROPERTY_SESSION_INITIATOR_VERSION_INFO:
|
||||
writable = true;
|
||||
// fall through
|
||||
FALLTHROUGH_INTENDED;
|
||||
|
||||
@@ -72,6 +72,7 @@ static jfieldID field_deviceInfo_version;
|
||||
static jfieldID field_deviceInfo_serialNumber;
|
||||
static jfieldID field_deviceInfo_operationsSupported;
|
||||
static jfieldID field_deviceInfo_eventsSupported;
|
||||
static jfieldID field_deviceInfo_devicePropertySupported;
|
||||
|
||||
// MtpStorageInfo fields
|
||||
static jfieldID field_storageInfo_storageId;
|
||||
@@ -129,6 +130,8 @@ static void initializeJavaIDs(JNIEnv* env) {
|
||||
GetFieldIDOrDie(env, clazz_deviceInfo, "mOperationsSupported", "[I");
|
||||
field_deviceInfo_eventsSupported =
|
||||
GetFieldIDOrDie(env, clazz_deviceInfo, "mEventsSupported", "[I");
|
||||
field_deviceInfo_devicePropertySupported =
|
||||
GetFieldIDOrDie(env, clazz_deviceInfo, "mDevicePropertySupported", "[I");
|
||||
|
||||
clazz_storageInfo =
|
||||
(jclass)env->NewGlobalRef(FindClassOrDie(env, "android/mtp/MtpStorageInfo"));
|
||||
@@ -377,9 +380,65 @@ android_mtp_MtpDevice_get_device_info(JNIEnv *env, jobject thiz)
|
||||
}
|
||||
}
|
||||
|
||||
assert(deviceInfo->mDeviceProperties);
|
||||
{
|
||||
const size_t size = deviceInfo->mDeviceProperties->size();
|
||||
ScopedLocalRef<jintArray> events(env, static_cast<jintArray>(env->NewIntArray(size)));
|
||||
{
|
||||
ScopedIntArrayRW elements(env, events.get());
|
||||
if (elements.get() == NULL) {
|
||||
ALOGE("Could not create devicePropertySupported element.");
|
||||
return NULL;
|
||||
}
|
||||
for (size_t i = 0; i < size; ++i) {
|
||||
elements[i] = static_cast<int>(deviceInfo->mDeviceProperties->at(i));
|
||||
}
|
||||
env->SetObjectField(info, field_deviceInfo_devicePropertySupported, events.get());
|
||||
}
|
||||
}
|
||||
|
||||
return info;
|
||||
}
|
||||
|
||||
static jint
|
||||
android_mtp_MtpDevice_set_device_property_init_version(JNIEnv *env, jobject thiz,
|
||||
jstring property_str) {
|
||||
MtpDevice* const device = get_device_from_object(env, thiz);
|
||||
|
||||
if (!device) {
|
||||
ALOGD("%s device is null\n", __func__);
|
||||
env->ThrowNew(clazz_io_exception, "Failed to obtain MtpDevice.");
|
||||
return -1;
|
||||
}
|
||||
|
||||
const char *propertyStr = env->GetStringUTFChars(property_str, NULL);
|
||||
if (propertyStr == NULL) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
MtpProperty* property = new MtpProperty(MTP_DEVICE_PROPERTY_SESSION_INITIATOR_VERSION_INFO,
|
||||
MTP_TYPE_STR, true);
|
||||
if (!property) {
|
||||
env->ThrowNew(clazz_io_exception, "Failed to obtain property.");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (property->getDataType() != MTP_TYPE_STR) {
|
||||
env->ThrowNew(clazz_io_exception, "Unexpected property data type.");
|
||||
return -1;
|
||||
}
|
||||
|
||||
property->setCurrentValue(propertyStr);
|
||||
if (!device->setDevicePropValueStr(property)) {
|
||||
env->ThrowNew(clazz_io_exception, "Failed to obtain property value.");
|
||||
return -1;
|
||||
}
|
||||
|
||||
env->ReleaseStringUTFChars(property_str, propertyStr);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static jintArray
|
||||
android_mtp_MtpDevice_get_storage_ids(JNIEnv *env, jobject thiz)
|
||||
{
|
||||
@@ -847,6 +906,8 @@ static const JNINativeMethod gMethods[] = {
|
||||
{"native_close", "()V", (void *)android_mtp_MtpDevice_close},
|
||||
{"native_get_device_info", "()Landroid/mtp/MtpDeviceInfo;",
|
||||
(void *)android_mtp_MtpDevice_get_device_info},
|
||||
{"native_set_device_property_init_version", "(Ljava/lang/String;)I",
|
||||
(void *)android_mtp_MtpDevice_set_device_property_init_version},
|
||||
{"native_get_storage_ids", "()[I", (void *)android_mtp_MtpDevice_get_storage_ids},
|
||||
{"native_get_storage_info", "(I)Landroid/mtp/MtpStorageInfo;",
|
||||
(void *)android_mtp_MtpDevice_get_storage_info},
|
||||
|
||||
Reference in New Issue
Block a user