• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /******************************************************************************
2  *
3  * Copyright (C) 2021 The Android Open Source Project
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at:
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  *****************************************************************************
18  * Originally developed and contributed by Ittiam Systems Pvt. Ltd, Bangalore
19  */
20 
21 #define LOG_TAG "CameraServiceFuzzer"
22 //#define LOG_NDEBUG 0
23 
24 #include <CameraService.h>
25 #include <device3/Camera3StreamInterface.h>
26 #include <android/hardware/BnCameraServiceListener.h>
27 #include <android/hardware/camera2/BnCameraDeviceCallbacks.h>
28 #include <android/hardware/ICameraServiceListener.h>
29 #include <android/hardware/camera2/ICameraDeviceUser.h>
30 #include <camera/camera2/OutputConfiguration.h>
31 #include <gui/BufferItemConsumer.h>
32 #include <gui/IGraphicBufferProducer.h>
33 #include <gui/Surface.h>
34 #include <gui/SurfaceComposerClient.h>
35 #include <private/android_filesystem_config.h>
36 #include "fuzzer/FuzzedDataProvider.h"
37 
38 using namespace android;
39 using namespace hardware;
40 using namespace std;
41 
42 const int32_t kPreviewThreshold = 8;
43 const int32_t kNumRequestsTested = 8;
44 const nsecs_t kPreviewTimeout = 5000000000;  // .5 [s.]
45 const nsecs_t kEventTimeout = 10000000000;   // 1 [s.]
46 const size_t kMaxNumLines = USHRT_MAX;
47 const size_t kMinArgs = 1;
48 const size_t kMaxArgs = 5;
49 const int32_t kCamType[] = {hardware::ICameraService::CAMERA_TYPE_BACKWARD_COMPATIBLE,
50                             hardware::ICameraService::CAMERA_TYPE_ALL};
51 const int kCameraApiVersion[] = {android::CameraService::API_VERSION_1,
52                                  android::CameraService::API_VERSION_2};
53 const uint8_t kSensorPixelModes[] = {ANDROID_SENSOR_PIXEL_MODE_DEFAULT,
54         ANDROID_SENSOR_PIXEL_MODE_MAXIMUM_RESOLUTION};
55 const int32_t kRequestTemplates[] = {
56     hardware::camera2::ICameraDeviceUser::TEMPLATE_PREVIEW,
57     hardware::camera2::ICameraDeviceUser::TEMPLATE_STILL_CAPTURE,
58     hardware::camera2::ICameraDeviceUser::TEMPLATE_RECORD,
59     hardware::camera2::ICameraDeviceUser::TEMPLATE_VIDEO_SNAPSHOT,
60     hardware::camera2::ICameraDeviceUser::TEMPLATE_MANUAL,
61     hardware::camera2::ICameraDeviceUser::TEMPLATE_ZERO_SHUTTER_LAG
62 };
63 
64 const int32_t kRotations[] = {
65     camera3::CAMERA_STREAM_ROTATION_0,
66     camera3::CAMERA_STREAM_ROTATION_90,
67     camera3::CAMERA_STREAM_ROTATION_270
68 };
69 
70 const int kLayerMetadata[] = {
71     0x00100000 /*GRALLOC_USAGE_RENDERSCRIPT*/, 0x00000003 /*GRALLOC_USAGE_SW_READ_OFTEN*/,
72     0x00000100 /*GRALLOC_USAGE_HW_TEXTURE*/,   0x00000800 /*GRALLOC_USAGE_HW_COMPOSER*/,
73     0x00000200 /*GRALLOC_USAGE_HW_RENDER*/,    0x00010000 /*GRALLOC_USAGE_HW_VIDEO_ENCODER*/};
74 const int kCameraMsg[] = {0x001 /*CAMERA_MSG_ERROR*/,
75                           0x002 /*CAMERA_MSG_SHUTTER*/,
76                           0x004 /*CAMERA_MSG_FOCUS*/,
77                           0x008 /*CAMERA_MSG_ZOOM*/,
78                           0x010 /*CAMERA_MSG_PREVIEW_FRAME*/,
79                           0x020 /*CAMERA_MSG_VIDEO_FRAME */,
80                           0x040 /*CAMERA_MSG_POSTVIEW_FRAME*/,
81                           0x080 /*CAMERA_MSG_RAW_IMAGE */,
82                           0x100 /*CAMERA_MSG_COMPRESSED_IMAGE*/,
83                           0x200 /*CAMERA_MSG_RAW_IMAGE_NOTIFY*/,
84                           0x400 /*CAMERA_MSG_PREVIEW_METADATA*/,
85                           0x800 /*CAMERA_MSG_FOCUS_MOVE*/};
86 const int32_t kEventId[] = {ICameraService::EVENT_USER_SWITCHED, ICameraService::EVENT_NONE};
87 const android::CameraService::sound_kind kSoundKind[] = {
88     android::CameraService::SOUND_SHUTTER, android::CameraService::SOUND_RECORDING_START,
89     android::CameraService::SOUND_RECORDING_STOP};
90 const String16 kShellCmd[] = {String16("set-uid-state"),       String16("reset-uid-state"),
91                               String16("get-uid-state"),       String16("set-rotate-and-crop"),
92                               String16("get-rotate-and-crop"), String16("help")};
93 const size_t kNumLayerMetaData = size(kLayerMetadata);
94 const size_t kNumCameraMsg = size(kCameraMsg);
95 const size_t kNumSoundKind = size(kSoundKind);
96 const size_t kNumShellCmd = size(kShellCmd);
97 
98 class CameraFuzzer : public ::android::hardware::BnCameraClient {
99    public:
CameraFuzzer(sp<CameraService> cs,std::shared_ptr<FuzzedDataProvider> fp)100     CameraFuzzer(sp<CameraService> cs, std::shared_ptr<FuzzedDataProvider> fp) :
101           mCameraService(cs), mFuzzedDataProvider(fp) {};
~CameraFuzzer()102     ~CameraFuzzer() { deInit(); }
103     void process();
104     void deInit();
105 
106    private:
107     sp<CameraService> mCameraService = nullptr;
108     std::shared_ptr<FuzzedDataProvider> mFuzzedDataProvider = nullptr;
109     sp<SurfaceComposerClient> mComposerClient = nullptr;
110     int32_t mNumCameras = 0;
111     size_t mPreviewBufferCount = 0;
112     bool mAutoFocusMessage = false;
113     bool mSnapshotNotification = false;
114     bool mRecordingNotification = false;
115     mutable Mutex mPreviewLock;
116     mutable Condition mPreviewCondition;
117     mutable Mutex mAutoFocusLock;
118     mutable Condition mAutoFocusCondition;
119     mutable Mutex mSnapshotLock;
120     mutable Condition mSnapshotCondition;
121     mutable Mutex mRecordingLock;
122     mutable Condition mRecordingCondition;
123 
124     void getNumCameras();
125     void getCameraInformation(int32_t cameraId);
126     void invokeCameraAPIs();
127     void invokeCameraSound();
128     void invokeDump();
129     void invokeShellCommand();
130     void invokeNotifyCalls();
131     void invokeTorchAPIs(int32_t cameraId);
132 
133     // CameraClient interface
134     void notifyCallback(int32_t msgType, int32_t, int32_t) override;
135     void dataCallback(int32_t msgType, const sp<IMemory> &, camera_frame_metadata_t *) override;
dataCallbackTimestamp(nsecs_t,int32_t,const sp<IMemory> &)136     void dataCallbackTimestamp(nsecs_t, int32_t, const sp<IMemory> &) override{};
recordingFrameHandleCallbackTimestamp(nsecs_t,native_handle_t *)137     void recordingFrameHandleCallbackTimestamp(nsecs_t, native_handle_t *) override{};
recordingFrameHandleCallbackTimestampBatch(const std::vector<nsecs_t> &,const std::vector<native_handle_t * > &)138     void recordingFrameHandleCallbackTimestampBatch(
139         const std::vector<nsecs_t> &, const std::vector<native_handle_t *> &) override{};
140     status_t waitForPreviewStart();
141     status_t waitForEvent(Mutex &mutex, Condition &condition, bool &flag);
142 };
143 
notifyCallback(int32_t msgType,int32_t,int32_t)144 void CameraFuzzer::notifyCallback(int32_t msgType, int32_t, int32_t) {
145     if (CAMERA_MSG_FOCUS == msgType) {
146         Mutex::Autolock l(mAutoFocusLock);
147         mAutoFocusMessage = true;
148         mAutoFocusCondition.broadcast();
149     }
150 };
151 
dataCallback(int32_t msgType,const sp<IMemory> &,camera_frame_metadata_t *)152 void CameraFuzzer::dataCallback(int32_t msgType, const sp<IMemory> & /*data*/,
153                                 camera_frame_metadata_t *) {
154     switch (msgType) {
155         case CAMERA_MSG_PREVIEW_FRAME: {
156             Mutex::Autolock l(mPreviewLock);
157             ++mPreviewBufferCount;
158             mPreviewCondition.broadcast();
159             mRecordingNotification = true;
160             mRecordingCondition.broadcast();
161             break;
162         }
163         case CAMERA_MSG_COMPRESSED_IMAGE: {
164             Mutex::Autolock l(mSnapshotLock);
165             mSnapshotNotification = true;
166             mSnapshotCondition.broadcast();
167             break;
168         }
169         default:
170             break;
171     }
172 };
173 
waitForPreviewStart()174 status_t CameraFuzzer::waitForPreviewStart() {
175     status_t rc = NO_ERROR;
176     Mutex::Autolock l(mPreviewLock);
177     mPreviewBufferCount = 0;
178 
179     while (mPreviewBufferCount < kPreviewThreshold) {
180         rc = mPreviewCondition.waitRelative(mPreviewLock, kPreviewTimeout);
181         if (NO_ERROR != rc) {
182             break;
183         }
184     }
185 
186     return rc;
187 }
188 
waitForEvent(Mutex & mutex,Condition & condition,bool & flag)189 status_t CameraFuzzer::waitForEvent(Mutex &mutex, Condition &condition, bool &flag) {
190     status_t rc = NO_ERROR;
191     Mutex::Autolock l(mutex);
192     flag = false;
193 
194     while (!flag) {
195         rc = condition.waitRelative(mutex, kEventTimeout);
196         if (NO_ERROR != rc) {
197             break;
198         }
199     }
200 
201     return rc;
202 }
203 
deInit()204 void CameraFuzzer::deInit() {
205     if (mComposerClient) {
206         mComposerClient->dispose();
207     }
208 }
209 
getNumCameras()210 void CameraFuzzer::getNumCameras() {
211     bool shouldPassInvalidCamType = mFuzzedDataProvider->ConsumeBool();
212     int32_t camType;
213     if (shouldPassInvalidCamType) {
214         camType = mFuzzedDataProvider->ConsumeIntegral<int32_t>();
215     } else {
216         camType = kCamType[mFuzzedDataProvider->ConsumeBool()];
217     }
218     mCameraService->getNumberOfCameras(camType, &mNumCameras);
219 }
220 
getCameraInformation(int32_t cameraId)221 void CameraFuzzer::getCameraInformation(int32_t cameraId) {
222     String16 cameraIdStr = String16(String8::format("%d", cameraId));
223     bool isSupported = false;
224     mCameraService->supportsCameraApi(
225         cameraIdStr, kCameraApiVersion[mFuzzedDataProvider->ConsumeBool()], &isSupported);
226     mCameraService->isHiddenPhysicalCamera(cameraIdStr, &isSupported);
227 
228     String16 parameters;
229     mCameraService->getLegacyParameters(cameraId, &parameters);
230 
231     std::vector<hardware::camera2::utils::ConcurrentCameraIdCombination> concurrentCameraIds;
232     mCameraService->getConcurrentCameraIds(&concurrentCameraIds);
233 
234     hardware::camera2::params::VendorTagDescriptorCache cache;
235     mCameraService->getCameraVendorTagCache(&cache);
236 
237     CameraInfo cameraInfo;
238     mCameraService->getCameraInfo(cameraId, /*overrideToPortrait*/false, &cameraInfo);
239 
240     CameraMetadata metadata;
241     mCameraService->getCameraCharacteristics(cameraIdStr,
242             /*targetSdkVersion*/__ANDROID_API_FUTURE__, /*overrideToPortrait*/false, &metadata);
243 }
244 
invokeCameraSound()245 void CameraFuzzer::invokeCameraSound() {
246     mCameraService->increaseSoundRef();
247     mCameraService->decreaseSoundRef();
248     bool shouldPassInvalidPlaySound = mFuzzedDataProvider->ConsumeBool();
249     bool shouldPassInvalidLockSound = mFuzzedDataProvider->ConsumeBool();
250     android::CameraService::sound_kind playSound, lockSound;
251     if (shouldPassInvalidPlaySound) {
252         playSound = static_cast<android::CameraService::sound_kind>(
253             mFuzzedDataProvider->ConsumeIntegral<size_t>());
254     } else {
255         playSound =
256             kSoundKind[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(0, kNumSoundKind - 1)];
257     }
258 
259     if (shouldPassInvalidLockSound) {
260         lockSound = static_cast<android::CameraService::sound_kind>(
261             mFuzzedDataProvider->ConsumeIntegral<size_t>());
262     } else {
263         lockSound =
264             kSoundKind[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(0, kNumSoundKind - 1)];
265     }
266     mCameraService->playSound(playSound);
267     mCameraService->loadSoundLocked(lockSound);
268 }
269 
invokeDump()270 void CameraFuzzer::invokeDump() {
271     Vector<String16> args;
272     size_t numberOfLines = mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(0, kMaxNumLines);
273     for (size_t lineIdx = 0; lineIdx < numberOfLines; ++lineIdx) {
274         args.add(static_cast<String16>(mFuzzedDataProvider->ConsumeRandomLengthString().c_str()));
275     }
276     const char *fileName = "logDumpFile";
277     int fd = memfd_create(fileName, MFD_ALLOW_SEALING);
278     mCameraService->dump(fd, args);
279     close(fd);
280 }
281 
invokeShellCommand()282 void CameraFuzzer::invokeShellCommand() {
283     int in = mFuzzedDataProvider->ConsumeIntegral<int>();
284     int out = mFuzzedDataProvider->ConsumeIntegral<int>();
285     int err = mFuzzedDataProvider->ConsumeIntegral<int>();
286     Vector<String16> args;
287     size_t numArgs = mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(kMinArgs, kMaxArgs);
288     for (size_t argsIdx = 0; argsIdx < numArgs; ++argsIdx) {
289         bool shouldPassInvalidCommand = mFuzzedDataProvider->ConsumeBool();
290         if (shouldPassInvalidCommand) {
291             args.add(
292                 static_cast<String16>(mFuzzedDataProvider->ConsumeRandomLengthString().c_str()));
293         } else {
294             args.add(kShellCmd[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(
295                 0, kNumShellCmd - 1)]);
296         }
297     }
298     mCameraService->shellCommand(in, out, err, args);
299 }
300 
invokeNotifyCalls()301 void CameraFuzzer::invokeNotifyCalls() {
302     mCameraService->notifyMonitoredUids();
303     int64_t newState = mFuzzedDataProvider->ConsumeIntegral<int64_t>();
304     mCameraService->notifyDeviceStateChange(newState);
305     std::vector<int32_t> args;
306     size_t numArgs = mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(kMinArgs, kMaxArgs);
307     for (size_t argsIdx = 0; argsIdx < numArgs; ++argsIdx) {
308         args.push_back(mFuzzedDataProvider->ConsumeIntegral<int32_t>());
309     }
310     bool shouldPassInvalidEvent = mFuzzedDataProvider->ConsumeBool();
311     int32_t eventId;
312     if (shouldPassInvalidEvent) {
313         eventId = mFuzzedDataProvider->ConsumeIntegral<int32_t>();
314     } else {
315         eventId = kEventId[mFuzzedDataProvider->ConsumeBool()];
316     }
317     mCameraService->notifySystemEvent(eventId, args);
318 }
319 
invokeTorchAPIs(int32_t cameraId)320 void CameraFuzzer::invokeTorchAPIs(int32_t cameraId) {
321     String16 cameraIdStr = String16(String8::format("%d", cameraId));
322     sp<IBinder> binder = new BBinder;
323 
324     mCameraService->setTorchMode(cameraIdStr, true, binder);
325     ALOGV("Turned torch on.");
326     int32_t torchStrength = rand() % 5 + 1;
327     ALOGV("Changing torch strength level to %d", torchStrength);
328     mCameraService->turnOnTorchWithStrengthLevel(cameraIdStr, torchStrength, binder);
329     mCameraService->setTorchMode(cameraIdStr, false, binder);
330     ALOGV("Turned torch off.");
331 }
332 
invokeCameraAPIs()333 void CameraFuzzer::invokeCameraAPIs() {
334     /** In order to avoid the timeout issue caused due to multiple iteration of loops, the 'for'
335      * loops are removed and the 'cameraId', 'pictureSize' and 'videoSize' are derived using the
336      * FuzzedDataProvider from the available cameras and vectors of 'pictureSizes' and 'videoSizes'
337      */
338     int32_t cameraId = mFuzzedDataProvider->ConsumeIntegralInRange<int32_t>(0, mNumCameras - 1);
339     getCameraInformation(cameraId);
340     invokeTorchAPIs(cameraId);
341 
342     ::android::binder::Status rc;
343     sp<ICamera> cameraDevice;
344 
345     rc = mCameraService->connect(this, cameraId, String16(),
346                                  android::CameraService::USE_CALLING_UID,
347                                  android::CameraService::USE_CALLING_PID,
348                                  /*targetSdkVersion*/ __ANDROID_API_FUTURE__,
349                                  /*overrideToPortrait*/true, /*forceSlowJpegMode*/false,
350                                  &cameraDevice);
351     if (!rc.isOk()) {
352         // camera not connected
353         return;
354     }
355     if (cameraDevice) {
356         sp<Surface> previewSurface;
357         sp<SurfaceControl> surfaceControl;
358         CameraParameters params(cameraDevice->getParameters());
359         String8 focusModes(params.get(CameraParameters::KEY_SUPPORTED_FOCUS_MODES));
360         bool isAFSupported = false;
361         const char* focusMode = nullptr;
362 
363         if (focusModes.contains(CameraParameters::FOCUS_MODE_AUTO)) {
364             isAFSupported = true;
365         } else if (focusModes.contains(CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE)) {
366             isAFSupported = true;
367             focusMode = CameraParameters::FOCUS_MODE_CONTINUOUS_PICTURE;
368         } else if (focusModes.contains(CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO)) {
369             isAFSupported = true;
370             focusMode = CameraParameters::FOCUS_MODE_CONTINUOUS_VIDEO;
371         } else if (focusModes.contains(CameraParameters::FOCUS_MODE_MACRO)) {
372             isAFSupported = true;
373             focusMode = CameraParameters::FOCUS_MODE_MACRO;
374         }
375         if (nullptr != focusMode) {
376             params.set(CameraParameters::KEY_FOCUS_MODE, focusMode);
377             cameraDevice->setParameters(params.flatten());
378         }
379         int previewWidth, previewHeight;
380         params.getPreviewSize(&previewWidth, &previewHeight);
381 
382         mComposerClient = new SurfaceComposerClient;
383         mComposerClient->initCheck();
384 
385         bool shouldPassInvalidLayerMetaData = mFuzzedDataProvider->ConsumeBool();
386         int layerMetaData;
387         if (shouldPassInvalidLayerMetaData) {
388             layerMetaData = mFuzzedDataProvider->ConsumeIntegral<int>();
389         } else {
390             layerMetaData = kLayerMetadata[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(
391                     0, kNumLayerMetaData - 1)];
392         }
393         surfaceControl = mComposerClient->createSurface(
394                 String8("Test Surface"), previewWidth, previewHeight,
395                 CameraParameters::previewFormatToEnum(params.getPreviewFormat()), layerMetaData);
396 
397         if (surfaceControl.get()) {
398             SurfaceComposerClient::Transaction{}
399                     .setLayer(surfaceControl, 0x7fffffff)
400                     .show(surfaceControl)
401                     .apply();
402 
403             previewSurface = surfaceControl->getSurface();
404             if (previewSurface.get()) {
405                 cameraDevice->setPreviewTarget(previewSurface->getIGraphicBufferProducer());
406             }
407         }
408         cameraDevice->setPreviewCallbackFlag(CAMERA_FRAME_CALLBACK_FLAG_CAMCORDER);
409 
410         Vector<Size> pictureSizes;
411         params.getSupportedPictureSizes(pictureSizes);
412 
413         if (pictureSizes.size()) {
414             Size pictureSize = pictureSizes[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(
415                     0, pictureSizes.size() - 1)];
416             params.setPictureSize(pictureSize.width, pictureSize.height);
417             cameraDevice->setParameters(params.flatten());
418             cameraDevice->startPreview();
419             waitForPreviewStart();
420             cameraDevice->autoFocus();
421             waitForEvent(mAutoFocusLock, mAutoFocusCondition, mAutoFocusMessage);
422             bool shouldPassInvalidCameraMsg = mFuzzedDataProvider->ConsumeBool();
423             int msgType;
424             if (shouldPassInvalidCameraMsg) {
425                 msgType = mFuzzedDataProvider->ConsumeIntegral<int>();
426             } else {
427                 msgType = kCameraMsg[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(
428                         0, kNumCameraMsg - 1)];
429             }
430             cameraDevice->takePicture(msgType);
431 
432             waitForEvent(mSnapshotLock, mSnapshotCondition, mSnapshotNotification);
433             cameraDevice->stopPreview();
434         }
435 
436         Vector<Size> videoSizes;
437         params.getSupportedVideoSizes(videoSizes);
438 
439         if (videoSizes.size()) {
440             Size videoSize = videoSizes[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(
441                     0, videoSizes.size() - 1)];
442             params.setVideoSize(videoSize.width, videoSize.height);
443 
444             cameraDevice->setParameters(params.flatten());
445             cameraDevice->startPreview();
446             waitForPreviewStart();
447             cameraDevice->setVideoBufferMode(
448                     android::hardware::BnCamera::VIDEO_BUFFER_MODE_BUFFER_QUEUE);
449             sp<SurfaceControl> surfaceControlVideo = mComposerClient->createSurface(
450                     String8("Test Surface Video"), previewWidth, previewHeight,
451                     CameraParameters::previewFormatToEnum(params.getPreviewFormat()),
452                     layerMetaData);
453             if (surfaceControlVideo.get()) {
454                 SurfaceComposerClient::Transaction{}
455                         .setLayer(surfaceControlVideo, 0x7fffffff)
456                         .show(surfaceControlVideo)
457                         .apply();
458                 sp<Surface> previewSurfaceVideo = surfaceControlVideo->getSurface();
459                 if (previewSurfaceVideo.get()) {
460                     cameraDevice->setVideoTarget(previewSurfaceVideo->getIGraphicBufferProducer());
461                 }
462             }
463             cameraDevice->stopPreview();
464             cameraDevice->startRecording();
465             waitForEvent(mRecordingLock, mRecordingCondition, mRecordingNotification);
466             cameraDevice->stopRecording();
467         }
468         cameraDevice->disconnect();
469     }
470 }
471 
process()472 void CameraFuzzer::process() {
473     getNumCameras();
474     invokeCameraSound();
475     if (mNumCameras > 0) {
476         invokeCameraAPIs();
477     }
478     invokeDump();
479     invokeShellCommand();
480     invokeNotifyCalls();
481 }
482 
483 class TestCameraServiceListener : public hardware::BnCameraServiceListener {
484 public:
~TestCameraServiceListener()485     virtual ~TestCameraServiceListener() {};
486 
onStatusChanged(int32_t,const String16 &)487     virtual binder::Status onStatusChanged(int32_t , const String16&) {
488         return binder::Status::ok();
489     };
490 
onPhysicalCameraStatusChanged(int32_t,const String16 &,const String16 &)491     virtual binder::Status onPhysicalCameraStatusChanged(int32_t /*status*/,
492             const String16& /*cameraId*/, const String16& /*physicalCameraId*/) {
493         // No op
494         return binder::Status::ok();
495     };
496 
onTorchStatusChanged(int32_t,const String16 &)497     virtual binder::Status onTorchStatusChanged(int32_t /*status*/, const String16& /*cameraId*/) {
498         return binder::Status::ok();
499     };
500 
onCameraAccessPrioritiesChanged()501     virtual binder::Status onCameraAccessPrioritiesChanged() {
502         // No op
503         return binder::Status::ok();
504     }
505 
onCameraOpened(const String16 &,const String16 &)506     virtual binder::Status onCameraOpened(const String16& /*cameraId*/,
507             const String16& /*clientPackageName*/) {
508         // No op
509         return binder::Status::ok();
510     }
511 
onCameraClosed(const String16 &)512     virtual binder::Status onCameraClosed(const String16& /*cameraId*/) {
513         // No op
514         return binder::Status::ok();
515     }
516 
onTorchStrengthLevelChanged(const String16 &,int32_t)517     virtual binder::Status onTorchStrengthLevelChanged(const String16& /*cameraId*/,
518             int32_t /*torchStrength*/) {
519         // No op
520         return binder::Status::ok();
521     }
522 };
523 
524 class TestCameraDeviceCallbacks : public hardware::camera2::BnCameraDeviceCallbacks {
525 public:
TestCameraDeviceCallbacks()526     TestCameraDeviceCallbacks() {}
527 
~TestCameraDeviceCallbacks()528     virtual ~TestCameraDeviceCallbacks() {}
529 
onDeviceError(int,const CaptureResultExtras &)530     virtual binder::Status onDeviceError(int /*errorCode*/,
531             const CaptureResultExtras& /*resultExtras*/) {
532         return binder::Status::ok();
533     }
534 
onDeviceIdle()535     virtual binder::Status onDeviceIdle() {
536         return binder::Status::ok();
537     }
538 
onCaptureStarted(const CaptureResultExtras &,int64_t)539     virtual binder::Status onCaptureStarted(const CaptureResultExtras& /*resultExtras*/,
540             int64_t /*timestamp*/) {
541         return binder::Status::ok();
542     }
543 
onResultReceived(const CameraMetadata &,const CaptureResultExtras &,const std::vector<PhysicalCaptureResultInfo> &)544     virtual binder::Status onResultReceived(const CameraMetadata& /*metadata*/,
545             const CaptureResultExtras& /*resultExtras*/,
546             const std::vector<PhysicalCaptureResultInfo>& /*physicalResultInfos*/) {
547         return binder::Status::ok();
548     }
549 
onPrepared(int)550     virtual binder::Status onPrepared(int /*streamId*/) {
551         return binder::Status::ok();
552     }
553 
onRepeatingRequestError(int64_t,int32_t)554     virtual binder::Status onRepeatingRequestError(
555             int64_t /*lastFrameNumber*/, int32_t /*stoppedSequenceId*/) {
556         return binder::Status::ok();
557     }
558 
onRequestQueueEmpty()559     virtual binder::Status onRequestQueueEmpty() {
560         return binder::Status::ok();
561     }
562 };
563 
564 class Camera2Fuzzer {
565    public:
Camera2Fuzzer(sp<CameraService> cs,std::shared_ptr<FuzzedDataProvider> fp)566     Camera2Fuzzer(sp<CameraService> cs, std::shared_ptr<FuzzedDataProvider> fp) :
567           mCameraService(cs), mFuzzedDataProvider(fp) { };
~Camera2Fuzzer()568     ~Camera2Fuzzer() {}
569     void process();
570    private:
571     sp<CameraService> mCameraService = nullptr;
572     std::shared_ptr<FuzzedDataProvider> mFuzzedDataProvider = nullptr;
573 };
574 
process()575 void Camera2Fuzzer::process() {
576     sp<TestCameraServiceListener> listener = new TestCameraServiceListener();
577     std::vector<hardware::CameraStatus> statuses;
578     mCameraService->addListenerTest(listener, &statuses);
579     for (auto s : statuses) {
580         sp<TestCameraDeviceCallbacks> callbacks(new TestCameraDeviceCallbacks());
581         sp<hardware::camera2::ICameraDeviceUser> device;
582         mCameraService->connectDevice(callbacks, String16(s.cameraId), String16(), {},
583                 android::CameraService::USE_CALLING_UID, 0/*oomScoreDiff*/,
584                 /*targetSdkVersion*/__ANDROID_API_FUTURE__, /*overrideToPortrait*/true,
585                 &device);
586         if (device == nullptr) {
587             continue;
588         }
589         device->beginConfigure();
590         sp<IGraphicBufferProducer> gbProducer;
591         sp<IGraphicBufferConsumer> gbConsumer;
592         BufferQueue::createBufferQueue(&gbProducer, &gbConsumer);
593         sp<BufferItemConsumer> opaqueConsumer = new BufferItemConsumer(gbConsumer,
594                 GRALLOC_USAGE_SW_READ_NEVER, /*maxImages*/8, /*controlledByApp*/true);
595         opaqueConsumer->setName(String8("Roger"));
596 
597         // Set to VGA dimension for default, as that is guaranteed to be present
598         gbConsumer->setDefaultBufferSize(640, 480);
599         gbConsumer->setDefaultBufferFormat(HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED);
600 
601         sp<Surface> surface(new Surface(gbProducer, /*controlledByApp*/false));
602 
603         String16 noPhysicalId;
604         size_t rotations = sizeof(kRotations) / sizeof(int32_t) - 1;
605         OutputConfiguration output(gbProducer,
606                 kRotations[mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(0, rotations)],
607                 noPhysicalId);
608         int streamId;
609         device->createStream(output, &streamId);
610         CameraMetadata sessionParams;
611         std::vector<int> offlineStreamIds;
612         device->endConfigure(/*isConstrainedHighSpeed*/ mFuzzedDataProvider->ConsumeBool(),
613                 sessionParams, ns2ms(systemTime()), &offlineStreamIds);
614 
615         CameraMetadata requestTemplate;
616         size_t requestTemplatesSize =  sizeof(kRequestTemplates) /sizeof(int32_t)  - 1;
617         device->createDefaultRequest(kRequestTemplates[
618                 mFuzzedDataProvider->ConsumeIntegralInRange<size_t>(0, requestTemplatesSize)],
619                 /*out*/&requestTemplate);
620         hardware::camera2::CaptureRequest request;
621         request.mSurfaceList.add(surface);
622         request.mIsReprocess = false;
623         hardware::camera2::utils::SubmitInfo info;
624         for (int i = 0; i < kNumRequestsTested; i++) {
625             uint8_t sensorPixelMode =
626                     kSensorPixelModes[mFuzzedDataProvider->ConsumeBool() ? 1 : 0];
627             requestTemplate.update(ANDROID_SENSOR_PIXEL_MODE, &sensorPixelMode, 1);
628             request.mPhysicalCameraSettings.clear();
629             request.mPhysicalCameraSettings.push_back({s.cameraId.string(), requestTemplate});
630             device->submitRequest(request, /*streaming*/false, /*out*/&info);
631             ALOGV("%s : camera id %s submit request id %d",__FUNCTION__, s.cameraId.string(),
632                     info.mRequestId);
633         }
634         device->disconnect();
635     }
636 }
637 
LLVMFuzzerTestOneInput(const uint8_t * data,size_t size)638 extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
639     if (size < 1) {
640         return 0;
641     }
642     setuid(AID_CAMERASERVER);
643     std::shared_ptr<FuzzedDataProvider> fp = std::make_shared<FuzzedDataProvider>(data, size);
644     sp<CameraService> cs = new CameraService();
645     cs->clearCachedVariables();
646     sp<CameraFuzzer> camerafuzzer = new CameraFuzzer(cs, fp);
647     if (!camerafuzzer) {
648         return 0;
649     }
650     camerafuzzer->process();
651     Camera2Fuzzer camera2fuzzer(cs, fp);
652     camera2fuzzer.process();
653     return 0;
654 }
655