File indexing completed on 2025-10-26 08:27:44
0001 
0002 
0003 
0004 
0005 
0006 
0007 #ifndef BOOST_NOWIDE_ARGS_HPP_INCLUDED
0008 #define BOOST_NOWIDE_ARGS_HPP_INCLUDED
0009 
0010 #include <boost/config.hpp>
0011 #ifdef BOOST_WINDOWS
0012 #include <boost/nowide/stackstring.hpp>
0013 #include <boost/nowide/windows.hpp>
0014 #include <stdexcept>
0015 #include <vector>
0016 #endif
0017 
0018 namespace boost {
0019 namespace nowide {
0020 #if !defined(BOOST_WINDOWS) && !defined(BOOST_NOWIDE_DOXYGEN)
0021     class args
0022     {
0023     public:
0024         args(int&, char**&)
0025         {}
0026         args(int&, char**&, char**&)
0027         {}
0028     };
0029 
0030 #else
0031 
0032     
0033     
0034     
0035     
0036     
0037     
0038     
0039     
0040     
0041     
0042     
0043     
0044     
0045     
0046     
0047     
0048     
0049     
0050     
0051     
0052     
0053     
0054     
0055     
0056     class args
0057     {
0058     public:
0059         
0060         
0061         
0062         args(int& argc, char**& argv) :
0063             old_argc_(argc), old_argv_(argv), old_env_(0), old_argc_ptr_(&argc), old_argv_ptr_(&argv), old_env_ptr_(0)
0064         {
0065             fix_args(argc, argv);
0066         }
0067         
0068         
0069         
0070         args(int& argc, char**& argv, char**& env) :
0071             old_argc_(argc), old_argv_(argv), old_env_(env), old_argc_ptr_(&argc), old_argv_ptr_(&argv),
0072             old_env_ptr_(&env)
0073         {
0074             fix_args(argc, argv);
0075             fix_env(env);
0076         }
0077         
0078         
0079         
0080         ~args()
0081         {
0082             if(old_argc_ptr_)
0083                 *old_argc_ptr_ = old_argc_;
0084             if(old_argv_ptr_)
0085                 *old_argv_ptr_ = old_argv_;
0086             if(old_env_ptr_)
0087                 *old_env_ptr_ = old_env_;
0088         }
0089 
0090     private:
0091         class wargv_ptr
0092         {
0093             wchar_t** p;
0094             int argc;
0095 
0096         public:
0097             wargv_ptr()
0098             {
0099                 p = CommandLineToArgvW(GetCommandLineW(), &argc);
0100             }
0101             ~wargv_ptr()
0102             {
0103                 if(p)
0104                     LocalFree(p);
0105             }
0106             wargv_ptr(const wargv_ptr&) = delete;
0107             wargv_ptr& operator=(const wargv_ptr&) = delete;
0108 
0109             int size() const
0110             {
0111                 return argc;
0112             }
0113             operator bool() const
0114             {
0115                 return p != nullptr;
0116             }
0117             const wchar_t* operator[](size_t i) const
0118             {
0119                 return p[i];
0120             }
0121         };
0122         class wenv_ptr
0123         {
0124             wchar_t* p;
0125 
0126         public:
0127             wenv_ptr() : p(GetEnvironmentStringsW())
0128             {}
0129             ~wenv_ptr()
0130             {
0131                 if(p)
0132                     FreeEnvironmentStringsW(p);
0133             }
0134             wenv_ptr(const wenv_ptr&) = delete;
0135             wenv_ptr& operator=(const wenv_ptr&) = delete;
0136 
0137             operator const wchar_t*() const
0138             {
0139                 return p;
0140             }
0141         };
0142 
0143         void fix_args(int& argc, char**& argv)
0144         {
0145             const wargv_ptr wargv;
0146             if(!wargv)
0147                 throw std::runtime_error("Could not get command line!");
0148             args_.resize(wargv.size() + 1, 0);
0149             arg_values_.resize(wargv.size());
0150             for(int i = 0; i < wargv.size(); i++)
0151                 args_[i] = arg_values_[i].convert(wargv[i]);
0152             argc = wargv.size();
0153             argv = &args_[0];
0154         }
0155         void fix_env(char**& env)
0156         {
0157             const wenv_ptr wstrings;
0158             if(!wstrings)
0159                 throw std::runtime_error("Could not get environment strings!");
0160             const wchar_t* wstrings_end = 0;
0161             int count = 0;
0162             for(wstrings_end = wstrings; *wstrings_end; wstrings_end += wcslen(wstrings_end) + 1)
0163                 count++;
0164             env_.convert(wstrings, wstrings_end);
0165             envp_.resize(count + 1, 0);
0166             char* p = env_.get();
0167             int pos = 0;
0168             for(int i = 0; i < count; i++)
0169             {
0170                 if(*p != '=')
0171                     envp_[pos++] = p;
0172                 p += strlen(p) + 1;
0173             }
0174             env = &envp_[0];
0175         }
0176 
0177         std::vector<char*> args_;
0178         std::vector<short_stackstring> arg_values_;
0179         stackstring env_;
0180         std::vector<char*> envp_;
0181 
0182         int old_argc_;
0183         char** old_argv_;
0184         char** old_env_;
0185 
0186         int* old_argc_ptr_;
0187         char*** old_argv_ptr_;
0188         char*** old_env_ptr_;
0189     };
0190 
0191 #endif
0192 
0193 } 
0194 } 
0195 #endif