objective-c - CoreGraphics 随机崩溃

标签 objective-c core-graphics

这是一个小测试程序,用于在更大的类中复制间歇性问题。真实的类创建 4 个不同大小的拇指。

此 main.m 程序在使用 EXC_BAD_ACCESS 运行时,五分之一会崩溃,并突出显示 CGImageRelease(imgRef);如果我注释掉 CGImageRelease(imgRef) 那么应用程序会遇到严重的内存泄漏但不会崩溃...

#import <Foundation/Foundation.h>
#import <Cocoa/Cocoa.h>

int main(int argc, const char * argv[])
{

    @autoreleasepool {


        NSString * image = @"/Users/xxx/Pictures/wallpaper/7gjMT.jpg";
        NSData * imageData = [NSData dataWithContentsOfFile:image];

        CFDataRef imgData = (__bridge CFDataRef)imageData;
        CGImageRef imgRef;
        CGDataProviderRef imgDataProvider = NULL;
        imgDataProvider = CGDataProviderCreateWithCFData(imgData);
        imgRef = CGImageCreateWithJPEGDataProvider(imgDataProvider, NULL, true, kCGRenderingIntentDefault);
        CGDataProviderRelease(imgDataProvider);

        for (int i = 0; i < 1000; i++) {
            // create context, keeping original image properties
            CGColorSpaceRef colorspace = CGImageGetColorSpace(imgRef);

            CGContextRef context = CGBitmapContextCreate(NULL, 2560, 1440,
                                            CGImageGetBitsPerComponent(imgRef),
                                            CGImageGetBytesPerRow(imgRef),
                                            colorspace,
                                            kCGImageAlphaPremultipliedFirst);

            CGColorSpaceRelease(colorspace);

            // draw image to context (resizing it)
            CGContextDrawImage(context, CGRectMake(0, 0, 2560, 1440), imgRef);

            // extract resulting image from context
            CGImageRef newImgRef;
            newImgRef = CGBitmapContextCreateImage(context);
            CGImageRelease(imgRef);
            CGContextRelease(context);

            imgRef = newImgRef;
        }



    }
    return 0;
}

我发现如果我先释放上下文,那么十分之一的失败会突出显示 CGImageGetBytesPerRow(imgRef) 并出现相同的错误。

我为 malloc_error_break 添加了一个断点,并在 CGImageRelease 上得到了这个:

enter image description here

CGImageRelease 和 CGI​​mageRelease 是否正在释放共享资源?

最佳答案

主要问题几乎可以肯定是您正在释放不属于您的色彩空间。 CGImageGetColorSpace(imgRef) 不会为您提供返回的色彩空间对象的所有权,因此您不应稍后调用 CGColorSpaceRelease(colorspace)。 (顺便说一句,虽然我碰巧遇到了另一个失败,这让我发现了问题,但静态分析器也捕获了这个问题。)

作为次要问题,我无法创建上下文,因为您使用了不适当的每行字节值。 CGImageGetBytesPerRow(imgRef) 是该图像的每行字节数,但这仅适用于该图像的宽度。鉴于您对宽度进行硬编码而不是使用图像的宽度(因为您正在缩放),因此您不应该使用图像的每行字节数。

我想如果你缩小规模它会起作用,但会浪费空间。如果你扩大规模,就会失败。

无论如何,传递 0。这可以让 CGBitmapContextCreate() 计算最佳值。

关于objective-c - CoreGraphics 随机崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28910973/

相关文章:

objective-c - 是否可以定义一个符合协议(protocol)的Class类型的属性?

objective-c - 从具有 NSArray 返回值的方法返回 NSMutableArray 对象

ios - 如何使用 Core Graphics 在 iOS 中计算和绘制尺寸线(具有垂直端线的线)?

ios - 如何通过 Swift 在拍摄的照片上插入文字?

ios - 有阴影的 View

ios - 如何删除两个 UICollectionView 列之间的边距

objective-c - 为什么 Objective-C 没有命名空间?

ios - CG 光栅数据 - CGProviderCreateWithCopyOfData - 无法发布?

ios - 在 iOS 中关闭硬件加速

ios - SKShapeNode(路径: path) does not draw