blob: ab3187da6964bf21286550d1389523935ff0c3d6 [file] [log] [blame]
/*
* smart_analyzer_loader.cpp - smart analyzer loader
*
* Copyright (c) 2015 Intel Corporation
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* Author: Zong Wei <wei.zong@intel.com>
*/
#include "smart_analyzer_loader.h"
#include "analyzer_loader.h"
#include "smart_analyzer.h"
#include "smart_analysis_handler.h"
#include <dirent.h>
namespace XCam {
#define MAX_PLUGIN_LIB_COUNT 10
SmartAnalyzerLoader::SmartAnalyzerLoader (const char *lib_path, const char *name, const char *symbol)
: AnalyzerLoader (lib_path, symbol)
, _name (NULL)
{
if (name)
_name = strndup (name, XCAM_MAX_STR_SIZE);
}
SmartAnalyzerLoader::~SmartAnalyzerLoader ()
{
if (_name)
xcam_free (_name);
}
SmartHandlerList
SmartAnalyzerLoader::load_smart_handlers (const char *dir_path)
{
SmartHandlerList ret_handers;
AnalyzerLoaderList loaders = create_analyzer_loader (dir_path);
for (AnalyzerLoaderList::iterator i_loader = loaders.begin ();
i_loader != loaders.end (); ++i_loader)
{
SmartPtr<SmartAnalysisHandler> handler = (*i_loader)->load_smart_handler(*i_loader);
if (!handler.ptr ())
continue;
SmartHandlerList::iterator i_pos = ret_handers.begin ();
for (; i_pos != ret_handers.end (); ++i_pos)
{
if (handler->get_priority() < (*i_pos)->get_priority ())
break;
}
ret_handers.insert (i_pos, handler);
}
return ret_handers;
}
AnalyzerLoaderList
SmartAnalyzerLoader::create_analyzer_loader (const char *dir_path)
{
XCAM_ASSERT (dir_path);
char lib_path[512];
DIR *lib_dir = NULL;
struct dirent *dirent_lib = NULL;
SmartPtr<SmartAnalyzerLoader> loader;
AnalyzerLoaderList loader_list;
uint8_t count = 0;
lib_dir = opendir (dir_path);
if (lib_dir) {
while ((count < MAX_PLUGIN_LIB_COUNT) && (dirent_lib = readdir (lib_dir)) != NULL) {
if (dirent_lib->d_type != DT_LNK &&
dirent_lib->d_type != DT_REG)
continue;
snprintf (lib_path, sizeof(lib_path), "%s/%s", dir_path, dirent_lib->d_name);
loader = new SmartAnalyzerLoader (lib_path, dirent_lib->d_name);
if (loader.ptr ()) {
loader_list.push_back (loader);
}
}
}
if (lib_dir)
closedir (lib_dir);
return loader_list;
}
SmartPtr<SmartAnalysisHandler>
SmartAnalyzerLoader::load_smart_handler (SmartPtr<SmartAnalyzerLoader> &self)
{
XCAM_ASSERT (self.ptr () == this);
SmartPtr<SmartAnalysisHandler> handler;
XCamSmartAnalysisDescription *desc = (XCamSmartAnalysisDescription*)load_library (get_lib_path ());
if (NULL == desc) {
XCAM_LOG_WARNING ("load smart handler lib symbol failed");
return NULL;
}
handler = new SmartAnalysisHandler (desc, self, (desc->name ? desc->name : _name));
if (!handler.ptr ()) {
XCAM_LOG_WARNING ("create smart handler failed");
close_handle ();
return NULL;
}
XCAM_LOG_INFO ("smart handler(%s) created from lib", XCAM_STR (handler->get_name()));
return handler;
}
void *
SmartAnalyzerLoader::load_symbol (void* handle)
{
XCamSmartAnalysisDescription *desc = NULL;
desc = (XCamSmartAnalysisDescription *)AnalyzerLoader::get_symbol (handle);
if (!desc) {
XCAM_LOG_DEBUG ("get symbol failed from lib");
return NULL;
}
if (desc->version < xcam_version ()) {
XCAM_LOG_WARNING ("get symbol version is:0x%04x, but expect:0x%04x",
desc->version, xcam_version ());
}
if (desc->size < sizeof (XCamSmartAnalysisDescription)) {
XCAM_LOG_DEBUG ("get symbol failed, XCamSmartAnalysisDescription size is:%" PRIu32 ", but expect:%" PRIuS,
desc->size, sizeof (XCamSmartAnalysisDescription));
return NULL;
}
if (!desc->create_context || !desc->destroy_context ||
!desc->update_params || !desc->analyze ||
!desc->free_results) {
XCAM_LOG_DEBUG ("some functions in symbol not set from lib");
return NULL;
}
return (void*)desc;
}
};