ipa: Pass IPA initialization settings to IPAInterface::init()

Add a new IPASettings class to pass IPA initialization settings through
the IPAInterface::init() method. The settings currently only contain the
name of a configuration file, and are expected to be extended later.

Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
Reviewed-by: Jacopo Mondi <jacopo@jmondi.org>
This commit is contained in:
Laurent Pinchart 2020-04-27 02:36:18 +03:00
parent 26a4b03ed8
commit a6de903089
14 changed files with 82 additions and 21 deletions

View file

@ -18,6 +18,10 @@ struct ipa_context {
const struct ipa_context_ops *ops; const struct ipa_context_ops *ops;
}; };
struct ipa_settings {
const char *configuration_file;
};
struct ipa_stream { struct ipa_stream {
unsigned int id; unsigned int id;
unsigned int pixel_format; unsigned int pixel_format;
@ -63,7 +67,8 @@ struct ipa_callback_ops {
struct ipa_context_ops { struct ipa_context_ops {
void (*destroy)(struct ipa_context *ctx); void (*destroy)(struct ipa_context *ctx);
void *(*get_interface)(struct ipa_context *ctx); void *(*get_interface)(struct ipa_context *ctx);
void (*init)(struct ipa_context *ctx); void (*init)(struct ipa_context *ctx,
const struct ipa_settings *settings);
int (*start)(struct ipa_context *ctx); int (*start)(struct ipa_context *ctx);
void (*stop)(struct ipa_context *ctx); void (*stop)(struct ipa_context *ctx);
void (*register_callbacks)(struct ipa_context *ctx, void (*register_callbacks)(struct ipa_context *ctx,
@ -100,6 +105,10 @@ struct ipa_context *ipaCreate();
namespace libcamera { namespace libcamera {
struct IPASettings {
std::string configurationFile;
};
struct IPAStream { struct IPAStream {
unsigned int pixelFormat; unsigned int pixelFormat;
Size size; Size size;
@ -121,7 +130,7 @@ class IPAInterface
public: public:
virtual ~IPAInterface() {} virtual ~IPAInterface() {}
virtual int init() = 0; virtual int init(const IPASettings &settings) = 0;
virtual int start() = 0; virtual int start() = 0;
virtual void stop() = 0; virtual void stop() = 0;

View file

@ -79,11 +79,15 @@ void *IPAInterfaceWrapper::get_interface(struct ipa_context *_ctx)
return ctx->ipa_.get(); return ctx->ipa_.get();
} }
void IPAInterfaceWrapper::init(struct ipa_context *_ctx) void IPAInterfaceWrapper::init(struct ipa_context *_ctx,
const struct ipa_settings *settings)
{ {
IPAInterfaceWrapper *ctx = static_cast<IPAInterfaceWrapper *>(_ctx); IPAInterfaceWrapper *ctx = static_cast<IPAInterfaceWrapper *>(_ctx);
ctx->ipa_->init(); IPASettings ipaSettings{
.configurationFile = settings->configuration_file
};
ctx->ipa_->init(ipaSettings);
} }
int IPAInterfaceWrapper::start(struct ipa_context *_ctx) int IPAInterfaceWrapper::start(struct ipa_context *_ctx)

View file

@ -23,7 +23,8 @@ public:
private: private:
static void destroy(struct ipa_context *ctx); static void destroy(struct ipa_context *ctx);
static void *get_interface(struct ipa_context *ctx); static void *get_interface(struct ipa_context *ctx);
static void init(struct ipa_context *ctx); static void init(struct ipa_context *ctx,
const struct ipa_settings *settings);
static int start(struct ipa_context *ctx); static int start(struct ipa_context *ctx);
static void stop(struct ipa_context *ctx); static void stop(struct ipa_context *ctx);
static void register_callbacks(struct ipa_context *ctx, static void register_callbacks(struct ipa_context *ctx,

View file

@ -32,7 +32,7 @@ LOG_DEFINE_CATEGORY(IPARkISP1)
class IPARkISP1 : public IPAInterface class IPARkISP1 : public IPAInterface
{ {
public: public:
int init() override { return 0; } int init(const IPASettings &settings) override { return 0; }
int start() override { return 0; } int start() override { return 0; }
void stop() override {} void stop() override {}

View file

@ -31,7 +31,7 @@ public:
IPAVimc(); IPAVimc();
~IPAVimc(); ~IPAVimc();
int init() override; int init(const IPASettings &settings) override;
int start() override; int start() override;
void stop() override; void stop() override;
@ -61,7 +61,7 @@ IPAVimc::~IPAVimc()
::close(fd_); ::close(fd_);
} }
int IPAVimc::init() int IPAVimc::init(const IPASettings &settings)
{ {
trace(IPAOperationInit); trace(IPAOperationInit);

View file

@ -19,7 +19,7 @@ public:
IPAContextWrapper(struct ipa_context *context); IPAContextWrapper(struct ipa_context *context);
~IPAContextWrapper(); ~IPAContextWrapper();
int init() override; int init(const IPASettings &settings) override;
int start() override; int start() override;
void stop() override; void stop() override;
void configure(const std::map<unsigned int, IPAStream> &streamConfig, void configure(const std::map<unsigned int, IPAStream> &streamConfig,

View file

@ -69,15 +69,18 @@ IPAContextWrapper::~IPAContextWrapper()
ctx_->ops->destroy(ctx_); ctx_->ops->destroy(ctx_);
} }
int IPAContextWrapper::init() int IPAContextWrapper::init(const IPASettings &settings)
{ {
if (intf_) if (intf_)
return intf_->init(); return intf_->init(settings);
if (!ctx_) if (!ctx_)
return 0; return 0;
ctx_->ops->init(ctx_); struct ipa_settings c_settings;
c_settings.configuration_file = settings.configurationFile.c_str();
ctx_->ops->init(ctx_, &c_settings);
return 0; return 0;
} }

View file

@ -92,6 +92,16 @@
* \brief The IPA context operations * \brief The IPA context operations
*/ */
/**
* \struct ipa_settings
* \brief IPA initialization settings for the IPA context operations
* \sa IPASettings
*
* \var ipa_settings::configuration_file
* \brief The name of the IPA configuration file (may be null or point to an
* empty string)
*/
/** /**
* \struct ipa_stream * \struct ipa_stream
* \brief Stream information for the IPA context operations * \brief Stream information for the IPA context operations
@ -231,6 +241,7 @@
* \var ipa_context_ops::init * \var ipa_context_ops::init
* \brief Initialise the IPA context * \brief Initialise the IPA context
* \param[in] ctx The IPA context * \param[in] ctx The IPA context
* \param[in] settings The IPA initialization settings
* *
* \sa libcamera::IPAInterface::init() * \sa libcamera::IPAInterface::init()
*/ */
@ -310,6 +321,24 @@
namespace libcamera { namespace libcamera {
/**
* \struct IPASettings
* \brief IPA interface initialization settings
*
* The IPASettings structure stores data passed to the IPAInterface::init()
* function. The data contains settings that don't depend on a particular camera
* or pipeline configuration and are valid for the whole life time of the IPA
* interface.
*/
/**
* \var IPASettings::configurationFile
* \brief The name of the IPA configuration file
*
* This field may be an empty string if the IPA doesn't require a configuration
* file.
*/
/** /**
* \struct IPAStream * \struct IPAStream
* \brief Stream configuration for the IPA interface * \brief Stream configuration for the IPA interface
@ -424,6 +453,11 @@ namespace libcamera {
/** /**
* \fn IPAInterface::init() * \fn IPAInterface::init()
* \brief Initialise the IPAInterface * \brief Initialise the IPAInterface
* \param[in] settings The IPA initialization settings
*
* This function initializes the IPA interface. It shall be called before any
* other function of the IPAInterface. The \a settings carry initialization
* parameters that are valid for the whole life time of the IPA interface.
*/ */
/** /**

View file

@ -401,7 +401,7 @@ int RkISP1CameraData::loadIPA()
ipa_->queueFrameAction.connect(this, ipa_->queueFrameAction.connect(this,
&RkISP1CameraData::queueFrameAction); &RkISP1CameraData::queueFrameAction);
ipa_->init(); ipa_->init(IPASettings{});
return 0; return 0;
} }

View file

@ -385,7 +385,7 @@ bool PipelineHandlerVimc::match(DeviceEnumerator *enumerator)
if (data->ipa_ == nullptr) if (data->ipa_ == nullptr)
LOG(VIMC, Warning) << "no matching IPA found"; LOG(VIMC, Warning) << "no matching IPA found";
else else
data->ipa_->init(); data->ipa_->init(IPASettings{});
/* Locate and open the capture video node. */ /* Locate and open the capture video node. */
if (data->init(media)) if (data->init(media))

View file

@ -26,7 +26,7 @@ public:
IPAProxyLinux(IPAModule *ipam); IPAProxyLinux(IPAModule *ipam);
~IPAProxyLinux(); ~IPAProxyLinux();
int init() override { return 0; } int init(const IPASettings &settings) override { return 0; }
int start() override { return 0; } int start() override { return 0; }
void stop() override {} void stop() override {}
void configure(const std::map<unsigned int, IPAStream> &streamConfig, void configure(const std::map<unsigned int, IPAStream> &streamConfig,

View file

@ -25,7 +25,7 @@ class IPAProxyThread : public IPAProxy, public Object
public: public:
IPAProxyThread(IPAModule *ipam); IPAProxyThread(IPAModule *ipam);
int init() override; int init(const IPASettings &settings) override;
int start() override; int start() override;
void stop() override; void stop() override;
@ -97,9 +97,9 @@ IPAProxyThread::IPAProxyThread(IPAModule *ipam)
valid_ = true; valid_ = true;
} }
int IPAProxyThread::init() int IPAProxyThread::init(const IPASettings &settings)
{ {
int ret = ipa_->init(); int ret = ipa_->init(settings);
if (ret) if (ret)
return ret; return ret;

View file

@ -98,7 +98,8 @@ protected:
} }
/* Test initialization of IPA module. */ /* Test initialization of IPA module. */
ipa_->init(); IPASettings settings;
ipa_->init(settings);
timer.start(1000); timer.start(1000);
while (timer.isRunning() && trace_ != IPAOperationInit) while (timer.isRunning() && trace_ != IPAOperationInit)
dispatcher->processEvents(); dispatcher->processEvents();

View file

@ -43,8 +43,14 @@ public:
{ {
} }
int init() override int init(const IPASettings &settings) override
{ {
if (settings.configurationFile != "/ipa/configuration/file") {
cerr << "init(): Invalid configuration file" << endl;
report(Op_init, TestFail);
return 0;
}
report(Op_init, TestPass); report(Op_init, TestPass);
return 0; return 0;
} }
@ -339,7 +345,10 @@ protected:
* Test init(), start() and stop() last to ensure nothing in the * Test init(), start() and stop() last to ensure nothing in the
* wrappers or serializer depends on them being called first. * wrappers or serializer depends on them being called first.
*/ */
ret = INVOKE(init); IPASettings settings{
.configurationFile = "/ipa/configuration/file"
};
ret = INVOKE(init, settings);
if (ret == TestFail) { if (ret == TestFail) {
cerr << "Failed to run init()"; cerr << "Failed to run init()";
return TestFail; return TestFail;