aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core
diff options
context:
space:
mode:
Diffstat (limited to 'src/core')
-rw-r--r--src/core/SkPathRef.cpp17
1 files changed, 11 insertions, 6 deletions
diff --git a/src/core/SkPathRef.cpp b/src/core/SkPathRef.cpp
index 55ee9914fa..f0fda2703b 100644
--- a/src/core/SkPathRef.cpp
+++ b/src/core/SkPathRef.cpp
@@ -219,11 +219,10 @@ static bool deduce_pts_conics(const uint8_t verbs[], int vCount, int* ptCountPtr
}
SkPathRef* SkPathRef::CreateFromBuffer(SkRBuffer* buffer) {
- SkPathRef* ref = new SkPathRef;
+ std::unique_ptr<SkPathRef> ref(new SkPathRef);
int32_t packed;
if (!buffer->readS32(&packed)) {
- delete ref;
return nullptr;
}
@@ -231,6 +230,10 @@ SkPathRef* SkPathRef::CreateFromBuffer(SkRBuffer* buffer) {
uint8_t segmentMask = (packed >> kSegmentMask_SerializationShift) & 0xF;
bool isOval = (packed >> kIsOval_SerializationShift) & 1;
bool isRRect = (packed >> kIsRRect_SerializationShift) & 1;
+ if (isOval && isRRect) {
+ // Fuzzing generates data with both oval and rrect flags set; abort early in this case/
+ return nullptr;
+ }
bool rrectOrOvalIsCCW = (packed >> kRRectOrOvalIsCCW_SerializationShift) & 1;
unsigned rrectOrOvalStartIdx = (packed >> kRRectOrOvalStartIdx_SerializationShift) & 0x7;
@@ -247,7 +250,6 @@ SkPathRef* SkPathRef::CreateFromBuffer(SkRBuffer* buffer) {
static_cast<size_t>(maxPtrDiff) ||
!buffer->readS32(&conicCount) ||
conicCount < 0) {
- delete ref;
return nullptr;
}
@@ -260,7 +262,6 @@ SkPathRef* SkPathRef::CreateFromBuffer(SkRBuffer* buffer) {
!buffer->read(ref->fPoints, pointCount * sizeof(SkPoint)) ||
!buffer->read(ref->fConicWeights.begin(), conicCount * sizeof(SkScalar)) ||
!buffer->read(&ref->fBounds, sizeof(SkRect))) {
- delete ref;
return nullptr;
}
@@ -269,7 +270,11 @@ SkPathRef* SkPathRef::CreateFromBuffer(SkRBuffer* buffer) {
int pCount, cCount;
if (!deduce_pts_conics(ref->verbsMemBegin(), ref->countVerbs(), &pCount, &cCount) ||
pCount != ref->countPoints() || cCount != ref->fConicWeights.count()) {
- delete ref;
+ return nullptr;
+ }
+ // Check that the bounds match the serialized bounds.
+ SkRect bounds;
+ if (ComputePtBounds(&bounds, *ref) != SkToBool(ref->fIsFinite) || bounds != ref->fBounds) {
return nullptr;
}
}
@@ -282,7 +287,7 @@ SkPathRef* SkPathRef::CreateFromBuffer(SkRBuffer* buffer) {
ref->fIsRRect = isRRect;
ref->fRRectOrOvalIsCCW = rrectOrOvalIsCCW;
ref->fRRectOrOvalStartIdx = rrectOrOvalStartIdx;
- return ref;
+ return ref.release();
}
void SkPathRef::Rewind(sk_sp<SkPathRef>* pathRef) {