"Fossies" - the Fresh Open Source Software Archive

Member "stella-6.0.2/src/common/bspf.hxx" (11 Oct 2019, 6833 Bytes) of package /linux/privat/stella-6.0.2-src.tar.xz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "bspf.hxx" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 6.0.1_vs_6.0.2.

    1 //============================================================================
    2 //
    3 //  BBBBB    SSSS   PPPPP   FFFFFF
    4 //  BB  BB  SS  SS  PP  PP  FF
    5 //  BB  BB  SS      PP  PP  FF
    6 //  BBBBB    SSSS   PPPPP   FFFF    --  "Brad's Simple Portability Framework"
    7 //  BB  BB      SS  PP      FF
    8 //  BB  BB  SS  SS  PP      FF
    9 //  BBBBB    SSSS   PP      FF
   10 //
   11 // Copyright (c) 1995-2019 by Bradford W. Mott, Stephen Anthony
   12 // and the Stella Team
   13 //
   14 // See the file "License.txt" for information on usage and redistribution of
   15 // this file, and for a DISCLAIMER OF ALL WARRANTIES.
   16 //============================================================================
   17 
   18 #ifndef BSPF_HXX
   19 #define BSPF_HXX
   20 
   21 /**
   22   This file defines various basic data types and preprocessor variables
   23   that need to be defined for different operating systems.
   24 
   25   @author Bradford W. Mott and Stephen Anthony
   26 */
   27 
   28 #include <climits>
   29 #include <cstdint>
   30 // Types for 8/16/32/64-bit signed and unsigned integers
   31 using Int8   = int8_t;
   32 using uInt8  = uint8_t;
   33 using Int16  = int16_t;
   34 using uInt16 = uint16_t;
   35 using Int32  = int32_t;
   36 using uInt32 = uint32_t;
   37 using Int64  = int64_t;
   38 using uInt64 = uint64_t;
   39 
   40 // The following code should provide access to the standard C++ objects and
   41 // types: cout, cerr, string, ostream, istream, etc.
   42 #include <algorithm>
   43 #include <iostream>
   44 #include <fstream>
   45 #include <iomanip>
   46 #include <memory>
   47 #include <string>
   48 #include <sstream>
   49 #include <cstring>
   50 #include <cctype>
   51 #include <cstdio>
   52 #include <ctime>
   53 #include <utility>
   54 #include <vector>
   55 
   56 using std::cin;
   57 using std::cout;
   58 using std::cerr;
   59 using std::endl;
   60 using std::string;
   61 using std::istream;
   62 using std::ostream;
   63 using std::fstream;
   64 using std::iostream;
   65 using std::ifstream;
   66 using std::ofstream;
   67 using std::ostringstream;
   68 using std::istringstream;
   69 using std::stringstream;
   70 using std::unique_ptr;
   71 using std::shared_ptr;
   72 using std::make_unique;
   73 using std::make_shared;
   74 using std::array;
   75 using std::vector;
   76 using std::runtime_error;
   77 using std::memcpy;
   78 
   79 // Common array types
   80 using IntArray = std::vector<Int32>;
   81 using uIntArray = std::vector<uInt32>;
   82 using BoolArray = std::vector<bool>;
   83 using ByteArray = std::vector<uInt8>;
   84 using ShortArray = std::vector<uInt16>;
   85 using StringList = std::vector<std::string>;
   86 using BytePtr = std::unique_ptr<uInt8[]>;
   87 
   88 static const string EmptyString("");
   89 
   90 namespace BSPF
   91 {
   92   // Defines to help with path handling
   93   #if defined(BSPF_UNIX) || defined(BSPF_MACOS)
   94     static const string PATH_SEPARATOR = "/";
   95     #define ATTRIBUTE_FMT_PRINTF __attribute__((__format__ (__printf__, 2, 0)))
   96   #elif defined(BSPF_WINDOWS)
   97     static const string PATH_SEPARATOR = "\\";
   98     #define ATTRIBUTE_FMT_PRINTF
   99   #else
  100     #error Update src/common/bspf.hxx for path separator
  101   #endif
  102 
  103   // CPU architecture type
  104   // This isn't complete yet, but takes care of all the major platforms
  105   #if defined(__i386__) || defined(_M_IX86)
  106     static const string ARCH = "i386";
  107   #elif defined(__x86_64__) || defined(_WIN64)
  108     static const string ARCH = "x86_64";
  109   #elif defined(__powerpc__) || defined(__ppc__)
  110     static const string ARCH = "ppc";
  111   #else
  112     static const string ARCH = "NOARCH";
  113   #endif
  114 
  115   // Combines 'max' and 'min', and clamps value to the upper/lower value
  116   // if it is outside the specified range
  117   template<class T> inline T clamp(T val, T lower, T upper)
  118   {
  119     return (val < lower) ? lower : (val > upper) ? upper : val;
  120   }
  121   template<class T> inline void clamp(T& val, T lower, T upper, T setVal)
  122   {
  123     if(val < lower || val > upper)  val = setVal;
  124   }
  125 
  126   // Compare two strings, ignoring case
  127   inline int compareIgnoreCase(const string& s1, const string& s2)
  128   {
  129   #if defined BSPF_WINDOWS && !defined __GNUG__
  130     return _stricmp(s1.c_str(), s2.c_str());
  131   #else
  132     return strcasecmp(s1.c_str(), s2.c_str());
  133   #endif
  134   }
  135   inline int compareIgnoreCase(const char* s1, const char* s2)
  136   {
  137   #if defined BSPF_WINDOWS && !defined __GNUG__
  138     return _stricmp(s1, s2);
  139   #else
  140     return strcasecmp(s1, s2);
  141   #endif
  142   }
  143 
  144   // Test whether the first string starts with the second one (case insensitive)
  145   inline bool startsWithIgnoreCase(const string& s1, const string& s2)
  146   {
  147   #if defined BSPF_WINDOWS && !defined __GNUG__
  148     return _strnicmp(s1.c_str(), s2.c_str(), s2.length()) == 0;
  149   #else
  150     return strncasecmp(s1.c_str(), s2.c_str(), s2.length()) == 0;
  151   #endif
  152   }
  153   inline bool startsWithIgnoreCase(const char* s1, const char* s2)
  154   {
  155   #if defined BSPF_WINDOWS && !defined __GNUG__
  156     return _strnicmp(s1, s2, strlen(s2)) == 0;
  157   #else
  158     return strncasecmp(s1, s2, strlen(s2)) == 0;
  159   #endif
  160   }
  161 
  162   // Test whether two strings are equal (case insensitive)
  163   inline bool equalsIgnoreCase(const string& s1, const string& s2)
  164   {
  165     return compareIgnoreCase(s1, s2) == 0;
  166   }
  167 
  168   // Find location (if any) of the second string within the first,
  169   // starting from 'startpos' in the first string
  170   inline size_t findIgnoreCase(const string& s1, const string& s2, size_t startpos = 0)
  171   {
  172     auto pos = std::search(s1.cbegin()+startpos, s1.cend(),
  173       s2.cbegin(), s2.cend(), [](char ch1, char ch2) {
  174         return toupper(uInt8(ch1)) == toupper(uInt8(ch2));
  175       });
  176     return pos == s1.cend() ? string::npos : pos - (s1.cbegin()+startpos);
  177   }
  178 
  179   // Test whether the first string ends with the second one (case insensitive)
  180   inline bool endsWithIgnoreCase(const string& s1, const string& s2)
  181   {
  182     if(s1.length() >= s2.length())
  183     {
  184       const char* end = s1.c_str() + s1.length() - s2.length();
  185       return compareIgnoreCase(end, s2.c_str()) == 0;
  186     }
  187     return false;
  188   }
  189 
  190   // Test whether the first string contains the second one (case insensitive)
  191   inline bool containsIgnoreCase(const string& s1, const string& s2)
  192   {
  193     return findIgnoreCase(s1, s2) != string::npos;
  194   }
  195 
  196   // Test whether the first string matches the second one (case insensitive)
  197   // - the first character must match
  198   // - the following characters must appear in the order of the first string
  199   inline bool matches(const string& s1, const string& s2)
  200   {
  201     if(BSPF::startsWithIgnoreCase(s1, s2.substr(0, 1)))
  202     {
  203       size_t pos = 1;
  204       for(uInt32 j = 1; j < s2.size(); ++j)
  205       {
  206         size_t found = BSPF::findIgnoreCase(s1, s2.substr(j, 1), pos);
  207         if(found == string::npos)
  208           return false;
  209         pos += found + 1;
  210       }
  211       return true;
  212     }
  213     return false;
  214   }
  215 
  216   // C++11 way to get local time
  217   // Equivalent to the C-style localtime() function, but is thread-safe
  218   inline std::tm localTime()
  219   {
  220     std::time_t currtime;
  221     std::time(&currtime);
  222     std::tm tm_snapshot;
  223   #if defined BSPF_WINDOWS && !defined __GNUG__
  224     localtime_s(&tm_snapshot, &currtime);
  225   #else
  226     localtime_r(&currtime, &tm_snapshot);
  227   #endif
  228     return tm_snapshot;
  229   }
  230 } // namespace BSPF
  231 
  232 #endif