1 /*
2  * Copyright (C) 2024 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 #include <FrameDecoder.h>
18 #include <fuzzer/FuzzedDataProvider.h>
19 #include <media/IMediaSource.h>
20 #include <media/stagefright/MetaData.h>
21 #include <media/stagefright/foundation/AString.h>
22 #include "FrameDecoderHelpers.h"
23 #include "IMediaSourceFuzzImpl.h"
24 
25 namespace android {
26 
27 #define MAX_MEDIA_BUFFER_SIZE 2048
28 
29 // Fuzzer entry point.
LLVMFuzzerTestOneInput(const uint8_t * data,size_t size)30 extern "C" int LLVMFuzzerTestOneInput(const uint8_t *data, size_t size) {
31     // Init our wrapper
32     FuzzedDataProvider fdp(data, size);
33 
34     std::string name = fdp.ConsumeRandomLengthString(fdp.remaining_bytes());
35     AString componentName(name.c_str());
36     sp<MetaData> trackMeta = generateMetaData(&fdp);
37     sp<IMediaSource> source = new IMediaSourceFuzzImpl(&fdp, MAX_MEDIA_BUFFER_SIZE);
38 
39     // Image or video Decoder?
40     sp<FrameDecoder> decoder;
41     bool isVideoDecoder = fdp.ConsumeBool();
42     if (isVideoDecoder) {
43         decoder = new VideoFrameDecoder(componentName, trackMeta, source);
44     } else {
45         decoder = new MediaImageDecoder(componentName, trackMeta, source);
46     }
47 
48     while (fdp.remaining_bytes()) {
49         if (fdp.ConsumeBool()) {
50             int64_t frameTimeUs = fdp.ConsumeIntegral<int64_t>();
51             int option = fdp.ConsumeIntegral<int>();
52             int colorFormat = fdp.ConsumeIntegral<int>();
53             decoder->init(frameTimeUs, option, colorFormat);
54             decoder->extractFrame();
55         } else {
56             FrameRect rect;
57             rect.left = fdp.ConsumeIntegral<int32_t>();
58             rect.top = fdp.ConsumeIntegral<int32_t>();
59             rect.right = fdp.ConsumeIntegral<int32_t>();
60             rect.bottom = fdp.ConsumeIntegral<int32_t>();
61             int64_t frameTimeUs = fdp.ConsumeIntegral<int64_t>();
62             int option = fdp.ConsumeIntegral<int>();
63             int colorFormat = fdp.ConsumeIntegral<int>();
64             decoder->init(frameTimeUs, option, colorFormat);
65             decoder->extractFrame(&rect);
66         }
67     }
68 
69     generated_mime_types.clear();
70 
71     return 0;
72 }
73 }  // namespace android