From: Pawel Wasowski Date: Thu, 21 Jan 2021 09:19:14 +0000 (+0100) Subject: [ML][pipeline] implement Valve::{setOpen, isOpen} X-Git-Tag: submit/tizen/20210202.064821~4 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=7dc3386b9966d1726525f57a3775bd4b15231c50;p=platform%2Fcore%2Fapi%2Fwebapi-plugins.git [ML][pipeline] implement Valve::{setOpen, isOpen} ACR: TWDAPI-274 [Verification] Tested in Chrome DevTools with the snippets below, works fine. var pipeline_def = "videotestsrc is-live=true ! videoconvert ! videoscale" + " ! video/x-raw,format=RGBx,width=16,height=16,framerate=10/1" + " ! tensor_converter ! valve name=valve1 ! fakesink"; var pipeline = tizen.ml.pipeline.createPipeline(pipeline_def, function(state) {console.log(state);}); // READY // PAUSED var v = pipeline.getValve('valve1') // ValveĀ {name: "valve1", _pipeline_id: 1} v.isOpen // true pipeline.isOpen = false v.isOpen // true v.setOpen(false) v.isOpen // false Change-Id: Ibdeaba23082356b5143c2a1796bbd181b4d5d027 Signed-off-by: Pawel Wasowski --- diff --git a/src/ml/js/ml_pipeline.js b/src/ml/js/ml_pipeline.js index 16a18c9e..cf92f3f5 100755 --- a/src/ml/js/ml_pipeline.js +++ b/src/ml/js/ml_pipeline.js @@ -329,6 +329,11 @@ Pipeline.prototype.getSwitch = function() { //Pipeline::getSwitch() end //Pipeline::getValve() begin +var ValidValveIsOpenAndSetOpenExceptions = [ + 'NotFoundError', + 'NotSupportedError', + 'AbortError' +]; function Valve(name, pipeline_id) { Object.defineProperties(this, { name: { @@ -337,6 +342,26 @@ function Valve(name, pipeline_id) { }, _pipeline_id: { value: pipeline_id + }, + isOpen: { + get: function() { + var result = native_.callSync('MLPipelineValveIsOpen', { + id: this._pipeline_id, + name: this.name + }); + + if (native_.isFailure(result)) { + throw native_.getErrorObjectAndValidate( + result, + ValidValveIsOpenAndSetOpenExceptions, + AbortError + ); + } + + return result.result; + }, + set: function() {}, + enumerable: true } }); } @@ -559,7 +584,36 @@ Switch.prototype.select = function() { //Switch::select() end //Valve::setOpen() begin +Valve.prototype.setOpen = function() { + var args = validator_.validateArgs(arguments, [ + { + name: 'open', + type: validator_.Types.BOOLEAN + } + ]); + + if (!args.has.open) { + throw new WebAPIException( + WebAPIException.INVALID_VALUES_ERR, + 'Invalid parameter: open is mandatory' + ); + } + var nativeArgs = { + id: this._pipeline_id, + name: this.name, + open: args.open + }; + + var result = native_.callSync('MLPipelineValveSetOpen', nativeArgs); + if (native_.isFailure(result)) { + throw native_.getErrorObjectAndValidate( + result, + ValidValveIsOpenAndSetOpenExceptions, + AbortError + ); + } +}; //Valve::setOpen() end var MachineLearningPipeline = function() {}; diff --git a/src/ml/ml_instance.cc b/src/ml/ml_instance.cc index 72bef27c..6e4262e4 100644 --- a/src/ml/ml_instance.cc +++ b/src/ml/ml_instance.cc @@ -40,6 +40,7 @@ const std::string kDefinition = "definition"; const std::string kPipelineStateChangeListenerName = "listenerName"; const std::string kOtherId = "otherId"; const std::string kPadName = "padName"; +const std::string kOpen = "open"; const std::string kNodeName = "nodeName"; const std::string kProperty = "property"; const std::string kBOOLEAN = "BOOLEAN"; @@ -98,6 +99,8 @@ MlInstance::MlInstance() REGISTER_METHOD(MLTensorsInfoClone); REGISTER_METHOD(MLTensorsInfoEquals); REGISTER_METHOD(MLTensorsInfoDispose); + REGISTER_METHOD(MLPipelineValveSetOpen); + REGISTER_METHOD(MLPipelineValveIsOpen); REGISTER_METHOD(MLTensorsDataDispose); @@ -1117,9 +1120,48 @@ void MlInstance::MLPipelineSwitchSelect(const picojson::value& args, picojson::o // Switch::select() end // Valve::setOpen() begin +void MlInstance::MLPipelineValveSetOpen(const picojson::value& args, picojson::object& out) { + ScopeLogger("args: %s", args.serialize().c_str()); + + CHECK_ARGS(args, kId, double, out); + CHECK_ARGS(args, kName, std::string, out); + CHECK_ARGS(args, kOpen, bool, out); + auto name = args.get(kName).get(); + auto pipeline_id = args.get(kId).get(); + auto open = args.get(kOpen).get(); + + auto ret = pipeline_manager_.ValveSetOpen(pipeline_id, name, open); + if (!ret) { + LogAndReportError(ret, &out); + return; + } + + ReportSuccess(out); +} // Valve::setOpen() end +// Valve::isOpen() begin +void MlInstance::MLPipelineValveIsOpen(const picojson::value& args, picojson::object& out) { + ScopeLogger("args: %s", args.serialize().c_str()); + + CHECK_ARGS(args, kId, double, out); + CHECK_ARGS(args, kName, std::string, out); + + auto name = args.get(kName).get(); + auto pipeline_id = args.get(kId).get(); + auto open = true; + + auto ret = pipeline_manager_.ValveIsOpen(pipeline_id, name, &open); + if (!ret) { + LogAndReportError(ret, &out); + return; + } + + ReportSuccess(picojson::value{open}, out); +} +// Valve::isOpen() end + // Pipeline API end #undef CHECK_EXIST diff --git a/src/ml/ml_instance.h b/src/ml/ml_instance.h index f0622576..a6f1b9f8 100644 --- a/src/ml/ml_instance.h +++ b/src/ml/ml_instance.h @@ -155,8 +155,12 @@ class MlInstance : public common::ParsedInstance { // Switch::select() end // Valve::setOpen() begin - + void MLPipelineValveSetOpen(const picojson::value& args, picojson::object& out); // Valve::setOpen() end + + // Valve::isOpen() begin + void MLPipelineValveIsOpen(const picojson::value& args, picojson::object& out); + // Valve::isOpen() end // Pipeline API end }; diff --git a/src/ml/ml_pipeline.cc b/src/ml/ml_pipeline.cc index c7e868d8..1d1cce50 100644 --- a/src/ml/ml_pipeline.cc +++ b/src/ml/ml_pipeline.cc @@ -212,7 +212,7 @@ PlatformResult Pipeline::Dispose() { // Pipeline::dispose() end // Pipeline::getNodeInfo() begin -PlatformResult Pipeline::GetNodeInfo(std::string& name) { +PlatformResult Pipeline::GetNodeInfo(const std::string& name) { ScopeLogger("id_: [%d], name: [%s]", id_, name.c_str()); auto nodeinfo_it = node_info_.find(name); @@ -287,7 +287,7 @@ PlatformResult Pipeline::GetValve(const std::string& name) { LoggerD("Creating [%s] Valve", name.c_str()); std::unique_ptr valve_ptr; - auto ret = Valve::CreateValve(name, pipeline_, &valve_ptr); + auto ret = Valve::CreateValve(name, pipeline_, *this, &valve_ptr); if (ret) { valves_.insert({name, std::move(valve_ptr)}); } @@ -376,7 +376,26 @@ PlatformResult Pipeline::GetSwitch(const std::string& name, Switch** out) { // Switch::getPadList() end // Valve::setOpen() begin +PlatformResult Pipeline::GetNodeInfo(const std::string& name, NodeInfo** out) { + ScopeLogger("id_: [%d], name: [%s]", id_, name.c_str()); + + auto ret = GetNodeInfo(name); + if (ret) { + *out = node_info_[name].get(); + } + + return ret; +} +PlatformResult Pipeline::GetValve(const std::string& name, Valve** out) { + ScopeLogger("id: [%d], name: [%s]", id_, name.c_str()); + + auto ret = GetValve(name); + if (ret) { + *out = valves_[name].get(); + } + return ret; +} // Valve::setOpen() end } // namespace extension diff --git a/src/ml/ml_pipeline.h b/src/ml/ml_pipeline.h index 59df3119..d6606c85 100644 --- a/src/ml/ml_pipeline.h +++ b/src/ml/ml_pipeline.h @@ -73,7 +73,7 @@ class Pipeline { // Pipeline::dispose() end // Pipeline::getNodeInfo() begin - PlatformResult GetNodeInfo(std::string& name); + PlatformResult GetNodeInfo(const std::string& name); // Pipeline::getNodeInfo() end // Pipeline::getSource() begin @@ -128,7 +128,8 @@ class Pipeline { // Switch::getPadList() end // Valve::setOpen() begin - + PlatformResult GetNodeInfo(const std::string& name, NodeInfo** out); + PlatformResult GetValve(const std::string& name, Valve** out); // Valve::setOpen() end private: Pipeline(int id, const std::string& state_change_listener_name, common::Instance* instance_ptr); diff --git a/src/ml/ml_pipeline_manager.cc b/src/ml/ml_pipeline_manager.cc index 364426fc..32512296 100644 --- a/src/ml/ml_pipeline_manager.cc +++ b/src/ml/ml_pipeline_manager.cc @@ -307,8 +307,47 @@ PlatformResult PipelineManager::SwitchSelect(int pipeline_id, const std::string& // Switch::select() end // Valve::setOpen() begin +PlatformResult PipelineManager::ValveSetOpen(int pipeline_id, const std::string& valve_name, + bool open) { + ScopeLogger("pipeline_id: [%d], valve_name: [%s], open: [%s]", pipeline_id, valve_name.c_str(), + open ? "true" : "false"); + auto pipeline_it = pipelines_.find(pipeline_id); + if (pipelines_.end() == pipeline_it) { + LoggerD("Pipeline not found: [%d]", pipeline_id); + return PlatformResult{ErrorCode::NOT_FOUND_ERR, "Pipeline not found"}; + } + + Valve* valve_ptr = nullptr; + auto ret = pipeline_it->second->GetValve(valve_name, &valve_ptr); + if (!ret) { + return ret; + } + + return valve_ptr->SetOpen(open); +} // Valve::setOpen() end +// Valve::isOpen() begin +PlatformResult PipelineManager::ValveIsOpen(int pipeline_id, const std::string& valve_name, + bool* open) { + ScopeLogger("pipeline_id: [%d], valve_name: [%s]", pipeline_id, valve_name.c_str()); + + auto pipeline_it = pipelines_.find(pipeline_id); + if (pipelines_.end() == pipeline_it) { + LoggerD("Pipeline not found: [%d]", pipeline_id); + return PlatformResult{ErrorCode::NOT_FOUND_ERR, "Pipeline not found"}; + } + + Valve* valve_ptr = nullptr; + auto ret = pipeline_it->second->GetValve(valve_name, &valve_ptr); + if (!ret) { + return ret; + } + + return valve_ptr->IsOpen(open); +} +// Valve::isOpen() end + } // namespace ml } // namespace extension diff --git a/src/ml/ml_pipeline_manager.h b/src/ml/ml_pipeline_manager.h index 6e363dd5..18e8c4f7 100644 --- a/src/ml/ml_pipeline_manager.h +++ b/src/ml/ml_pipeline_manager.h @@ -121,8 +121,12 @@ class PipelineManager { // Switch::select() end // Valve::setOpen() begin - + PlatformResult ValveSetOpen(int pipeline_id, const std::string& valve_name, bool open); // Valve::setOpen() end + + // Valve::isOpen() begin + PlatformResult ValveIsOpen(int pipeline_id, const std::string& valve_name, bool* open); + // Valve::isOpen() end private: common::Instance* instance_ptr_; TensorsInfoManager* tensors_info_manager_; diff --git a/src/ml/ml_pipeline_valve.cc b/src/ml/ml_pipeline_valve.cc index cbd6fda5..06d5a5e5 100644 --- a/src/ml/ml_pipeline_valve.cc +++ b/src/ml/ml_pipeline_valve.cc @@ -14,29 +14,33 @@ * limitations under the License. */ +#include "common/picojson.h" + +#include "ml_pipeline.h" #include "ml_pipeline_valve.h" #include "ml_utils.h" using common::PlatformResult; using common::ErrorCode; +using extension::ml::Pipeline; namespace extension { namespace ml { namespace pipeline { -PlatformResult Valve::CreateValve(const std::string& name, ml_pipeline_h pipeline, - std::unique_ptr* out) { - ScopeLogger("name: [%s], pipeline: [%p]", name.c_str(), pipeline); +PlatformResult Valve::CreateValve(const std::string& name, ml_pipeline_h native_pipeline_handle, + Pipeline& pipeline, std::unique_ptr* out) { + ScopeLogger("name: [%s], native_pipeline_handle: [%p]", name.c_str(), native_pipeline_handle); ml_pipeline_valve_h valve_handle = nullptr; - auto ret = ml_pipeline_valve_get_handle(pipeline, name.c_str(), &valve_handle); + auto ret = ml_pipeline_valve_get_handle(native_pipeline_handle, name.c_str(), &valve_handle); if (ML_ERROR_NONE != ret) { LoggerE("ml_pipeline_valve_get_handle() failed: [%d] (%s)", ret, get_error_message(ret)); return util::ToPlatformResult(ret, "Could not get valve"); } LoggerD("ml_pipeline_valve_get_handle() succeeded"); - out->reset(new (std::nothrow) Valve{name, valve_handle}); + out->reset(new (std::nothrow) Valve{name, valve_handle, pipeline}); if (!out) { ret = ml_pipeline_valve_release_handle(valve_handle); if (ML_ERROR_NONE != ret) { @@ -51,8 +55,8 @@ PlatformResult Valve::CreateValve(const std::string& name, ml_pipeline_h pipelin return PlatformResult{}; } -Valve::Valve(const std::string& name, ml_pipeline_valve_h valve_handle) - : name_{name}, valve_{valve_handle} { +Valve::Valve(const std::string& name, ml_pipeline_valve_h valve_handle, Pipeline& pipeline) + : name_{name}, valve_{valve_handle}, pipeline_{pipeline} { ScopeLogger("name: [%s], handle: [%p]", name.c_str(), valve_handle); } @@ -67,6 +71,42 @@ Valve::~Valve() { } } +PlatformResult Valve::SetOpen(bool open) { + ScopeLogger("name: [%s], open: [%s]", name_.c_str(), open ? "true" : "false"); + + auto ret = ml_pipeline_valve_set_open(valve_, open); + if (ML_ERROR_NONE != ret) { + LoggerE("ml_pipeline_valve_set_open() failed: [%d] (%s)", ret, get_error_message(ret)); + return util::ToPlatformResult(ret, "Could not set valve open state"); + } + LoggerD("ml_pipeline_valve_set_open() succeeded"); + + return PlatformResult{}; +} + +PlatformResult Valve::IsOpen(bool* out) { + ScopeLogger("name: [%s]", name_.c_str()); + + NodeInfo* node_info_ptr = nullptr; + auto ret = pipeline_.GetNodeInfo(name_, &node_info_ptr); + if (!ret) { + return ret; + } + + // Valve's drop property doc: + // https://gstreamer.freedesktop.org/documentation/coreelements/valve.html?gi-language=c#valve:drop + const std::string kPropertyToNegate = "drop"; + const std::string kProperty = "property"; + const std::string kType = "BOOLEAN"; + + picojson::object propertyToNegate; + ret = node_info_ptr->getProperty(kPropertyToNegate, kType, &propertyToNegate); + if (ret) { + *out = !propertyToNegate[kProperty].get(); + } + return ret; +} + } // namespace pipeline } // namespace ml } // namespace extension \ No newline at end of file diff --git a/src/ml/ml_pipeline_valve.h b/src/ml/ml_pipeline_valve.h index a03e0e77..75452b02 100644 --- a/src/ml/ml_pipeline_valve.h +++ b/src/ml/ml_pipeline_valve.h @@ -28,22 +28,28 @@ using common::PlatformResult; namespace extension { namespace ml { + +class Pipeline; namespace pipeline { class Valve { public: - static PlatformResult CreateValve(const std::string& name, ml_pipeline_h pipeline, - std::unique_ptr* out); + static PlatformResult CreateValve(const std::string& name, ml_pipeline_h native_pipeline_handle, + Pipeline& pipeline, std::unique_ptr* out); ~Valve(); + PlatformResult SetOpen(bool open); + PlatformResult IsOpen(bool* out); + Valve(const Valve&) = delete; Valve& operator=(const Valve&) = delete; private: - Valve(const std::string& name, ml_pipeline_valve_h valve_handle); + Valve(const std::string& name, ml_pipeline_valve_h valve_handle, Pipeline& pipeline); const std::string name_; const ml_pipeline_valve_h valve_; + Pipeline& pipeline_; }; } // namespace pipeline