API quản lý vùng đệm HAL3 cho máy ảnh

Android 10 ra mắt tính năng không bắt buộc vùng đệm HAL3 cho máy ảnh các API quản lý giúp bạn triển khai logic quản lý vùng đệm nhằm đạt được các mức bộ nhớ khác nhau và sự đánh đổi độ trễ khi triển khai lớp trừu tượng phần cứng (HAL) cho máy ảnh.

Lớp trừu tượng phần cứng (HAL) cho máy ảnh đòi hỏi N yêu cầu (trong đó N bằng độ sâu của quy trình) đưa vào hàng đợi trong quy trình, nhưng thường không yêu cầu toàn bộ N tập hợp bộ đệm đầu ra cùng một lúc.

Ví dụ: HAL có thể có 8 yêu cầu được đưa vào hàng đợi trong quy trình, nhưng chỉ yêu cầu vùng đệm đầu ra cho hai yêu cầu trong giai đoạn cuối của quy trình. Trên các thiết bị chạy Android 9 trở xuống, khung máy ảnh sẽ phân bổ vùng đệm khi yêu cầu được xếp hàng đợi trong HAL để có thể có 6 tập hợp vùng đệm trong HAL mà không được sử dụng. Trong Android 10, API quản lý vùng đệm HAL3 của máy ảnh cho phép tách đầu ra để giải phóng 6 nhóm bộ đệm. Điều này có thể dẫn đến hàng trăm megabyte bộ nhớ trên các thiết bị cao cấp và cũng có thể có lợi cho thiết bị có bộ nhớ thấp.

Hình 1 cho thấy sơ đồ giao diện HAL của máy ảnh cho các thiết bị đang chạy Android 9 trở xuống. Hình 2 minh hoạ giao diện lớp trừu tượng phần cứng (HAL) của máy ảnh trong Android 10 với triển khai API quản lý vùng đệm HAL3 cho máy ảnh.

Quản lý vùng đệm trong 9 cấp trở xuống

Hình 1. Giao diện HAL (Lớp trừu tượng phần cứng) cho máy ảnh trong Android 9 trở xuống

Quản lý vùng đệm trong Android 10

Hình 2. Giao diện HAL (Lớp trừu tượng phần cứng) cho máy ảnh trong Android 10 sử dụng API quản lý vùng đệm

Triển khai API quản lý vùng đệm

Để triển khai các API quản lý vùng đệm, lớp trừu tượng phần cứng (HAL) của máy ảnh phải:

HAL của máy ảnh sử dụng requestStreamBuffersreturnStreamBuffers trong ICameraDeviceCallback.hal để yêu cầu và trả về vùng đệm. HAL cũng phải triển khai signalStreamFlush phương thức trong ICameraDeviceSession.hal để báo hiệu HAL của máy ảnh để trả về vùng đệm.

requestStreamBuffer

Sử dụng requestStreamBuffers để yêu cầu vùng đệm từ khung máy ảnh. Khi sử dụng máy ảnh HAL3 API quản lý vùng đệm, ghi lại các yêu cầu từ khung máy ảnh sẽ không chứa vùng đệm đầu ra, tức là trường bufferId trong StreamBuffer0. Do đó, lớp trừu tượng phần cứng (HAL) của máy ảnh phải sử dụng requestStreamBuffers để yêu cầu vùng đệm khỏi khung máy ảnh.

Phương thức requestStreamBuffers cho phép phương thức gọi yêu cầu nhiều vùng đệm từ nhiều luồng đầu ra trong một lệnh gọi, cho phép giảm số lượng IPC HIDL cuộc gọi. Tuy nhiên, các lệnh gọi sẽ mất nhiều thời gian hơn khi yêu cầu thêm vùng đệm tại và điều này có thể ảnh hưởng tiêu cực đến tổng độ trễ từ yêu cầu đến kết quả. Ngoài ra, vì các lệnh gọi vào requestStreamBuffers được chuyển đổi tuần tự trong máy ảnh dịch vụ, bạn nên sử dụng lớp trừu tượng phần cứng (HAL) cho máy ảnh bằng chế độ chuyên dụng có mức độ ưu tiên cao luồng để yêu cầu vùng đệm.

Nếu yêu cầu vùng đệm không thành công, thì lớp trừu tượng phần cứng (HAL) của máy ảnh phải có khả năng xử lý đúng cách lỗi không nghiêm trọng. Danh sách sau đây mô tả các lý do phổ biến khiến vùng đệm yêu cầu không thành công và cách xử lý các yêu cầu đó bằng lớp trừu tượng phần cứng (HAL) của máy ảnh.

  • Ứng dụng ngắt kết nối khỏi luồng đầu ra: Đây là lỗi không nghiêm trọng. Lớp trừu tượng phần cứng (HAL) của camera sẽ gửi ERROR_REQUEST cho mọi yêu cầu chụp nhắm mục tiêu đến luồng đã ngắt kết nối và sẵn sàng xử lý các yêu cầu tiếp theo thông thường.
  • Hết thời gian chờ: Điều này có thể xảy ra khi một ứng dụng đang bận thực hiện xử lý chuyên sâu trong khi giữ lại một số vùng đệm. Lớp trừu tượng phần cứng (HAL) của máy ảnh gửi ERROR_REQUEST cho các yêu cầu chụp không thể được thực hiện do hết thời gian chờ và sẵn sàng xử lý các yêu cầu tiếp theo một cách bình thường.
  • Khung máy ảnh đang chuẩn bị một cấu hình phát trực tiếp mới: Lớp trừu tượng phần cứng (HAL) của máy ảnh phải đợi đến configureStreams cuộc gọi đã hoàn tất trước khi gọi lại requestStreamBuffers.
  • Lớp trừu tượng phần cứng (HAL) của camera đã đạt đến giới hạn vùng đệm (trường maxBuffers): Lớp trừu tượng phần cứng (HAL) của máy ảnh phải chờ cho đến khi trả về ít nhất một vùng đệm của luồng trước khi gọi lại requestStreamBuffers.

ReturnStreamBuffers

Sử dụng returnStreamBuffers để trả về vùng đệm bổ sung cho khung máy ảnh. HAL của camera như bình thường trả về vùng đệm cho khung máy ảnh thông qua processCaptureResult nhưng chỉ có thể tính đến các yêu cầu chụp đã được gửi đến lớp trừu tượng phần cứng (HAL) cho máy ảnh. Với phương thức requestStreamBuffers, có thể triển khai lớp trừu tượng phần cứng (HAL) cho máy ảnh để giữ lại nhiều vùng đệm hơn so với yêu cầu của khung máy ảnh. Đây là thời điểm nên sử dụng phương thức returnStreamBuffers đã sử dụng. Nếu việc triển khai HAL không bao giờ chứa nhiều vùng đệm hơn mức yêu cầu, thì Việc triển khai lớp trừu tượng phần cứng (HAL) cho máy ảnh không cần gọi returnStreamBuffers .

tín hiệuStreamFlush

Chiến lược phát hành đĩa đơn signalStreamFlush được khung máy ảnh gọi để thông báo cho lớp trừu tượng phần cứng (HAL) của máy ảnh để trả về tất cả có sẵn. Lệnh này thường được gọi khi khung máy ảnh sắp cuộc gọi configureStreams và phải làm tiêu hao đường ống chụp ảnh của máy ảnh. Tương tự như returnStreamBuffers nếu việc triển khai HAL của máy ảnh không chứa nhiều vùng đệm hơn yêu cầu, thì bạn có thể triển khai phương thức này theo cách trống.

Sau khi khung máy ảnh gọi signalStreamFlush! khung sẽ ngừng gửi các yêu cầu chụp mới đến HAL (Lớp trừu tượng phần cứng) cho máy ảnh cho đến khi vùng đệm đã được trả về khung máy ảnh. Khi tất cả các vùng đệm đều đã trả về, các lệnh gọi phương thức requestStreamBuffers không thành công và máy ảnh khung có thể tiếp tục hoạt động ở trạng thái mới. Sau đó, khung máy ảnh gọi hàm configureStreams hoặc processCaptureRequest . Nếu khung máy ảnh gọi phương thức configureStreams, thì máy ảnh HAL có thể bắt đầu yêu cầu vùng đệm lại sau khi lệnh gọi configureStreams trở về thành công. Nếu khung máy ảnh gọi phương thức processCaptureRequest, lớp trừu tượng phần cứng (HAL) của máy ảnh có thể bắt đầu yêu cầu vùng đệm trong processCaptureRequest .

Ngữ nghĩa của phương thức signalStreamFlush và phương thức là khác nhau flush . Khi phương thức flush được gọi, HAL có thể huỷ quá trình thu thập đang chờ xử lý yêu cầu có ERROR_REQUEST để thoát đường ống càng sớm càng tốt. Thời gian phương thức signalStreamFlush được gọi, HAL phải hoàn tất mọi nội dung đang chờ xử lý ghi lại các yêu cầu một cách bình thường và trả về tất cả vùng đệm cho khung máy ảnh.

Một điểm khác biệt khác giữa phương thức signalStreamFlush và các phương thức khác là signalStreamFlush là phương thức HIDL một chiều, tức là camera khung có thể gọi vào các API chặn khác trước khi HAL nhận được Cuộc gọi signalStreamFlush. Điều này có nghĩa là phương thức signalStreamFlush và các phương thức khác (cụ thể là phương thức configureStreams) có thể đến HAL của máy ảnh theo thứ tự khác so với thứ tự chúng được gọi trong khung máy ảnh. Để giải quyết vấn đề này sự cố không đồng bộ, trường streamConfigCounter đã được thêm vào StreamConfiguration và được thêm làm đối số vào signalStreamFlush . Việc triển khai lớp trừu tượng phần cứng (HAL) cho máy ảnh phải sử dụng streamConfigCounter đối số để xác định xem lệnh gọi signalStreamFlush có đến trễ hơn lệnh gọi configureStreams tương ứng. Xem Hình 3 để biết ví dụ.

Xử lý các cuộc gọi đến trễ

Hình 3. Cách lớp trừu tượng phần cứng (HAL) của máy ảnh sẽ phát hiện và xử lý các lệnh gọi tín hiệuStreamFlush đến trễ

Thay đổi về hành vi khi triển khai API quản lý vùng đệm

Khi sử dụng API quản lý vùng đệm để triển khai logic quản lý vùng đệm, hãy cân nhắc những thay đổi có thể xảy ra sau đây về hành vi của camera và triển khai lớp trừu tượng phần cứng (HAL) cho máy ảnh:

  • Yêu cầu ghi lại đến máy ảnh HAL nhanh hơn và hiệu quả hơn thường xuyên: Nếu không có API quản lý vùng đệm, khung máy ảnh sẽ yêu cầu vùng đệm đầu ra cho mỗi yêu cầu chụp trước khi gửi yêu cầu chụp đến lớp trừu tượng phần cứng (HAL) cho camera. Khi sử dụng API quản lý vùng đệm, khung máy ảnh không còn phải đợi vùng đệm và do đó có thể gửi yêu cầu chụp với máy ảnh HAL trước đó.

    Ngoài ra, nếu không có API quản lý vùng đệm, khung máy ảnh sẽ dừng gửi yêu cầu chụp nếu một trong các luồng đầu ra của bản chụp yêu cầu đã đạt đến số vùng đệm tối đa mà HAL có thể chứa một lần (giá trị này được chỉ định bởi lớp trừu tượng phần cứng (HAL) của máy ảnh trong Trường HalStream::maxBuffers trong giá trị trả về của configureStreams cuộc gọi). Với các API quản lý vùng đệm, hành vi điều tiết này không còn và việc triển khai lớp trừu tượng phần cứng (HAL) cho máy ảnh không được chấp nhận processCaptureRequest gọi khi HAL có quá nhiều yêu cầu chụp đã xếp hàng đợi.

  • Độ trễ của cuộc gọi requestStreamBuffers thay đổi đáng kể: Có nhiều lý do khiến cuộc gọi requestStreamBuffers có thể mất nhiều thời gian hơn trung bình. Ví dụ:

    • Đối với một số vùng đệm đầu tiên của luồng mới tạo, lệnh gọi có thể mất nhiều thời gian hơn vì thiết bị cần phân bổ bộ nhớ.
    • Độ trễ dự kiến tăng tương ứng với số lượng vùng đệm được yêu cầu trong mỗi lệnh gọi.
    • Ứng dụng đang lưu vùng đệm và bận xử lý. Chiến dịch này có thể làm cho các yêu cầu bộ đệm chậm lại hoặc hết thời gian chờ do thiếu bộ đệm hoặc CPU bận.

Chiến lược quản lý vùng đệm

API quản lý vùng đệm cho phép nhiều loại quản lý vùng đệm các chiến lược cần triển khai. Dưới đây là một số ví dụ:

  • Tương thích ngược: HAL yêu cầu vùng đệm cho một yêu cầu chụp trong cuộc gọi processCaptureRequest. Chiến lược này không cung cấp bất kỳ mức tiết kiệm bộ nhớ, nhưng có thể đóng vai trò là phương thức triển khai đầu tiên của vùng đệm các API quản lý, yêu cầu rất ít thay đổi mã đối với lớp trừu tượng phần cứng (HAL) cho máy ảnh hiện có.
  • Tiết kiệm bộ nhớ tối đa: Lớp trừu tượng phần cứng (HAL) của máy ảnh chỉ yêu cầu vùng đệm đầu ra ngay trước khi cần điền một giá trị. Chiến lược này cho phép tiết kiệm bộ nhớ tối đa. Nhược điểm tiềm ẩn là có nhiều đường dẫn camera hơn hiện tượng giật khi các yêu cầu vùng đệm mất nhiều thời gian bất thường để kết thúc.
  • Đã lưu vào bộ nhớ đệm: Lớp trừu tượng phần cứng (HAL) của máy ảnh sẽ lưu vào bộ nhớ đệm một vài vùng đệm để ít có khả năng thỉnh thoảng bị ảnh hưởng bởi một yêu cầu tải chậm.

Lớp trừu tượng phần cứng (HAL) cho máy ảnh có thể áp dụng các chiến lược khác nhau cho các trường hợp sử dụng cụ thể, ví dụ: sử dụng chiến lược tiết kiệm bộ nhớ tối đa cho các trường hợp sử dụng sử dụng nhiều bộ nhớ và sử dụng chiến lược tương thích ngược cho các trường hợp sử dụng khác.

Triển khai mẫu trong lớp trừu tượng phần cứng (HAL) cho máy ảnh bên ngoài

Lớp trừu tượng phần cứng (HAL) cho máy ảnh bên ngoài đã được giới thiệu trong Android 9 và có thể được tìm thấy trong cây nguồn tại hardware/interfaces/camera/device/3.5/. Trên Android 10, tính năng này đã được cập nhật để bao gồm ExternalCameraDeviceSession.cpp! việc triển khai API quản lý vùng đệm. Lớp trừu tượng phần cứng (HAL) cho camera bên ngoài này triển khai chiến lược tiết kiệm bộ nhớ tối đa được đề cập trong phần Quản lý vùng đệm thông qua hàng trăm dòng mã Mã C++.