summaryrefslogtreecommitdiff
path: root/src/ipa/simple
diff options
context:
space:
mode:
Diffstat (limited to 'src/ipa/simple')
-rw-r--r--src/ipa/simple/algorithms/agc.cpp2
-rw-r--r--src/ipa/simple/algorithms/blc.cpp19
-rw-r--r--src/ipa/simple/algorithms/blc.h1
-rw-r--r--src/ipa/simple/ipa_context.h4
-rw-r--r--src/ipa/simple/soft_simple.cpp21
5 files changed, 43 insertions, 4 deletions
diff --git a/src/ipa/simple/algorithms/agc.cpp b/src/ipa/simple/algorithms/agc.cpp
index 783dfb8b..df92edd7 100644
--- a/src/ipa/simple/algorithms/agc.cpp
+++ b/src/ipa/simple/algorithms/agc.cpp
@@ -29,7 +29,7 @@ static constexpr unsigned int kExposureBinsCount = 5;
static constexpr float kExposureOptimal = kExposureBinsCount / 2.0;
/*
- * The below value implements the hysteresis for the exposure adjustment.
+ * This implements the hysteresis for the exposure adjustment.
* It is small enough to have the exposure close to the optimal, and is big
* enough to prevent the exposure from wobbling around the optimal value.
*/
diff --git a/src/ipa/simple/algorithms/blc.cpp b/src/ipa/simple/algorithms/blc.cpp
index b9f2aaa6..b4e32fe1 100644
--- a/src/ipa/simple/algorithms/blc.cpp
+++ b/src/ipa/simple/algorithms/blc.cpp
@@ -21,10 +21,24 @@ BlackLevel::BlackLevel()
{
}
+int BlackLevel::init(IPAContext &context, const YamlObject &tuningData)
+{
+ auto blackLevel = tuningData["blackLevel"].get<int16_t>();
+ if (blackLevel.has_value()) {
+ /*
+ * Convert 16 bit values from the tuning file to 8 bit black
+ * level for the SoftISP.
+ */
+ context.configuration.black.level = blackLevel.value() >> 8;
+ }
+ return 0;
+}
+
int BlackLevel::configure(IPAContext &context,
[[maybe_unused]] const IPAConfigInfo &configInfo)
{
- context.activeState.blc.level = 255;
+ context.activeState.blc.level =
+ context.configuration.black.level.value_or(255);
return 0;
}
@@ -34,6 +48,9 @@ void BlackLevel::process(IPAContext &context,
const SwIspStats *stats,
[[maybe_unused]] ControlList &metadata)
{
+ if (context.configuration.black.level.has_value())
+ return;
+
if (frameContext.sensor.exposure == exposure_ &&
frameContext.sensor.gain == gain_) {
return;
diff --git a/src/ipa/simple/algorithms/blc.h b/src/ipa/simple/algorithms/blc.h
index 828ad8b1..2cf2a877 100644
--- a/src/ipa/simple/algorithms/blc.h
+++ b/src/ipa/simple/algorithms/blc.h
@@ -19,6 +19,7 @@ public:
BlackLevel();
~BlackLevel() = default;
+ int init(IPAContext &context, const YamlObject &tuningData) override;
int configure(IPAContext &context, const IPAConfigInfo &configInfo) override;
void process(IPAContext &context, const uint32_t frame,
IPAFrameContext &frameContext,
diff --git a/src/ipa/simple/ipa_context.h b/src/ipa/simple/ipa_context.h
index 3519f20f..fd121eeb 100644
--- a/src/ipa/simple/ipa_context.h
+++ b/src/ipa/simple/ipa_context.h
@@ -8,6 +8,7 @@
#pragma once
#include <array>
+#include <optional>
#include <stdint.h>
#include <libipa/fc_queue.h>
@@ -22,6 +23,9 @@ struct IPASessionConfiguration {
int32_t exposureMin, exposureMax;
double againMin, againMax, againMinStep;
} agc;
+ struct {
+ std::optional<uint8_t> level;
+ } black;
};
struct IPAActiveState {
diff --git a/src/ipa/simple/soft_simple.cpp b/src/ipa/simple/soft_simple.cpp
index b28c7039..ac2a9421 100644
--- a/src/ipa/simple/soft_simple.cpp
+++ b/src/ipa/simple/soft_simple.cpp
@@ -57,7 +57,7 @@ public:
void stop() override;
void queueRequest(const uint32_t frame, const ControlList &controls) override;
- void fillParamsBuffer(const uint32_t frame) override;
+ void computeParams(const uint32_t frame) override;
void processStats(const uint32_t frame, const uint32_t bufferId,
const ControlList &sensorControls) override;
@@ -184,6 +184,11 @@ int IPASoftSimple::configure(const IPAConfigInfo &configInfo)
const ControlInfo &exposureInfo = sensorInfoMap_.find(V4L2_CID_EXPOSURE)->second;
const ControlInfo &gainInfo = sensorInfoMap_.find(V4L2_CID_ANALOGUE_GAIN)->second;
+ /* Clear the IPA context before the streaming session. */
+ context_.configuration = {};
+ context_.activeState = {};
+ context_.frameContexts.clear();
+
context_.configuration.agc.exposureMin = exposureInfo.min().get<int32_t>();
context_.configuration.agc.exposureMax = exposureInfo.max().get<int32_t>();
if (!context_.configuration.agc.exposureMin) {
@@ -201,6 +206,17 @@ int IPASoftSimple::configure(const IPAConfigInfo &configInfo)
(context_.configuration.agc.againMax -
context_.configuration.agc.againMin) /
100.0;
+ if (!context_.configuration.black.level.has_value() &&
+ camHelper_->blackLevel().has_value()) {
+ /*
+ * The black level from camHelper_ is a 16 bit value, software ISP
+ * works with 8 bit pixel values, both regardless of the actual
+ * sensor pixel width. Hence we obtain the pixel-based black value
+ * by dividing the value from the helper by 256.
+ */
+ context_.configuration.black.level =
+ camHelper_->blackLevel().value() / 256;
+ }
} else {
/*
* The camera sensor gain (g) is usually not equal to the value written
@@ -245,6 +261,7 @@ int IPASoftSimple::start()
void IPASoftSimple::stop()
{
+ context_.frameContexts.clear();
}
void IPASoftSimple::queueRequest(const uint32_t frame, const ControlList &controls)
@@ -255,7 +272,7 @@ void IPASoftSimple::queueRequest(const uint32_t frame, const ControlList &contro
algo->queueRequest(context_, frame, frameContext, controls);
}
-void IPASoftSimple::fillParamsBuffer(const uint32_t frame)
+void IPASoftSimple::computeParams(const uint32_t frame)
{
IPAFrameContext &frameContext = context_.frameContexts.get(frame);
for (auto const &algo : algorithms())