Skip to content
Browse files
Retain cropData object in ImageEditingManager.cropImage
All struct args are passed into NativeModule methods via references. If blocks access those references, we don't move those references to the heap. This means that by the time that the block accesses the struct arg, it could be freed. This can crash the program.

The solution is simple: we copy the struct arg, and access the copy in the block. This ensures that the block will make a copy, which prevents the underlying data structures from being released by the time that the block accesses the struct arg.

[iOS][Fixed] - Retain cropData struct arg in ImageEditingManager.cropImage call

Differential Revision: D18076026

fbshipit-source-id: 1a7bb602606ff1afac38ad5451662c82fa86f205
  • Loading branch information
RSNara authored and facebook-github-bot committed Oct 23, 2019
1 parent 94845b5 commit 002d3c179dd2515f0a4d894d9b7f70c4e538f728
Showing 1 changed file with 6 additions and 3 deletions.
@@ -53,6 +53,9 @@ @implementation RCTImageEditingManager
@"height": @(cropData.size().height()),

// We must keep a copy of cropData so that we can access data from it at a later time
JS::NativeImageEditor::Options cropDataCopy = cropData;

[[_bridge moduleForName:@"ImageLoader" lazilyLoadIfNecessary:YES]
loadImageWithURLRequest:imageRequest callback:^(NSError *error, UIImage *image) {
@@ -68,9 +71,9 @@ @implementation RCTImageEditingManager
UIImage *croppedImage = RCTTransformImage(image, targetSize, image.scale, transform);

// Scale image
if (cropData.displaySize()) {
targetSize = [RCTConvert CGSize:@{@"width": @(cropData.displaySize()->width()), @"height": @(cropData.displaySize()->height())}]; // in pixels
RCTResizeMode resizeMode = [RCTConvert RCTResizeMode:cropData.resizeMode() ?: @"contain"];
if (cropDataCopy.displaySize()) {
targetSize = [RCTConvert CGSize:@{@"width": @(cropDataCopy.displaySize()->width()), @"height": @(cropDataCopy.displaySize()->height())}]; // in pixels
RCTResizeMode resizeMode = [RCTConvert RCTResizeMode:cropDataCopy.resizeMode() ?: @"contain"];
targetRect = RCTTargetRect(croppedImage.size, targetSize, 1, resizeMode);
transform = RCTTransformFromTargetRect(croppedImage.size, targetRect);
croppedImage = RCTTransformImage(croppedImage, targetSize, image.scale, transform);

0 comments on commit 002d3c1

Please sign in to comment.