Bug 1166585 - Check for CreateFilter() call returning NULL. r=mstange

This commit is contained in:
Kyle 2015-05-28 14:50:15 -04:00
parent b723dc7062
commit 9c222f8082
2 changed files with 155 additions and 56 deletions

View File

@ -549,8 +549,8 @@ FilterNodeD2D1::Create(ID2D1DeviceContext *aDC, FilterType aType)
hr = aDC->CreateEffect(GetCLDIDForFilterType(aType), byRef(effect));
if (FAILED(hr)) {
gfxWarning() << "Failed to create effect for FilterType: " << hexa(hr);
if (FAILED(hr) || !effect) {
gfxCriticalErrorOnce() << "Failed to create effect for FilterType: " << hexa(hr);
return nullptr;
}

View File

@ -102,64 +102,82 @@ namespace FilterWrappers {
Unpremultiply(DrawTarget* aDT, FilterNode* aInput)
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::UNPREMULTIPLY);
filter->SetInput(IN_UNPREMULTIPLY_IN, aInput);
return filter.forget();
if (filter) {
filter->SetInput(IN_UNPREMULTIPLY_IN, aInput);
return filter.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
Premultiply(DrawTarget* aDT, FilterNode* aInput)
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::PREMULTIPLY);
filter->SetInput(IN_PREMULTIPLY_IN, aInput);
return filter.forget();
if (filter) {
filter->SetInput(IN_PREMULTIPLY_IN, aInput);
return filter.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
LinearRGBToSRGB(DrawTarget* aDT, FilterNode* aInput)
{
RefPtr<FilterNode> transfer = aDT->CreateFilter(FilterType::DISCRETE_TRANSFER);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_R, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_R, glinearRGBTosRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_G, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_G, glinearRGBTosRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_B, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_B, glinearRGBTosRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_A, true);
transfer->SetInput(IN_DISCRETE_TRANSFER_IN, aInput);
return transfer.forget();
if (transfer) {
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_R, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_R, glinearRGBTosRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_G, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_G, glinearRGBTosRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_B, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_B, glinearRGBTosRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_A, true);
transfer->SetInput(IN_DISCRETE_TRANSFER_IN, aInput);
return transfer.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
SRGBToLinearRGB(DrawTarget* aDT, FilterNode* aInput)
{
RefPtr<FilterNode> transfer = aDT->CreateFilter(FilterType::DISCRETE_TRANSFER);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_R, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_R, gsRGBToLinearRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_G, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_G, gsRGBToLinearRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_B, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_B, gsRGBToLinearRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_A, true);
transfer->SetInput(IN_DISCRETE_TRANSFER_IN, aInput);
return transfer.forget();
if (transfer) {
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_R, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_R, gsRGBToLinearRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_G, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_G, gsRGBToLinearRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_B, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_B, gsRGBToLinearRGBMap, 256);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_A, true);
transfer->SetInput(IN_DISCRETE_TRANSFER_IN, aInput);
return transfer.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
Crop(DrawTarget* aDT, FilterNode* aInputFilter, const IntRect& aRect)
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::CROP);
filter->SetAttribute(ATT_CROP_RECT, Rect(aRect));
filter->SetInput(IN_CROP_IN, aInputFilter);
return filter.forget();
if (filter) {
filter->SetAttribute(ATT_CROP_RECT, Rect(aRect));
filter->SetInput(IN_CROP_IN, aInputFilter);
return filter.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
Offset(DrawTarget* aDT, FilterNode* aInputFilter, const IntPoint& aOffset)
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::TRANSFORM);
filter->SetAttribute(ATT_TRANSFORM_MATRIX, Matrix::Translation(aOffset.x, aOffset.y));
filter->SetInput(IN_TRANSFORM_IN, aInputFilter);
return filter.forget();
if (filter) {
filter->SetAttribute(ATT_TRANSFORM_MATRIX, Matrix::Translation(aOffset.x, aOffset.y));
filter->SetInput(IN_TRANSFORM_IN, aInputFilter);
return filter.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
@ -169,27 +187,36 @@ namespace FilterWrappers {
float stdY = float(std::min(aStdDeviation.height, kMaxStdDeviation));
if (stdX == stdY) {
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::GAUSSIAN_BLUR);
filter->SetAttribute(ATT_GAUSSIAN_BLUR_STD_DEVIATION, stdX);
filter->SetInput(IN_GAUSSIAN_BLUR_IN, aInputFilter);
return filter.forget();
if (filter) {
filter->SetAttribute(ATT_GAUSSIAN_BLUR_STD_DEVIATION, stdX);
filter->SetInput(IN_GAUSSIAN_BLUR_IN, aInputFilter);
return filter.forget();
}
return nullptr;
}
RefPtr<FilterNode> filterH = aDT->CreateFilter(FilterType::DIRECTIONAL_BLUR);
RefPtr<FilterNode> filterV = aDT->CreateFilter(FilterType::DIRECTIONAL_BLUR);
filterH->SetAttribute(ATT_DIRECTIONAL_BLUR_DIRECTION, (uint32_t)BLUR_DIRECTION_X);
filterH->SetAttribute(ATT_DIRECTIONAL_BLUR_STD_DEVIATION, stdX);
filterV->SetAttribute(ATT_DIRECTIONAL_BLUR_DIRECTION, (uint32_t)BLUR_DIRECTION_Y);
filterV->SetAttribute(ATT_DIRECTIONAL_BLUR_STD_DEVIATION, stdY);
filterH->SetInput(IN_DIRECTIONAL_BLUR_IN, aInputFilter);
filterV->SetInput(IN_DIRECTIONAL_BLUR_IN, filterH);
return filterV.forget();
if (filterH && filterV) {
filterH->SetAttribute(ATT_DIRECTIONAL_BLUR_DIRECTION, (uint32_t)BLUR_DIRECTION_X);
filterH->SetAttribute(ATT_DIRECTIONAL_BLUR_STD_DEVIATION, stdX);
filterV->SetAttribute(ATT_DIRECTIONAL_BLUR_DIRECTION, (uint32_t)BLUR_DIRECTION_Y);
filterV->SetAttribute(ATT_DIRECTIONAL_BLUR_STD_DEVIATION, stdY);
filterH->SetInput(IN_DIRECTIONAL_BLUR_IN, aInputFilter);
filterV->SetInput(IN_DIRECTIONAL_BLUR_IN, filterH);
return filterV.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
Clear(DrawTarget* aDT)
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::FLOOD);
filter->SetAttribute(ATT_FLOOD_COLOR, Color(0,0,0,0));
return filter.forget();
if (filter) {
filter->SetAttribute(ATT_FLOOD_COLOR, Color(0, 0, 0, 0));
return filter.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
@ -197,10 +224,13 @@ namespace FilterWrappers {
const IntPoint& aSurfacePosition)
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::TRANSFORM);
filter->SetAttribute(ATT_TRANSFORM_MATRIX,
Matrix::Translation(aSurfacePosition.x, aSurfacePosition.y));
filter->SetInput(IN_TRANSFORM_IN, aSurface);
return filter.forget();
if (filter) {
filter->SetAttribute(ATT_TRANSFORM_MATRIX,
Matrix::Translation(aSurfacePosition.x, aSurfacePosition.y));
filter->SetInput(IN_TRANSFORM_IN, aSurface);
return filter.forget();
}
return nullptr;
}
static TemporaryRef<FilterNode>
@ -208,15 +238,18 @@ namespace FilterWrappers {
{
float zero = 0.0f;
RefPtr<FilterNode> transfer = aDT->CreateFilter(FilterType::DISCRETE_TRANSFER);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_R, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_R, &zero, 1);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_G, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_G, &zero, 1);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_B, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_B, &zero, 1);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_A, true);
transfer->SetInput(IN_DISCRETE_TRANSFER_IN, aInput);
return transfer.forget();
if (transfer) {
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_R, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_R, &zero, 1);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_G, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_G, &zero, 1);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_B, false);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_TABLE_B, &zero, 1);
transfer->SetAttribute(ATT_DISCRETE_TRANSFER_DISABLE_A, true);
transfer->SetInput(IN_DISCRETE_TRANSFER_IN, aInput);
return transfer.forget();
}
return nullptr;
}
}
@ -535,6 +568,9 @@ ConvertComponentTransferFunctionToFilter(const AttributeMap& aFunctionAttributes
if (!aTableTransfer) {
aTableTransfer = aDT->CreateFilter(FilterType::TABLE_TRANSFER);
if (!aTableTransfer) {
return;
}
DisableAllTransfers(aTableTransfer);
}
filter = aTableTransfer;
@ -558,6 +594,9 @@ ConvertComponentTransferFunctionToFilter(const AttributeMap& aFunctionAttributes
if (!aDiscreteTransfer) {
aDiscreteTransfer = aDT->CreateFilter(FilterType::DISCRETE_TRANSFER);
if (!aDiscreteTransfer) {
return;
}
DisableAllTransfers(aDiscreteTransfer);
}
filter = aDiscreteTransfer;
@ -589,6 +628,9 @@ ConvertComponentTransferFunctionToFilter(const AttributeMap& aFunctionAttributes
};
if (!aLinearTransfer) {
aLinearTransfer = aDT->CreateFilter(FilterType::LINEAR_TRANSFER);
if (!aLinearTransfer) {
return;
}
DisableAllTransfers(aLinearTransfer);
}
filter = aLinearTransfer;
@ -622,6 +664,9 @@ ConvertComponentTransferFunctionToFilter(const AttributeMap& aFunctionAttributes
};
if (!aGammaTransfer) {
aGammaTransfer = aDT->CreateFilter(FilterType::GAMMA_TRANSFER);
if (!aGammaTransfer) {
return;
}
DisableAllTransfers(aGammaTransfer);
}
filter = aGammaTransfer;
@ -672,10 +717,16 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
}
if (mode == SVG_FEBLEND_MODE_NORMAL) {
filter = aDT->CreateFilter(FilterType::COMPOSITE);
if (!filter) {
return nullptr;
}
filter->SetInput(IN_COMPOSITE_IN_START, aSources[1]);
filter->SetInput(IN_COMPOSITE_IN_START + 1, aSources[0]);
} else {
filter = aDT->CreateFilter(FilterType::BLEND);
if (!filter) {
return nullptr;
}
static const uint8_t blendModes[SVG_FEBLEND_MODE_LUMINOSITY + 1] = {
0,
0,
@ -717,6 +768,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
colorMatrix[3], colorMatrix[8], colorMatrix[13], colorMatrix[18],
colorMatrix[4], colorMatrix[9], colorMatrix[14], colorMatrix[19]);
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::COLOR_MATRIX);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_COLOR_MATRIX_MATRIX, matrix);
filter->SetAttribute(ATT_COLOR_MATRIX_ALPHA_MODE, (uint32_t)ALPHA_MODE_STRAIGHT);
filter->SetInput(IN_COLOR_MATRIX_IN, aSources[0]);
@ -744,6 +798,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
MORPHOLOGY_OPERATOR_ERODE : MORPHOLOGY_OPERATOR_DILATE;
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::MORPHOLOGY);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_MORPHOLOGY_RADII, IntSize(rx, ry));
filter->SetAttribute(ATT_MORPHOLOGY_OPERATOR, (uint32_t)op);
filter->SetInput(IN_MORPHOLOGY_IN, aSources[0]);
@ -754,6 +811,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
{
Color color = atts.GetColor(eFloodColor);
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::FLOOD);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_FLOOD_COLOR, color);
return filter.forget();
}
@ -761,6 +821,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
case PrimitiveType::Tile:
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::TILE);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_TILE_SOURCE_RECT, aSourceRegions[0]);
filter->SetInput(IN_TILE_IN, aSources[0]);
return filter.forget();
@ -797,6 +860,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
case PrimitiveType::ConvolveMatrix:
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::CONVOLVE_MATRIX);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_CONVOLVE_MATRIX_KERNEL_SIZE, atts.GetIntSize(eConvolveMatrixKernelSize));
const nsTArray<float>& matrix = atts.GetFloats(eConvolveMatrixKernelMatrix);
filter->SetAttribute(ATT_CONVOLVE_MATRIX_KERNEL_MATRIX,
@ -834,6 +900,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
case PrimitiveType::DisplacementMap:
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::DISPLACEMENT_MAP);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_DISPLACEMENT_MAP_SCALE,
atts.GetFloat(eDisplacementMapScale));
static const uint8_t channel[SVG_CHANNEL_A+1] = {
@ -855,6 +924,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
case PrimitiveType::Turbulence:
{
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::TURBULENCE);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_TURBULENCE_BASE_FREQUENCY,
atts.GetSize(eTurbulenceBaseFrequency));
filter->SetAttribute(ATT_TURBULENCE_NUM_OCTAVES,
@ -881,6 +953,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
uint32_t op = atts.GetUint(eCompositeOperator);
if (op == SVG_FECOMPOSITE_OPERATOR_ARITHMETIC) {
filter = aDT->CreateFilter(FilterType::ARITHMETIC_COMBINE);
if (!filter) {
return nullptr;
}
const nsTArray<float>& coefficients = atts.GetFloats(eCompositeCoefficients);
filter->SetAttribute(ATT_ARITHMETIC_COMBINE_COEFFICIENTS,
coefficients.Elements(), coefficients.Length());
@ -888,6 +963,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
filter->SetInput(IN_ARITHMETIC_COMBINE_IN2, aSources[1]);
} else {
filter = aDT->CreateFilter(FilterType::COMPOSITE);
if (!filter) {
return nullptr;
}
static const uint8_t operators[SVG_FECOMPOSITE_OPERATOR_ARITHMETIC] = {
COMPOSITE_OPERATOR_OVER, // SVG_FECOMPOSITE_OPERATOR_UNKNOWN
COMPOSITE_OPERATOR_OVER, // SVG_FECOMPOSITE_OPERATOR_OVER
@ -913,6 +991,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
return filter.forget();
}
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::COMPOSITE);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_COMPOSITE_OPERATOR, (uint32_t)COMPOSITE_OPERATOR_OVER);
for (size_t i = 0; i < aSources.Length(); i++) {
filter->SetInput(IN_COMPOSITE_IN_START + i, aSources[i]);
@ -934,6 +1015,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
RefPtr<FilterNode> offsetBlur = FilterWrappers::Offset(aDT, blur,
atts.GetIntPoint(eDropShadowOffset));
RefPtr<FilterNode> flood = aDT->CreateFilter(FilterType::FLOOD);
if (!flood) {
return nullptr;
}
Color color = atts.GetColor(eDropShadowColor);
if (aDescription.InputColorSpace(0) == ColorSpace::LinearRGB) {
color = Color(gsRGBToLinearRGBMap[uint8_t(color.r * 255)],
@ -944,11 +1028,17 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
flood->SetAttribute(ATT_FLOOD_COLOR, color);
RefPtr<FilterNode> composite = aDT->CreateFilter(FilterType::COMPOSITE);
if (!composite) {
return nullptr;
}
composite->SetAttribute(ATT_COMPOSITE_OPERATOR, (uint32_t)COMPOSITE_OPERATOR_IN);
composite->SetInput(IN_COMPOSITE_IN_START, offsetBlur);
composite->SetInput(IN_COMPOSITE_IN_START + 1, flood);
RefPtr<FilterNode> filter = aDT->CreateFilter(FilterType::COMPOSITE);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_COMPOSITE_OPERATOR, (uint32_t)COMPOSITE_OPERATOR_OVER);
filter->SetInput(IN_COMPOSITE_IN_START, composite);
filter->SetInput(IN_COMPOSITE_IN_START + 1, aSources[0]);
@ -981,6 +1071,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
};
RefPtr<FilterNode> filter =
aDT->CreateFilter(filterType[isSpecular][lightType]);
if (!filter) {
return nullptr;
}
filter->SetAttribute(ATT_LIGHTING_COLOR,
atts.GetColor(eLightingColor));
@ -1040,6 +1133,9 @@ FilterNodeFromPrimitiveDescription(const FilterPrimitiveDescription& aDescriptio
aInputImages[atts.GetUint(eImageInputIndex)];
RefPtr<FilterNode> transform = aDT->CreateFilter(FilterType::TRANSFORM);
if (!transform) {
return nullptr;
}
transform->SetInput(IN_TRANSFORM_IN, inputImage);
transform->SetAttribute(ATT_TRANSFORM_MATRIX, TM);
transform->SetAttribute(ATT_TRANSFORM_FILTER, atts.GetUint(eImageFilter));
@ -1250,7 +1346,10 @@ FilterSupport::RenderFilterDescription(DrawTarget* aDT,
FilterNodeGraphFromDescription(aDT, aFilter, aRenderRect,
aSourceGraphic, aSourceGraphicRect, aFillPaint, aFillPaintRect,
aStrokePaint, aStrokePaintRect, aAdditionalImages);
if (!resultFilter) {
gfxWarning() << "Filter is NULL.";
return;
}
aDT->DrawFilter(resultFilter, aRenderRect, aDestPoint, aOptions);
}