switch to new MPL based Fraunhofer FOKUS Public License
[senf.git] / senf / Utils / Console / Node.cci
1 // $Id$
2 //
3 // Copyright (C) 2008
4 // Fraunhofer Institute for Open Communication Systems (FOKUS)
5 //
6 // The contents of this file are subject to the Fraunhofer FOKUS Public License
7 // Version 1.0 (the "License"); you may not use this file except in compliance
8 // with the License. You may obtain a copy of the License at 
9 // http://senf.berlios.de/license.html
10 //
11 // The Fraunhofer FOKUS Public License Version 1.0 is based on, 
12 // but modifies the Mozilla Public License Version 1.1.
13 // See the full license text for the amendments.
14 //
15 // Software distributed under the License is distributed on an "AS IS" basis, 
16 // WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License 
17 // for the specific language governing rights and limitations under the License.
18 //
19 // The Original Code is Fraunhofer FOKUS code.
20 //
21 // The Initial Developer of the Original Code is Fraunhofer-Gesellschaft e.V. 
22 // (registered association), Hansastraße 27 c, 80686 Munich, Germany.
23 // All Rights Reserved.
24 //
25 // Contributor(s):
26 //   Stefan Bund <g0dil@berlios.de>
27
28 /** \file
29     \brief Node inline non-template implementation */
30
31 #include "Node.ih"
32
33 // Custom includes
34
35 #define prefix_ inline
36 //-/////////////////////////////////////////////////////////////////////////////////////////////////
37
38 //-/////////////////////////////////////////////////////////////////////////////////////////////////
39 // senf::console::GenericNode
40
41 prefix_ senf::console::GenericNode::ptr senf::console::GenericNode::thisptr()
42 {
43     return shared_from_this();
44 }
45
46 prefix_ senf::console::GenericNode::cptr senf::console::GenericNode::thisptr()
47     const
48 {
49     return shared_from_this();
50 }
51
52 prefix_ senf::console::GenericNode::~GenericNode()
53 {}
54
55 prefix_ std::string const & senf::console::GenericNode::name()
56     const
57 {
58     return name_;
59 }
60
61 prefix_ senf::console::GenericNode::GenericNode()
62     : parent_ (0)
63 {}
64
65 prefix_ void senf::console::GenericNode::name(std::string const & name)
66 {
67     name_ = name;
68 }
69
70 prefix_ boost::shared_ptr<senf::console::DirectoryNode> senf::console::GenericNode::parent()
71     const
72 {
73     return boost::static_pointer_cast<DirectoryNode>(
74         parent_ ? parent_->shared_from_this() : ptr() );
75 }
76
77 prefix_ senf::console::GenericNode::ptr senf::console::GenericNode::unlink()
78 {
79     if (parent_)
80         return parent()->remove(name());
81     else
82         return thisptr();
83 }
84
85 prefix_ void senf::console::GenericNode::help(std::ostream & output)
86     const
87 {
88     v_help(output);
89 }
90
91 prefix_ std::string senf::console::GenericNode::shorthelp()
92     const
93 {
94     return v_shorthelp();
95 }
96
97 prefix_ bool senf::console::GenericNode::operator==(GenericNode & other)
98     const
99 {
100     return this == & other;
101 }
102
103 prefix_ bool senf::console::GenericNode::operator!=(GenericNode & other)
104     const
105 {
106     return this != & other;
107 }
108
109 prefix_ bool senf::console::GenericNode::isDirectory()
110     const
111 {
112     return dynamic_cast<DirectoryNode const *>(this);
113 }
114
115 prefix_ bool senf::console::GenericNode::isLink()
116     const
117 {
118     return dynamic_cast<LinkNode const *>(this);
119 }
120
121 prefix_ bool senf::console::GenericNode::isCommand()
122     const
123 {
124     return dynamic_cast<CommandNode const *>(this);
125 }
126
127 prefix_ senf::console::GenericNode const & senf::console::GenericNode::followLink()
128     const
129 {
130     return isLink()
131         ? dynamic_cast<LinkNode const *>(this)->follow()
132         : *this;
133 }
134
135 prefix_ senf::console::GenericNode & senf::console::GenericNode::followLink()
136 {
137     return isLink()
138         ? dynamic_cast<LinkNode *>(this)->follow()
139         : *this;
140 }
141
142 //-/////////////////////////////////////////////////////////////////////////////////////////////////
143 // senf::console::LinkNode
144
145 prefix_ senf::console::GenericNode & senf::console::LinkNode::follow()
146     const
147 {
148     return *node_;
149 }
150
151 prefix_ senf::console::LinkNode::ptr senf::console::LinkNode::create(GenericNode & node)
152 {
153     GenericNode::ptr p (node.thisptr());
154     while ( p->isLink() )
155         p = dynamic_cast<LinkNode&>(*p).follow().thisptr();
156     return ptr(new LinkNode(*p));
157 }
158
159 prefix_ senf::console::LinkNode::LinkNode(GenericNode & node)
160     : node_ (node.thisptr())
161 {}
162
163 //-/////////////////////////////////////////////////////////////////////////////////////////////////
164 // senf::console::DirectoryNode
165
166 prefix_ senf::console::DirectoryNode::ptr senf::console::DirectoryNode::create()
167 {
168     return ptr(new DirectoryNode());
169 }
170
171 prefix_ bool senf::console::DirectoryNode::hasChild(std::string const & name)
172     const
173 {
174     ChildMap::const_iterator i (children_.find(name));
175     return i != children_.end();
176 }
177
178 prefix_ senf::console::GenericNode &
179 senf::console::DirectoryNode::get(std::string const & name)
180     const
181 {
182     return getLink(name).followLink();
183 }
184
185 prefix_ senf::console::DirectoryNode &
186 senf::console::DirectoryNode::getDirectory(std::string const & name)
187     const
188 {
189     try {
190         return dynamic_cast<DirectoryNode&>(get(name));
191     }
192     SENF_WRAP_EXC(std::bad_cast)
193 }
194
195 prefix_ senf::console::DirectoryNode &
196 senf::console::DirectoryNode::operator[](std::string const & name)
197     const
198 {
199     return getDirectory(name);
200 }
201
202 prefix_ senf::console::CommandNode &
203 senf::console::DirectoryNode::getCommand(std::string const & name)
204     const
205 {
206     try {
207         return dynamic_cast<CommandNode&>(get(name));
208     }
209     SENF_WRAP_EXC(std::bad_cast)
210 }
211
212 prefix_ senf::console::CommandNode &
213 senf::console::DirectoryNode::operator()(std::string const & name)
214     const
215 {
216     return getCommand(name);
217 }
218
219 prefix_ senf::console::DirectoryNode::ChildrenRange senf::console::DirectoryNode::children()
220     const
221 {
222     return boost::make_iterator_range(children_.begin(), children_.end());
223 }
224
225 prefix_ senf::console::DirectoryNode::ChildrenRange
226 senf::console::DirectoryNode::completions(std::string const & s)
227     const
228 {
229     return boost::make_iterator_range(children_.lower_bound(s),
230                                       children_.lower_bound(s + "\xff"));
231 }
232
233 prefix_ senf::console::DirectoryNode::DirectoryNode()
234 {}
235
236 prefix_ senf::console::DirectoryNode &
237 senf::console::DirectoryNode::doc(std::string const & doc)
238 {
239     doc_ = doc;
240     return *this;
241 }
242
243 prefix_ senf::console::DirectoryNode &
244 senf::console::DirectoryNode::shortdoc(std::string const & doc)
245 {
246     shortdoc_ = doc;
247     return *this;
248 }
249
250 prefix_ senf::console::DirectoryNode::ptr senf::console::DirectoryNode::thisptr()
251 {
252     return boost::static_pointer_cast<DirectoryNode>(shared_from_this());
253 }
254
255 prefix_ senf::console::DirectoryNode::cptr senf::console::DirectoryNode::thisptr()
256     const
257 {
258     return boost::static_pointer_cast<DirectoryNode const>(shared_from_this());
259 }
260
261 //-/////////////////////////////////////////////////////////////////////////////////////////////////
262 // senf::console::detail::NodeTraverser
263 #ifndef DOXYGEN
264
265 prefix_ senf::console::detail::NodeTraverser::NodeTraverser(DirectoryNode & root,
266                                                             DirectoryNode & dir,
267                                                             bool autocomplete)
268     : root_ (root), dir_ (dir.thisptr()), autocomplete_ (autocomplete), init_ (false)
269 {}
270
271 #endif
272
273 //-/////////////////////////////////////////////////////////////////////////////////////////////////
274 // senf::console::CommandNode
275
276 prefix_ senf::console::CommandNode::ptr senf::console::CommandNode::thisptr()
277 {
278     return boost::static_pointer_cast<CommandNode>(shared_from_this());
279 }
280
281 prefix_ senf::console::CommandNode::cptr senf::console::CommandNode::thisptr()
282     const
283 {
284     return boost::static_pointer_cast<CommandNode const>(shared_from_this());
285 }
286
287 prefix_ senf::console::CommandNode::CommandNode()
288 {}
289
290 prefix_ void senf::console::CommandNode::execute(std::ostream & output,
291                                                  ParseCommandInfo const & command)
292     const
293 {
294     boost::any rv;
295     execute(rv, output, command);
296 }
297
298 prefix_ void senf::console::CommandNode::execute(boost::any & rv, std::ostream & output,
299                                                  ParseCommandInfo const & command)
300     const
301 {
302     rv = boost::any();
303     v_execute(rv, output, command);
304 }
305
306 prefix_ void senf::console::CommandNode::operator()(std::ostream & output,
307                                                     ParseCommandInfo const & command)
308     const
309 {
310     execute(output, command);
311 }
312
313 prefix_ void senf::console::CommandNode::operator()(boost::any & rv, std::ostream & output,
314                                                     ParseCommandInfo const & command)
315     const
316 {
317     execute(rv, output, command);
318 }
319
320 //-/////////////////////////////////////////////////////////////////////////////////////////////////
321 // senf::console::SimpleCommandNode
322
323 prefix_ senf::console::SimpleCommandNode::SimpleCommandNode(Function const & fn)
324     : fn_ (fn)
325 {}
326
327 prefix_ senf::console::SimpleCommandNode::ptr
328 senf::console::SimpleCommandNode::create(Function const & fn)
329 {
330     return ptr(new SimpleCommandNode(fn));
331 }
332
333 prefix_ senf::console::SimpleCommandNode &
334 senf::console::SimpleCommandNode::doc(std::string const & doc)
335 {
336     doc_ = doc;
337     return *this;
338 }
339
340 prefix_ senf::console::SimpleCommandNode &
341 senf::console::SimpleCommandNode::shortdoc(std::string const & doc)
342 {
343     shortdoc_ = doc;
344     return *this;
345 }
346
347 prefix_ senf::console::SimpleCommandNode::ptr senf::console::SimpleCommandNode::thisptr()
348 {
349     return boost::static_pointer_cast<SimpleCommandNode>(shared_from_this());
350 }
351
352 prefix_ senf::console::SimpleCommandNode::cptr senf::console::SimpleCommandNode::thisptr()
353     const
354 {
355     return boost::static_pointer_cast<SimpleCommandNode const>(shared_from_this());
356 }
357
358 //-/////////////////////////////////////////////////////////////////////////////////////////////////
359
360 prefix_ senf::console::DirectoryNode & senf::console::provideDirectory(DirectoryNode & dir,
361                                                                        std::string const & name)
362 {
363     return dir.hasChild(name) ? dir.getDirectory(name) : dir.add(name, factory::Directory());
364 }
365
366
367 //-/////////////////////////////////////////////////////////////////////////////////////////////////
368 // senf::console::factory::SimpleCommand
369
370 prefix_ senf::console::factory::SimpleCommand::SimpleCommand(SimpleCommandNode::Function fn)
371     : node_ (SimpleCommandNode::create(fn))
372 {}
373
374 prefix_ senf::console::SimpleCommandNode &
375 senf::console::factory::SimpleCommand::create(DirectoryNode & dir, std::string const & name)
376     const
377 {
378     return dir.add(name, node_);
379 }
380
381 prefix_ senf::console::factory::SimpleCommand const &
382 senf::console::factory::SimpleCommand::doc(std::string const & doc)
383     const
384 {
385     node_->doc(doc);
386     return *this;
387 }
388
389 prefix_ senf::console::factory::SimpleCommand const &
390 senf::console::factory::SimpleCommand::shortdoc(std::string const & doc)
391     const
392 {
393     node_->shortdoc(doc);
394     return *this;
395 }
396
397 //-/////////////////////////////////////////////////////////////////////////////////////////////////
398 // senf::console::factory::Directory
399
400 prefix_ senf::console::factory::Directory::Directory()
401     : node_ (DirectoryNode::create())
402 {}
403
404 prefix_ senf::console::DirectoryNode &
405 senf::console::factory::Directory::create(DirectoryNode & dir, std::string const & name)
406     const
407 {
408     return dir.add(name, node_);
409 }
410
411 prefix_ senf::console::factory::Directory const &
412 senf::console::factory::Directory::doc(std::string const & doc)
413     const
414 {
415     node_->doc(doc);
416     return *this;
417 }
418
419 prefix_ senf::console::factory::Directory const &
420 senf::console::factory::Directory::shortdoc(std::string const & doc)
421     const
422 {
423     node_->shortdoc(doc);
424     return *this;
425 }
426
427 //-/////////////////////////////////////////////////////////////////////////////////////////////////
428 // senf::console::factory::Link
429
430 prefix_ senf::console::factory::Link::Link(GenericNode & target)
431     : node_ (LinkNode::create(target))
432 {}
433
434 prefix_ senf::console::LinkNode & senf::console::factory::Link::create(DirectoryNode & dir,
435                                                                        std::string const & name)
436     const
437 {
438     return dir.add(name, node_);
439 }
440
441 //-/////////////////////////////////////////////////////////////////////////////////////////////////
442 #undef prefix_
443
444 \f
445 // Local Variables:
446 // mode: c++
447 // fill-column: 100
448 // comment-column: 40
449 // c-file-style: "senf"
450 // indent-tabs-mode: nil
451 // ispell-local-dictionary: "american"
452 // compile-command: "scons -u test"
453 // End: