Merge changes I96f8ad86,I84dcd82e,Ifcece69f
* changes:
SurfaceFlinger and libgui: Support for child layers.
SurfaceFlinger: Use traversal functions to iterate LayerList.
SurfaceFlinger and libgui: Switch Z-order to signed type.
diff --git a/cmds/installd/InstalldNativeService.cpp b/cmds/installd/InstalldNativeService.cpp
index ede31fc..4589241 100644
--- a/cmds/installd/InstalldNativeService.cpp
+++ b/cmds/installd/InstalldNativeService.cpp
@@ -1890,6 +1890,22 @@
return error();
}
+binder::Status InstalldNativeService::removeIdmap(const std::string& overlayApkPath) {
+ const char* overlay_apk = overlayApkPath.c_str();
+ char idmap_path[PATH_MAX];
+
+ if (flatten_path(IDMAP_PREFIX, IDMAP_SUFFIX, overlay_apk,
+ idmap_path, sizeof(idmap_path)) == -1) {
+ ALOGE("idmap cannot generate idmap path for overlay %s\n", overlay_apk);
+ return error();
+ }
+ if (unlink(idmap_path) < 0) {
+ ALOGE("couldn't unlink idmap file %s\n", idmap_path);
+ return error();
+ }
+ return ok();
+}
+
binder::Status InstalldNativeService::restoreconAppData(const std::unique_ptr<std::string>& uuid,
const std::string& packageName, int32_t userId, int32_t flags, int32_t appId,
const std::string& seInfo) {
diff --git a/cmds/installd/InstalldNativeService.h b/cmds/installd/InstalldNativeService.h
index 0a9f12f..c8b5927 100644
--- a/cmds/installd/InstalldNativeService.h
+++ b/cmds/installd/InstalldNativeService.h
@@ -92,6 +92,7 @@
binder::Status idmap(const std::string& targetApkPath, const std::string& overlayApkPath,
int32_t uid);
+ binder::Status removeIdmap(const std::string& overlayApkPath);
binder::Status rmPackageDir(const std::string& packageDir);
binder::Status markBootComplete(const std::string& instructionSet);
binder::Status freeCache(const std::unique_ptr<std::string>& uuid, int64_t freeStorageSize,
diff --git a/cmds/installd/binder/android/os/IInstalld.aidl b/cmds/installd/binder/android/os/IInstalld.aidl
index aa5e4f2..4b1496f 100644
--- a/cmds/installd/binder/android/os/IInstalld.aidl
+++ b/cmds/installd/binder/android/os/IInstalld.aidl
@@ -58,6 +58,7 @@
void destroyAppProfiles(@utf8InCpp String packageName);
void idmap(@utf8InCpp String targetApkPath, @utf8InCpp String overlayApkPath, int uid);
+ void removeIdmap(@utf8InCpp String overlayApkPath);
void rmPackageDir(@utf8InCpp String packageDir);
void markBootComplete(@utf8InCpp String instructionSet);
void freeCache(@nullable @utf8InCpp String uuid, long freeStorageSize, int flags);
diff --git a/include/android/configuration.h b/include/android/configuration.h
index c9f63ae..6287332 100644
--- a/include/android/configuration.h
+++ b/include/android/configuration.h
@@ -465,7 +465,7 @@
* <a href="@dacRoot/guide/topics/resources/providing-resources.html#WideColorGamutQualifier">wide color gamut</a>
* and <a href="@dacRoot/guide/topics/resources/providing-resources.html#HDRQualifier">HDR</a> configurations.
*/
- ACONFIGURATION_COLORIMETRY = 0x10000,
+ ACONFIGURATION_COLOR_MODE = 0x10000,
/**
* Constant used to to represent MNC (Mobile Network Code) zero.
* 0 cannot be used, since it is used to represent an undefined MNC.
diff --git a/include/android/hardware_buffer.h b/include/android/hardware_buffer.h
index a6c832f..24e217e 100644
--- a/include/android/hardware_buffer.h
+++ b/include/android/hardware_buffer.h
@@ -66,7 +66,13 @@
* Vulkan: VK_FORMAT_R16G16B16A16_SFLOAT
* OpenGL ES: GL_RGBA16F
*/
- AHARDWAREBUFFER_FORMAT_R16G16B16A16_SFLOAT = 5,
+ AHARDWAREBUFFER_FORMAT_R16G16B16A16_SFLOAT = 0x16,
+
+ /**
+ * An opaque binary blob format that must have height 1, with width equal to
+ * the buffer size in bytes.
+ */
+ AHARDWAREBUFFER_FORMAT_BLOB = 0x21,
};
enum {
diff --git a/include/gui/IGraphicBufferProducer.h b/include/gui/IGraphicBufferProducer.h
index 304a0c0..258cd2f 100644
--- a/include/gui/IGraphicBufferProducer.h
+++ b/include/gui/IGraphicBufferProducer.h
@@ -385,6 +385,7 @@
uint32_t numPendingBuffers{0};
uint64_t nextFrameNumber{0};
FrameEventHistoryDelta frameTimestamps;
+ bool bufferReplaced{false};
};
virtual status_t queueBuffer(int slot, const QueueBufferInput& input,
diff --git a/include/gui/Surface.h b/include/gui/Surface.h
index 0b6a8f7..4be11b4 100644
--- a/include/gui/Surface.h
+++ b/include/gui/Surface.h
@@ -151,6 +151,9 @@
nsecs_t* outDisplayPresentTime, nsecs_t* outDisplayRetireTime,
nsecs_t* outDequeueReadyTime, nsecs_t* outReleaseTime);
+ status_t getDisplayRefreshCyclePeriod(nsecs_t* outMinRefreshDuration,
+ nsecs_t* outMaxRefreshDuration);
+
status_t getUniqueId(uint64_t* outId) const;
protected:
@@ -207,6 +210,7 @@
int dispatchSetAutoRefresh(va_list args);
int dispatchEnableFrameTimestamps(va_list args);
int dispatchGetFrameTimestamps(va_list args);
+ int dispatchGetDisplayRefreshCyclePeriod(va_list args);
protected:
virtual int dequeueBuffer(ANativeWindowBuffer** buffer, int* fenceFd);
diff --git a/libs/gui/BufferQueueProducer.cpp b/libs/gui/BufferQueueProducer.cpp
index 39b9a0b..3f69b1f 100644
--- a/libs/gui/BufferQueueProducer.cpp
+++ b/libs/gui/BufferQueueProducer.cpp
@@ -879,6 +879,7 @@
mCore->mSharedBufferCache.dataspace = dataSpace;
}
+ output->bufferReplaced = false;
if (mCore->mQueue.empty()) {
// When the queue is empty, we can ignore mDequeueBufferCannotBlock
// and simply queue this buffer
@@ -905,6 +906,7 @@
if (!mSlots[last.mSlot].mBufferState.isShared()) {
mCore->mActiveBuffers.erase(last.mSlot);
mCore->mFreeBuffers.push_back(last.mSlot);
+ output->bufferReplaced = true;
}
}
@@ -1158,6 +1160,7 @@
output->numPendingBuffers =
static_cast<uint32_t>(mCore->mQueue.size());
output->nextFrameNumber = mCore->mFrameCounter + 1;
+ output->bufferReplaced = false;
if (listener != NULL) {
// Set up a death notification so that we can disconnect
diff --git a/libs/gui/IGraphicBufferProducer.cpp b/libs/gui/IGraphicBufferProducer.cpp
index 18a80e8..abdf649 100644
--- a/libs/gui/IGraphicBufferProducer.cpp
+++ b/libs/gui/IGraphicBufferProducer.cpp
@@ -831,7 +831,8 @@
sizeof(height) +
sizeof(transformHint) +
sizeof(numPendingBuffers) +
- sizeof(nextFrameNumber);
+ sizeof(nextFrameNumber) +
+ sizeof(bufferReplaced);
}
size_t IGraphicBufferProducer::QueueBufferOutput::getFlattenedSize() const {
@@ -854,6 +855,7 @@
FlattenableUtils::write(buffer, size, transformHint);
FlattenableUtils::write(buffer, size, numPendingBuffers);
FlattenableUtils::write(buffer, size, nextFrameNumber);
+ FlattenableUtils::write(buffer, size, bufferReplaced);
return frameTimestamps.flatten(buffer, size, fds, count);
}
@@ -870,6 +872,7 @@
FlattenableUtils::read(buffer, size, transformHint);
FlattenableUtils::read(buffer, size, numPendingBuffers);
FlattenableUtils::read(buffer, size, nextFrameNumber);
+ FlattenableUtils::read(buffer, size, bufferReplaced);
return frameTimestamps.unflatten(buffer, size, fds, count);
}
diff --git a/libs/gui/Surface.cpp b/libs/gui/Surface.cpp
index c859828..851a495 100644
--- a/libs/gui/Surface.cpp
+++ b/libs/gui/Surface.cpp
@@ -28,6 +28,7 @@
#include <ui/Fence.h>
#include <ui/Region.h>
+#include <ui/DisplayStatInfo.h>
#include <gui/IProducerListener.h>
#include <gui/ISurfaceComposer.h>
@@ -261,6 +262,18 @@
return NO_ERROR;
}
+status_t Surface::getDisplayRefreshCyclePeriod(nsecs_t* outMinRefreshDuration,
+ nsecs_t* outMaxRefreshDuration) {
+ ATRACE_CALL();
+
+ DisplayStatInfo stats;
+ status_t err = composerService()->getDisplayStats(NULL, &stats);
+
+ *outMinRefreshDuration = stats.vsyncPeriod;
+ *outMaxRefreshDuration = stats.vsyncPeriod;
+
+ return NO_ERROR;
+}
int Surface::hook_setSwapInterval(ANativeWindow* window, int interval) {
Surface* c = getSelf(window);
@@ -828,6 +841,9 @@
case NATIVE_WINDOW_GET_FRAME_TIMESTAMPS:
res = dispatchGetFrameTimestamps(args);
break;
+ case NATIVE_WINDOW_GET_REFRESH_CYCLE_PERIOD:
+ res = dispatchGetDisplayRefreshCyclePeriod(args);
+ break;
default:
res = NAME_NOT_FOUND;
break;
@@ -973,6 +989,13 @@
outDisplayRetireTime, outDequeueReadyTime, outReleaseTime);
}
+int Surface::dispatchGetDisplayRefreshCyclePeriod(va_list args) {
+ nsecs_t* outMinRefreshDuration = va_arg(args, int64_t*);
+ nsecs_t* outMaxRefreshDuration = va_arg(args, int64_t*);
+ return getDisplayRefreshCyclePeriod(outMinRefreshDuration,
+ outMaxRefreshDuration);
+}
+
int Surface::connect(int api) {
static sp<IProducerListener> listener = new DummyProducerListener();
return connect(api, listener);
diff --git a/libs/gui/tests/BufferQueue_test.cpp b/libs/gui/tests/BufferQueue_test.cpp
index 98c0449..91ce531 100644
--- a/libs/gui/tests/BufferQueue_test.cpp
+++ b/libs/gui/tests/BufferQueue_test.cpp
@@ -1076,4 +1076,45 @@
}
}
+TEST_F(BufferQueueTest, TestBufferReplacedInQueueBuffer) {
+ createBufferQueue();
+ sp<DummyConsumer> dc(new DummyConsumer);
+ ASSERT_EQ(OK, mConsumer->consumerConnect(dc, true));
+ IGraphicBufferProducer::QueueBufferOutput output;
+ ASSERT_EQ(OK, mProducer->connect(new DummyProducerListener,
+ NATIVE_WINDOW_API_CPU, true, &output));
+ ASSERT_EQ(OK, mConsumer->setMaxAcquiredBufferCount(1));
+
+ int slot = BufferQueue::INVALID_BUFFER_SLOT;
+ sp<Fence> fence = Fence::NO_FENCE;
+ sp<GraphicBuffer> buffer = nullptr;
+ IGraphicBufferProducer::QueueBufferInput input(0ull, true,
+ HAL_DATASPACE_UNKNOWN, Rect::INVALID_RECT,
+ NATIVE_WINDOW_SCALING_MODE_FREEZE, 0, Fence::NO_FENCE);
+ BufferItem item{};
+
+ // Preallocate, dequeue, request, and cancel 2 buffers so we don't get
+ // BUFFER_NEEDS_REALLOCATION below
+ int slots[2] = {};
+ ASSERT_EQ(OK, mProducer->setMaxDequeuedBufferCount(2));
+ for (size_t i = 0; i < 2; ++i) {
+ status_t result = mProducer->dequeueBuffer(&slots[i], &fence,
+ 0, 0, 0, 0, nullptr);
+ ASSERT_EQ(IGraphicBufferProducer::BUFFER_NEEDS_REALLOCATION, result);
+ ASSERT_EQ(OK, mProducer->requestBuffer(slots[i], &buffer));
+ }
+ for (size_t i = 0; i < 2; ++i) {
+ ASSERT_EQ(OK, mProducer->cancelBuffer(slots[i], Fence::NO_FENCE));
+ }
+
+ // Fill 2 buffers without consumer consuming them. Verify that all
+ // queued buffer returns proper bufferReplaced flag
+ ASSERT_EQ(OK, mProducer->dequeueBuffer(&slot, &fence, 0, 0, 0, 0, nullptr));
+ ASSERT_EQ(OK, mProducer->queueBuffer(slot, input, &output));
+ ASSERT_EQ(false, output.bufferReplaced);
+ ASSERT_EQ(OK, mProducer->dequeueBuffer(&slot, &fence, 0, 0, 0, 0, nullptr));
+ ASSERT_EQ(OK, mProducer->queueBuffer(slot, input, &output));
+ ASSERT_EQ(true, output.bufferReplaced);
+}
+
} // namespace android
diff --git a/services/sensorservice/SensorDevice.cpp b/services/sensorservice/SensorDevice.cpp
index 41ad918..de0321d 100644
--- a/services/sensorservice/SensorDevice.cpp
+++ b/services/sensorservice/SensorDevice.cpp
@@ -491,6 +491,11 @@
}
int32_t SensorDevice::registerDirectChannel(const sensors_direct_mem_t* memory) {
+
+ if (!isDirectReportSupported()) {
+ return INVALID_OPERATION;
+ }
+
Mutex::Autolock _l(mLock);
int32_t channelHandle = mSensorDevice->register_direct_channel(
@@ -506,6 +511,11 @@
int32_t SensorDevice::configureDirectChannel(int32_t sensorHandle, int32_t channelHandle,
const struct sensors_direct_cfg_t *config) {
+
+ if (!isDirectReportSupported()) {
+ return INVALID_OPERATION;
+ }
+
Mutex::Autolock _l(mLock);
int32_t ret = mSensorDevice->config_direct_report(
@@ -513,6 +523,12 @@
ALOGE_IF(ret < 0, "SensorDevice::configureDirectChannel ret %d", ret);
return ret;
}
+
+bool SensorDevice::isDirectReportSupported() const {
+ bool ret = mSensorDevice->register_direct_channel != nullptr
+ && mSensorDevice->config_direct_report != nullptr;
+ return ret;
+}
// ---------------------------------------------------------------------------
}; // namespace android
diff --git a/services/sensorservice/SensorDevice.h b/services/sensorservice/SensorDevice.h
index b6886a2..7dd256a 100644
--- a/services/sensorservice/SensorDevice.h
+++ b/services/sensorservice/SensorDevice.h
@@ -59,6 +59,7 @@
status_t flush(void* ident, int handle);
status_t setMode(uint32_t mode);
+ bool isDirectReportSupported() const;
int32_t registerDirectChannel(const sensors_direct_mem_t *memory);
void unregisterDirectChannel(int32_t channelHandle);
int32_t configureDirectChannel(int32_t sensorHandle,
@@ -147,6 +148,8 @@
const hardware::hidl_vec<Event> &src,
const hardware::hidl_vec<SensorInfo> &dynamicSensorsAdded,
sensors_event_t *dst);
+
+ bool mIsDirectReportSupported;
#endif // ENABLE_TREBLE
};
diff --git a/services/sensorservice/SensorDeviceTreble.cpp b/services/sensorservice/SensorDeviceTreble.cpp
index 0a75400..3edd50b 100644
--- a/services/sensorservice/SensorDeviceTreble.cpp
+++ b/services/sensorservice/SensorDeviceTreble.cpp
@@ -77,6 +77,9 @@
mSensors->activate(list[i].sensorHandle, 0 /* enabled */);
}
});
+
+ mIsDirectReportSupported =
+ (mSensors->unregisterDirectChannel(-1) != Result::INVALID_OPERATION);
}
void SensorDevice::handleDynamicSensorConnection(int handle, bool connected) {
@@ -581,6 +584,10 @@
return ret;
}
+bool SensorDevice::isDirectReportSupported() const {
+ return mIsDirectReportSupported;
+}
+
void SensorDevice::convertToSensorEvent(
const Event &src, sensors_event_t *dst) {
::android::hardware::sensors::V1_0::implementation::convertToSensorEvent(
diff --git a/services/sensorservice/SensorFusion.cpp b/services/sensorservice/SensorFusion.cpp
index 9863f62..414f673 100644
--- a/services/sensorservice/SensorFusion.cpp
+++ b/services/sensorservice/SensorFusion.cpp
@@ -163,7 +163,7 @@
}
mSensorDevice.batch(ident, mAcc.getHandle(), 0, ns, 0);
if (mode != FUSION_NOMAG) {
- mSensorDevice.batch(ident, mMag.getHandle(), 0, ms2ns(20), 0);
+ mSensorDevice.batch(ident, mMag.getHandle(), 0, ms2ns(10), 0);
}
if (mode != FUSION_NOGYRO) {
mSensorDevice.batch(ident, mGyro.getHandle(), 0, mTargetDelayNs, 0);
diff --git a/vulkan/libvulkan/swapchain.cpp b/vulkan/libvulkan/swapchain.cpp
index 243ea69..08eee37 100644
--- a/vulkan/libvulkan/swapchain.cpp
+++ b/vulkan/libvulkan/swapchain.cpp
@@ -196,11 +196,22 @@
num_images(num_images_),
frame_timestamps_enabled(false) {
timing.clear();
+ ANativeWindow* window = surface.window.get();
+ int64_t min_rdur;
+ int64_t max_rdur;
+ native_window_get_refresh_cycle_period(
+ window,
+ &min_rdur,
+ &max_rdur);
+ min_refresh_duration = static_cast<uint64_t>(min_rdur);
+ max_refresh_duration = static_cast<uint64_t>(max_rdur);
}
Surface& surface;
uint32_t num_images;
bool frame_timestamps_enabled;
+ uint64_t min_refresh_duration;
+ uint64_t max_refresh_duration;
struct Image {
Image() : image(VK_NULL_HANDLE), dequeue_fence(-1), dequeued(false) {}
@@ -345,9 +356,7 @@
// timestamps to calculate the info that should
// be reported to the user:
//
- // FIXME: GET ACTUAL VALUE RATHER THAN HARD-CODE
- // IT:
- ti->calculate(16666666);
+ ti->calculate(swapchain.min_refresh_duration);
num_ready++;
}
break;
@@ -1274,13 +1283,13 @@
VKAPI_ATTR
VkResult GetRefreshCycleDurationGOOGLE(
VkDevice,
- VkSwapchainKHR,
+ VkSwapchainKHR swapchain_handle,
VkRefreshCycleDurationGOOGLE* pDisplayTimingProperties) {
+ Swapchain& swapchain = *SwapchainFromHandle(swapchain_handle);
VkResult result = VK_SUCCESS;
- // TODO(ianelliott): FULLY IMPLEMENT THIS FUNCTION!!!
- pDisplayTimingProperties->minRefreshDuration = 16666666;
- pDisplayTimingProperties->maxRefreshDuration = 16666666;
+ pDisplayTimingProperties->minRefreshDuration = swapchain.min_refresh_duration;
+ pDisplayTimingProperties->maxRefreshDuration = swapchain.max_refresh_duration;
return result;
}