aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGeorgios Pinitas <georgios.pinitas@arm.com>2017-10-12 17:34:20 +0100
committerAnthony Barbier <anthony.barbier@arm.com>2018-11-02 16:35:24 +0000
commit7d3d1b923b7793f1cf5e29c78bfda2582522cf25 (patch)
tree7a924958ee7f4c9b7e6245170513862dcc016b87
parent3756186e54d77639564e999082f4bbd1ceec5a2f (diff)
downloadComputeLibrary-7d3d1b923b7793f1cf5e29c78bfda2582522cf25.tar.gz
COMPMID-619: Logging interface
Change-Id: I73d1433ee7a682aeabb7540aa2ea1f6564f90aae Reviewed-on: http://mpd-gerrit.cambridge.arm.com/91775 Tested-by: Kaizen <jeremy.johnson+kaizengerrit@arm.com> Reviewed-by: Anthony Barbier <anthony.barbier@arm.com>
-rw-r--r--SConscript1
-rw-r--r--SConstruct4
-rw-r--r--arm_compute/core/utils/io/FileHandler.h (renamed from arm_compute/core/Logger.h)75
-rw-r--r--arm_compute/core/utils/logging/FilePrinter.h54
-rw-r--r--arm_compute/core/utils/logging/Helpers.h77
-rw-r--r--arm_compute/core/utils/logging/IPrinter.h74
-rw-r--r--arm_compute/core/utils/logging/LogMsgDecorators.h140
-rw-r--r--arm_compute/core/utils/logging/Logger.h176
-rw-r--r--arm_compute/core/utils/logging/LoggerRegistry.h88
-rw-r--r--arm_compute/core/utils/logging/Macros.h68
-rw-r--r--arm_compute/core/utils/logging/Printers.h31
-rw-r--r--arm_compute/core/utils/logging/StdPrinter.h (renamed from src/core/Logger.cpp)41
-rw-r--r--arm_compute/core/utils/logging/Types.h58
-rw-r--r--arm_compute/graph/Types.h9
-rw-r--r--examples/graph_alexnet.cpp5
-rw-r--r--examples/graph_lenet.cpp5
-rw-r--r--src/core/utils/io/FileHandler.cpp66
-rw-r--r--src/core/utils/logging/FilePrinter.cpp37
-rw-r--r--src/core/utils/logging/Helpers.cpp42
-rw-r--r--src/core/utils/logging/Logger.cpp154
-rw-r--r--src/core/utils/logging/LoggerRegistry.cpp79
-rw-r--r--src/graph/nodes/ActivationLayer.cpp17
-rw-r--r--src/graph/nodes/BatchNormalizationLayer.cpp13
-rw-r--r--src/graph/nodes/ConvolutionLayer.cpp23
-rw-r--r--src/graph/nodes/FloorLayer.cpp13
-rw-r--r--src/graph/nodes/FullyConnectedLayer.cpp15
-rw-r--r--src/graph/nodes/L2NormalizeLayer.cpp13
-rw-r--r--src/graph/nodes/NormalizationLayer.cpp13
-rw-r--r--src/graph/nodes/PoolingLayer.cpp11
-rw-r--r--src/graph/nodes/SoftmaxLayer.cpp11
-rw-r--r--support/ToolchainSupport.h42
31 files changed, 1323 insertions, 132 deletions
diff --git a/SConscript b/SConscript
index 79f6bf37f..195eff18b 100644
--- a/SConscript
+++ b/SConscript
@@ -137,6 +137,7 @@ arm_compute_env.Append(LIBS = ['dl'])
core_files = Glob('src/core/*.cpp')
core_files += Glob('src/core/CPP/*.cpp')
core_files += Glob('src/core/CPP/kernels/*.cpp')
+core_files += Glob('src/core/utils/*/*.cpp')
runtime_files = Glob('src/runtime/*.cpp')
# CLHarrisCorners uses the Scheduler to run CPP kernels
diff --git a/SConstruct b/SConstruct
index 4ef67efe0..c2c76fbf9 100644
--- a/SConstruct
+++ b/SConstruct
@@ -39,6 +39,7 @@ vars = Variables("scons")
vars.AddVariables(
BoolVariable("debug", "Debug", False),
BoolVariable("asserts", "Enable asserts (this flag is forced to 1 for debug=1)", False),
+ BoolVariable("logging", "Logging", False),
EnumVariable("arch", "Target Architecture", "armv7a", allowed_values=("armv7a", "arm64-v8a", "arm64-v8.2-a", "x86_32", "x86_64")),
EnumVariable("os", "Target OS", "linux", allowed_values=("linux", "android", "bare_metal")),
EnumVariable("build", "Build type", "cross_compile", allowed_values=("native", "cross_compile")),
@@ -207,6 +208,9 @@ if env['asserts']:
env.Append(CPPDEFINES = ['ARM_COMPUTE_ASSERTS_ENABLED'])
env.Append(CXXFLAGS = ['-fstack-protector-strong'])
+if env['logging']:
+ env.Append(CPPDEFINES = ['ARM_COMPUTE_LOGGING_ENABLED'])
+
env.Append(CPPPATH = ['#/include', "#"])
env.Append(CXXFLAGS = env['extra_cxx_flags'])
diff --git a/arm_compute/core/Logger.h b/arm_compute/core/utils/io/FileHandler.h
index 0848479d3..d915dbe28 100644
--- a/arm_compute/core/Logger.h
+++ b/arm_compute/core/utils/io/FileHandler.h
@@ -21,51 +21,56 @@
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
+#ifndef __ARM_COMPUTE_IO_FILE_HANDLER_H__
+#define __ARM_COMPUTE_IO_FILE_HANDLER_H__
-#ifndef __ARM_COMPUTE_LOGGER_H__
-#define __ARM_COMPUTE_LOGGER_H__
-
-#include <iostream>
-#include <memory>
-
-#ifdef ARM_COMPUTE_DEBUG_ENABLED
-#define ARM_COMPUTE_LOG(x) (arm_compute::Logger::get().log_info() << x)
-#else /* ARM_COMPUTE_DEBUG_ENABLED */
-#define ARM_COMPUTE_LOG(...)
-#endif /* ARM_COMPUTE_DEBUG_ENABLED */
+#include <fstream>
+#include <string>
namespace arm_compute
{
-/**< Verbosity of the logger */
-enum class LoggerVerbosity
+namespace io
{
- NONE, /**< No info */
- INFO /**< Log info */
-};
-
-/** Logger singleton class */
-class Logger
+/** File Handling interface */
+class FileHandler
{
public:
- static Logger &get();
- void set_logger(std::ostream &ostream, LoggerVerbosity verbosity);
- std::ostream &log_info();
-
-private:
- /** Default constructor */
- Logger();
+ /** Default Constructor */
+ FileHandler();
+ /** Default Destructor */
+ ~FileHandler();
/** Allow instances of this class to be moved */
- Logger(Logger &&) = default;
+ FileHandler(FileHandler &&) = default;
/** Prevent instances of this class from being copied (As this class contains pointers) */
- Logger(const Logger &) = delete;
+ FileHandler(const FileHandler &) = delete;
/** Prevent instances of this class from being copied (As this class contains pointers) */
- Logger &operator=(const Logger &) = delete;
+ FileHandler &operator=(const FileHandler &) = delete;
/** Allow instances of this class to be moved */
- Logger &operator=(Logger &&) = default;
+ FileHandler &operator=(FileHandler &&) = default;
+ /** Opens file
+ *
+ * @param[in] filename File name
+ * @param[in] mode File open mode
+ */
+ void open(const std::string &filename, std::ios_base::openmode mode);
+ /** Closes file */
+ void close();
+ /** Returns the file stream
+ *
+ * @return File stream
+ */
+ std::fstream &stream();
+ /** Returns filename of the handled file
+ *
+ * @return File filename
+ */
+ std::string filename() const;
- std::ostream *_ostream;
- std::ostream _nullstream;
- LoggerVerbosity _verbosity;
+private:
+ std::fstream _filestream;
+ std::string _filename;
+ std::ios_base::openmode _mode;
};
-} // arm_compute
-#endif /* __ARM_COMPUTE_LOGGER_H__ */ \ No newline at end of file
+} // namespace io
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_IO_FILE_HANDLER_H__ */
diff --git a/arm_compute/core/utils/logging/FilePrinter.h b/arm_compute/core/utils/logging/FilePrinter.h
new file mode 100644
index 000000000..e2ae95208
--- /dev/null
+++ b/arm_compute/core/utils/logging/FilePrinter.h
@@ -0,0 +1,54 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_FILE_PRINTER_H__
+#define __ARM_COMPUTE_LOGGING_FILE_PRINTER_H__
+
+#include "arm_compute/core/utils/logging/IPrinter.h"
+
+#include "arm_compute/core/utils/io/FileHandler.h"
+
+namespace arm_compute
+{
+namespace logging
+{
+/** File Printer */
+class FilePrinter final : public Printer
+{
+public:
+ /** Default Constructor
+ *
+ * @param[in] filename File name
+ */
+ FilePrinter(const std::string &filename);
+
+private:
+ // Inherited methods overridden:
+ void print_internal(const std::string &msg) override;
+
+private:
+ io::FileHandler _handler;
+};
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_LOGGING_FILE_PRINTER_H__ */
diff --git a/arm_compute/core/utils/logging/Helpers.h b/arm_compute/core/utils/logging/Helpers.h
new file mode 100644
index 000000000..4bc54e80d
--- /dev/null
+++ b/arm_compute/core/utils/logging/Helpers.h
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_HELPERS_H__
+#define __ARM_COMPUTE_LOGGING_HELPERS_H__
+
+#include "arm_compute/core/utils/logging/Types.h"
+#include "support/ToolchainSupport.h"
+
+#include <cstddef>
+#include <cstdio>
+#include <memory>
+#include <sstream>
+#include <string>
+
+namespace arm_compute
+{
+namespace logging
+{
+/** Create a string given a format
+ *
+ * @param[in] fmt String format
+ * @param[in] args Arguments
+ *
+ * @return The formatted string
+ */
+template <typename... Ts>
+inline std::string string_with_format(const std::string &fmt, Ts &&... args)
+{
+ size_t size = support::cpp11::snprintf(nullptr, 0, fmt.c_str(), args...) + 1;
+ auto char_str = support::cpp14::make_unique<char[]>(size);
+ support::cpp11::snprintf(char_str.get(), size, fmt.c_str(), args...);
+ return std::string(char_str.get(), char_str.get() + size - 1);
+}
+/** Wraps a value with angles and returns the string
+ *
+ * @param[in] val Value to wrap
+ *
+ * @return Wrapped string
+ */
+template <typename T>
+inline std::string angle_wrap_value(const T &val)
+{
+ std::ostringstream ss;
+ ss << "[" << val << "]";
+ return ss.str();
+}
+/** Translates a given log level to a string.
+ *
+ * @param[in] log_level @ref LogLevel to be translated to string.
+ *
+ * @return The string describing the logging level.
+ */
+const std::string &string_from_log_level(LogLevel log_level);
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_LOGGING_HELPERS_H__ */
diff --git a/arm_compute/core/utils/logging/IPrinter.h b/arm_compute/core/utils/logging/IPrinter.h
new file mode 100644
index 000000000..6b410d4d1
--- /dev/null
+++ b/arm_compute/core/utils/logging/IPrinter.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_PRINTER_H__
+#define __ARM_COMPUTE_LOGGING_PRINTER_H__
+
+#include "support/Mutex.h"
+
+namespace arm_compute
+{
+namespace logging
+{
+/** Base printer class to be inherited by other printer classes */
+class Printer
+{
+public:
+ /** Default Constructor */
+ Printer()
+ : _mtx()
+ {
+ }
+ /** Prevent instances of this class from being copied */
+ Printer(const Printer &) = delete;
+ /** Prevent instances of this class from being copied */
+ Printer &operator=(const Printer &) = delete;
+ /** Prevent instances of this class from being moved */
+ Printer(Printer &&) = delete;
+ /** Prevent instances of this class from being moved */
+ Printer &operator=(Printer &&) = delete;
+ /** Defaults Destructor */
+ virtual ~Printer() = default;
+ /** Print message
+ *
+ * @param[in] msg Message to print
+ */
+ inline void print(const std::string &msg)
+ {
+ std::lock_guard<arm_compute::Mutex> lock(_mtx);
+ print_internal(msg);
+ }
+
+private:
+ /** Interface to be implemented by the child to print a message
+ *
+ * @param[in] msg Message to print
+ */
+ virtual void print_internal(const std::string &msg) = 0;
+
+private:
+ arm_compute::Mutex _mtx;
+};
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_LOGGING_PRINTER_H__ */
diff --git a/arm_compute/core/utils/logging/LogMsgDecorators.h b/arm_compute/core/utils/logging/LogMsgDecorators.h
new file mode 100644
index 000000000..32cb977bf
--- /dev/null
+++ b/arm_compute/core/utils/logging/LogMsgDecorators.h
@@ -0,0 +1,140 @@
+/*
+ * Copyright (c) 2016, 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_LOG_MSG_DECORATORS_H__
+#define __ARM_COMPUTE_LOGGING_LOG_MSG_DECORATORS_H__
+
+#include "arm_compute/core/utils/logging/Helpers.h"
+#include "arm_compute/core/utils/logging/Types.h"
+
+#include <chrono>
+#include <ctime>
+#include <string>
+#include <thread>
+
+namespace arm_compute
+{
+namespace logging
+{
+/** Log message decorator interface */
+class IDecorator
+{
+public:
+ /** Default Destructor */
+ virtual ~IDecorator() = default;
+ /** Decorates log message
+ *
+ * @param[in] log_msg Log message to decorate
+ */
+ virtual void decorate(LogMsg &log_msg) = 0;
+};
+
+/** String Decorator
+ *
+ * Appends a user defined string in the log message
+ */
+class StringDecorator : public IDecorator
+{
+public:
+ /** Defaults constructor
+ *
+ * @param str Sting to append
+ */
+ StringDecorator(const std::string &str)
+ : _str(str)
+ {
+ _str = angle_wrap_value(str);
+ }
+
+ // Inherited methods overridden:
+ void decorate(LogMsg &log_msg) override
+ {
+ log_msg.raw_ += _str;
+ }
+
+private:
+ std::string _str;
+};
+
+/** Date Decorator
+ *
+ * Appends the date and time in the log message
+ */
+class DateDecorator : public IDecorator
+{
+public:
+ // Inherited methods overridden:
+ void decorate(LogMsg &log_msg) override
+ {
+ log_msg.raw_ += angle_wrap_value(get_time());
+ }
+
+private:
+ /** Gets current system local time
+ *
+ * @return Local time
+ */
+ std::string get_time()
+ {
+ auto now = std::chrono::system_clock::now();
+ auto time = std::chrono::system_clock::to_time_t(now);
+
+ // TODO: use put_time for gcc > 4.9
+ char buf[100] = { 0 };
+ std::strftime(buf, sizeof(buf), "%d-%m-%Y %I:%M:%S", std::localtime(&time));
+ return buf;
+ }
+};
+
+/** Thread ID Decorator
+ *
+ * Appends the thread ID in the log message
+ */
+class ThreadIdDecorator : public IDecorator
+{
+public:
+ // Inherited methods overridden:
+ void decorate(LogMsg &log_msg) override
+ {
+#ifndef NO_MULTI_THREADING
+ log_msg.raw_ += angle_wrap_value(std::this_thread::get_id());
+#endif /* NO_MULTI_THREADING */
+ }
+};
+
+/** Log Level Decorator
+ *
+ * Appends the logging level in the log message
+ */
+class LogLevelDecorator : public IDecorator
+{
+public:
+ // Inherited methods overridden:
+ void decorate(LogMsg &log_msg) override
+ {
+ log_msg.raw_ += angle_wrap_value(string_from_log_level(log_msg.log_level_));
+ }
+};
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_LOGGING_LOG_MSG_DECORATORS_H__ */
diff --git a/arm_compute/core/utils/logging/Logger.h b/arm_compute/core/utils/logging/Logger.h
new file mode 100644
index 000000000..eb9bdd2e3
--- /dev/null
+++ b/arm_compute/core/utils/logging/Logger.h
@@ -0,0 +1,176 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_LOGGER_H__
+#define __ARM_COMPUTE_LOGGING_LOGGER_H__
+
+#include "arm_compute/core/utils/logging/Helpers.h"
+#include "arm_compute/core/utils/logging/IPrinter.h"
+#include "arm_compute/core/utils/logging/LogMsgDecorators.h"
+#include "arm_compute/core/utils/logging/Types.h"
+
+#include <memory>
+#include <sstream>
+#include <string>
+#include <vector>
+
+namespace arm_compute
+{
+namespace logging
+{
+/** Logger class */
+class Logger
+{
+public:
+ /** Default Constructor
+ *
+ * @param[in] name Name of the logger
+ * @param[in] log_level Logger log level
+ * @param[in] printer Printer to push the messages
+ */
+ Logger(std::string name, LogLevel log_level, std::shared_ptr<Printer> printer);
+ /** Default Constructor
+ *
+ * @param[in] name Name of the logger
+ * @param[in] log_level Logger log level
+ * @param[in] printers Printers to push the messages
+ */
+ Logger(std::string name, LogLevel log_level, std::vector<std::shared_ptr<Printer>> printers = {});
+ /** Default Constructor
+ *
+ * @param[in] name Name of the logger
+ * @param[in] log_level Logger log level
+ * @param[in] printers Printers to push the messages
+ * @param[in] decorators Message decorators, which append information in the logged message
+ */
+ Logger(std::string name,
+ LogLevel log_level,
+ std::vector<std::shared_ptr<Printer>> printers,
+ std::vector<std::unique_ptr<IDecorator>> decorators);
+ /** Allow instances of this class to be moved */
+ Logger(Logger &&) = default;
+ /** Prevent instances of this class from being copied (As this class contains pointers) */
+ Logger(const Logger &) = delete;
+ /** Prevent instances of this class from being copied (As this class contains pointers) */
+ Logger &operator=(const Logger &) = delete;
+ /** Allow instances of this class to be moved */
+ Logger &operator=(Logger &&) = default;
+ /** Logs a message
+ *
+ * @param[in] log_level Log level of the message
+ * @param[in] msg Message to log
+ */
+ void log(LogLevel log_level, const std::string &msg);
+ /** Logs a formatted message
+ *
+ * @param[in] log_level Log level of the message
+ * @param[in] fmt Message format
+ * @param[in] args Message arguments
+ */
+ template <typename... Ts>
+ void log(LogLevel log_level, const std::string &fmt, Ts &&... args);
+ /** Sets log level of the logger
+ *
+ * @warning Not thread-safe
+ *
+ * @param[in] log_level Log level to set
+ */
+ void set_log_level(LogLevel log_level);
+ /** Returns logger's log level
+ *
+ * @return Logger's log level
+ */
+ LogLevel log_level() const;
+ /** Returns logger's name
+ *
+ * @return Logger's name
+ */
+ std::string name() const;
+ /** Adds a printer to the logger
+ *
+ * @warning Not thread-safe
+ *
+ * @param[in] printer
+ */
+ void add_printer(std::shared_ptr<Printer> printer);
+ /** Adds a log message decorator to the logger
+ *
+ * @warning Not thread-safe
+ *
+ * @param[in] decorator
+ */
+ void add_decorator(std::unique_ptr<IDecorator> decorator);
+
+private:
+ /** Set default message decorators */
+ void set_default_decorators();
+ /** Checks if a message should be logged depending
+ * on the message log level and the loggers one
+ *
+ * @param[in] log_level Log level
+ *
+ * @return True if message should be logged else false
+ */
+ bool is_loggable(LogLevel log_level);
+ /** Decorate log message
+ *
+ * @param[in] Log message to decorate
+ */
+ void decorate_log_msg(LogMsg &msg);
+ /** Creates final log message by creating the prefix
+ *
+ * @param[in] str Log message
+ * @param[in] log_level Message's log level
+ *
+ * @return Final log message to print
+ */
+ std::string create_log_msg(const std::string &str, LogLevel log_level);
+ /** Prints the message to all the printers
+ *
+ * @param[in] msg Message to print
+ */
+ void print_all(const std::string &msg);
+
+private:
+ std::string _name;
+ LogLevel _log_level;
+ std::vector<std::shared_ptr<Printer>> _printers;
+ std::vector<std::unique_ptr<IDecorator>> _decorators;
+};
+
+template <typename... Ts>
+inline void Logger::log(LogLevel log_level, const std::string &fmt, Ts &&... args)
+{
+ // Return if message shouldn't be logged
+ // i.e. if log level does not match the logger's
+ if(!is_loggable(log_level))
+ {
+ return;
+ }
+
+ // Print message to all printers
+ print_all(create_log_msg(string_with_format(fmt, args...), log_level));
+}
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_LOGGING_LOGGER_H__ */
diff --git a/arm_compute/core/utils/logging/LoggerRegistry.h b/arm_compute/core/utils/logging/LoggerRegistry.h
new file mode 100644
index 000000000..d861476fe
--- /dev/null
+++ b/arm_compute/core/utils/logging/LoggerRegistry.h
@@ -0,0 +1,88 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_LOGGER_REGISTRY_H__
+#define __ARM_COMPUTE_LOGGING_LOGGER_REGISTRY_H__
+
+#include "arm_compute/core/utils/logging/Logger.h"
+#include "arm_compute/core/utils/logging/Printers.h"
+#include "arm_compute/core/utils/logging/Types.h"
+#include "support/Mutex.h"
+
+#include <memory>
+#include <set>
+#include <unordered_map>
+
+namespace arm_compute
+{
+namespace logging
+{
+/** Registry class holding all the instantiated loggers */
+class LoggerRegistry final
+{
+public:
+ /** Gets registry instance
+ *
+ * @return Logger registry instance
+ */
+ static LoggerRegistry &get();
+ /** Creates a logger
+ *
+ * @note Some names are reserved e.g. [CORE, RUNTIME, GRAPH]
+ *
+ * @param[in] name Logger's name
+ * @param[in] log_level Logger's log level
+ * @param[in] printers Printers to attach to the system loggers
+ */
+ void create_logger(const std::string &name, LogLevel log_level, std::vector<std::shared_ptr<Printer>> printers = {});
+ /** Remove a logger
+ *
+ * @param name Logger's name
+ */
+ void remove_logger(const std::string &name);
+ /** Returns a logger instance
+ *
+ * @param[in] name Logger to return
+ *
+ * @return Logger
+ */
+ std::shared_ptr<Logger> logger(const std::string &name);
+ /** Creates reserved library loggers
+ *
+ * @param[in] log_level Logger's log level
+ * @param[in] printers Printers to attach to the system loggers
+ */
+ void create_reserved_loggers(LogLevel log_level, std::vector<std::shared_ptr<Printer>> printers = {});
+
+private:
+ /** Default constructor */
+ LoggerRegistry();
+
+private:
+ arm_compute::Mutex _mtx;
+ std::unordered_map<std::string, std::shared_ptr<Logger>> _loggers;
+ static std::set<std::string> _reserved_loggers;
+};
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_LOGGING_LOGGER_REGISTRY_H__ */
diff --git a/arm_compute/core/utils/logging/Macros.h b/arm_compute/core/utils/logging/Macros.h
new file mode 100644
index 000000000..b17354bed
--- /dev/null
+++ b/arm_compute/core/utils/logging/Macros.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_MACROS_H__
+#define __ARM_COMPUTE_LOGGING_MACROS_H__
+
+#include "arm_compute/core/utils/logging/LoggerRegistry.h"
+
+#include <sstream>
+
+#ifdef ARM_COMPUTE_LOGGING_ENABLED
+
+#define ARM_COMPUTE_LOG_MSG(logger_name, log_level, msg) \
+ { \
+ auto logger = arm_compute::logging::LoggerRegistry::get().logger(logger_name); \
+ if(logger != nullptr) \
+ { \
+ logger->log(log_level, msg); \
+ } \
+ }
+
+#define ARM_COMPUTE_LOG_MSG_WITH_FORMAT(logger_name, log_level, fmt, ...) \
+ { \
+ auto logger = arm_compute::logging::LoggerRegistry::get().logger(logger_name); \
+ if(logger != nullptr) \
+ { \
+ logger->log(log_level, fmt, __VA_ARGS__); \
+ } \
+ }
+
+#define ARM_COMPUTE_LOG_STREAM(logger_name, log_level, stream) \
+ { \
+ auto logger = arm_compute::logging::LoggerRegistry::get().logger(logger_name); \
+ if(logger != nullptr) \
+ { \
+ logger->log(log_level, static_cast<std::ostringstream &>(std::ostringstream() << stream).str()); \
+ } \
+ }
+
+#else /* ARM_COMPUTE_LOGGING_ENABLED */
+
+#define ARM_COMPUTE_LOG_MSG(logger_name, log_level, msg)
+#define ARM_COMPUTE_LOG_MSG_WITH_FORMAT(logger_name, log_level, fmt, ...)
+#define ARM_COMPUTE_LOG_STREAM(logger_name, log_level, stream)
+
+#endif /* ARM_COMPUTE_LOGGING_ENABLED */
+
+#endif /* __ARM_COMPUTE_LOGGING_MACROS_H__ */
diff --git a/arm_compute/core/utils/logging/Printers.h b/arm_compute/core/utils/logging/Printers.h
new file mode 100644
index 000000000..7e5eef6a0
--- /dev/null
+++ b/arm_compute/core/utils/logging/Printers.h
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_PRINTERS_H__
+#define __ARM_COMPUTE_LOGGING_PRINTERS_H__
+
+#include "arm_compute/core/utils/logging/FilePrinter.h"
+#include "arm_compute/core/utils/logging/IPrinter.h"
+#include "arm_compute/core/utils/logging/StdPrinter.h"
+
+#endif /* __ARM_COMPUTE_LOGGING_PRINTERS_H__ */
diff --git a/src/core/Logger.cpp b/arm_compute/core/utils/logging/StdPrinter.h
index 9c3bf263a..0b41b2602 100644
--- a/src/core/Logger.cpp
+++ b/arm_compute/core/utils/logging/StdPrinter.h
@@ -21,36 +21,27 @@
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
+#ifndef __ARM_COMPUTE_LOGGING_STD_PRINTER_H__
+#define __ARM_COMPUTE_LOGGING_STD_PRINTER_H__
-#include "arm_compute/core/Logger.h"
+#include "arm_compute/core/utils/logging/IPrinter.h"
-using namespace arm_compute;
+#include <iostream>
-Logger::Logger()
- : _ostream(&std::cout), _nullstream(nullptr), _verbosity(LoggerVerbosity::NONE)
+namespace arm_compute
{
-}
-
-Logger &Logger::get()
-{
- static Logger _instance;
- return _instance;
-}
-
-void Logger::set_logger(std::ostream &ostream, LoggerVerbosity verbosity)
+namespace logging
{
- _ostream = &ostream;
- _verbosity = verbosity;
-}
-
-std::ostream &Logger::log_info()
+/** Std Printer */
+class StdPrinter final : public Printer
{
- if(_verbosity == LoggerVerbosity::INFO)
- {
- return *_ostream;
- }
- else
+private:
+ // Inherited methods overridden:
+ void print_internal(const std::string &msg) override
{
- return _nullstream;
+ std::cout << msg << std::endl;
}
-} \ No newline at end of file
+};
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_LOGGING_STD_PRINTER_H__ */
diff --git a/arm_compute/core/utils/logging/Types.h b/arm_compute/core/utils/logging/Types.h
new file mode 100644
index 000000000..171270d4e
--- /dev/null
+++ b/arm_compute/core/utils/logging/Types.h
@@ -0,0 +1,58 @@
+/*
+ * Copyright (c) 2016, 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#ifndef __ARM_COMPUTE_LOGGING_TYPES_H__
+#define __ARM_COMPUTE_LOGGING_TYPES_H__
+
+#include <string>
+
+namespace arm_compute
+{
+namespace logging
+{
+/** Logging level enumeration */
+enum class LogLevel : unsigned int
+{
+ VERBOSE, /**< All logging messages */
+ INFO, /**< Information log level */
+ WARN, /**< Warning log level */
+ OFF /**< No logging */
+};
+
+struct LogMsg
+{
+ LogMsg()
+ : raw_(), log_level_(LogLevel::OFF)
+ {
+ }
+ LogMsg(std::string msg, LogLevel log_level = LogLevel::OFF)
+ : raw_(msg), log_level_(log_level)
+ {
+ }
+
+ std::string raw_;
+ LogLevel log_level_;
+};
+} // namespace logging
+} // namespace arm_compute
+#endif /* __ARM_COMPUTE_TYPES_H__ */
diff --git a/arm_compute/graph/Types.h b/arm_compute/graph/Types.h
index c4396412a..f02fa7df3 100644
--- a/arm_compute/graph/Types.h
+++ b/arm_compute/graph/Types.h
@@ -27,6 +27,13 @@
#include "arm_compute/core/ITensor.h"
#include "arm_compute/core/SubTensorInfo.h"
#include "arm_compute/core/TensorInfo.h"
+#include "arm_compute/core/utils/logging/Macros.h"
+
+#define ARM_COMPUTE_LOG_GRAPH(log_level, x) \
+ ARM_COMPUTE_LOG_STREAM("GRAPH", log_level, x)
+
+#define ARM_COMPUTE_LOG_GRAPH_INFO(x) \
+ ARM_COMPUTE_LOG_STREAM("GRAPH", arm_compute::logging::LogLevel::INFO, x)
namespace arm_compute
{
@@ -47,6 +54,8 @@ using arm_compute::TensorInfo;
using arm_compute::TensorShape;
using arm_compute::WeightsInfo;
+using arm_compute::logging::LogLevel;
+
/**< Execution hint to the graph executor */
enum class TargetHint
{
diff --git a/examples/graph_alexnet.cpp b/examples/graph_alexnet.cpp
index dce713278..9a747b6b0 100644
--- a/examples/graph_alexnet.cpp
+++ b/examples/graph_alexnet.cpp
@@ -25,7 +25,7 @@
#error "This example needs to be built with -DARM_COMPUTE_CL"
#endif /* ARM_COMPUTE_CL */
-#include "arm_compute/core/Logger.h"
+#include "arm_compute/core/utils/logging/LoggerRegistry.h"
#include "arm_compute/graph/Graph.h"
#include "arm_compute/graph/Nodes.h"
#include "arm_compute/runtime/CL/CLScheduler.h"
@@ -41,6 +41,7 @@
using namespace arm_compute::graph;
using namespace arm_compute::graph_utils;
+using namespace arm_compute::logging;
/** Generates appropriate accessor according to the specified path
*
@@ -103,7 +104,7 @@ void main_graph_alexnet(int argc, const char **argv)
}
Graph graph;
- arm_compute::Logger::get().set_logger(std::cout, arm_compute::LoggerVerbosity::INFO);
+ LoggerRegistry::get().create_reserved_loggers(LogLevel::INFO, { std::make_shared<StdPrinter>() });
graph << hint
<< Tensor(TensorInfo(TensorShape(227U, 227U, 3U, batches), 1, DataType::F32), DummyAccessor())
diff --git a/examples/graph_lenet.cpp b/examples/graph_lenet.cpp
index 1427abe15..82f4c5a4c 100644
--- a/examples/graph_lenet.cpp
+++ b/examples/graph_lenet.cpp
@@ -25,7 +25,7 @@
#error "This example needs to be built with -DARM_COMPUTE_CL"
#endif /* ARM_COMPUTE_CL */
-#include "arm_compute/core/Logger.h"
+#include "arm_compute/core/utils/logging/LoggerRegistry.h"
#include "arm_compute/graph/Graph.h"
#include "arm_compute/graph/Nodes.h"
#include "arm_compute/runtime/CL/CLScheduler.h"
@@ -40,6 +40,7 @@
using namespace arm_compute::graph;
using namespace arm_compute::graph_utils;
+using namespace arm_compute::logging;
/** Generates appropriate accessor according to the specified path
*
@@ -102,7 +103,7 @@ void main_graph_lenet(int argc, const char **argv)
}
Graph graph;
- arm_compute::Logger::get().set_logger(std::cout, arm_compute::LoggerVerbosity::INFO);
+ LoggerRegistry::get().create_reserved_loggers(LogLevel::INFO, { std::make_shared<StdPrinter>() });
//conv1 << pool1 << conv2 << pool2 << fc1 << act1 << fc2 << smx
graph << hint
diff --git a/src/core/utils/io/FileHandler.cpp b/src/core/utils/io/FileHandler.cpp
new file mode 100644
index 000000000..70bce42b0
--- /dev/null
+++ b/src/core/utils/io/FileHandler.cpp
@@ -0,0 +1,66 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#include <string>
+
+#include "arm_compute/core/utils/io/FileHandler.h"
+
+#include "arm_compute/core/Error.h"
+#include "support/ToolchainSupport.h"
+
+using namespace arm_compute::io;
+
+FileHandler::FileHandler()
+ : _filestream(), _filename(" "), _mode()
+{
+}
+
+FileHandler::~FileHandler()
+{
+ close();
+}
+
+void FileHandler::open(const std::string &filename, std::ios_base::openmode mode)
+{
+ close();
+ ;
+ _filestream.open(filename, mode);
+ ARM_COMPUTE_ERROR_ON(!_filestream.good());
+ _filename = filename;
+ _mode = mode;
+}
+
+void FileHandler::close()
+{
+ _filestream.close();
+}
+
+std::fstream &FileHandler::stream()
+{
+ return _filestream;
+}
+
+std::string FileHandler::filename() const
+{
+ return _filename;
+}
diff --git a/src/core/utils/logging/FilePrinter.cpp b/src/core/utils/logging/FilePrinter.cpp
new file mode 100644
index 000000000..b699afc22
--- /dev/null
+++ b/src/core/utils/logging/FilePrinter.cpp
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#include "arm_compute/core/utils/logging/FilePrinter.h"
+
+using namespace arm_compute::logging;
+
+FilePrinter::FilePrinter(const std::string &filename)
+ : _handler()
+{
+ _handler.open(filename, std::fstream::out | std::fstream::trunc);
+}
+
+void FilePrinter::print_internal(const std::string &msg)
+{
+ _handler.stream() << msg << std::endl;
+} \ No newline at end of file
diff --git a/src/core/utils/logging/Helpers.cpp b/src/core/utils/logging/Helpers.cpp
new file mode 100644
index 000000000..f5ab608c3
--- /dev/null
+++ b/src/core/utils/logging/Helpers.cpp
@@ -0,0 +1,42 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#include "arm_compute/core/utils/logging/Helpers.h"
+
+#include <map>
+#include <string>
+
+using namespace arm_compute::logging;
+
+const std::string &arm_compute::logging::string_from_log_level(LogLevel log_level)
+{
+ static std::map<LogLevel, const std::string> log_level_map =
+ {
+ { LogLevel::VERBOSE, "VERBOSE" },
+ { LogLevel::INFO, "INFO" },
+ { LogLevel::WARN, "WARN" },
+ { LogLevel::OFF, "OFF" },
+ };
+
+ return log_level_map[log_level];
+} \ No newline at end of file
diff --git a/src/core/utils/logging/Logger.cpp b/src/core/utils/logging/Logger.cpp
new file mode 100644
index 000000000..b025ca809
--- /dev/null
+++ b/src/core/utils/logging/Logger.cpp
@@ -0,0 +1,154 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#include "arm_compute/core/utils/logging/Logger.h"
+
+#include "arm_compute/core/Error.h"
+#include "support/ToolchainSupport.h"
+
+using namespace arm_compute::logging;
+
+Logger::Logger(std::string name, LogLevel log_level, std::shared_ptr<Printer> printer)
+ : _name(std::move(name)), _log_level(log_level), _printers(
+{
+ std::move(printer)
+}), _decorators()
+{
+ // Check printer
+ ARM_COMPUTE_ERROR_ON(printer == nullptr);
+
+ // Set default message decorators
+ set_default_decorators();
+}
+
+Logger::Logger(std::string name, LogLevel log_level, std::vector<std::shared_ptr<Printer>> printers)
+ : _name(std::move(name)), _log_level(log_level), _printers(std::move(printers)), _decorators()
+{
+ // Check printers
+ for(const auto &p : _printers)
+ {
+ ARM_COMPUTE_UNUSED(p);
+ ARM_COMPUTE_ERROR_ON(p == nullptr);
+ }
+ // Set default message decorators
+ set_default_decorators();
+}
+
+Logger::Logger(std::string name,
+ LogLevel log_level,
+ std::vector<std::shared_ptr<Printer>> printers,
+ std::vector<std::unique_ptr<IDecorator>> decorators)
+ : _name(std::move(name)), _log_level(log_level), _printers(std::move(printers)), _decorators(std::move(decorators))
+{
+ // Check printers
+ for(const auto &p : _printers)
+ {
+ ARM_COMPUTE_UNUSED(p);
+ ARM_COMPUTE_ERROR_ON(p == nullptr);
+ }
+ // Check decorators
+ for(const auto &d : _decorators)
+ {
+ ARM_COMPUTE_UNUSED(d);
+ ARM_COMPUTE_ERROR_ON(d == nullptr);
+ }
+}
+
+void Logger::log(LogLevel log_level, const std::string &msg)
+{
+ // Return if message shouldn't be logged
+ // i.e. if log level does not match the logger's
+ if(!is_loggable(log_level))
+ {
+ return;
+ }
+
+ // Print message to all printers
+ print_all(create_log_msg(msg, log_level));
+}
+
+void Logger::set_log_level(LogLevel log_level)
+{
+ _log_level = log_level;
+}
+
+LogLevel Logger::log_level() const
+{
+ return _log_level;
+}
+
+std::string Logger::name() const
+{
+ return _name;
+}
+
+void Logger::add_printer(std::shared_ptr<Printer> printer)
+{
+ ARM_COMPUTE_ERROR_ON(printer == nullptr);
+ _printers.push_back(std::move(printer));
+}
+
+void Logger::add_decorator(std::unique_ptr<IDecorator> decorator)
+{
+ ARM_COMPUTE_ERROR_ON(decorator == nullptr);
+ _decorators.push_back(std::move(decorator));
+}
+
+void Logger::set_default_decorators()
+{
+ _decorators.emplace_back(support::cpp14::make_unique<StringDecorator>(_name));
+ _decorators.emplace_back(support::cpp14::make_unique<DateDecorator>());
+ _decorators.emplace_back(support::cpp14::make_unique<LogLevelDecorator>());
+}
+
+bool Logger::is_loggable(LogLevel log_level)
+{
+ return (log_level >= _log_level);
+}
+
+void Logger::decorate_log_msg(LogMsg &msg)
+{
+ for(const auto &d : _decorators)
+ {
+ d->decorate(msg);
+ }
+ msg.raw_ += std::string(" ");
+}
+
+std::string Logger::create_log_msg(const std::string &str, LogLevel log_level)
+{
+ // Adding space string to avoid Android failures
+ LogMsg log_msg(" ", log_level);
+ decorate_log_msg(log_msg);
+ std::ostringstream ss;
+ ss << log_msg.raw_ << " " << str;
+ return ss.str();
+}
+
+void Logger::print_all(const std::string &msg)
+{
+ for(auto &p : _printers)
+ {
+ p->print(msg);
+ }
+} \ No newline at end of file
diff --git a/src/core/utils/logging/LoggerRegistry.cpp b/src/core/utils/logging/LoggerRegistry.cpp
new file mode 100644
index 000000000..99236d25c
--- /dev/null
+++ b/src/core/utils/logging/LoggerRegistry.cpp
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2017 ARM Limited.
+ *
+ * SPDX-License-Identifier: MIT
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to
+ * deal in the Software without restriction, including without limitation the
+ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+#include "arm_compute/core/utils/logging/LoggerRegistry.h"
+
+#include "arm_compute/core/Error.h"
+#include "support/ToolchainSupport.h"
+
+using namespace arm_compute::logging;
+
+/** Reserved logger used by the library */
+std::set<std::string> LoggerRegistry::_reserved_loggers = { "CORE", "RUNTIME", "GRAPH" };
+
+LoggerRegistry::LoggerRegistry()
+ : _mtx(), _loggers()
+{
+}
+
+LoggerRegistry &LoggerRegistry::get()
+{
+ static LoggerRegistry _instance;
+ return _instance;
+}
+
+void LoggerRegistry::create_logger(const std::string &name, LogLevel log_level, std::vector<std::shared_ptr<Printer>> printers)
+{
+ std::lock_guard<arm_compute::Mutex> lock(_mtx);
+ if((_loggers.find(name) == _loggers.end()) && (_reserved_loggers.find(name) == _reserved_loggers.end()))
+ {
+ _loggers[name] = std::make_shared<Logger>(name, log_level, std::move(printers));
+ }
+}
+
+void LoggerRegistry::remove_logger(const std::string &name)
+{
+ std::lock_guard<arm_compute::Mutex> lock(_mtx);
+ if(_loggers.find(name) != _loggers.end())
+ {
+ _loggers.erase(name);
+ }
+}
+
+std::shared_ptr<Logger> LoggerRegistry::logger(const std::string &name)
+{
+ std::lock_guard<arm_compute::Mutex> lock(_mtx);
+ return (_loggers.find(name) != _loggers.end()) ? _loggers[name] : nullptr;
+}
+
+void LoggerRegistry::create_reserved_loggers(LogLevel log_level, std::vector<std::shared_ptr<Printer>> printers)
+{
+ std::lock_guard<arm_compute::Mutex> lock(_mtx);
+ for(const auto &r : _reserved_loggers)
+ {
+ if(_loggers.find(r) == _loggers.end())
+ {
+ _loggers[r] = std::make_shared<Logger>(r, log_level, printers);
+ }
+ }
+}
diff --git a/src/graph/nodes/ActivationLayer.cpp b/src/graph/nodes/ActivationLayer.cpp
index 5e75c28bc..df73ba707 100644
--- a/src/graph/nodes/ActivationLayer.cpp
+++ b/src/graph/nodes/ActivationLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/ActivationLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/CLTensor.h"
#include "arm_compute/runtime/CL/functions/CLActivationLayer.h"
#include "arm_compute/runtime/NEON/functions/NEActivationLayer.h"
@@ -82,18 +81,20 @@ std::unique_ptr<arm_compute::IFunction> ActivationLayer::instantiate_node(GraphC
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, out, _activation_info);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLActivationLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, out, _activation_info);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NEActivationLayer");
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input shape: " << in->info()->tensor_shape()
- << " Output shape: " << out->info()->tensor_shape()
- << " Activation function: " << _activation_info.activation()
- << " a: " << _activation_info.a()
- << " b: " << _activation_info.b()
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input shape: " << in->info()->tensor_shape()
+ << " Output shape: " << out->info()->tensor_shape()
+ << " Activation function: " << _activation_info.activation()
+ << " a: " << _activation_info.a()
+ << " b: " << _activation_info.b()
+ << std::endl);
return func;
}
diff --git a/src/graph/nodes/BatchNormalizationLayer.cpp b/src/graph/nodes/BatchNormalizationLayer.cpp
index 25e9e9bff..db809f4ee 100644
--- a/src/graph/nodes/BatchNormalizationLayer.cpp
+++ b/src/graph/nodes/BatchNormalizationLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/BatchNormalizationLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/CLTensor.h"
#include "arm_compute/runtime/CL/functions/CLBatchNormalizationLayer.h"
#include "arm_compute/runtime/NEON/functions/NEBatchNormalizationLayer.h"
@@ -100,18 +99,18 @@ std::unique_ptr<arm_compute::IFunction> BatchNormalizationLayer::instantiate_nod
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, out, _mean, _var, _beta, _gamma, _epsilon);
- ARM_COMPUTE_LOG("Instantiating CLBatchNormalizationLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLBatchNormalizationLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, out, _mean, _var, _beta, _gamma, _epsilon);
- ARM_COMPUTE_LOG("Instantiating NEBatchNormalizationLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NEBatchNormalizationLayer");
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input shape: " << in->info()->tensor_shape()
- << " Output shape: " << out->info()->tensor_shape()
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input shape: " << in->info()->tensor_shape()
+ << " Output shape: " << out->info()->tensor_shape()
+ << std::endl);
return func;
} \ No newline at end of file
diff --git a/src/graph/nodes/ConvolutionLayer.cpp b/src/graph/nodes/ConvolutionLayer.cpp
index 303780ff3..07d42617e 100644
--- a/src/graph/nodes/ConvolutionLayer.cpp
+++ b/src/graph/nodes/ConvolutionLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/ConvolutionLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/functions/CLConvolutionLayer.h"
#include "arm_compute/runtime/CL/functions/CLDirectConvolutionLayer.h"
#include "arm_compute/runtime/IFunction.h"
@@ -217,12 +216,12 @@ std::unique_ptr<arm_compute::IFunction> ConvolutionLayer::instantiate_node(Graph
if(_num_groups == 1)
{
func = instantiate_convolution(in, out, conv_method_hint);
- ARM_COMPUTE_LOG("Instantiating CLConvolutionLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLConvolutionLayer");
}
else
{
func = instantiate_grouped_convolution(in, out, conv_method_hint);
- ARM_COMPUTE_LOG("Instantiating NEConvolutionLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NEConvolutionLayer");
}
// Fill weights
@@ -236,15 +235,15 @@ std::unique_ptr<arm_compute::IFunction> ConvolutionLayer::instantiate_node(Graph
_biases.allocate_and_fill_if_needed();
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input Shape: " << in->info()->tensor_shape()
- << " Weights shape: " << _weights.info().tensor_shape()
- << " Biases Shape: " << _biases.info().tensor_shape()
- << " Output Shape: " << out->info()->tensor_shape()
- << " PadStrideInfo: " << _conv_info
- << " Groups: " << _num_groups
- << " WeightsInfo: " << _weights_info
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input Shape: " << in->info()->tensor_shape()
+ << " Weights shape: " << _weights.info().tensor_shape()
+ << " Biases Shape: " << _biases.info().tensor_shape()
+ << " Output Shape: " << out->info()->tensor_shape()
+ << " PadStrideInfo: " << _conv_info
+ << " Groups: " << _num_groups
+ << " WeightsInfo: " << _weights_info
+ << std::endl);
return func;
}
diff --git a/src/graph/nodes/FloorLayer.cpp b/src/graph/nodes/FloorLayer.cpp
index 3224799e3..45e2c3ee4 100644
--- a/src/graph/nodes/FloorLayer.cpp
+++ b/src/graph/nodes/FloorLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/FloorLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/CLTensor.h"
#include "arm_compute/runtime/CL/functions/CLFloor.h"
#include "arm_compute/runtime/NEON/functions/NEFloor.h"
@@ -76,18 +75,18 @@ std::unique_ptr<arm_compute::IFunction> FloorLayer::instantiate_node(GraphContex
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, out);
- ARM_COMPUTE_LOG("Instantiating CLFloorLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLFloorLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, out);
- ARM_COMPUTE_LOG("Instantiating NEFloorLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NEFloorLayer");
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input shape: " << in->info()->tensor_shape()
- << " Output shape: " << out->info()->tensor_shape()
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input shape: " << in->info()->tensor_shape()
+ << " Output shape: " << out->info()->tensor_shape()
+ << std::endl);
return func;
}
diff --git a/src/graph/nodes/FullyConnectedLayer.cpp b/src/graph/nodes/FullyConnectedLayer.cpp
index fa5ead8bd..5f4807ad4 100644
--- a/src/graph/nodes/FullyConnectedLayer.cpp
+++ b/src/graph/nodes/FullyConnectedLayer.cpp
@@ -24,7 +24,6 @@
#include "arm_compute/graph/nodes/FullyConnectedLayer.h"
#include "arm_compute/core/Helpers.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/functions/CLFullyConnectedLayer.h"
#include "arm_compute/runtime/NEON/functions/NEFullyConnectedLayer.h"
#include "support/ToolchainSupport.h"
@@ -123,18 +122,20 @@ std::unique_ptr<arm_compute::IFunction> FullyConnectedLayer::instantiate_node(Gr
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, _weights, _biases, out);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLFullyConnectedLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, _weights, _biases, out);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NEFullyConnectedLayer");
}
- ARM_COMPUTE_LOG(" Type: " << in->info()->data_type()
- << " Input Shape: " << in->info()->tensor_shape()
- << " Weights shape: " << _weights.info().tensor_shape()
- << " Biases Shape: " << _biases.info().tensor_shape()
- << " Output Shape: " << out->info()->tensor_shape()
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Type: " << in->info()->data_type()
+ << " Input Shape: " << in->info()->tensor_shape()
+ << " Weights shape: " << _weights.info().tensor_shape()
+ << " Biases Shape: " << _biases.info().tensor_shape()
+ << " Output Shape: " << out->info()->tensor_shape()
+ << std::endl);
return func;
}
diff --git a/src/graph/nodes/L2NormalizeLayer.cpp b/src/graph/nodes/L2NormalizeLayer.cpp
index 7abc69c13..c5689e159 100644
--- a/src/graph/nodes/L2NormalizeLayer.cpp
+++ b/src/graph/nodes/L2NormalizeLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/L2NormalizeLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/CLTensor.h"
#include "arm_compute/runtime/CL/functions/CLL2Normalize.h"
#include "arm_compute/runtime/NEON/functions/NEL2Normalize.h"
@@ -78,18 +77,18 @@ std::unique_ptr<arm_compute::IFunction> L2NormalizeLayer::instantiate_node(Graph
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, out, _axis, _epsilon);
- ARM_COMPUTE_LOG("Instantiating CLL2NormalizeLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLL2NormalizeLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, out, _axis, _epsilon);
- ARM_COMPUTE_LOG("Instantiating NEL2NormalizeLayer");
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NEL2NormalizeLayer");
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input shape: " << in->info()->tensor_shape()
- << " Output shape: " << out->info()->tensor_shape()
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input shape: " << in->info()->tensor_shape()
+ << " Output shape: " << out->info()->tensor_shape()
+ << std::endl);
return func;
}
diff --git a/src/graph/nodes/NormalizationLayer.cpp b/src/graph/nodes/NormalizationLayer.cpp
index 319a4252b..680925a2b 100644
--- a/src/graph/nodes/NormalizationLayer.cpp
+++ b/src/graph/nodes/NormalizationLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/NormalizationLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/CLTensor.h"
#include "arm_compute/runtime/CL/functions/CLNormalizationLayer.h"
#include "arm_compute/runtime/NEON/functions/NENormalizationLayer.h"
@@ -82,17 +81,19 @@ std::unique_ptr<arm_compute::IFunction> NormalizationLayer::instantiate_node(Gra
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, out, _norm_info);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLNormalizationLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, out, _norm_info);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NENormalizationLayer");
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input shape: " << in->info()->tensor_shape()
- << " Output shape: " << out->info()->tensor_shape()
- << " Normalization info: " << _norm_info
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input shape: " << in->info()->tensor_shape()
+ << " Output shape: " << out->info()->tensor_shape()
+ << " Normalization info: " << _norm_info
+ << std::endl);
return func;
}
diff --git a/src/graph/nodes/PoolingLayer.cpp b/src/graph/nodes/PoolingLayer.cpp
index 904ba1816..63579155c 100644
--- a/src/graph/nodes/PoolingLayer.cpp
+++ b/src/graph/nodes/PoolingLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/PoolingLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/CLTensor.h"
#include "arm_compute/runtime/CL/functions/CLPoolingLayer.h"
#include "arm_compute/runtime/NEON/functions/NEPoolingLayer.h"
@@ -82,16 +81,18 @@ std::unique_ptr<arm_compute::IFunction> PoolingLayer::instantiate_node(GraphCont
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, out, _pool_info);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLPoolingLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, out, _pool_info);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NEPoolingLayer");
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input shape: " << in->info()->tensor_shape()
- << " Output shape: " << out->info()->tensor_shape()
- << " Pooling info: " << _pool_info << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input shape: " << in->info()->tensor_shape()
+ << " Output shape: " << out->info()->tensor_shape()
+ << " Pooling info: " << _pool_info << std::endl);
return func;
}
diff --git a/src/graph/nodes/SoftmaxLayer.cpp b/src/graph/nodes/SoftmaxLayer.cpp
index e3345f140..3cdbc9c96 100644
--- a/src/graph/nodes/SoftmaxLayer.cpp
+++ b/src/graph/nodes/SoftmaxLayer.cpp
@@ -23,7 +23,6 @@
*/
#include "arm_compute/graph/nodes/SoftmaxLayer.h"
-#include "arm_compute/core/Logger.h"
#include "arm_compute/runtime/CL/CLTensor.h"
#include "arm_compute/runtime/CL/functions/CLSoftmaxLayer.h"
#include "arm_compute/runtime/NEON/functions/NESoftmaxLayer.h"
@@ -76,16 +75,18 @@ std::unique_ptr<arm_compute::IFunction> SoftmaxLayer::instantiate_node(GraphCont
if(_target_hint == TargetHint::OPENCL)
{
func = instantiate<TargetHint::OPENCL>(in, out);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating CLSoftmaxLayer");
}
else
{
func = instantiate<TargetHint::NEON>(in, out);
+ ARM_COMPUTE_LOG_GRAPH_INFO("Instantiating NESoftmaxLayer");
}
- ARM_COMPUTE_LOG(" Data Type: " << in->info()->data_type()
- << " Input shape: " << in->info()->tensor_shape()
- << " Output shape: " << out->info()->tensor_shape()
- << std::endl);
+ ARM_COMPUTE_LOG_GRAPH_INFO(" Data Type: " << in->info()->data_type()
+ << " Input shape: " << in->info()->tensor_shape()
+ << " Output shape: " << out->info()->tensor_shape()
+ << std::endl);
return func;
}
diff --git a/support/ToolchainSupport.h b/support/ToolchainSupport.h
index b9d910365..ab2a9fe80 100644
--- a/support/ToolchainSupport.h
+++ b/support/ToolchainSupport.h
@@ -144,8 +144,8 @@ inline T trunc(T value)
* @note This function implements the same behaviour as std::copysign except that it doesn't
* support Integral type. The latter is not in the namespace std in some Android toolchains.
*
- * @param[in] x value that contains the magnitued to be used in constructing the result.
- * @param[in] y value that contains the sign to be used in constructin the result.
+ * @param[in] x value that contains the magnitude to be used in constructing the result.
+ * @param[in] y value that contains the sign to be used in construct in the result.
*
* @return Floating-point value with magnitude of @p x and sign of @p y.
*/
@@ -154,6 +154,23 @@ inline T copysign(T x, T y)
{
return ::copysign(x, y);
}
+
+/** Loads the data from the given location, converts them to character string equivalents
+ * and writes the result to a character string buffer.
+ *
+ * @param[in] s Pointer to a character string to write to
+ * @param[in] n Up to buf_size - 1 characters may be written, plus the null terminator
+ * @param[in] fmt Pointer to a null-terminated multibyte string specifying how to interpret the data.
+ * @param[in] args Arguments forwarded to snprintf.
+ *
+ * @return Number of characters that would have been written for a sufficiently large buffer
+ * if successful (not including the terminating null character), or a negative value if an error occurred.
+ */
+template <typename... Ts>
+inline int snprintf(char *s, size_t n, const char *fmt, Ts &&... args)
+{
+ return ::snprintf(s, n, fmt, std::forward<Ts>(args)...);
+}
#else /* (__ANDROID__ || BARE_METAL) */
/** Convert integer and float values to string.
*
@@ -250,8 +267,8 @@ inline T trunc(T value)
* @note This function implements the same behaviour as std::copysign except that it doesn't
* support Integral type. The latter is not in the namespace std in some Android toolchains.
*
- * @param[in] x value that contains the magnitued to be used in constructing the result.
- * @param[in] y value that contains the sign to be used in constructin the result.
+ * @param[in] x value that contains the magnitude to be used in constructing the result.
+ * @param[in] y value that contains the sign to be used in construct in the result.
*
* @return Floating-point value with magnitude of @p x and sign of @p y.
*/
@@ -260,6 +277,23 @@ inline T copysign(T x, T y)
{
return std::copysign(x, y);
}
+
+/** Loads the data from the given location, converts them to character string equivalents
+ * and writes the result to a character string buffer.
+ *
+ * @param[in] s Pointer to a character string to write to
+ * @param[in] n Up to buf_size - 1 characters may be written, plus the null terminator
+ * @param[in] fmt Pointer to a null-terminated multibyte string specifying how to interpret the data.
+ * @param[in] args Arguments forwarded to std::snprintf.
+ *
+ * @return Number of characters that would have been written for a sufficiently large buffer
+ * if successful (not including the terminating null character), or a negative value if an error occurred.
+ */
+template <typename... Ts>
+inline int snprintf(char *s, std::size_t n, const char *fmt, Ts &&... args)
+{
+ return std::snprintf(s, n, fmt, std::forward<Ts>(args)...);
+}
#endif /* (__ANDROID__ || BARE_METAL) */
inline std::string to_string(bool value)