OpcUaCanOpen
CANopen OPC-UA server
LogItInstance.cpp
Go to the documentation of this file.
1 /* © Copyright CERN, 2015. All rights not expressly granted are reserved.
2  * LogItInstance.cpp
3  *
4  * Created on: Apr 4, 2016
5  * Author: Benjamin Farnham <benjamin.farnham@cern.ch>
6  *
7  * This file is part of Quasar.
8  *
9  * Quasar is free software: you can redistribute it and/or modify
10  * it under the terms of the GNU Lesser General Public Licence as published by
11  * the Free Software Foundation, either version 3 of the Licence.
12  *
13  * Quasar is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU Lesser General Public Licence for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public License
19  * along with Quasar. If not, see <http://www.gnu.org/licenses/>.
20  */
21 #include "LogItInstance.h"
22 #include "LogItStaticDefinitions.h"
23 #include <iostream>
24 #include <sstream>
25 
26 using std::cerr;
27 using std::endl;
28 using std::map;
29 using std::string;
30 using std::ostringstream;
31 
32 LogItInstance* LogItInstance::g_sLogItInstance(NULL); // initially - set by any LogIt::initialize*Logging() call.
33 
35 :m_isLoggingInitialized(false), m_nonComponentLogLevel(Log::INF), m_componentNames(new MapOfComponentNameToHandle)
36 {
38 }
39 
41 {}
42 
44 {
45  return LogItInstance::g_sLogItInstance != NULL;
46 }
47 
49 {
51 }
52 
54 {
55  if(!remoteInstance)
56  {
57  cerr << "Failed to set LogItInstance with NULL remoteInstance. Ignoring (and returning false)" << endl;
58  return false;
59  }
60  if(instanceExists())
61  {
62  if(getInstance() == remoteInstance) return true; // fine - do nothing.
63  cerr << "Failed to set LogItInstance with remoteInstance ["<<remoteInstance<<"], already have incumbent instance ["<<getInstance()<<"]. Ignoring (and returning false)" << endl;
64  return false;
65  }
66  g_sLogItInstance = remoteInstance;
67  return true;
68 }
69 
71 {
72  if(instanceExists())
73  {
74  cerr << "Failed to create new LogItInstance, already have instance ["<<getInstance()<<"]. Ignoring (and returning instance)" << endl;
75  }
76  else
77  {
79  }
80  return getInstance();
81 }
82 
83 ComponentAttributes& LogItInstance::registerLoggingComponent(const string& componentName, const Log::LOG_LEVEL& nonComponentLogLevel)
84 {
85  // serialization: mutex ownership required to change contents of the vector of logging components
86  std::lock_guard<decltype(m_componentsLock)> scopedLock(m_componentsLock);
87 
88  // check whether component is already registered (if so, should be a handle, handle ids the component attributes
89  Log::LogComponentHandle existingComponentHandle = Log::INVALID_HANDLE;
90  if(getComponentHandle(componentName, existingComponentHandle))
91  {
92  ComponentAttributes* componentAttributes = nullptr;
93  if(getComponentAttributes(existingComponentHandle, componentAttributes))
94  {
95  return *componentAttributes;
96  }
97  else
98  {
99  ostringstream msg;
100  msg << __FUNCTION__<<" FAILED: logging component ["<<componentName<<"] has handle ["<<existingComponentHandle<<"], but no attributes found. Probably a programming error. Current entry count ["<<m_components.size()<<"]";
101  throw std::runtime_error(msg.str());
102  }
103  }
104 
105  // is there room to add this component?
107  {
108  ostringstream msg;
109  msg << __FUNCTION__<<" FAILED: cannot add logging component ["<<componentName<<"] to components list, the list is full (entry count ["<<m_components.size()<<"])";
110  throw std::runtime_error(msg.str());
111  }
112 
113  // Note: a components LogComponentHandle is its index in the vector of logging components.
114  const Log::LogComponentHandle newComponentHandle(m_components.size());
115  m_components.emplace_back(ComponentAttributes(newComponentHandle, componentName, nonComponentLogLevel));
116 
117  // clone existing map, add new component and reset shared pointer to use new map.
119  newComponentNames->emplace(componentName, newComponentHandle);
120  m_componentNames.reset(newComponentNames);
121 
122  return m_components[newComponentHandle];
123 }
124 
125 bool LogItInstance::getComponentAttributes(const Log::LogComponentHandle& componentHandle, ComponentAttributes*& componentAttributes)
126 {
127  if(componentHandle >= m_components.size()) return false;
128 
129  componentAttributes = &(m_components[componentHandle]);
130  return true;
131 }
132 
133 bool LogItInstance::getComponentHandle(const std::string& componentName, Log::LogComponentHandle& componentHandle)
134 {
135  const auto it = m_componentNames->find(componentName);
136  if(it == m_componentNames->end()) return false;
137 
138  componentHandle = it->second;
139  return true;
140 }
141 
142 map<Log::LogComponentHandle, string> LogItInstance::getLoggingComponentsList() const
143 {
144  // serialization: mutex ownership required to loop through vector of logging components
145  std::lock_guard<decltype(m_componentsLock)> scopedLock(m_componentsLock);
146 
147  map<Log::LogComponentHandle, string> result;
148 
149  for(size_t i=0; i<m_components.size(); ++i)
150  {
151  const ComponentAttributes& componentAttributes = m_components[i];
152  result[componentAttributes.getHandle()] = componentAttributes.getName();
153  }
154 
155  return result;
156 }