1 /*
2  * Copyright (c) 2022 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "rsproperty_fuzzer.h"
17 
18 #include <cstddef>
19 #include <cstdint>
20 #include <securec.h>
21 
22 #include "property/rs_properties.h"
23 #include "property/rs_properties_painter.h"
24 #include "property/rs_property_trace.h"
25 
26 namespace OHOS {
27 namespace Rosen {
28 namespace {
29 const uint8_t* g_data = nullptr;
30 size_t g_size = 0;
31 size_t g_pos;
32 } // namespace
33 
34 /*
35  * describe: get data from outside untrusted data(g_data) which size is according to sizeof(T)
36  * tips: only support basic type
37  */
38 template<class T>
GetData()39 T GetData()
40 {
41     T object {};
42     size_t objectSize = sizeof(object);
43     if (g_data == nullptr || objectSize > g_size - g_pos) {
44         return object;
45     }
46     errno_t ret = memcpy_s(&object, objectSize, g_data + g_pos, objectSize);
47     if (ret != EOK) {
48         return {};
49     }
50     g_pos += objectSize;
51     return object;
52 }
53 
54 /*
55  * get a string from g_data
56  */
GetStringFromData(int strlen)57 std::string GetStringFromData(int strlen)
58 {
59     if (strlen <= 0) {
60         return "fuzz";
61     }
62     char cstr[strlen];
63     cstr[strlen - 1] = '\0';
64     for (int i = 0; i < strlen - 1; i++) {
65         char tmp = GetData<char>();
66         if (tmp == '\0') {
67             tmp = '1';
68         }
69         cstr[i] = tmp;
70     }
71     std::string str(cstr);
72     return str;
73 }
74 
RSPropertiesFuzzTestInner01(RSProperties & properties)75 void RSPropertiesFuzzTestInner01(RSProperties& properties)
76 {
77     float x1 = GetData<float>();
78     float y1 = GetData<float>();
79     float z1 = GetData<float>();
80     float w1 = GetData<float>();
81     Vector4f bounds(x1, y1, z1, w1);
82     float x2 = GetData<float>();
83     float y2 = GetData<float>();
84     Vector2f size_vec(x2, y2);
85     float width = GetData<float>();
86     float height = GetData<float>();
87     float x3 = GetData<float>();
88     float y3 = GetData<float>();
89     Vector2f position(x3, y3);
90     float positionX = GetData<float>();
91     float positionY = GetData<float>();
92     float x4 = GetData<float>();
93     float y4 = GetData<float>();
94     float z4 = GetData<float>();
95     float w4 = GetData<float>();
96     Vector4f frame(x4, y4, z4, w4);
97     float positionZ = GetData<float>();
98     float x5 = GetData<float>();
99     float y5 = GetData<float>();
100     Vector2f pivot(x5, y5);
101     float pivotX = GetData<float>();
102     float pivotY = GetData<float>();
103     float x6 = GetData<float>();
104     float y6 = GetData<float>();
105     float z6 = GetData<float>();
106     float w6 = GetData<float>();
107     Vector4f cornerRadius(x6, y6, z6, w6);
108     properties.SetBounds(bounds);
109     properties.SetBoundsSize(size_vec);
110     properties.SetBoundsWidth(width);
111     properties.SetBoundsHeight(height);
112     properties.SetBoundsPosition(position);
113     properties.SetBoundsPositionX(positionX);
114     properties.SetBoundsPositionY(positionY);
115     properties.SetFrame(frame);
116     properties.SetFrameSize(size_vec);
117     properties.SetFrameWidth(width);
118     properties.SetFrameHeight(height);
119     properties.SetFramePosition(position);
120     properties.SetFramePositionX(positionX);
121     properties.SetFramePositionY(positionY);
122     properties.SetPositionZ(positionZ);
123     properties.SetPivot(pivot);
124     properties.SetPivotX(pivotX);
125     properties.SetPivotY(pivotY);
126     properties.SetCornerRadius(cornerRadius);
127 }
128 
RSPropertiesFuzzTestInner02(RSProperties & properties)129 void RSPropertiesFuzzTestInner02(RSProperties& properties)
130 {
131     float x7 = GetData<float>();
132     float y7 = GetData<float>();
133     float z7 = GetData<float>();
134     float w7 = GetData<float>();
135     Quaternion quaternion(x7, y7, z7, w7);
136     float degree = GetData<float>();
137     float x8 = GetData<float>();
138     float y8 = GetData<float>();
139     Vector2f translateVector(x8, y8);
140     float translate = GetData<float>();
141     float x9 = GetData<float>();
142     float y9 = GetData<float>();
143     Vector2f scale(x9, y9);
144     float x10 = GetData<float>();
145     float y10 = GetData<float>();
146     Vector2f skew(x10, y10);
147     float x11 = GetData<float>();
148     float y11 = GetData<float>();
149     Vector2f persp(x11, y11);
150     float alpha = GetData<float>();
151     bool alphaOffscreen = GetData<bool>();
152     int16_t red1 = GetData<int16_t>();
153     int16_t green1 = GetData<int16_t>();
154     int16_t blue1 = GetData<int16_t>();
155     Color color1(red1, green1, blue1);
156     std::shared_ptr<RSShader> shader = RSShader::CreateRSShader();
157     int16_t red2 = GetData<int16_t>();
158     int16_t green2 = GetData<int16_t>();
159     int16_t blue2 = GetData<int16_t>();
160     Color color2(red2, green2, blue2);
161     int16_t red3 = GetData<int16_t>();
162     int16_t green3 = GetData<int16_t>();
163     int16_t blue3 = GetData<int16_t>();
164     Color color3(red3, green3, blue3);
165     int16_t red4 = GetData<int16_t>();
166     int16_t green4 = GetData<int16_t>();
167     int16_t blue4 = GetData<int16_t>();
168     Color color4(red4, green4, blue4);
169     Vector4<Color> colorVector(color1, color2, color3, color4);
170 
171     properties.SetQuaternion(quaternion);
172     properties.SetRotation(degree);
173     properties.SetRotationX(degree);
174     properties.SetRotationY(degree);
175     properties.SetTranslate(translateVector);
176     properties.SetTranslateX(translate);
177     properties.SetTranslateY(translate);
178     properties.SetTranslateZ(translate);
179     properties.SetScale(scale);
180     properties.SetSkew(skew);
181     properties.SetPersp(persp);
182     properties.SetAlpha(alpha);
183     properties.SetAlphaOffscreen(alphaOffscreen);
184     properties.SetForegroundColor(color1);
185     properties.SetBackgroundColor(color2);
186     properties.SetBackgroundShader(shader);
187     properties.SetBorderColor(colorVector);
188 }
189 
RSPropertiesFuzzTestInner03(RSProperties & properties)190 void RSPropertiesFuzzTestInner03(RSProperties& properties)
191 {
192     float x10 = GetData<float>();
193     float y10 = GetData<float>();
194     float z10 = GetData<float>();
195     float w10 = GetData<float>();
196     Vector4f widthVector(x10, y10, z10, w10);
197     uint32_t x11 = GetData<float>();
198     uint32_t y11 = GetData<float>();
199     uint32_t z11 = GetData<float>();
200     uint32_t w11 = GetData<float>();
201     Vector4<uint32_t> style(x11, y11, z11, w11);
202     float blurRadiusX = GetData<float>();
203     float blurRadiusY = GetData<float>();
204     std::shared_ptr<RSFilter> backgroundFilter = RSFilter::CreateBlurFilter(blurRadiusX, blurRadiusY);
205     int styleInt = GetData<int>();
206     float dipScale = GetData<float>();
207     std::shared_ptr<RSFilter> filter = RSFilter::CreateMaterialFilter(styleInt, dipScale);
208     float offsetX = GetData<float>();
209     float offsetY = GetData<float>();
210     float radius = GetData<float>();
211     std::shared_ptr<RSPath> shadowpath = std::make_shared<RSPath>();
212     Gravity gravity = GetData<Gravity>();
213     int intLeft = GetData<int>();
214     int intTop = GetData<int>();
215     int intWidth = GetData<int>();
216     int intHeight = GetData<int>();
217     std::shared_ptr<RectI> rect = std::make_shared<RectI>(intLeft, intTop, intWidth, intHeight);
218     int16_t red1 = GetData<int16_t>();
219     int16_t green1 = GetData<int16_t>();
220     int16_t blue1 = GetData<int16_t>();
221     Color color1(red1, green1, blue1);
222     float alpha = GetData<float>();
223 
224     properties.SetBorderWidth(widthVector);
225     properties.SetBorderDashWidth(widthVector);
226     properties.SetBorderDashGap(widthVector);
227     properties.SetOutlineDashWidth(widthVector);
228     properties.SetOutlineDashGap(widthVector);
229     properties.SetBorderStyle(style);
230     properties.SetBackgroundFilter(backgroundFilter);
231     properties.SetFilter(filter);
232     properties.SetShadowColor(color1);
233     properties.SetShadowOffsetX(offsetX);
234     properties.SetShadowOffsetY(offsetY);
235     properties.SetShadowAlpha(alpha);
236     properties.SetShadowElevation(radius);
237     properties.SetShadowRadius(radius);
238     properties.SetShadowPath(shadowpath);
239     properties.SetFrameGravity(gravity);
240 }
241 
RSPropertiesFuzzTestInner04(RSProperties & properties)242 void RSPropertiesFuzzTestInner04(RSProperties& properties)
243 {
244     float sx = GetData<float>();
245     float sy = GetData<float>();
246     std::shared_ptr<RSImage> image = std::make_shared<RSImage>();
247     float width = GetData<float>();
248     float height = GetData<float>();
249     float positionX = GetData<float>();
250     float positionY = GetData<float>();
251     bool clipToBounds = GetData<bool>();
252     bool clipToFrame = GetData<bool>();
253     bool visible = GetData<bool>();
254     float distortionK = GetData<float>();
255     bool distortionDirty = GetData<bool>();
256 
257     properties.SetScaleX(sx);
258     properties.SetScaleY(sy);
259     properties.SetBgImage(image);
260     properties.SetBgImageWidth(width);
261     properties.SetBgImageHeight(height);
262     properties.SetBgImagePositionX(positionX);
263     properties.SetBgImagePositionY(positionY);
264     properties.SetClipToBounds(clipToBounds);
265     properties.SetClipToFrame(clipToFrame);
266     properties.SetVisible(visible);
267     properties.SetDistortionK(distortionK);
268     properties.SetDistortionDirty(distortionDirty);
269 }
270 
RSPropertiesFuzzTest(const uint8_t * data,size_t size)271 bool RSPropertiesFuzzTest(const uint8_t* data, size_t size)
272 {
273     if (data == nullptr) {
274         return false;
275     }
276 
277     // initialize
278     g_data = data;
279     g_size = size;
280     g_pos = 0;
281 
282     RSProperties properties;
283 
284     // test
285     RSPropertiesFuzzTestInner01(properties);
286     RSPropertiesFuzzTestInner02(properties);
287     RSPropertiesFuzzTestInner03(properties);
288     RSPropertiesFuzzTestInner04(properties);
289 
290     return true;
291 }
292 
RSPropertiesPainterFuzzTest(const uint8_t * data,size_t size)293 bool RSPropertiesPainterFuzzTest(const uint8_t* data, size_t size)
294 {
295     if (data == nullptr) {
296         return false;
297     }
298 
299     // initialize
300     g_data = data;
301     g_size = size;
302     g_pos = 0;
303 
304     // getdata
305     Drawing::Canvas tmpCanvas;
306     float fLeft = GetData<float>();
307     float fTop = GetData<float>();
308     float fWidth = GetData<float>();
309     float fHeight = GetData<float>();
310     RectF rect(fLeft, fTop, fWidth, fHeight);
311     RSProperties properties;
312     int iLeft = GetData<int>();
313     int iTop = GetData<int>();
314     int iWidth = GetData<int>();
315     int iHeight = GetData<int>();
316     RectI dirtyShadow(iLeft, iTop, iWidth, iHeight);
317     float skLeft = GetData<float>();
318     float skTop = GetData<float>();
319     float skRight = GetData<float>();
320     float skBottom = GetData<float>();
321     Drawing::Rect maskBounds { skLeft, skTop, skRight, skBottom };
322     Drawing::Matrix mat;
323     Gravity gravity = GetData<Gravity>();
324     float fW = GetData<float>();
325     float fH = GetData<float>();
326 
327     RSPropertiesPainter::Clip(tmpCanvas, rect);
328     RSPropertiesPainter::DrawBorder(properties, tmpCanvas);
329     RSPropertiesPainter::GetShadowDirtyRect(dirtyShadow, properties);
330     RSPropertiesPainter::DrawForegroundColor(properties, tmpCanvas);
331     RSPropertiesPainter::DrawMask(properties, tmpCanvas);
332     RSPropertiesPainter::DrawMask(properties, tmpCanvas, maskBounds);
333     RSPropertiesPainter::GetGravityMatrix(gravity, rect, fW, fH, mat);
334     RSPropertiesPainter::Rect2DrawingRect(rect);
335 
336     return true;
337 }
338 
339 } // namespace Rosen
340 } // namespace OHOS
341 
342 /* Fuzzer entry point */
LLVMFuzzerTestOneInput(const uint8_t * data,size_t size)343 extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size)
344 {
345     /* Run your code on data */
346     OHOS::Rosen::RSPropertiesFuzzTest(data, size);
347     OHOS::Rosen::RSPropertiesPainterFuzzTest(data, size);
348     return 0;
349 }
350