RouteCommand.cc

Go to the documentation of this file.
00001 /*
00002  *    Copyright 2004-2006 Intel Corporation
00003  * 
00004  *    Licensed under the Apache License, Version 2.0 (the "License");
00005  *    you may not use this file except in compliance with the License.
00006  *    You may obtain a copy of the License at
00007  * 
00008  *        http://www.apache.org/licenses/LICENSE-2.0
00009  * 
00010  *    Unless required by applicable law or agreed to in writing, software
00011  *    distributed under the License is distributed on an "AS IS" BASIS,
00012  *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00013  *    See the License for the specific language governing permissions and
00014  *    limitations under the License.
00015  */
00016 
00017 #include <config.h>
00018 
00019 #include <oasys/util/StringBuffer.h>
00020 #include <oasys/serialize/XMLSerialize.h>
00021 
00022 #include "RouteCommand.h"
00023 #include "CompletionNotifier.h"
00024 
00025 #include "contacts/Link.h"
00026 #include "contacts/ContactManager.h"
00027 
00028 #include "bundling/BundleEvent.h"
00029 #include "bundling/BundleDaemon.h"
00030 
00031 #include "routing/BundleRouter.h"
00032 #include "routing/RouteEntry.h"
00033 #include "routing/ExternalRouter.h"
00034 
00035 namespace dtn {
00036 
00037 RouteCommand::RouteCommand()
00038     : TclCommand("route")
00039 {
00040     bind_var(new oasys::StringOpt("type", &BundleRouter::config_.type_, 
00041                                   "type", "Which routing algorithm to use."));
00042 
00043     bind_var(new oasys::BoolOpt("add_nexthop_routes",
00044                                 &BundleRouter::config_.add_nexthop_routes_,
00045                                 "Whether or not to automatically add routes "
00046                                 "for next hop links"));
00047     
00048     bind_var(new oasys::IntOpt("default_priority",
00049                                &BundleRouter::config_.default_priority_,
00050                                "priority",
00051                                "Default priority for new routes "
00052                                "(initially zero)"));
00053     
00054     add_to_help("add <dest> <link/endpoint> [opts]", "add a route");
00055     add_to_help("del <dest> <link/endpoint>", "delete a route");
00056     add_to_help("dump", "dump all of the static routes");
00057 
00058 #ifdef XERCES_C_ENABLED
00059     bind_var(new oasys::UInt16Opt("server_port",
00060                                   &ExternalRouter::server_port,
00061                                   "port",
00062                                   "UDP port for IPC with external router(s)"));
00063     
00064     bind_var(new oasys::UInt16Opt("hello_interval",
00065                                   &ExternalRouter::hello_interval,
00066                                   "interval",
00067                                   "seconds between hello messages"));
00068     
00069     bind_var(new oasys::StringOpt("schema", &ExternalRouter::schema,
00070                                   "file",
00071                                   "The external router interface "
00072                                   "message schema."));
00073 
00074     bind_var(new oasys::BoolOpt("xml_server_validation",
00075                                 &ExternalRouter::server_validation,
00076                                 "Perform xml validation on plug-in "
00077                                 "interface messages (default is true)"));
00078     
00079     bind_var(new oasys::BoolOpt("xml_client_validation",
00080                                 &ExternalRouter::client_validation,
00081                                 "Include meta-info in xml messages "
00082                                 "so plug-in routers"
00083                                 "can perform validation (default is false)"));
00084 #endif
00085 }
00086 
00087 int
00088 RouteCommand::exec(int argc, const char** argv, Tcl_Interp* interp)
00089 {
00090     (void)interp;
00091     
00092     if (argc < 2) {
00093         resultf("need a route subcommand");
00094         return TCL_ERROR;
00095     }
00096 
00097     const char* cmd = argv[1];
00098     
00099     if (strcmp(cmd, "add") == 0) {
00100         // route add <dest> <link/endpoint> <args>
00101         if (argc < 4) {
00102             wrong_num_args(argc, argv, 2, 4, INT_MAX);
00103             return TCL_ERROR;
00104         }
00105 
00106         const char* dest_str = argv[2];
00107 
00108         EndpointIDPattern dest(dest_str);
00109         if (!dest.valid()) {
00110             resultf("invalid destination eid %s", dest_str);
00111             return TCL_ERROR;
00112         }
00113         const char* name = argv[3];
00114         Link* link = NULL;
00115         
00116         link = BundleDaemon::instance()->contactmgr()->find_link(name);
00117 
00118         if (link == NULL) {
00119             resultf("no such link %s", name);
00120             return TCL_ERROR;
00121         }
00122 
00123         RouteEntry* entry = new RouteEntry(dest, link);
00124         
00125         // skip over the consumed arguments and parse optional ones.
00126         // any invalid options are shifted into argv[0]
00127         argc -= 4;
00128         argv += 4;
00129         if (argc != 0 && (entry->parse_options(argc, argv) != argc))
00130         {
00131             resultf("invalid argument '%s'", argv[0]);
00132             return TCL_ERROR;
00133         }
00134         
00135         // post the event -- if the daemon has been started, we wait
00136         // for the event to be consumed, otherwise we just return
00137         // immediately. this allows the command to have the
00138         // appropriate semantics both in the static config file and in
00139         // an interactive mode
00140         
00141         if (BundleDaemon::instance()->started()) {
00142             BundleDaemon::post_and_wait(new RouteAddEvent(entry),
00143                                         CompletionNotifier::notifier());
00144         } else {
00145             BundleDaemon::post(new RouteAddEvent(entry));
00146         }
00147 
00148         return TCL_OK;
00149     }
00150 
00151     else if (strcmp(cmd, "del") == 0) {
00152         // route del <dest>
00153         if (argc != 3) {
00154             wrong_num_args(argc, argv, 2, 3, 3);
00155             return TCL_ERROR;
00156         }
00157 
00158         EndpointIDPattern pat(argv[2]);
00159         if (!pat.valid()) {
00160             resultf("invalid endpoint id pattern '%s'", argv[2]);
00161             return TCL_ERROR;
00162         }
00163 
00164         if (BundleDaemon::instance()->started()) {
00165             BundleDaemon::post_and_wait(new RouteDelEvent(pat),
00166                                         CompletionNotifier::notifier());
00167         } else {
00168             BundleDaemon::post(new RouteDelEvent(pat));
00169         }
00170         
00171         return TCL_OK;
00172     }
00173 
00174     else if (strcmp(cmd, "dump") == 0) {
00175         oasys::StringBuffer buf;
00176         BundleDaemon::instance()->get_routing_state(&buf);
00177         set_result(buf.c_str());
00178         return TCL_OK;
00179     }
00180 
00181     else if (strcmp(cmd, "local_eid") == 0) {
00182         if (argc == 2) {
00183             // route local_eid
00184             set_result(BundleDaemon::instance()->local_eid().c_str());
00185             return TCL_OK;
00186             
00187         } else if (argc == 3) {
00188             // route local_eid <eid?>
00189             BundleDaemon::instance()->set_local_eid(argv[2]);
00190             if (! BundleDaemon::instance()->local_eid().valid()) {
00191                 resultf("invalid eid '%s'", argv[2]);
00192                 return TCL_ERROR;
00193             }
00194             if (! BundleDaemon::instance()->local_eid().known_scheme()) {
00195                 resultf("local eid '%s' has unknown scheme", argv[2]);
00196                 return TCL_ERROR;
00197             }
00198         } else {
00199             wrong_num_args(argc, argv, 2, 2, 3);
00200             return TCL_ERROR;
00201         }
00202     }
00203 
00204     else {
00205         resultf("unimplemented route subcommand %s", cmd);
00206         return TCL_ERROR;
00207     }
00208     
00209     return TCL_OK;
00210 }
00211 
00212 } // namespace dtn

Generated on Sat Sep 8 08:36:18 2007 for DTN Reference Implementation by  doxygen 1.5.3