Ginkgo Generated from branch based on main. Ginkgo version 1.9.0
A numerical linear algebra library targeting many-core architectures
 
Loading...
Searching...
No Matches
logger.hpp
1// SPDX-FileCopyrightText: 2017 - 2024 The Ginkgo authors
2//
3// SPDX-License-Identifier: BSD-3-Clause
4
5#ifndef GKO_PUBLIC_CORE_LOG_LOGGER_HPP_
6#define GKO_PUBLIC_CORE_LOG_LOGGER_HPP_
7
8
9#include <algorithm>
10#include <memory>
11#include <string>
12#include <type_traits>
13#include <vector>
14
15#include <ginkgo/core/base/types.hpp>
16#include <ginkgo/core/base/utils_helper.hpp>
17
18
19namespace gko {
20
21class half;
22
23/* Eliminate circular dependencies the hard way */
24template <typename ValueType>
25class array;
26class Executor;
27class LinOp;
28class LinOpFactory;
30class Operation;
31class stopping_status;
32
33
34namespace batch {
35
36
37class BatchLinOp;
39
40template <typename ValueType>
41class MultiVector;
42
43
44} // namespace batch
45
46
52namespace stop {
53class Criterion;
54} // namespace stop
55
56
57namespace log {
58
59
76class Logger {
77public:
79 using mask_type = gko::uint64;
80
84 static constexpr size_type event_count_max = sizeof(mask_type) * byte_size;
85
89 static constexpr mask_type all_events_mask = ~mask_type{0};
90
112#define GKO_LOGGER_REGISTER_EVENT(_id, _event_name, ...) \
113protected: \
114 virtual void on_##_event_name(__VA_ARGS__) const {} \
115 \
116public: \
117 template <size_type Event, typename... Params> \
118 std::enable_if_t<Event == _id && (_id < event_count_max)> on( \
119 Params&&... params) const \
120 { \
121 if (enabled_events_ & (mask_type{1} << _id)) { \
122 this->on_##_event_name(std::forward<Params>(params)...); \
123 } \
124 } \
125 static constexpr size_type _event_name{_id}; \
126 static constexpr mask_type _event_name##_mask{mask_type{1} << _id};
127
134 GKO_LOGGER_REGISTER_EVENT(0, allocation_started, const Executor* exec,
135 const size_type& num_bytes)
136
137
144 GKO_LOGGER_REGISTER_EVENT(1, allocation_completed, const Executor* exec,
145 const size_type& num_bytes,
146 const uintptr& location)
147
148
154 GKO_LOGGER_REGISTER_EVENT(2, free_started, const Executor* exec,
155 const uintptr& location)
156
157
163 GKO_LOGGER_REGISTER_EVENT(3, free_completed, const Executor* exec,
164 const uintptr& location)
165
166
175 GKO_LOGGER_REGISTER_EVENT(4, copy_started, const Executor* exec_from,
176 const Executor* exec_to, const uintptr& loc_from,
177 const uintptr& loc_to, const size_type& num_bytes)
178
179
188 GKO_LOGGER_REGISTER_EVENT(5, copy_completed, const Executor* exec_from,
189 const Executor* exec_to, const uintptr& loc_from,
190 const uintptr& loc_to, const size_type& num_bytes)
191
192
198 GKO_LOGGER_REGISTER_EVENT(6, operation_launched, const Executor* exec,
199 const Operation* op)
200
201
212 GKO_LOGGER_REGISTER_EVENT(7, operation_completed, const Executor* exec,
213 const Operation* op)
214
215
221 GKO_LOGGER_REGISTER_EVENT(8, polymorphic_object_create_started,
222 const Executor* exec, const PolymorphicObject* po)
223
224
231 GKO_LOGGER_REGISTER_EVENT(9, polymorphic_object_create_completed,
232 const Executor* exec,
233 const PolymorphicObject* input,
234 const PolymorphicObject* output)
235
236
243 GKO_LOGGER_REGISTER_EVENT(10, polymorphic_object_copy_started,
244 const Executor* exec,
245 const PolymorphicObject* input,
246 const PolymorphicObject* output)
247
248
255 GKO_LOGGER_REGISTER_EVENT(11, polymorphic_object_copy_completed,
256 const Executor* exec,
257 const PolymorphicObject* input,
258 const PolymorphicObject* output)
259
260
266 GKO_LOGGER_REGISTER_EVENT(12, polymorphic_object_deleted,
267 const Executor* exec, const PolymorphicObject* po)
268
269
276 GKO_LOGGER_REGISTER_EVENT(13, linop_apply_started, const LinOp* A,
277 const LinOp* b, const LinOp* x)
278
279
286 GKO_LOGGER_REGISTER_EVENT(14, linop_apply_completed, const LinOp* A,
287 const LinOp* b, const LinOp* x)
288
289
298 GKO_LOGGER_REGISTER_EVENT(15, linop_advanced_apply_started, const LinOp* A,
299 const LinOp* alpha, const LinOp* b,
300 const LinOp* beta, const LinOp* x)
301
302
311 GKO_LOGGER_REGISTER_EVENT(16, linop_advanced_apply_completed,
312 const LinOp* A, const LinOp* alpha,
313 const LinOp* b, const LinOp* beta, const LinOp* x)
314
315
322 GKO_LOGGER_REGISTER_EVENT(17, linop_factory_generate_started,
323 const LinOpFactory* factory, const LinOp* input)
324
325
333 GKO_LOGGER_REGISTER_EVENT(18, linop_factory_generate_completed,
334 const LinOpFactory* factory, const LinOp* input,
335 const LinOp* output)
336
337
348 GKO_LOGGER_REGISTER_EVENT(19, criterion_check_started,
350 const size_type& it, const LinOp* r,
351 const LinOp* tau, const LinOp* x,
352 const uint8& stopping_id,
353 const bool& set_finalized)
354
355
375 GKO_LOGGER_REGISTER_EVENT(
376 20, criterion_check_completed, const stop::Criterion* criterion,
377 const size_type& it, const LinOp* r, const LinOp* tau, const LinOp* x,
378 const uint8& stopping_id, const bool& set_finalized,
379 const array<stopping_status>* status, const bool& one_changed,
380 const bool& all_converged)
381protected:
399 virtual void on_criterion_check_completed(
400 const stop::Criterion* criterion, const size_type& it, const LinOp* r,
401 const LinOp* tau, const LinOp* implicit_tau_sq, const LinOp* x,
402 const uint8& stopping_id, const bool& set_finalized,
403 const array<stopping_status>* status, const bool& one_changed,
404 const bool& all_converged) const
405 {
406 this->on_criterion_check_completed(criterion, it, r, tau, x,
407 stopping_id, set_finalized, status,
408 one_changed, all_converged);
409 }
410
411public:
412 static constexpr size_type iteration_complete{21};
413 static constexpr mask_type iteration_complete_mask{mask_type{1} << 21};
414
415 template <size_type Event, typename... Params>
416 std::enable_if_t<Event == 21 && (21 < event_count_max)> on(
417 Params&&... params) const
418 {
419 if (enabled_events_ & (mask_type{1} << 21)) {
420 this->on_iteration_complete(std::forward<Params>(params)...);
421 }
422 }
423
424protected:
437 GKO_DEPRECATED(
438 "Please use the version with the additional stopping "
439 "information.")
440 virtual void on_iteration_complete(const LinOp* solver, const size_type& it,
441 const LinOp* r, const LinOp* x = nullptr,
442 const LinOp* tau = nullptr) const
443 {}
444
458 GKO_DEPRECATED(
459 "Please use the version with the additional stopping "
460 "information.")
461 virtual void on_iteration_complete(const LinOp* solver, const size_type& it,
462 const LinOp* r, const LinOp* x,
463 const LinOp* tau,
464 const LinOp* implicit_tau_sq) const
465 {
466 GKO_BEGIN_DISABLE_DEPRECATION_WARNINGS
467 this->on_iteration_complete(solver, it, r, x, tau);
468 GKO_END_DISABLE_DEPRECATION_WARNINGS
469 }
470
486 virtual void on_iteration_complete(const LinOp* solver, const LinOp* b,
487 const LinOp* x, const size_type& it,
488 const LinOp* r, const LinOp* tau,
489 const LinOp* implicit_tau_sq,
490 const array<stopping_status>* status,
491 bool stopped) const
492 {
493 GKO_BEGIN_DISABLE_DEPRECATION_WARNINGS
494 this->on_iteration_complete(solver, it, r, x, tau, implicit_tau_sq);
495 GKO_END_DISABLE_DEPRECATION_WARNINGS
496 }
497
498public:
506 GKO_LOGGER_REGISTER_EVENT(22, polymorphic_object_move_started,
507 const Executor* exec,
508 const PolymorphicObject* input,
509 const PolymorphicObject* output)
510
511
518 GKO_LOGGER_REGISTER_EVENT(23, polymorphic_object_move_completed,
519 const Executor* exec,
520 const PolymorphicObject* input,
521 const PolymorphicObject* output)
522
523
530 GKO_LOGGER_REGISTER_EVENT(24, batch_linop_factory_generate_started,
531 const batch::BatchLinOpFactory* factory,
532 const batch::BatchLinOp* input)
533
534
542 GKO_LOGGER_REGISTER_EVENT(25, batch_linop_factory_generate_completed,
543 const batch::BatchLinOpFactory* factory,
544 const batch::BatchLinOp* input,
545 const batch::BatchLinOp* output)
546
547public:
548 static constexpr size_type batch_solver_completed{26};
549 static constexpr mask_type batch_solver_completed_mask{mask_type{1} << 26};
550
551 template <size_type Event, typename... Params>
552 std::enable_if_t<Event == 26 && (26 < event_count_max)> on(
553 Params&&... params) const
554 {
555 if (enabled_events_ & batch_solver_completed_mask) {
556 this->on_batch_solver_completed(std::forward<Params>(params)...);
557 }
558 }
559
560protected:
568 virtual void on_batch_solver_completed(
569 const array<int>& iters, const array<double>& residual_norms) const
570 {}
571
579 virtual void on_batch_solver_completed(
580 const array<int>& iters, const array<float>& residual_norms) const
581 {}
582
590 virtual void on_batch_solver_completed(
591 const array<int>& iters, const array<gko::half>& residual_norms) const
592 {}
593
594public:
595#undef GKO_LOGGER_REGISTER_EVENT
596
600 static constexpr mask_type executor_events_mask =
601 allocation_started_mask | allocation_completed_mask |
602 free_started_mask | free_completed_mask | copy_started_mask |
603 copy_completed_mask;
604
608 static constexpr mask_type operation_events_mask =
609 operation_launched_mask | operation_completed_mask;
610
614 static constexpr mask_type polymorphic_object_events_mask =
615 polymorphic_object_create_started_mask |
616 polymorphic_object_create_completed_mask |
617 polymorphic_object_copy_started_mask |
618 polymorphic_object_copy_completed_mask |
619 polymorphic_object_move_started_mask |
620 polymorphic_object_move_completed_mask |
621 polymorphic_object_deleted_mask;
622
626 static constexpr mask_type linop_events_mask =
627 linop_apply_started_mask | linop_apply_completed_mask |
628 linop_advanced_apply_started_mask | linop_advanced_apply_completed_mask;
629
633 static constexpr mask_type linop_factory_events_mask =
634 linop_factory_generate_started_mask |
635 linop_factory_generate_completed_mask;
636
640 static constexpr mask_type batch_linop_factory_events_mask =
641 batch_linop_factory_generate_started_mask |
642 batch_linop_factory_generate_completed_mask;
643
647 static constexpr mask_type criterion_events_mask =
648 criterion_check_started_mask | criterion_check_completed_mask;
649
654 virtual bool needs_propagation() const { return false; }
655
656 virtual ~Logger() = default;
657
658protected:
673 GKO_DEPRECATED("use single-parameter constructor")
674 explicit Logger(std::shared_ptr<const gko::Executor> exec,
675 const mask_type& enabled_events = all_events_mask)
676 : Logger{enabled_events}
677 {}
678
693 explicit Logger(const mask_type& enabled_events = all_events_mask)
694 : enabled_events_{enabled_events}
695 {}
696
697private:
698 mask_type enabled_events_;
699};
700
701
707class Loggable {
708public:
709 virtual ~Loggable() = default;
710
716 virtual void add_logger(std::shared_ptr<const Logger> logger) = 0;
717
727 virtual void remove_logger(const Logger* logger) = 0;
728
730 {
731 remove_logger(logger.get());
732 }
733
739 virtual const std::vector<std::shared_ptr<const Logger>>& get_loggers()
740 const = 0;
741
743 virtual void clear_loggers() = 0;
744};
745
746
759template <typename ConcreteLoggable, typename PolymorphicBase = Loggable>
760class EnableLogging : public PolymorphicBase {
761public:
762 void add_logger(std::shared_ptr<const Logger> logger) override
763 {
764 loggers_.push_back(logger);
765 }
766
767 void remove_logger(const Logger* logger) override
768 {
769 auto idx =
770 find_if(begin(loggers_), end(loggers_),
771 [&logger](const auto& l) { return l.get() == logger; });
772 if (idx != end(loggers_)) {
773 loggers_.erase(idx);
774 } else {
775 throw OutOfBoundsError(__FILE__, __LINE__, loggers_.size(),
776 loggers_.size());
777 }
778 }
779
781 {
782 remove_logger(logger.get());
783 }
784
785 const std::vector<std::shared_ptr<const Logger>>& get_loggers()
786 const override
787 {
788 return loggers_;
789 }
790
791 void clear_loggers() override { loggers_.clear(); }
792
793private:
801 template <size_type Event, typename ConcreteLoggableT, typename = void>
802 struct propagate_log_helper {
803 template <typename... Args>
804 static void propagate_log(const ConcreteLoggableT*, Args&&...)
805 {}
806 };
807
808 template <size_type Event, typename ConcreteLoggableT>
809 struct propagate_log_helper<
810 Event, ConcreteLoggableT,
811 std::void_t<
812 decltype(std::declval<ConcreteLoggableT>().get_executor())>> {
813 template <typename... Args>
814 static void propagate_log(const ConcreteLoggableT* loggable,
815 Args&&... args)
816 {
817 const auto exec = loggable->get_executor();
818 if (exec->should_propagate_log()) {
819 for (auto& logger : exec->get_loggers()) {
820 if (logger->needs_propagation()) {
821 logger->template on<Event>(std::forward<Args>(args)...);
822 }
823 }
824 }
825 }
826 };
827
828protected:
829 template <size_type Event, typename... Params>
830 void log(Params&&... params) const
831 {
832 propagate_log_helper<Event, ConcreteLoggable>::propagate_log(
833 static_cast<const ConcreteLoggable*>(this),
834 std::forward<Params>(params)...);
835 for (auto& logger : loggers_) {
836 logger->template on<Event>(std::forward<Params>(params)...);
837 }
838 }
839
840 std::vector<std::shared_ptr<const Logger>> loggers_;
841};
842
843
844} // namespace log
845} // namespace gko
846
847
848#endif // GKO_PUBLIC_CORE_LOG_LOGGER_HPP_
The first step in using the Ginkgo library consists of creating an executor.
Definition executor.hpp:615
A LinOpFactory represents a higher order mapping which transforms one linear operator into another.
Definition lin_op.hpp:385
Definition lin_op.hpp:117
Operations can be used to define functionalities whose implementations differ among devices.
Definition executor.hpp:258
OutOfBoundsError is thrown if a memory access is detected to be out-of-bounds.
Definition exception.hpp:558
A PolymorphicObject is the abstract base for all "heavy" objects in Ginkgo that behave polymorphicall...
Definition polymorphic_object.hpp:43
An array is a container which encapsulates fixed-sized arrays, stored on the Executor tied to the arr...
Definition array.hpp:166
A BatchLinOpFactory represents a higher order mapping which transforms one batch linear operator into...
Definition batch_lin_op.hpp:195
Definition batch_lin_op.hpp:59
MultiVector stores multiple vectors in a batched fashion and is useful for batched operations.
Definition batch_multi_vector.hpp:59
A class providing basic support for half precision floating point types.
Definition half.hpp:286
EnableLogging is a mixin which should be inherited by any class which wants to enable logging.
Definition logger.hpp:760
void clear_loggers() override
Remove all loggers registered at this object.
Definition logger.hpp:791
const std::vector< std::shared_ptr< const Logger > > & get_loggers() const override
Returns the vector containing all loggers registered at this object.
Definition logger.hpp:785
void add_logger(std::shared_ptr< const Logger > logger) override
Adds a new logger to the list of subscribed loggers.
Definition logger.hpp:762
void remove_logger(const Logger *logger) override
Removes a logger from the list of subscribed loggers.
Definition logger.hpp:767
Loggable class is an interface which should be implemented by classes wanting to support logging.
Definition logger.hpp:707
virtual const std::vector< std::shared_ptr< const Logger > > & get_loggers() const =0
Returns the vector containing all loggers registered at this object.
virtual void clear_loggers()=0
Remove all loggers registered at this object.
virtual void remove_logger(const Logger *logger)=0
Removes a logger from the list of subscribed loggers.
virtual void add_logger(std::shared_ptr< const Logger > logger)=0
Adds a new logger to the list of subscribed loggers.
Definition logger.hpp:76
static constexpr mask_type all_events_mask
Bitset Mask which activates all events.
Definition logger.hpp:89
static constexpr mask_type operation_events_mask
Bitset Mask which activates all operation events.
Definition logger.hpp:608
static constexpr mask_type batch_linop_factory_events_mask
Bitset Mask which activates all batch linop factory events.
Definition logger.hpp:640
static constexpr mask_type linop_events_mask
Bitset Mask which activates all linop events.
Definition logger.hpp:626
static constexpr mask_type polymorphic_object_events_mask
Bitset Mask which activates all polymorphic object events.
Definition logger.hpp:614
virtual bool needs_propagation() const
Returns true if this logger, when attached to an Executor, needs to be forwarded all events from obje...
Definition logger.hpp:654
static constexpr mask_type criterion_events_mask
Bitset Mask which activates all criterion events.
Definition logger.hpp:647
static constexpr size_type event_count_max
Maximum amount of events (bits) with the current implementation.
Definition logger.hpp:84
static constexpr mask_type linop_factory_events_mask
Bitset Mask which activates all linop factory events.
Definition logger.hpp:633
static constexpr mask_type executor_events_mask
Bitset Mask which activates all executor events.
Definition logger.hpp:600
This class is used for function parameters in the place of raw pointers.
Definition utils_helper.hpp:41
T * get() const
Definition utils_helper.hpp:75
The Criterion class is a base class for all stopping criteria.
Definition criterion.hpp:36
This class is used to keep track of the stopping status of one vector.
Definition stopping_status.hpp:21
The logger namespace .
Definition convergence.hpp:22
@ criterion
Stopping criterion events.
Definition profiler_hook.hpp:36
@ solver
Solver events.
Definition profiler_hook.hpp:34
@ factory
LinOpFactory events.
Definition profiler_hook.hpp:32
The Stopping criterion namespace.
Definition logger.hpp:52
The Ginkgo namespace.
Definition abstract_factory.hpp:20
std::uint8_t uint8
8-bit unsigned integral type.
Definition types.hpp:118
std::uint64_t uint64
64-bit unsigned integral type.
Definition types.hpp:135
std::uintptr_t uintptr
Unsigned integer type capable of holding a pointer to void.
Definition types.hpp:141
std::size_t size_type
Integral type used for allocation quantities.
Definition types.hpp:89
constexpr size_type byte_size
Number of bits in a byte.
Definition types.hpp:177
@ array
The matrix should be written as dense matrix in column-major order.
Definition mtx_io.hpp:96
STL namespace.