Publishing 2019 R1 content
[platform/upstream/dldt.git] / inference-engine / samples / validation_app / user_exception.hpp
1 // Copyright (C) 2018-2019 Intel Corporation
2 // SPDX-License-Identifier: Apache-2.0
3 //
4
5 /**
6  * @brief A header file for the user input exception
7  * \file user_exception.hpp
8  */
9 #pragma once
10
11 #include <memory>
12 #include <string>
13 #include <sstream>
14 #include <list>
15 #include <functional>
16
17 /**
18  * @def THROW_USER_EXCEPTION
19  * @brief A macro used to throw the exception with a notable description
20  */
21 #define THROW_USER_EXCEPTION(exitCode) \
22     throw UserException(exitCode)
23
24 /**
25  * @class UserException
26  * @brief The UserException class implements an exception appearing as a result of user input
27  */
28 class UserException : public std::exception {
29     mutable std::string errorDesc;
30     std::shared_ptr<std::stringstream> exception_stream;
31     int _exitCode;
32
33 public:
34     /**
35      * @brief A C++ std::exception API member
36      * @return An exception description with a file name and file line
37      */
38     const char *what() const noexcept override {
39         if (errorDesc.empty() && exception_stream) {
40             errorDesc = exception_stream->str();
41         }
42         return errorDesc.c_str();
43     }
44
45     /**
46      * @brief A constructor. Creates a UserException object
47      */
48     explicit UserException(int exitCode) : _exitCode(exitCode) {
49     }
50
51     UserException(int exitCode, std::string msg) : _exitCode(exitCode) {
52         *this << msg;
53     }
54
55     /**
56      * @brief A stream output operator to be used within exception
57      * @param arg Object for serialization in the exception message
58      */
59     template<class T>
60     UserException &operator<<(const T &arg) {
61         if (!exception_stream) {
62             exception_stream.reset(new std::stringstream());
63         }
64         (*exception_stream) << arg;
65         return *this;
66     }
67
68     int exitCode() const { return _exitCode; }
69 };
70
71 class UserExceptions : public std::exception {
72     std::list<UserException> _list;
73     mutable std::string msg;
74
75 public:
76     UserExceptions &operator<<(const UserException &arg) {
77         _list.push_back(arg);
78         return *this;
79     }
80
81     const char *what() const noexcept override {
82         std::stringstream ss;
83
84         if (_list.size() == 1) {
85             ss << _list.back().what();
86         } else {
87             auto iter = _list.begin();
88             for (size_t i = 0; i < _list.size() - 1; i++) {
89                 ss << "\t* " << (*iter++).what() << std::endl;
90             }
91             ss << "\t* " << _list.back().what();
92         }
93
94         msg = ss.str();
95         return msg.c_str();
96     }
97
98     const std::list<UserException>& list() const {
99         return _list;
100     }
101
102     bool empty() const { return _list.empty(); }
103 };
104