~azzar1/unity/fix-trash-li-blocking

« back to all changes in this revision

Viewing changes to plugins/unityshell/src/DebugDBusInterface.cpp

  • Committer: Daniel van Vugt
  • Date: 2012-03-14 06:24:18 UTC
  • mfrom: (2108 unity)
  • mto: This revision was merged to the branch mainline in revision 2146.
  • Revision ID: daniel.van.vugt@canonical.com-20120314062418-nprucpbr0m7qky5e
MergedĀ latestĀ lp:unity

Show diffs side-by-side

added added

removed removed

Lines of Context:
18
18
 */
19
19
 
20
20
#include <queue>
 
21
#include <fstream>
21
22
#include <sstream>
22
23
#include <boost/algorithm/string.hpp>
23
24
#include <boost/algorithm/string/split.hpp>
25
26
#include <boost/bind.hpp>
26
27
#include <core/core.h>
27
28
#include <NuxCore/Logger.h>
 
29
#include <NuxCore/LoggingWriter.h>
28
30
 
29
31
#include "DebugDBusInterface.h"
30
32
#include "Introspectable.h"
38
40
{
39
41
namespace
40
42
{
41
 
  nux::logging::Logger logger("unity.debug.DebugDBusInterface");
 
43
nux::logging::Logger logger("unity.debug.DebugDBusInterface");
 
44
 
 
45
namespace local
 
46
{
 
47
  std::ofstream output_file;
 
48
}
42
49
}
43
50
 
44
51
GVariant* GetState(std::string const& query);
 
52
void StartLogToFile(std::string const& file_path);
 
53
void ResetLogging();
 
54
void SetLogSeverity(std::string const& log_component,
 
55
  std::string const& severity);
 
56
void LogMessage(std::string const& severity,
 
57
  std::string const& message);
45
58
 
46
59
const char* DebugDBusInterface::DBUS_DEBUG_OBJECT_PATH = "/com/canonical/Unity/Debug";
47
60
 
54
67
  "       <arg type='aa{sv}' name='state' direction='out' />"
55
68
  "     </method>"
56
69
  ""
 
70
  "     <method name='StartLogToFile'>"
 
71
  "       <arg type='s' name='file_path' direction='in' />"
 
72
  "     </method>"
 
73
  ""
 
74
  "     <method name='ResetLogging'>"
 
75
  "     </method>"
 
76
  ""
 
77
  "     <method name='SetLogSeverity'>"
 
78
  "       <arg type='s' name='log_component' direction='in' />"
 
79
  "       <arg type='s' name='severity' direction='in' />"
 
80
  "     </method>"
 
81
  ""
 
82
  "     <method name='LogMessage'>"
 
83
  "       <arg type='s' name='severity' direction='in' />"
 
84
  "       <arg type='s' name='message' direction='in' />"
 
85
  "     </method>"
 
86
  ""
57
87
  "   </interface>"
58
88
  " </node>";
59
89
 
67
97
static CompScreen* _screen;
68
98
static Introspectable* _parent_introspectable;
69
99
 
70
 
DebugDBusInterface::DebugDBusInterface(Introspectable* parent, 
 
100
DebugDBusInterface::DebugDBusInterface(Introspectable* parent,
71
101
                                       CompScreen* screen)
72
102
{
73
103
  _screen = screen;
100
130
    return;
101
131
  }
102
132
 
103
 
  while (introspection_data->interfaces[i] != NULL) 
 
133
  while (introspection_data->interfaces[i] != NULL)
104
134
  {
105
135
    error = NULL;
106
136
    g_dbus_connection_register_object(connection,
117
147
    }
118
148
    i++;
119
149
  }
 
150
  g_dbus_node_info_unref(introspection_data);
120
151
}
121
152
 
122
153
void
149
180
    g_dbus_method_invocation_return_value(invocation, ret);
150
181
    g_variant_unref(ret);
151
182
  }
 
183
  else if (g_strcmp0(method_name, "StartLogToFile") == 0)
 
184
  {
 
185
    const gchar* log_path;
 
186
    g_variant_get(parameters, "(&s)", &log_path);
 
187
 
 
188
    StartLogToFile(log_path);
 
189
    g_dbus_method_invocation_return_value(invocation, NULL);
 
190
  }
 
191
  else if (g_strcmp0(method_name, "ResetLogging") == 0)
 
192
  {
 
193
    ResetLogging();
 
194
    g_dbus_method_invocation_return_value(invocation, NULL);
 
195
  }
 
196
  else if (g_strcmp0(method_name, "SetLogSeverity") == 0)
 
197
  {
 
198
    const gchar* component;
 
199
    const gchar* severity;
 
200
    g_variant_get(parameters, "(&s&s)", &component, &severity);
 
201
 
 
202
    SetLogSeverity(component, severity);
 
203
    g_dbus_method_invocation_return_value(invocation, NULL);
 
204
  }
 
205
  else if (g_strcmp0(method_name, "LogMessage") == 0)
 
206
  {
 
207
    const gchar* severity;
 
208
    const gchar* message;
 
209
    g_variant_get(parameters, "(&s&s)", &severity, &message);
 
210
 
 
211
    LogMessage(severity, message);
 
212
    g_dbus_method_invocation_return_value(invocation, NULL);
 
213
  }
152
214
  else
153
215
  {
154
 
    g_dbus_method_invocation_return_dbus_error(invocation, 
 
216
    g_dbus_method_invocation_return_dbus_error(invocation,
155
217
                                               unity::DBUS_BUS_NAME.c_str(),
156
218
                                               "Failed to find method");
157
219
  }
164
226
  std::list<Introspectable*> parts = GetIntrospectableNodesFromQuery(query, _parent_introspectable);
165
227
  GVariantBuilder  builder;
166
228
  g_variant_builder_init(&builder, G_VARIANT_TYPE("aa{sv}"));
167
 
  
 
229
 
168
230
  for (Introspectable *node : parts)
169
231
  {
170
232
    g_variant_builder_add_value(&builder, node->Introspect());
171
233
  }
172
 
  
 
234
 
173
235
  return g_variant_new("(aa{sv})", &builder);
174
236
}
175
237
 
 
238
void StartLogToFile(std::string const& file_path)
 
239
{
 
240
  if (local::output_file.is_open())
 
241
    local::output_file.close();
 
242
  local::output_file.open(file_path.c_str());
 
243
  nux::logging::Writer::Instance().SetOutputStream(local::output_file);
 
244
}
 
245
 
 
246
void ResetLogging()
 
247
{
 
248
  if (local::output_file.is_open())
 
249
    local::output_file.close();
 
250
  nux::logging::Writer::Instance().SetOutputStream(std::cout);
 
251
  nux::logging::reset_logging();
 
252
}
 
253
 
 
254
void SetLogSeverity(std::string const& log_component,
 
255
                    std::string const& severity)
 
256
{
 
257
  nux::logging::Logger(log_component).SetLogLevel(nux::logging::get_logging_level(severity));
 
258
}
 
259
 
 
260
void LogMessage(std::string const& severity,
 
261
                std::string const& message)
 
262
{
 
263
  nux::logging::Level level = nux::logging::get_logging_level(severity);
 
264
  if (logger.GetEffectiveLogLevel() <= level)
 
265
  {
 
266
   nux::logging::LogStream(level, logger.module(), __FILE__, __LINE__).stream()
 
267
      << message;
 
268
  }
 
269
}
 
270
 
176
271
/*
177
 
 * Do a breadth-first search of the introspection tree and find all nodes that match the 
 
272
 * Do a breadth-first search of the introspection tree and find all nodes that match the
178
273
 * query.
179
274
 */
180
275
std::list<Introspectable*> GetIntrospectableNodesFromQuery(std::string const& query, Introspectable* tree_root)
196
291
  {
197
292
    std::list<std::string> query_strings;
198
293
    boost::algorithm::split(query_strings, sanitised_query, boost::algorithm::is_any_of("/"));
199
 
    // Boost's split() implementation does not match it's documentation! According to the 
200
 
    // docs, it's not supposed to add empty strings, but it does, which is a PITA. This 
 
294
    // Boost's split() implementation does not match it's documentation! According to the
 
295
    // docs, it's not supposed to add empty strings, but it does, which is a PITA. This
201
296
    // next line removes them:
202
 
    query_strings.erase( std::remove_if( query_strings.begin(), 
203
 
                                        query_strings.end(), 
204
 
                                        boost::bind( &std::string::empty, _1 ) ), 
 
297
    query_strings.erase( std::remove_if( query_strings.begin(),
 
298
                                        query_strings.end(),
 
299
                                        boost::bind( &std::string::empty, _1 ) ),
205
300
                      query_strings.end());
206
301
    foreach(std::string part, query_strings)
207
302
    {
228
323
    {
229
324
      LOG_WARNING(logger) << "Malformed relative introspection query: '" << query << "'.";
230
325
    }
231
 
    
 
326
 
232
327
    // non-recursive BFS traversal to find starting points:
233
328
    std::queue<Introspectable*> queue;
234
329
    queue.push(tree_root);
253
348
  // now we have the tree start points, process them:
254
349
  query_parts.pop_front();
255
350
  typedef std::pair<Introspectable*, std::list<XPathQueryPart>::iterator> node_match_pair;
256
 
  
 
351
 
257
352
  std::queue<node_match_pair> traverse_queue;
258
353
  foreach(Introspectable *node, start_points)
259
354
  {
260
355
    traverse_queue.push(node_match_pair(node, query_parts.begin()));
261
356
  }
262
357
  start_points.clear();
263
 
  
 
358
 
264
359
  while (!traverse_queue.empty())
265
360
  {
266
361
    node_match_pair p = traverse_queue.front();