21#include "rawspeedconfig.h"
45#if __has_feature(address_sanitizer) || defined(__SANITIZE_ADDRESS__)
61 if (
cpp > std::numeric_limits<
decltype(
cpp)>::max() / _bpc)
62 ThrowRDE(
"Components-per-pixel is too large.");
69 static constexpr const auto alignment = 16;
71 if (
dim.x > 65535 ||
dim.y > 65535)
72 ThrowRDE(
"Dimensions too large for allocation.");
73 if (
dim.x <= 0 ||
dim.y <= 0)
74 ThrowRDE(
"Dimension of one sides is less than 1 - cannot allocate image.");
76 ThrowRDE(
"Unspecified component count - cannot allocate image.");
78 ThrowRDE(
"Duplicate data allocation in createData.");
85#if defined(DEBUG) || __has_feature(address_sanitizer) || \
86 defined(__SANITIZE_ADDRESS__)
88 pitch += alignment * alignment;
94#if defined(DEBUG) || __has_feature(address_sanitizer) || \
95 defined(__SANITIZE_ADDRESS__)
106 for (
int j = 0; j <
dim.y; j++) {
115#if __has_feature(address_sanitizer) || defined(__SANITIZE_ADDRESS__)
134#if __has_feature(address_sanitizer) || defined(__SANITIZE_ADDRESS__)
155 ThrowRDE(
"Attempted to set Components per pixel after data allocation");
158 "Only up to 4 components per pixel is support - attempted to set: %u",
181 "to create new subframe larger than original "
182 "size. Crop skipped.");
187 "crop offset. Crop skipped.");
192 if (
isCFA &&
cfa.getDcrawFilter() != 1 &&
cfa.getDcrawFilter() != 9) {
203 ThrowRDE(
"(internal) Bad pixel map cannot be allocated before image.");
213 if (mBadPixelPositions.empty())
219 for (
unsigned int pos : mBadPixelPositions) {
229 mBadPixelPositions.clear();
233#if !defined(EMULATE_DCRAW_BAD_PIXELS)
245 i != mBadPixelPositions.end(); ++i) {
265 pix[0] = total / div;
273 const int height = [&]() {
283 const int y_per_thread = (height + threads - 1) / threads;
286#pragma omp parallel for default(none) \
287 firstprivate(threads, y_per_thread, height, task) num_threads(threads) \
290 for (
int i = 0; i < threads; i++) {
291 int y_offset = std::min(i * y_per_thread, height);
292 int y_end = std::min((i + 1) * y_per_thread, height);
304 for (
int y = start_y;
y < end_y;
y++) {
305 for (
int x = 0;
x < gw;
x++) {
306 const auto block = bad[
y].getBlock(32 / 8,
x);
309 if (std::all_of(block.begin(), block.end(),
310 [](
const auto&
val) { return val == 0; }))
314 for (
int i = 0; i < 4; i++) {
315 for (
int j = 0; j < 8; j++) {
316 if (1 != ((block(i) >> j) & 1))
329 if (area.
area() <= 0)
341 int _start_y,
int _end_y) noexcept
363 data->setError(e.what());
365 data->setError(e.what());
367 data->setError(e.what());
370 __builtin_unreachable();
375 if (
table ==
nullptr) {
382 table = std::move(t);
388 auto t = std::make_unique<TableLookUp>(1, dither);
389 t->setTable(0, table_);
assert(dim.area() >=area)
void fixBadPixels() REQUIRES(!mBadPixelMutex)
void setCpp(uint32_t val)
friend class RawImageWorker
iPoint2D RAWSPEED_READONLY getCropOffset() const
void transferBadPixelsToMap() REQUIRES(!mBadPixelMutex)
iPoint2D RAWSPEED_READONLY getUncroppedDim() const
void subFrame(iRectangle2D cropped)
virtual void fixBadPixel(uint32_t x, uint32_t y, int component=0)=0
Array2DRef< std::byte > getByteDataAsUncroppedArray2DRef() noexcept
virtual void anchor() const
void setTable(const std::vector< uint16_t > &table_, bool dither)
void fixBadPixelsThread(int start_y, int end_y)
std::vector< uint8_t, AlignedAllocator< uint8_t, 16 > > mBadPixelMap
void startWorker(RawImageWorker::RawImageWorkerTask task, bool cropped)
CroppedArray2DRef< uint16_t > getU16DataAsCroppedArray2DRef() noexcept
void clearArea(iRectangle2D area)
std::unique_ptr< TableLookUp > table
uint32_t mBadPixelMapPitch
std::vector< uint8_t, DefaultInitAllocatorAdaptor< uint8_t, AlignedAllocator< uint8_t, 16 > > > data
void performTask() noexcept
RawImageWorker(RawImageData *img, RawImageWorkerTask task, int start_y, int end_y) noexcept
constexpr bool RAWSPEED_READONLY isThisInside(const iPoint2D &rhs) const
constexpr int getTop() const
constexpr bool RAWSPEED_READONLY hasPositiveArea() const
constexpr int getBottom() const
iRectangle2D getOverlap(const iRectangle2D &other) const
constexpr int getWidth() const
constexpr int getLeft() const
int RAWSPEED_READNONE rawspeed_get_number_of_processor_cores()
constexpr uint64_t RAWSPEED_READNONE roundUpDivisionSafe(uint64_t value, uint64_t div)
constexpr uint64_t RAWSPEED_READNONE roundUp(uint64_t value, uint64_t multiple)
constexpr RAWSPEED_READNONE Ttgt implicit_cast(Tsrc value)
void writeLog(DEBUG_PRIO priority, const char *format,...)
Array2DRef(Array1DRef< T > data, int width, int height, int pitch) -> Array2DRef< T >
constexpr RAWSPEED_READNONE bool isAligned(T value, size_t multiple)
static void PoisonMemoryRegion(const volatile void *addr, size_t size)
static void UnPoisonMemoryRegion(const volatile void *addr, size_t size)