1 // (C) Copyright Gennadiy Rozental 2005-2008.
2 // Distributed under the Boost Software License, Version 1.0.
3 // (See accompanying file LICENSE_1_0.txt or copy at
4 // http://www.boost.org/LICENSE_1_0.txt)
5
6 // See http://www.boost.org/libs/test for the library home page.
7 //
8 // File : $RCSfile$
9 //
10 // Version : $Revision: 54633 $
11 //
12 // Description : defines model of program environment variable
13 // ***************************************************************************
14
15 #ifndef BOOST_RT_ENV_VARIABLE_HPP_062604GER
16 #define BOOST_RT_ENV_VARIABLE_HPP_062604GER
17
18 #ifdef UNDER_CE
19 #error Windows CE does not support environment variables.
20 #endif
21
22 // Boost.Runtime.Parameter
23 #include <boost/test/utils/runtime/config.hpp>
24 #include <boost/test/utils/runtime/fwd.hpp>
25 #include <boost/test/utils/runtime/parameter.hpp>
26 #include <boost/test/utils/runtime/argument.hpp>
27
28 #include <boost/test/utils/runtime/env/fwd.hpp>
29
30 // Boost
31 #include <boost/optional.hpp>
32
33 namespace boost {
34
35 namespace BOOST_RT_PARAM_NAMESPACE {
36
37 namespace environment {
38
39 // ************************************************************************** //
40 // ************** runtime::environment::variable_data ************** //
41 // ************************************************************************** //
42
43 namespace rt_env_detail {
44
45 struct variable_data : public runtime::parameter {
46 cstring m_var_name;
47 dstring m_global_id;
48 argument_ptr m_value;
49 };
50
51 } // namespace rt_env_detail
52
53 // ************************************************************************** //
54 // ************** runtime::environment::variable_base ************** //
55 // ************************************************************************** //
56
57 class variable_base {
58 public:
variable_base(rt_env_detail::variable_data & data)59 explicit variable_base( rt_env_detail::variable_data& data ) : m_data( &data ) {}
60
61 // arguments access
62 template<typename T>
value() const63 T const& value() const
64 {
65 return arg_value<T>( *m_data->m_value );
66 }
67
68 template<typename T>
value(boost::optional<T> & res) const69 void value( boost::optional<T>& res ) const
70 {
71 if( has_value() )
72 res = arg_value<T>( *m_data->m_value );
73 else
74 res.reset();
75 }
76
has_value() const77 bool has_value() const { return m_data->m_value; }
name() const78 cstring name() const { return m_data->m_var_name; }
79
80 protected:
81 // Data members
82 rt_env_detail::variable_data* m_data;
83 } ;
84
85 // ************************************************************************** //
86 // ************** runtime::environment::variable ************** //
87 // ************************************************************************** //
88
89 template<typename T = cstring>
90 class variable : public variable_base {
91 public:
92 // Constructors
93 explicit variable( cstring var_name );
94
95 template<typename Modifiers>
96 explicit variable( cstring var_name, Modifiers const& m );
97
variable(rt_env_detail::variable_data & data)98 explicit variable( rt_env_detail::variable_data& data )
99 : variable_base( data ) {}
100
101 // other variable assignment
operator =(variable const & v)102 void operator=( variable const& v ) { m_data = v.m_data; }
103
104 // access methods
value() const105 T const& value() const { return variable_base::value<T>(); }
106
107 #if BOOST_WORKAROUND(__MWERKS__, BOOST_TESTED_AT(0x3206)) || \
108 BOOST_WORKAROUND(__BORLANDC__, BOOST_TESTED_AT(0x0593))
109 template<typename T>
value(boost::optional<T> & res) const110 void value( boost::optional<T>& res ) const { variable_base::value( res ); }
111 #else
112 using variable_base::value;
113 #endif
114
115 // Value assignment
116 template<typename V>
operator =(V const & v)117 void operator=( V const& v )
118 {
119 if( !has_value() )
120 m_data->m_value.reset( new typed_argument<T>( *m_data ) );
121
122 arg_value<T>( *m_data->m_value ) = v;
123
124 rt_env_detail::sys_write_var( m_data->m_var_name, format_stream().ref() << value() );
125 }
126 }; // class variable
127
128 //____________________________________________________________________________//
129
130 template<typename CharT, typename Tr,typename T>
131 inline std::basic_ostream<CharT,Tr>&
operator <<(std::basic_ostream<CharT,Tr> & os,variable<T> const & v)132 operator<<( std::basic_ostream<CharT,Tr>& os, variable<T> const& v )
133 {
134 os << v.name() << '=';
135
136 if( v.has_value() )
137 os << v.value();
138
139 return os;
140 }
141
142 //____________________________________________________________________________//
143
144 template<typename T, typename V>
145 inline bool
operator ==(variable<T> ev,V const & v)146 operator==( variable<T> ev, V const& v )
147 {
148 return ev.has_value() && ev.value() == v;
149 }
150
151 //____________________________________________________________________________//
152
153 template<typename T, typename V>
154 inline bool
operator ==(V const & v,variable<T> ev)155 operator==( V const& v, variable<T> ev )
156 {
157 return ev.has_value() && ev.value() == v;
158 }
159
160 //____________________________________________________________________________//
161
162 template<typename T, typename V>
163 inline bool
operator !=(variable<T> ev,V const & v)164 operator!=( variable<T> ev, V const& v )
165 {
166 return !ev.has_value() || ev.value() != v;
167 }
168
169 //____________________________________________________________________________//
170
171 template<typename T, typename V>
172 inline bool
operator !=(V const & v,variable<T> ev)173 operator!=( V const& v, variable<T> ev )
174 {
175 return !ev.has_value() || ev.value() != v;
176 }
177
178 //____________________________________________________________________________//
179
180 } // namespace environment
181
182 } // namespace BOOST_RT_PARAM_NAMESPACE
183
184 } // namespace boost
185
186 // ************************************************************************** //
187 // ************************************************************************** //
188 // Implementation
189
190 #include <boost/test/utils/runtime/env/environment.hpp>
191
192 // ************************************************************************** //
193 // ************** runtime::environment::variable ************** //
194 // ************************************************************************** //
195
196 namespace boost {
197
198 namespace BOOST_RT_PARAM_NAMESPACE {
199
200 namespace environment {
201
202 template<typename T>
variable(cstring var_name)203 variable<T>::variable( cstring var_name )
204 : variable_base( environment::var<T>( var_name ) )
205 {}
206
207 //____________________________________________________________________________//
208
209 template<typename T>
210 template<typename Modifiers>
variable(cstring var_name,Modifiers const & m)211 variable<T>::variable( cstring var_name, Modifiers const& m )
212 : variable_base( environment::var<T>( var_name, m ) )
213 {}
214
215 //____________________________________________________________________________//
216
217 } // namespace environment
218
219 } // namespace BOOST_RT_PARAM_NAMESPACE
220
221 } // namespace boost
222
223 #endif // BOOST_RT_ENV_VARIABLE_HPP_062604GER
224