OptParser.cc

Go to the documentation of this file.
00001 /*
00002  * IMPORTANT: READ BEFORE DOWNLOADING, COPYING, INSTALLING OR USING. By
00003  * downloading, copying, installing or using the software you agree to
00004  * this license. If you do not agree to this license, do not download,
00005  * install, copy or use the software.
00006  * 
00007  * Intel Open Source License 
00008  * 
00009  * Copyright (c) 2005 Intel Corporation. All rights reserved. 
00010  * 
00011  * Redistribution and use in source and binary forms, with or without
00012  * modification, are permitted provided that the following conditions are
00013  * met:
00014  * 
00015  *   Redistributions of source code must retain the above copyright
00016  *   notice, this list of conditions and the following disclaimer.
00017  * 
00018  *   Redistributions in binary form must reproduce the above copyright
00019  *   notice, this list of conditions and the following disclaimer in the
00020  *   documentation and/or other materials provided with the distribution.
00021  * 
00022  *   Neither the name of the Intel Corporation nor the names of its
00023  *   contributors may be used to endorse or promote products derived from
00024  *   this software without specific prior written permission.
00025  *  
00026  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
00027  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00028  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
00029  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE INTEL OR
00030  * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
00031  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
00032  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
00033  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
00034  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
00035  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
00036  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00037  */
00038 #include "OptParser.h"
00039 
00040 namespace oasys {
00041 
00042 //----------------------------------------------------------------------
00043 OptParser::~OptParser()
00044 {
00045     for (u_int i = 0; i < allopts_.size(); ++i)
00046     {
00047         delete allopts_[i];
00048     }
00049     allopts_.clear();
00050 }
00051 
00052 //----------------------------------------------------------------------
00053 void
00054 OptParser::addopt(Opt* opt)
00055 {
00056     allopts_.push_back(opt);
00057 }
00058 
00059 //----------------------------------------------------------------------
00060 bool
00061 OptParser::parse_opt(const char* opt_str, size_t len, bool* invalid_value)
00062 {
00063     Opt* opt;
00064     const char* val_str;
00065     size_t opt_len, val_len;
00066 
00067     if (invalid_value) {
00068         *invalid_value = false;
00069     }
00070 
00071     opt_len = strcspn(opt_str, "= \t\r\n");
00072     if (opt_len == 0 || opt_len > len) {
00073         return false;
00074     }
00075 
00076     if (opt_str[opt_len] != '=') {
00077         val_str = NULL;
00078         val_len = 0;
00079     } else {
00080         val_str = opt_str + opt_len + 1;
00081         val_len = strcspn(val_str, " \t\r\n");
00082         if (val_len == 0 || (val_len + opt_len + 1) != len) {
00083             return false;
00084         }
00085     }
00086     
00087     int nopts = allopts_.size(); 
00088     for (int i = 0; i < nopts; ++i)
00089     {
00090         opt = allopts_[i];
00091         
00092         if (strncmp(opt_str, opt->longopt_, opt_len) == 0)
00093         {
00094             if (opt->needval_ && (val_str == NULL)) {
00095                 if (invalid_value) {
00096                     *invalid_value = true;
00097                 }
00098                 return false; // missing value
00099             }
00100 
00101             if (opt->set(val_str, val_len) != 0) {
00102                 if (invalid_value) {
00103                     *invalid_value = true;
00104                 }
00105                 return false; // error in set
00106             }
00107             
00108             return true; // all set
00109         }
00110     }
00111 
00112     return false; // no matching option
00113 }
00114 
00115 //----------------------------------------------------------------------
00116 bool
00117 OptParser::parse(const char* args, const char** invalidp)
00118 {
00119     const char* opt;
00120     size_t opt_len;
00121 
00122     opt = args;
00123     while (1) {
00124         opt_len = strcspn(opt, " \t\r\n");
00125         if (opt_len == 0) {
00126             return true; // all done
00127         }
00128 
00129         if (parse_opt(opt, opt_len) == false) {
00130             *invalidp = opt;
00131             return false;
00132         }
00133 
00134         // skip past the arg and all other whitespace
00135         opt = opt + opt_len;
00136         opt += strspn(opt, " \t\r\n");
00137     }
00138 }
00139 
00140 //----------------------------------------------------------------------
00141 bool
00142 OptParser::parse(int argc, const char* const argv[], const char** invalidp)
00143 {
00144     for (int i = 0; i < argc; ++i) {
00145         if (parse_opt(argv[i], strlen(argv[i])) == false) {
00146             *invalidp = argv[i];
00147             return false;
00148         }
00149     }
00150 
00151     return true;
00152 }
00153 
00154 //----------------------------------------------------------------------
00155 int
00156 OptParser::parse_and_shift(int argc, const char* argv[], const char** invalidp)
00157 {
00158     int last_slot = 0;
00159     int valid_count = 0;
00160     bool invalid_value;
00161 
00162     for (int i = 0; i < argc; ++i) {
00163         
00164         if (parse_opt(argv[i], strlen(argv[i]), &invalid_value) == true) {
00165             ++valid_count;
00166             
00167         } else {
00168             argv[last_slot] = argv[i];
00169             last_slot++;
00170             
00171             if (invalid_value) {
00172                 if (invalidp)
00173                     *invalidp = argv[i];
00174                 
00175                 return -1; // stop parsing
00176             }
00177         }
00178     }
00179     
00180     return valid_count;
00181 }
00182 
00183 //----------------------------------------------------------------------
00184 bool
00185 OptParser::parse(const std::vector<std::string>& args,
00186                  const char** invalidp)
00187 {
00188     std::vector<std::string>::const_iterator iter;
00189     for (iter = args.begin(); iter != args.end(); ++iter) {
00190         if (parse_opt(iter->c_str(), iter->length()) == false) {
00191             *invalidp = iter->c_str();
00192             return false;
00193         }
00194     }
00195 
00196     return true;
00197 }
00198 
00199 
00200 } // namespace oasys

Generated on Fri Dec 22 14:48:00 2006 for DTN Reference Implementation by  doxygen 1.5.1