CGBitmapContextCreateImage - vm_copy failed - iPhone SDK

不想你离开。 提交于 2019-11-28 03:10:23

问题


I am having an issue using CGBitmapContextCreateImage in my iPhone app.

I am using AV Foundation Framework to grab camera frames using this method:

- (void)captureOutput:(AVCaptureOutput *)captureOutput didOutputSampleBuffer:(CMSampleBufferRef)sampleBuffer fromConnection:(AVCaptureConnection *)connection {
    CVImageBufferRef imageBuffer = CMSampleBufferGetImageBuffer(sampleBuffer);
    CVPixelBufferLockBaseAddress(imageBuffer,0);
    uint8_t *baseAddress = (uint8_t *)CVPixelBufferGetBaseAddress(imageBuffer);
    size_t bytesPerRow = CVPixelBufferGetBytesPerRow(imageBuffer);
    size_t width = CVPixelBufferGetWidth(imageBuffer);
    size_t height = CVPixelBufferGetHeight(imageBuffer);
    CGColorSpaceRef colorSpace = CGColorSpaceCreateDeviceRGB();
    CGContextRef newContext = CGBitmapContextCreate(baseAddress, width, height, 8, bytesPerRow, colorSpace, kCGBitmapByteOrder32Little | kCGImageAlphaPremultipliedFirst);
    CGImageRef newImage = CGBitmapContextCreateImage(newContext);
    CVPixelBufferUnlockBaseAddress(imageBuffer,0);
    CGContextRelease(newContext);
    CGColorSpaceRelease(colorSpace);

    UIImage *image= [UIImage imageWithCGImage:newImage scale:1.0 orientation:UIImageOrientationRight];
    self.imageView.image = image;

    CGImageRelease(newImage);

} 

However, I am seeing an error in the debug console as its runs:

<Error>: CGDataProviderCreateWithCopyOfData: vm_copy failed: status 2.

Has anyone ever seen this? By commenting out lines I have narrowed the problem line out to:

CGImageRef newImage = CGBitmapContextCreateImage(newContext);

but I am not sure how to get rid of it. Functionally, it works great. So clearly, the CGImage is being created, but I need to know what is causing the error so it doesn't affect other parts.

Many thanks. Any help/advice would be great! Brett


回答1:


Disclaimer: this is pure speculation. Not anymore.

vm_copy() is a kernel call to copy virtual memory from one place to another (manpage).

The return value you get is KERN_PROTECTION_FAILURE, "The source region is protected against reading, or the destination region is protected against writing."

So for some reason CGDataProviderCreateWithCopyOfData calls this to copy some memory, and fails. maybe it is just trying vm_copy as a fast method first, and then falls back to a slower method (since you say everything works).

If you malloc a chunk of memory, memcpy the memory from baseAddress to your own memory, and use that to create the image, the warning vanishes. So:

uint8_t *tmp = (uint8_t *)CVPixelBufferGetBaseAddress(imageBuffer);
int bytes = ... // determine number of bytes from height * bytesperrow
uint8_t *baseAddress = malloc(bytes);
memcpy(baseAddress,tmp,bytes);

// unlock the memory, do other stuff, but don't forget:
free(baseAddress);


来源:https://stackoverflow.com/questions/3367849/cgbitmapcontextcreateimage-vm-copy-failed-iphone-sdk

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!