blob: b3aaed89cf083800b76928ced959d35dc1f1f63a [file] [log] [blame]
Jan Sebechlebsky5cb39962023-11-22 17:33:07 +01001/*
2 * Copyright (C) 2023 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef ANDROID_COMPANION_VIRTUALCAMERA_VIRTUALCAMERARENDERTHREAD_H
18#define ANDROID_COMPANION_VIRTUALCAMERA_VIRTUALCAMERARENDERTHREAD_H
19
20#include <deque>
21#include <future>
22#include <memory>
23#include <thread>
24
25#include "VirtualCameraSessionContext.h"
26#include "aidl/android/hardware/camera/device/ICameraDeviceCallback.h"
Jan Sebechlebsky042d1fb2023-12-12 16:37:00 +010027#include "android/binder_auto_utils.h"
Jan Sebechlebsky5cb39962023-11-22 17:33:07 +010028#include "util/EglDisplayContext.h"
Jan Sebechlebsky042d1fb2023-12-12 16:37:00 +010029#include "util/EglFramebuffer.h"
Jan Sebechlebsky5cb39962023-11-22 17:33:07 +010030#include "util/EglProgram.h"
31#include "util/EglSurfaceTexture.h"
32
33namespace android {
34namespace companion {
35namespace virtualcamera {
36
37// Represents single output buffer of capture request.
38class CaptureRequestBuffer {
39 public:
40 CaptureRequestBuffer(int streamId, int bufferId, sp<Fence> fence = nullptr);
41
42 int getStreamId() const;
43 int getBufferId() const;
44 sp<Fence> getFence() const;
45
46 private:
47 const int mStreamId;
48 const int mBufferId;
49 const sp<Fence> mFence;
50};
51
52// Represents single capture request to fill set of buffers.
53class ProcessCaptureRequestTask {
54 public:
55 ProcessCaptureRequestTask(
56 int frameNumber, const std::vector<CaptureRequestBuffer>& requestBuffers);
57
58 // Returns frame number corresponding to the request.
59 int getFrameNumber() const;
60
61 // Get reference to vector describing output buffers corresponding
62 // to this request.
63 //
64 // Note that the vector is owned by the ProcessCaptureRequestTask instance,
65 // so it cannot be access outside of its lifetime.
66 const std::vector<CaptureRequestBuffer>& getBuffers() const;
67
68 private:
69 const int mFrameNumber;
70 const std::vector<CaptureRequestBuffer> mBuffers;
71};
72
73// Wraps dedicated rendering thread and rendering business with corresponding
74// input surface.
75class VirtualCameraRenderThread {
76 public:
77 // Create VirtualCameraRenderThread instance:
78 // * sessionContext - VirtualCameraSessionContext reference for shared access
79 // to mapped buffers.
80 // * inputWidth - requested width of input surface ("virtual camera sensor")
81 // * inputHeight - requested height of input surface ("virtual camera sensor")
82 // * cameraDeviceCallback - callback for corresponding camera instance
83 // * testMode - when set to true, test pattern is rendered to input surface
84 // before each capture request is processed to simulate client input.
85 VirtualCameraRenderThread(
86 VirtualCameraSessionContext& sessionContext, int inputWidth,
87 int inputHeight,
88 std::shared_ptr<
89 ::aidl::android::hardware::camera::device::ICameraDeviceCallback>
90 cameraDeviceCallback,
91 bool testMode = false);
92
93 ~VirtualCameraRenderThread();
94
95 // Start rendering thread.
96 void start();
97 // Stop rendering thread.
98 void stop();
99
100 // Equeue capture task for processing on render thread.
101 void enqueueTask(std::unique_ptr<ProcessCaptureRequestTask> task)
102 EXCLUDES(mLock);
103
104 // Flush all in-flight requests.
105 void flush() EXCLUDES(mLock);
106
107 // Returns input surface corresponding to "virtual camera sensor".
108 sp<Surface> getInputSurface();
109
110 private:
111 std::unique_ptr<ProcessCaptureRequestTask> dequeueTask() EXCLUDES(mLock);
112
113 // Rendering thread entry point.
114 void threadLoop();
115
116 // Process single capture request task (always called on render thread).
117 void processCaptureRequest(const ProcessCaptureRequestTask& captureRequestTask);
118
119 // Flush single capture request task returning the error status immediately.
120 void flushCaptureRequest(const ProcessCaptureRequestTask& captureRequestTask);
121
122 // TODO(b/301023410) - Refactor the actual rendering logic off this class for
123 // easier testability.
124
125 // Render current image to the BLOB buffer.
126 // If fence is specified, this function will block until the fence is cleared
127 // before writing to the buffer.
128 // Always called on render thread.
129 ndk::ScopedAStatus renderIntoBlobStreamBuffer(const int streamId,
130 const int bufferId,
Jan Sebechlebsky5cb39962023-11-22 17:33:07 +0100131 sp<Fence> fence = nullptr);
132
133 // Render current image to the YCbCr buffer.
134 // If fence is specified, this function will block until the fence is cleared
135 // before writing to the buffer.
136 // Always called on render thread.
137 ndk::ScopedAStatus renderIntoImageStreamBuffer(int streamId, int bufferId,
138 sp<Fence> fence = nullptr);
139
Jan Sebechlebsky042d1fb2023-12-12 16:37:00 +0100140 // Render current image into provided EglFramebuffer.
141 // If fence is specified, this function will block until the fence is cleared
142 // before writing to the buffer.
143 // Always called on the render thread.
144 ndk::ScopedAStatus renderIntoEglFramebuffer(EglFrameBuffer& framebuffer,
145 sp<Fence> fence = nullptr);
146
Jan Sebechlebsky5cb39962023-11-22 17:33:07 +0100147 // Camera callback
148 const std::shared_ptr<
149 ::aidl::android::hardware::camera::device::ICameraDeviceCallback>
150 mCameraDeviceCallback;
151
152 const int mInputSurfaceWidth;
153 const int mInputSurfaceHeight;
154 const int mTestMode;
155
156 VirtualCameraSessionContext& mSessionContext;
157
158 std::thread mThread;
159
160 // Blocking queue implementation.
161 std::mutex mLock;
162 std::deque<std::unique_ptr<ProcessCaptureRequestTask>> mQueue GUARDED_BY(mLock);
163 std::condition_variable mCondVar;
164 volatile bool mPendingExit GUARDED_BY(mLock);
165
166 // EGL helpers - constructed and accessed only from rendering thread.
167 std::unique_ptr<EglDisplayContext> mEglDisplayContext;
Jan Sebechlebsky042d1fb2023-12-12 16:37:00 +0100168 std::unique_ptr<EglTextureProgram> mEglTextureYuvProgram;
169 std::unique_ptr<EglTextureProgram> mEglTextureRgbProgram;
Jan Sebechlebsky5cb39962023-11-22 17:33:07 +0100170 std::unique_ptr<EglSurfaceTexture> mEglSurfaceTexture;
171
172 std::promise<sp<Surface>> mInputSurfacePromise;
173};
174
175} // namespace virtualcamera
176} // namespace companion
177} // namespace android
178
179#endif // ANDROID_COMPANION_VIRTUALCAMERA_VIRTUALCAMERARENDERTHREAD_H