Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

OpenCV: avoiding memory corruption when using Mat constructors taking primitive arrays #1002

Merged
merged 8 commits into from
Feb 1, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@

* Add new array constructors to `opencv_core.Mat` that copy data for convenience ([pull #1002](https://github.com/bytedeco/javacpp-presets/pull/1002))
* Rebase `PrimitiveScalar` on `PrimitiveScalarBase` in presets for Arrow for easy access to `data()` ([issue #998](https://github.com/bytedeco/javacpp-presets/issues/998))
* Add `NamedMetadataOperations.h` implementing data retrieval operations for LLVM nodes ([pull #995](https://github.com/bytedeco/javacpp-presets/pull/995))
* Enable OpenMP for ONNX Runtime on Mac once again ([issue #917](https://github.com/bytedeco/javacpp-presets/issues/917))
Expand Down
67 changes: 44 additions & 23 deletions opencv/src/gen/java/org/bytedeco/opencv/opencv_core/Mat.java
Original file line number Diff line number Diff line change
Expand Up @@ -220,7 +220,7 @@ public class Mat extends AbstractMat {
return (Mat)super.position(position);
}
@Override public Mat getPointer(long i) {
return new Mat(this).position(position + i);
return new Mat((Pointer)this).position(position + i);
}

/**
Expand Down Expand Up @@ -358,31 +358,52 @@ the end of each row, if any. If the parameter is missing (set to AUTO_STEP ), no
public Mat(int rows, int cols, int type, Pointer data, @Cast("size_t") long step/*=AUTO_STEP*/) { super((Pointer)null); allocate(rows, cols, type, data, step); this.pointer = data; }
private native void allocate(int rows, int cols, int type, Pointer data, @Cast("size_t") long step/*=AUTO_STEP*/);
private Pointer pointer; // a reference to prevent deallocation
HGuillemet marked this conversation as resolved.
Show resolved Hide resolved
/** Calls {@link #Mat(int, int, int, Pointer, long) Mat(rows, cols, type, data, AUTO_STEP)} as with {@link #Mat(int, int, int, Pointer, boolean) Mat(rows, cols, type, data, false)}. */
public Mat(int rows, int cols, int type, Pointer data) { this(rows, cols, type, data, AUTO_STEP); }
public Mat(CvArr arr) { super(cvarrToMat(arr)); this.pointer = arr; }
public Mat(Point points) { this(1, Math.max(1, points.limit() - points.position()), CV_32SC2, points); this.pointer = points; }
public Mat(Point2f points) { this(1, Math.max(1, points.limit() - points.position()), CV_32FC2, points); this.pointer = points; }
public Mat(Point2d points) { this(1, Math.max(1, points.limit() - points.position()), CV_64FC2, points); this.pointer = points; }
public Mat(Point3i points) { this(1, Math.max(1, points.limit() - points.position()), CV_32SC3, points); this.pointer = points; }
public Mat(Point3f points) { this(1, Math.max(1, points.limit() - points.position()), CV_32FC3, points); this.pointer = points; }
public Mat(Point3d points) { this(1, Math.max(1, points.limit() - points.position()), CV_64FC3, points); this.pointer = points; }
public Mat(Scalar scalar) { this(1, Math.max(1, scalar.limit() - scalar.position()), CV_64FC4, scalar); this.pointer = scalar; }
public Mat(Scalar4i scalar) { this(1, Math.max(1, scalar.limit() - scalar.position()), CV_32SC4, scalar); this.pointer = scalar; }
/** Warning: If {@code copyData} is false, the data of the OpenCV Mat returned by this constructor is externally allocated from OpenCV point of view,
* and will not benefit from OpenCV reference counting feature. One must ensure that the data does not get implicitly or explicitly deallocated when
* another Mat has been created pointing to the same data with, e.g., reshape(), rowRange(), etc... */
public Mat(int rows, int cols, int type, Pointer data, boolean copyData) { super((Pointer)null);
if (copyData) { allocate(rows, cols, type); data().put(data); } else { allocate(rows, cols, type, data, AUTO_STEP); this.pointer = data; }
}
/** Calls {@link #Mat(int, int, int, Pointer, boolean) Mat(1, (int)Math.min(data.limit() - data.position(), Integer.MAX_VALUE), type, data, copyData)}. */
public Mat(int type, Pointer data, boolean copyData) { this(1, (int)Math.min(data.limit() - data.position(), Integer.MAX_VALUE), type, data, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_32SC2, points, copyData)}. */ public Mat(Point points, boolean copyData) { this(CV_32SC2, points, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_32FC2, points, copyData)}. */ public Mat(Point2f points, boolean copyData) { this(CV_32FC2, points, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_64FC2, points, copyData)}. */ public Mat(Point2d points, boolean copyData) { this(CV_64FC2, points, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_32SC3, points, copyData)}. */ public Mat(Point3i points, boolean copyData) { this(CV_32SC3, points, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_32FC3, points, copyData)}. */ public Mat(Point3f points, boolean copyData) { this(CV_32FC3, points, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_64FC3, points, copyData)}. */ public Mat(Point3d points, boolean copyData) { this(CV_64FC3, points, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_64FC4, scalar, copyData)}. */ public Mat(Scalar scalar, boolean copyData) { this(CV_64FC4, scalar, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_32SC4, scalar, copyData)}. */ public Mat(Scalar4i scalar, boolean copyData) { this(CV_32SC4, scalar, copyData); }
/** Calls {@link #Mat(Point, boolean) Mat(points, false)}. */ public Mat(Point points) { this(points, false); }
/** Calls {@link #Mat(Point2f, boolean) Mat(points, false)}. */ public Mat(Point2f points) { this(points, false); }
/** Calls {@link #Mat(Point2d, boolean) Mat(points, false)}. */ public Mat(Point2d points) { this(points, false); }
/** Calls {@link #Mat(Point3i, boolean) Mat(points, false)}. */ public Mat(Point3i points) { this(points, false); }
/** Calls {@link #Mat(Point3f, boolean) Mat(points, false)}. */ public Mat(Point3f points) { this(points, false); }
/** Calls {@link #Mat(Point3d, boolean) Mat(points, false)}. */ public Mat(Point3d points) { this(points, false); }
/** Calls {@link #Mat(Scalar, boolean) Mat(scalar, false)}. */ public Mat(Scalar scalar) { this(scalar, false); }
/** Calls {@link #Mat(Scalar4i, boolean) Mat(scalar, false)}. */ public Mat(Scalar4i scalar) { this(scalar, false); }
public Mat(byte ... b) { this(b, false); }
public Mat(byte[] b, boolean signed) { this(new BytePointer(b), signed); }
public Mat(short ... s) { this(s, true); }
public Mat(short[] s, boolean signed) { this(new ShortPointer(s), signed); }
public Mat(int ... n) { this(new IntPointer(n)); }
public Mat(double ... d) { this(new DoublePointer(d)); }
public Mat(float ... f) { this(new FloatPointer(f)); }
private Mat(long rows, long cols, int type, Pointer data) { this((int)Math.min(rows, Integer.MAX_VALUE), (int)Math.min(cols, Integer.MAX_VALUE), type, data, AUTO_STEP); }
public Mat(BytePointer p) { this(p, false); }
public Mat(BytePointer p, boolean signed) { this(1, Math.max(1, p.limit() - p.position()), signed ? CV_8SC1 : CV_8UC1, p); }
public Mat(ShortPointer p) { this(p, false); }
public Mat(ShortPointer p, boolean signed) { this(1, Math.max(1, p.limit() - p.position()), signed ? CV_16SC1 : CV_16UC1, p); }
public Mat(IntPointer p) { this(1, Math.max(1, p.limit() - p.position()), CV_32SC1, p); }
public Mat(FloatPointer p) { this(1, Math.max(1, p.limit() - p.position()), CV_32FC1, p); }
public Mat(DoublePointer p) { this(1, Math.max(1, p.limit() - p.position()), CV_64FC1, p); }
public Mat(short ... s) { this(s, false); }
public Mat(byte[] b, boolean signed) { this(1, b.length, signed ? CV_8SC1 : CV_8UC1); data().put(b); }
public Mat(short[] s, boolean signed) { this(1, s.length, signed ? CV_16SC1 : CV_16UC1); new ShortPointer(data()).put(s); }
public Mat(int ... n) { this(1, n.length, CV_32SC1); new IntPointer(data()).put(n); }
public Mat(double ... d) { this(1, d.length, CV_64FC1); new DoublePointer(data()).put(d); }
public Mat(float ... f) { this(1, f.length, CV_32FC1); new FloatPointer(data()).put(f); }
/** Calls {@link #Mat(BytePointer, boolean) Mat(p, false)}. */ public Mat(BytePointer p) { this(p, false); }
/** Calls {@link #Mat(ShortPointer, boolean) Mat(p, false)}. */ public Mat(ShortPointer p) { this(p, false); }
/** Calls {@link #Mat(BytePointer, boolean, boolean) Mat(p, signed, false)}. */ public Mat(BytePointer p, boolean signed) { this(p, signed, false); }
/** Calls {@link #Mat(ShortPointer, boolean, boolean) Mat(p, signed, false)}. */ public Mat(ShortPointer p, boolean signed) { this(p, signed, false); }
/** Calls {@link #Mat(IntPointer, boolean) Mat(p, false)}. */ public Mat(IntPointer p) { this(p, false); }
/** Calls {@link #Mat(FloatPointer, boolean) Mat(p, false)}. */ public Mat(FloatPointer p) { this(p, false); }
/** Calls {@link #Mat(DoublePointer, boolean) Mat(p, false)}. */ public Mat(DoublePointer p) { this(p, false); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(signed ? CV_8SC1 : CV_8UC1, p, copyData)}. */ public Mat(BytePointer p, boolean signed, boolean copyData) { this(signed ? CV_8SC1 : CV_8UC1, p, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(signed ? CV_16SC1 : CV_16UC1, p, copyData)}. */ public Mat(ShortPointer p, boolean signed, boolean copyData) { this(signed ? CV_16SC1 : CV_16UC1, p, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_32SC1, p, copyData)}. */ public Mat(IntPointer p, boolean copyData) { this(CV_32SC1, p, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_32FC1, p, copyData)}. */ public Mat(FloatPointer p, boolean copyData) { this(CV_32FC1, p, copyData); }
/** Calls {@link #Mat(int, Pointer, boolean) Mat(CV_64FC1, p, copyData)}. */ public Mat(DoublePointer p, boolean copyData) { this(CV_64FC1, p, copyData); }

/** \overload
@param size 2D array size: Size(cols, rows) . In the Size() constructor, the number of rows and the
Expand Down
Loading