همه قالبهای پیکسل جدید اضافهشده به Android باید در زبان تعریف واسط Android (AIDL) و در بافر سختافزار Android (AHB) گنجانده شوند. AIDL و AHB الزامات پایداری و استانداردسازی سختگیرانهای دارند که فرایند دقیقی را هنگام گسترش عملکرد ضروری میسازد. همه قالبهای پیکسل جدید باید در AOSP قرار بگیرند و همه بهروزرسانیها باید بهطور جداگانه توسط کارشناسان AIDL و AHB تأیید شوند. این فرایند تأیید دقیق عامل مهمی در استانداردسازی هر قالب پیکسل جدید در پلاتفرم است.
این صفحه تغییرات لازم در کد AOSP و فرایند موردنیاز برای افزودن قالبهای پیکسل جدید در AOSP را شرح میدهد.
قبلاز افزودن قالب پیکسل جدید، منبع را بارگیری کنید و وصلهها را همانطور که در ارسال وصلهها شرح داده شده است بارگذاری کنید.
افزودن قالب پیکسل جدید به AIDL
افزودن پشتیبانی از قالب پیکسل جدید مستلزم تغییر در هر دو فایل
PixelFormat.aidl واقع در AIDL است. برای کد منبع AIDL، به
hardware/interfaces/graphics/common/aidl/
مراجعه کنید.
برای افزودن قالب پیکسل جدید به AIDL، این مراحل را دنبال کنید:
- قالب پیکسل جدید را بهعنوان ورودی جدید به انتهای شمارش
PixelFormatدرPixelFormat.aidlبا پیروی از قرارداد کد موجود و تنظیم مقدار هگز برای ورودی خود بهگونهای که یک واحد بیشتر از ورودی قبلی باشد، اضافه کنید. تغییرات کدتان را با ورودیهای قبلی مطابقت دهید. برای ورودی قالب پیکسلRGBA_8888، مثال زیر را ببینید:/** * 32-bit format that has 8-bit R, G, B, and A components, in that order, * from the lowest memory address to the highest memory address. * * The component values are unsigned normalized to the range [0, 1], whose * interpretation is defined by the dataspace. */ RGBA_8888 = 0x1,
وقتی کد را پساز ایجاد تغییرات در
PixelFormat.aidlمیسازید، پیام خطای زیر را میبینید:android_developer:~/android/aosp-android-latest-release: m ... ############################################################################### # ERROR: AIDL API change detected # ############################################################################### Above AIDL file(s) has changed. Run `m android.hardware.graphics.common-update-api` to reflect the changes to the current version so that it is reviewed by android-aidl-api-council@google.com And then you need to change dependency on android.hardware.graphics.common-V(n)-* to android.hardware.graphics.common-V(n+1)-* to use new APIs.
-
برای پاک کردن این خطا، فرمان زیر را، همانطور که در پیام خطا مشخص شده است، اجرا کنید تا
PixelFormat.aidlدر دایرکتوریaidl_apiتغییر کند:m android.hardware.graphics.common-update-api
اجرای دستور بالا فایل صحیح را بهروز میکند تا بتوانید بهطور معمول بسازید.
افزودن قالب پیکسل جدید به AHB
افزودن پشتیبانی برای قالب پیکسل جدید نیازمند تغییراتی در
hardware_buffer.h
و AHardwareBuffer.cpp است.
برای کد منبع AHB،
frameworks/native/libs/nativewindow را ببینید.
برای افزودن قالب پیکسل جدید به AHB، این مراحل را دنبال کنید:
- در
hardware_buffer.h، قالب پیکسل جدید را بهعنوان ورودی جدید به انتهای عدد ثابتAHardwareBuffer_Formatاضافه کنید. از قراردادهای کد موجود پیروی کنید.بااستفاده از مثال قالب پیکسل
RGBA_8888، ورودی قالب پیکسل جدید را بهصورت زیر اضافه کنید:/** * Corresponding formats: * Vulkan: VK_FORMAT_R8G8B8A8_UNORM * OpenGL ES: GL_RGBA8 */ AHARDWAREBUFFER_FORMAT_R8G8B8A8_UNORM = 1,
توجه داشته باشید که قالب پیکسل جدید در AHB نامی دارد که باید با
AHARDWAREBUFFER_FORMAT_شروع شود، سپس مخففهای کانال و عمق بیت بیاید، و در آخر با کدبندی تمام شود. این ورودی شمارشی باید مقدار هگز یکسانی با مقدار هگز موجود درPixelFormat.aidlداشته باشد.انتظار میرود قالب پیکسل دارای یک یا هر دو قالب مرتبط Vulkan یا OpenGL ES باشد. درصورت لزوم، قالب مرتبط را مشخص کنید. اگر قالب مرتبطی وجود ندارد،
N/Aرا مشخص کنید. -
اگر قالب پیکسل دارای قالب OpenGL ES مرتبط است، آن را به آزمایش اختیاری تحت CTS اضافه کنید. برای انجام این کار، قالب GL جدید را به
AHardwareBufferGLTest.cppدرAHBFormatAsString(int32_t format)باFORMAT_CASE(...)وGL_FORMAT_CASE(...)برای قالب جدید اضافه کنید، که بهصورت زیر نشان داده شده است:const char* AHBFormatAsString(int32_t format) { switch (format) { ... FORMAT_CASE(R8G8B8A8_UNORM); ... GL_FORMAT_CASE(GL_RGB8); } return ""; } -
سپس، آزمایش جدیدی به
AHardwareBufferGLTest.cppاضافه کنید، که بهصورت زیر نشان داده میشود:class RGBA8Test : public AHardwareBufferGLTest {}; // Verify that if we can allocate an RGBA8 AHB we can render to it. TEST_P(RGBA8Test, Write) { AHardwareBuffer_Desc desc = GetParam(); desc.usage = AHARDWAREBUFFER_USAGE_GPU_FRAMEBUFFER; if (!SetUpBuffer(desc)) { return; } ASSERT_NO_FATAL_FAILURE(SetUpFramebuffer(desc.width, desc.height, 0, kBufferAsRenderbuffer)); ASSERT_NO_FATAL_FAILURE( SetUpProgram(kVertexShader, kColorFragmentShader, kPyramidPositions, 0.5f)); glDrawArrays(GL_TRIANGLES, 0, kPyramidVertexCount); ASSERT_EQ(GLenum{GL_NO_ERROR}, glGetError()); } INSTANTIATE_TEST_CASE_P( SingleLayer, RGBA8Test, ::testing::Values( AHardwareBuffer_Desc{57, 33, 1, AHARDWAREBUFFER_FORMAT_R16G16_UINT, 0, 0, 0, 0}), &GetTestName);حداقل یک مجموعه از
AHardwareBuffer_Descمقدار را مشخص کنید. درصورت نیاز، مقادیر بیشتری اضافه کنید. -
در
AHardwareBuffer.cpp، پایان ادعاهای ایستا را که در اینجا پیدا شده است پیدا کنید:// ---------------------------------------------------------------------------- // Validate hardware_buffer.h and PixelFormat.aidl agree // ----------------------------------------------------------------------------
بااستفاده از تعداد ثابت
HAL_PIXEL_FORMATو نه با شمارشPixelFormat::، یکstatic_assertجدید برای قالب پیکسل جدید اضافه کنید. بااستفاده از همان مثال برای قالب پیکسلRGBA_8888از قالب پیکسل جدیدی به AIDL اضافه کنید، ورودی قالب پیکسل جدید را بهصورت زیر اضافه کنید:static_assert(static_cast
(aidl::android::hardware::graphics::common::PixelFormat::RGBA_8888) == AHARDWAREBUFFER_FORMAT_R8G8B8A8_UNORM, "HAL and AHardwareBuffer pixel format don't match"); -
با افزودن قالب پیکسل جدید به انتهای
PrintAhbFormat()درAHardwareBufferTest.cpp، قالب پیکسل جدید را به آزمایشهای مناسب اضافه کنید. از قرارداد کد موجود، همانطور که در زیر نشان داده شده است، پیروی کنید:void PrintAhbFormat(std::ostream& os, uint64_t format) { switch (format) { ... FORMAT_CASE(R8G8B8A8_UNORM); default: os << "unknown"; break; } } -
با افزودن ورودی جدید به
@IntDef، قالب پیکسل جدید را به کیت توسعه نرمافزارHardwareBufferدرHardwareBuffer.javaاضافه کنید: برای مثال، ورودی قالبRGBA_8888بهصورت زیر نشان داده میشود:@Retention(RetentionPolicy.SOURCE) @IntDef(prefix = { "RGB", "BLOB", "YCBCR_", "D_", "DS_", "S_" }, value = { ... RGBA_8888, })اگر مقادیر عنصر بدون علامت نرمالسازیشده نیستند، مقدار را بهطور صریح در نام متغیر نشان دهید. برای مثال، نام متغیر برای قالب فقط کانال قرمز ۱۶ بیتی عدد صحیح بدون علامت باید
R_16UIباشد، و همان قالب با قالب کانال سبز ۱۶ بیتی عدد صحیح بدون علامت اضافی بایدRG_16UI16UIباشد. -
قالب پیکسل جدید را بهعنوان
static intدرHardwareBuffer.javaاضافه کنید با افزودن متغیر عضو عمومی جدید در انتهای@Format:@Format ... /** Format: 8 bits each red, green, blue, alpha */ public static final int RGBA_8888 = 0x1;
این ورودی شمارشی باید مقدار شانزدهشانزدهی یکسانی با مقدار
PixelFormat.aidlوhardware_buffer.hداشته باشد. از قراردادهای موجود پیروی کنید. -
تلاش برای ساخت با این تغییرات کد، خطای ساخت ایجاد میکند:
android_developer:~/android/aosp-android-latest-release: m ... ****************************** You have tried to change the API from what has been previously approved. To make these errors go away, you have two choices: 1. You can add '@hide' javadoc comments (and remove @SystemApi/@TestApi/etc) to the new methods, etc. shown in the above diff. 2. You can update current.txt and/or removed.txt by executing the following command: m api-stubs-docs-non-updatable-update-current-api To submit the revised current.txt to the main Android repository, you will need approval. ****************************** ...برای پاک کردن این خطا، فرمان زیر را، همانطور که در پیام خطا مشخص شده است، اجرا کنید تا
current.txtتغییر کند:m api-stubs-docs-non-updatable-update-current-api
اجرای دستور بالا فایل صحیح را بهروز میکند تا بتوانید بهطور معمول بسازید.
-
قالب پیکسل جدید را با افزودن قالب پیکسل جدید به انتهای
paramsForTestCreateOptionalFormats()درHardwareBufferTest.javaبه آزمایشهای Java اضافه کنید، بهصورت زیر نشان داده شده است:private static Object[] paramsForTestCreateOptionalFormats() { return new Integer[]{ HardwareBuffer.RGBA_8888 };
افزودن قالب پیکسل جدید به یکپارچهسازی «سیستم پنجره»
برای استفاده از قالب پیکسل جدید بهعنوان قالب یک قاببافر در یک میانای برنامهسازی کاربردی گرافیکی، آن را به «یکپارچهسازی سیستم پنجره» (WSI) مناسب برای میانای برنامهسازی کاربردی گرافیکی مربوطه اضافه کنید. برای برنامه یا فرایند سیستمی که از Vulkan API استفاده میکند، Vulkan Swapchain را بهروز کنید. برای برنامه یا فرایند سیستمی که از OpenGL ES API استفاده میکند، EGL API را بهروز کنید.
تغییرات Vulkan WSI برای قالبهای پیکسل جدید
Vulkan WSI را بهصورت زیر بهروز کنید:
-
افزودن مورد جدید به تابع
GetNativePixelFormat(VkFormat format)درswapchain.cpp:android::PixelFormat GetNativePixelFormat(VkFormat format) { ... switch (format) { ... case VK_FORMAT_R8G8B8A8_UNORM: native_format = PixelFormat::RGBA_8888; break; ... default: ALOGV("unsupported swapchain format %d", format); break; } return native_format; } - اگر قالب پیکسل برای عملکرد به افزونه Vulkan نیاز دارد، افزونه Vulkan را پُرسمان کنید.
برای نمونه، برای افزونههای کناری، از
instance_dataاستفاده کنید، که بهصورت زیر نشان داده میشود:bool colorspace_ext = instance_data.hook_extensions.test(ProcHook::EXT_swapchain_colorspace);
برای افزونههای سمت دستگاه، از موارد زیر استفاده کنید:
bool rgba10x6_formats_ext = false; uint32_t exts_count; const auto& driver = GetData(pdev).driver; driver.EnumerateDeviceExtensionProperties(pdev, nullptr, &exts_count, nullptr); std::vectorprops(exts_count); driver.EnumerateDeviceExtensionProperties(pdev, nullptr, &exts_count, props.data()); for (uint32_t i = 0; i < exts_count; i++) { VkExtensionProperties prop = props[i]; if (strcmp(prop.extensionName, VK_EXT_RGBA10X6_FORMATS_EXTENSION_NAME) == 0) { rgba10x6_formats_ext = true; } } Google زیرساخت لازم برای نمایان کردن نمونه یا افزونه دستگاه را برای
swapchain.cppمدیریت میکند. فهرست تغییرات اولیه برای راهاندازی صحیح افزونهها از بارکننده Vulkan لازم نیست. - سپس، جفتهای قالب و فضای رنگ را فهرست کنید:
desc.format = AHARDWAREBUFFER_FORMAT_R10G10B10A10_UNORM; if (AHardwareBuffer_isSupported(&desc) && rgba10x6_formats_ext) { all_formats.emplace_back( VkSurfaceFormatKHR{VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16, VK_COLOR_SPACE_SRGB_NONLINEAR_KHR}); if (colorspace_ext) { all_formats.emplace_back( VkSurfaceFormatKHR{VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16, VK_COLOR_SPACE_PASS_THROUGH_EXT}); all_formats.emplace_back( VkSurfaceFormatKHR{VK_FORMAT_R10X6G10X6B10X6A10X6_UNORM_4PACK16, VK_COLOR_SPACE_DISPLAY_P3_NONLINEAR_EXT}); }باید از جفتهای قالب و فضای رنگی سازگار اطلاع داشته باشید.
- قالب جدید را به
dEQP-VKواقع درexternal/deqpاضافه کنید. - «آزمونهای مطابقت Vulkan» را در
vktApiExternalMemoryTests.cppوvktExternalMemoryUtil.cppبا استنباط تغییرات لازم از منبع موجود یا تماس با پشتیبانی Android برای کسب اطلاعات بهروز کنید.
تغییرات EGL برای قالبهای پیکسل جدید
«فهرست استثناهای جهانی» را بهصورت زیر بهروز کنید:
- در تابع
getNativePixelFormat()، درختif-elseرا اصلاح کنید تا شمارش AIDL را برای قالب پیکسل جدید برگرداند.بااستفاده از مثال برای قالب پیکسل
RGBA_8888:if (a == 0) { ... } else { if (componentType == EGL_COLOR_COMPONENT_TYPE_FIXED_EXT) { if (colorDepth > 24) { ... } else { *format = PixelFormat::RGBA_8888; } } else { ... } } - برای افزودن قالب جدید به dEQP، ورودی جدیدی به
androidFormatsenum اضافه کنید، که بهصورت زیر نشان داده شده است:static const GLenum androidFormats[] = { ... GL_RGBA8, ... };
ارسال بهروزرسانی
برای همیاران را دنبال کنید تا فهرستهای تغییراتتان را ایجاد کنید و آنها را با تیم مناسب همرسانی کنید.