xorp

utils.hh

00001 // -*- c-basic-offset: 4; tab-width: 8; indent-tabs-mode: t -*-
00002 // vim:set sts=4 ts=8:
00003 
00004 // Copyright (c) 2001-2011 XORP, Inc and Others
00005 //
00006 // This program is free software; you can redistribute it and/or modify
00007 // it under the terms of the GNU Lesser General Public License, Version
00008 // 2.1, June 1999 as published by the Free Software Foundation.
00009 // Redistribution and/or modification of this program under the terms of
00010 // any other version of the GNU Lesser General Public License is not
00011 // permitted.
00012 // 
00013 // This program is distributed in the hope that it will be useful, but
00014 // WITHOUT ANY WARRANTY; without even the implied warranty of
00015 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
00016 // see the GNU Lesser General Public License, Version 2.1, a copy of
00017 // which can be found in the XORP LICENSE.lgpl file.
00018 // 
00019 // XORP, Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
00020 // http://xorp.net
00021 
00022 #ifndef __LIBXORP_UTILS_HH__
00023 #define __LIBXORP_UTILS_HH__
00024 
00025 
00026 #include "utility.h"
00027 
00028 //
00029 // Set of utilities
00030 //
00031 
00032 #define PATH_CURDIR         "."
00033 #define PATH_PARENT         ".."
00034 
00035 #define NT_PATH_DELIMITER_CHAR      '\\'
00036 #define NT_PATH_DELIMITER_STRING    "\\"
00037 #define NT_PATH_ENV_DELIMITER_CHAR  ';'
00038 #define NT_PATH_ENV_DELIMITER_STRING    ";"
00039 #define NT_PATH_DRIVE_DELIMITER_CH  ':'
00040 #define NT_EXECUTABLE_SUFFIX        ".exe"
00041 
00042 // NT specific
00043 #define NT_PATH_UNC_PREFIX      "\\\\"
00044 #define NT_PATH_DRIVE_SUFFIX        ":"
00045 
00046 #define UNIX_PATH_DELIMITER_CHAR    '/'
00047 #define UNIX_PATH_DELIMITER_STRING  "/"
00048 #define UNIX_PATH_ENV_DELIMITER_CHAR    ':'
00049 #define UNIX_PATH_ENV_DELIMITER_STRING  ":"
00050 #define UNIX_EXECUTABLE_SUFFIX      ""
00051 
00052 #ifdef  HOST_OS_WINDOWS
00053 #define PATH_DELIMITER_CHAR     NT_PATH_DELIMITER_CHAR
00054 #define PATH_DELIMITER_STRING       NT_PATH_DELIMITER_STRING
00055 #define PATH_ENV_DELIMITER_CHAR     NT_PATH_ENV_DELIMITER_CHAR
00056 #define PATH_ENV_DELIMITER_STRING   NT_PATH_ENV_DELIMITER_STRING
00057 #define EXECUTABLE_SUFFIX       NT_EXECUTABLE_SUFFIX
00058 #else   // ! HOST_OS_WINDOWS
00059 #define PATH_DELIMITER_CHAR     UNIX_PATH_DELIMITER_CHAR
00060 #define PATH_DELIMITER_STRING       UNIX_PATH_DELIMITER_STRING
00061 #define PATH_ENV_DELIMITER_CHAR     UNIX_PATH_ENV_DELIMITER_CHAR
00062 #define PATH_ENV_DELIMITER_STRING   UNIX_PATH_ENV_DELIMITER_STRING
00063 #define EXECUTABLE_SUFFIX       UNIX_EXECUTABLE_SUFFIX
00064 #endif  // ! HOST_OS_WINDOWS
00065 
00066 
00073 inline string
00074 unix_path_to_native(const string& unixpath)
00075 {
00076 #ifdef HOST_OS_WINDOWS
00077     string nativepath = unixpath;
00078     string::size_type n = 0;
00079     while (string::npos != (n = nativepath.find(UNIX_PATH_DELIMITER_CHAR, n))) {
00080         nativepath[n] = NT_PATH_DELIMITER_CHAR;
00081     }
00082     return (nativepath);
00083 #else // ! HOST_OS_WINDOWS
00084     return string(unixpath);
00085 #endif // ! HOST_OS_WINDOWS
00086 }
00087 
00097 inline bool
00098 is_absolute_path(const string& path, bool homeok = false)
00099 {
00100     if (path.empty())
00101     return false;
00102 
00103 #ifdef HOST_OS_WINDOWS
00104     if ((path.find(NT_PATH_UNC_PREFIX) == 0) ||
00105     ((path.size() >= 2) && isalpha(path[0]) && path[1] == ':'))
00106         return true;
00107     return false;
00108     UNUSED(homeok);
00109 #else // ! HOST_OS_WINDOWS
00110     if (path[0] == '/')
00111         return true;
00112     if (homeok && path[0] == '~')
00113         return true;
00114     return false;
00115 #endif // ! HOST_OS_WINDOWS
00116 }
00117 
00126 list<string> split(const string& s, char sep);
00127 
00134 string strip_empty_spaces(const string& s);
00135 
00142 bool has_empty_space(const string& s);
00143 
00149 const char* xorp_basename(const char* argv0);
00150 
00156 template<class T> void
00157 delete_pointers_list(list<T *>& delete_list)
00158 {
00159     list<T *> tmp_list;
00160     
00161     // Swap the elements, so the original container never contains
00162     // entries that point to deleted elements.
00163     swap(tmp_list, delete_list);
00164     
00165     for (typename list<T *>::iterator iter = tmp_list.begin();
00166      iter != tmp_list.end();
00167      ++iter) {
00168     T *elem = (*iter);
00169     delete elem;
00170     }
00171     tmp_list.clear();
00172 }
00173 
00179 template<class T> void
00180 delete_pointers_vector(vector<T *>& delete_vector)
00181 {
00182     vector<T *> tmp_vector;
00183     // Swap the elements, so the original container never contains
00184     // entries that point to deleted elements.
00185     swap(tmp_vector, delete_vector);
00186     
00187     for (typename vector<T *>::iterator iter = tmp_vector.begin();
00188      iter != tmp_vector.end();
00189      ++iter) {
00190     T *elem = (*iter);
00191     delete elem;
00192     }
00193     tmp_vector.clear();
00194 }
00195 
00235 FILE*   xorp_make_temporary_file(const string& tmp_dir,
00236                  const string& filename_template,
00237                  string& final_filename,
00238                  string& errmsg);
00239 
00240 #ifdef HOST_OS_WINDOWS
00241 
00262 void win_quote_args(const list<string>& args, string& cmdline);
00263 #endif // HOST_OS_WINDOWS
00264 
00279 inline uint32_t
00280 xorp_bit_count_uint32(uint32_t x)
00281 {
00282     //
00283     // 32-bit recursive reduction using SWAR...
00284     // but first step is mapping 2-bit values
00285     // into sum of 2 1-bit values in sneaky way.
00286     //
00287     x -= ((x >> 1) & 0x55555555);
00288     x = (((x >> 2) & 0x33333333) + (x & 0x33333333));
00289     x = (((x >> 4) + x) & 0x0f0f0f0f);
00290     x += (x >> 8);
00291     x += (x >> 16);
00292     x &= 0x0000003f;
00293 
00294     return (x);
00295 }
00296 
00306 inline uint32_t
00307 xorp_leading_zero_count_uint32(uint32_t x)
00308 {
00309     x |= (x >> 1);
00310     x |= (x >> 2);
00311     x |= (x >> 4);
00312     x |= (x >> 8);
00313     x |= (x >> 16);
00314 
00315     return (32 - xorp_bit_count_uint32(x));
00316 }
00317 
00337 template <typename A>
00338 class AlignData {
00339 public:
00345     AlignData(const vector<uint8_t>& buffer) {
00346     if (_data_is_copied) {
00347         _data = malloc(sizeof(uint8_t) * buffer.size());
00348         memcpy(_data, &buffer[0], sizeof(uint8_t) * buffer.size());
00349         _const_data = _data;
00350     } else {
00351         _data = NULL;
00352         _const_data = &buffer[0];
00353     }
00354     _payload = reinterpret_cast<const A*>(_const_data);
00355     }
00356 
00360     ~AlignData() {
00361     if (_data != NULL)
00362         free(_data);
00363     }
00364 
00370     const A* payload() const { return (_payload); }
00371 
00383     const A* payload_by_offset(size_t offset) const {
00384     const void* offset_data;
00385     offset_data = reinterpret_cast<const uint8_t*>(_const_data) + offset;
00386     return (reinterpret_cast<const A*>(offset_data));
00387     }
00388 
00389 private:
00390     // Damn..code assumes data is not coppied, see:
00391     // NetlinkSocket::force_recvmsg_flgs
00392     // Will just have to assume that alignment is OK till we can clean this up. --Ben
00393     static const bool _data_is_copied = false;
00394 
00395     void*   _data;
00396     const void* _const_data;
00397     const A*    _payload;
00398 };
00399 
00400 #endif // __LIBXORP_UTILS_HH__
 All Classes Namespaces Functions Variables Typedefs Enumerations