Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support building cpprestsdk with /MT on Windows #884

Closed
wants to merge 8 commits into from
105 changes: 45 additions & 60 deletions Release/include/cpprest/asyncrt_utils.h
Original file line number Diff line number Diff line change
Expand Up @@ -68,45 +68,45 @@ namespace conversions
/// </summary>
/// <param name="w">A two byte character UTF-16 string.</param>
/// <returns>A single byte character UTF-8 string.</returns>
_ASYNCRTIMP std::string __cdecl utf16_to_utf8(const utf16string &w);
_ASYNCRTIMP utility::string __cdecl utf16_to_utf8(const utf16string &w);

/// <summary>
/// Converts a UTF-8 string to a UTF-16
/// </summary>
/// <param name="s">A single byte character UTF-8 string.</param>
/// <returns>A two byte character UTF-16 string.</returns>
_ASYNCRTIMP utf16string __cdecl utf8_to_utf16(const std::string &s);
_ASYNCRTIMP utf16string __cdecl utf8_to_utf16(const utility::string &s);

/// <summary>
/// Converts a ASCII (us-ascii) string to a UTF-16 string.
/// </summary>
/// <param name="s">A single byte character us-ascii string.</param>
/// <returns>A two byte character UTF-16 string.</returns>
_ASYNCRTIMP utf16string __cdecl usascii_to_utf16(const std::string &s);
_ASYNCRTIMP utf16string __cdecl usascii_to_utf16(const utility::string &s);

/// <summary>
/// Converts a Latin1 (iso-8859-1) string to a UTF-16 string.
/// </summary>
/// <param name="s">A single byte character UTF-8 string.</param>
/// <returns>A two byte character UTF-16 string.</returns>
_ASYNCRTIMP utf16string __cdecl latin1_to_utf16(const std::string &s);
_ASYNCRTIMP utf16string __cdecl latin1_to_utf16(const utility::string &s);

/// <summary>
/// Converts a Latin1 (iso-8859-1) string to a UTF-8 string.
/// </summary>
/// <param name="s">A single byte character UTF-8 string.</param>
/// <returns>A single byte character UTF-8 string.</returns>
_ASYNCRTIMP utf8string __cdecl latin1_to_utf8(const std::string &s);
_ASYNCRTIMP utf8string __cdecl latin1_to_utf8(const utility::string &s);

/// <summary>
/// Converts to a platform dependent Unicode string type.
/// </summary>
/// <param name="s">A single byte character UTF-8 string.</param>
/// <returns>A platform dependent string type.</returns>
#ifdef _UTF16_STRINGS
_ASYNCRTIMP utility::string_t __cdecl to_string_t(std::string &&s);
_ASYNCRTIMP utility::string_t __cdecl to_string_t(utility::string &&s);
#else
inline utility::string_t&& to_string_t(std::string &&s) { return std::move(s); }
inline utility::string_t&& to_string_t(utility::string &&s) { return std::move(s); }
#endif

/// <summary>
Expand All @@ -125,9 +125,9 @@ namespace conversions
/// <param name="s">A single byte character UTF-8 string.</param>
/// <returns>A platform dependent string type.</returns>
#ifdef _UTF16_STRINGS
_ASYNCRTIMP utility::string_t __cdecl to_string_t(const std::string &s);
_ASYNCRTIMP utility::string_t __cdecl to_string_t(const utility::string &s);
#else
inline const utility::string_t& to_string_t(const std::string &s) { return s; }
inline const utility::string_t& to_string_t(const utility::string &s) { return s; }
#endif

/// <summary>
Expand All @@ -146,7 +146,7 @@ namespace conversions
/// </summary>
/// <param name="value">A single byte character UTF-8 string.</param>
/// <returns>A two byte character UTF-16 string.</returns>
_ASYNCRTIMP utf16string __cdecl to_utf16string(const std::string &value);
_ASYNCRTIMP utf16string __cdecl to_utf16string(const utility::string &value);

/// <summary>
/// Converts to a UTF-16 from string.
Expand All @@ -172,26 +172,26 @@ namespace conversions
/// </summary>
/// <param name="value">A single byte character UTF-8 string.</param>
/// <returns>A single byte character UTF-8 string.</returns>
inline std::string&& to_utf8string(std::string&& value) { return std::move(value); }
inline utility::string&& to_utf8string(utility::string&& value) { return std::move(value); }

/// <summary>
/// Converts to a UTF-8 string.
/// </summary>
/// <param name="value">A single byte character UTF-8 string.</param>
/// <returns>A single byte character UTF-8 string.</returns>
inline const std::string& to_utf8string(const std::string& value) { return value; }
inline const utility::string& to_utf8string(const utility::string& value) { return value; }

/// <summary>
/// Converts to a UTF-8 string.
/// </summary>
/// <param name="value">A two byte character UTF-16 string.</param>
/// <returns>A single byte character UTF-8 string.</returns>
_ASYNCRTIMP std::string __cdecl to_utf8string(const utf16string &value);
_ASYNCRTIMP utility::string __cdecl to_utf8string(const utf16string &value);

/// <summary>
/// Encode the given byte array into a base64 string
/// </summary>
_ASYNCRTIMP utility::string_t __cdecl to_base64(const std::vector<unsigned char>& data);
_ASYNCRTIMP utility::string_t __cdecl to_base64(const utility::vector<unsigned char>& data);

/// <summary>
/// Encode the given 8-byte integer into a base64 string
Expand All @@ -201,7 +201,7 @@ namespace conversions
/// <summary>
/// Decode the given base64 string to a byte array
/// </summary>
_ASYNCRTIMP std::vector<unsigned char> __cdecl from_base64(const utility::string_t& str);
_ASYNCRTIMP utility::vector<unsigned char> __cdecl from_base64(const utility::string_t& str);

template <typename Source>
CASABLANCA_DEPRECATED("All locale-sensitive APIs will be removed in a future update. Use stringstreams directly if locale support is required.")
Expand All @@ -226,28 +226,42 @@ namespace conversions
namespace details
{

#if defined(__ANDROID__)
template<class T>
inline std::string to_string(const T t)
inline utility::string to_string(const T t)
{
std::ostringstream os;
#if defined(__ANDROID__)
utility::ostringstream os;
os.imbue(std::locale::classic());
os << t;
return os.str();
#else
using std::to_string;
return to_string(t).c_str();
#endif
}

#if defined(_WIN32) || defined(_UTF16_STRINGS)
template<class T>
inline utility::wstring to_wstring(const T t) {
using std::to_wstring;
return to_wstring(t).c_str();
}
#endif

template<class T>
inline utility::string_t to_string_t(const T t)
{
#ifdef _UTF16_STRINGS
#if defined(_WIN32) || defined(_UTF16_STRINGS)
using std::to_wstring;
return to_wstring(t);
return to_wstring(t).c_str();
#elif defined(__ANDROID__)
utility::ostringstream os;
os.imbue(std::locale::classic());
os << t;
return os.str();
#else
#if !defined(__ANDROID__)
using std::to_string;
#endif
return to_string(t);
return to_string(t).c_str();
#endif
}

Expand Down Expand Up @@ -343,7 +357,7 @@ namespace details
#endif
private:
#ifdef _WIN32
std::string m_prevLocale;
utility::string m_prevLocale;
int m_prevThreadSetting;
#elif !(defined(ANDROID) || defined(__ANDROID__))
locale_t m_prevLocale;
Expand Down Expand Up @@ -397,78 +411,49 @@ namespace details
return (uch <= static_cast<UElem>('z') && is_alnum(static_cast<unsigned char>(uch)));
}

/// <summary>
/// Simplistic implementation of make_unique. A better implementation would be based on variadic templates
/// and therefore not be compatible with Dev10.
/// </summary>
template <typename _Type>
std::unique_ptr<_Type> make_unique() {
return std::unique_ptr<_Type>(new _Type());
}

template <typename _Type, typename _Arg1>
std::unique_ptr<_Type> make_unique(_Arg1&& arg1) {
return std::unique_ptr<_Type>(new _Type(std::forward<_Arg1>(arg1)));
}

template <typename _Type, typename _Arg1, typename _Arg2>
std::unique_ptr<_Type> make_unique(_Arg1&& arg1, _Arg2&& arg2) {
return std::unique_ptr<_Type>(new _Type(std::forward<_Arg1>(arg1), std::forward<_Arg2>(arg2)));
}

template <typename _Type, typename _Arg1, typename _Arg2, typename _Arg3>
std::unique_ptr<_Type> make_unique(_Arg1&& arg1, _Arg2&& arg2, _Arg3&& arg3) {
return std::unique_ptr<_Type>(new _Type(std::forward<_Arg1>(arg1), std::forward<_Arg2>(arg2), std::forward<_Arg3>(arg3)));
}

template <typename _Type, typename _Arg1, typename _Arg2, typename _Arg3, typename _Arg4>
std::unique_ptr<_Type> make_unique(_Arg1&& arg1, _Arg2&& arg2, _Arg3&& arg3, _Arg4&& arg4) {
return std::unique_ptr<_Type>(new _Type(std::forward<_Arg1>(arg1), std::forward<_Arg2>(arg2), std::forward<_Arg3>(arg3), std::forward<_Arg4>(arg4)));
}

/// <summary>
/// Cross platform utility function for performing case insensitive string equality comparision.
/// </summary>
/// <param name="left">First string to compare.</param>
/// <param name="right">Second strong to compare.</param>
/// <returns>true if the strings are equivalent, false otherwise</returns>
_ASYNCRTIMP bool __cdecl str_iequal(const std::string &left, const std::string &right) CPPREST_NOEXCEPT;
_ASYNCRTIMP bool __cdecl str_iequal(const utility::string &left, const utility::string &right) CPPREST_NOEXCEPT;

/// <summary>
/// Cross platform utility function for performing case insensitive string equality comparision.
/// </summary>
/// <param name="left">First string to compare.</param>
/// <param name="right">Second strong to compare.</param>
/// <returns>true if the strings are equivalent, false otherwise</returns>
_ASYNCRTIMP bool __cdecl str_iequal(const std::wstring &left, const std::wstring &right) CPPREST_NOEXCEPT;
_ASYNCRTIMP bool __cdecl str_iequal(const utility::wstring &left, const utility::wstring &right) CPPREST_NOEXCEPT;

/// <summary>
/// Cross platform utility function for performing case insensitive string less-than comparision.
/// </summary>
/// <param name="left">First string to compare.</param>
/// <param name="right">Second strong to compare.</param>
/// <returns>true if a lowercase view of left is lexicographically less than a lowercase view of right; otherwise, false.</returns>
_ASYNCRTIMP bool __cdecl str_iless(const std::string &left, const std::string &right) CPPREST_NOEXCEPT;
_ASYNCRTIMP bool __cdecl str_iless(const utility::string &left, const utility::string &right) CPPREST_NOEXCEPT;

/// <summary>
/// Cross platform utility function for performing case insensitive string less-than comparision.
/// </summary>
/// <param name="left">First string to compare.</param>
/// <param name="right">Second strong to compare.</param>
/// <returns>true if a lowercase view of left is lexicographically less than a lowercase view of right; otherwise, false.</returns>
_ASYNCRTIMP bool __cdecl str_iless(const std::wstring &left, const std::wstring &right) CPPREST_NOEXCEPT;
_ASYNCRTIMP bool __cdecl str_iless(const utility::wstring &left, const utility::wstring &right) CPPREST_NOEXCEPT;

/// <summary>
/// Convert a string to lowercase in place.
/// </summary>
/// <param name="target">The string to convert to lowercase.</param>
_ASYNCRTIMP void __cdecl inplace_tolower(std::string &target) CPPREST_NOEXCEPT;
_ASYNCRTIMP void __cdecl inplace_tolower(utility::string &target) CPPREST_NOEXCEPT;

/// <summary>
/// Convert a string to lowercase in place.
/// </summary>
/// <param name="target">The string to convert to lowercase.</param>
_ASYNCRTIMP void __cdecl inplace_tolower(std::wstring &target) CPPREST_NOEXCEPT;
_ASYNCRTIMP void __cdecl inplace_tolower(utility::wstring &target) CPPREST_NOEXCEPT;

#ifdef _WIN32

Expand Down Expand Up @@ -528,7 +513,7 @@ inline std::error_code __cdecl create_error_code(unsigned long errorCode)
/// </summary>
inline utility::string_t __cdecl create_error_message(unsigned long errorCode)
{
return utility::conversions::to_string_t(create_error_code(errorCode).message());
return utility::conversions::to_string_t(create_error_code(errorCode).message().c_str());
}

}
Expand Down
12 changes: 6 additions & 6 deletions Release/include/cpprest/base_uri.h
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ namespace web {
{
public:

uri_exception(std::string msg) : m_msg(std::move(msg)) {}
uri_exception(utility::string msg) : m_msg(std::move(msg)) {}

~uri_exception() CPPREST_NOEXCEPT {}

Expand All @@ -88,7 +88,7 @@ namespace web {
}

private:
std::string m_msg;
utility::string m_msg;
};

/// <summary>
Expand Down Expand Up @@ -167,15 +167,15 @@ namespace web {
/// Splits a path into its hierarchical components.
/// </summary>
/// <param name="path">The path as a string</param>
/// <returns>A <c>std::vector&lt;utility::string_t&gt;</c> containing the segments in the path.</returns>
_ASYNCRTIMP static std::vector<utility::string_t> __cdecl split_path(const utility::string_t &path);
/// <returns>A <c>utility::vector&lt;utility::string_t&gt;</c> containing the segments in the path.</returns>
_ASYNCRTIMP static utility::vector<utility::string_t> __cdecl split_path(const utility::string_t &path);

/// <summary>
/// Splits a query into its key-value components.
/// </summary>
/// <param name="query">The query string</param>
/// <returns>A <c>std::map&lt;utility::string_t, utility::string_t&gt;</c> containing the key-value components of the query.</returns>
_ASYNCRTIMP static std::map<utility::string_t, utility::string_t> __cdecl split_query(const utility::string_t &query);
/// <returns>A <c>utility::map&lt;utility::string_t, utility::string_t&gt;</c> containing the key-value components of the query.</returns>
_ASYNCRTIMP static utility::map<utility::string_t, utility::string_t> __cdecl split_query(const utility::string_t &query);

/// <summary>
/// Validates a string as a URI.
Expand Down
46 changes: 22 additions & 24 deletions Release/include/cpprest/containerstream.h
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,25 @@ namespace Concurrency { namespace streams {
return m_data;
}

/// <summary>
/// Constructor
/// </summary>
basic_container_buffer(std::ios_base::openmode mode)
: streambuf_state_manager<typename _CollectionType::value_type>(mode),
m_current_position(0) {
validate_mode(mode);
}

/// <summary>
/// Constructor
/// </summary>
basic_container_buffer(_CollectionType data, std::ios_base::openmode mode)
: streambuf_state_manager<typename _CollectionType::value_type>(mode),
m_data(std::move(data)),
m_current_position((mode & std::ios_base::in) ? 0 : m_data.size()) {
validate_mode(mode);
}

/// <summary>
/// Destructor
/// </summary>
Expand Down Expand Up @@ -363,27 +382,6 @@ namespace Concurrency { namespace streams {
private:
template<typename _CollectionType1> friend class streams::container_buffer;

/// <summary>
/// Constructor
/// </summary>
basic_container_buffer(std::ios_base::openmode mode)
: streambuf_state_manager<typename _CollectionType::value_type>(mode),
m_current_position(0)
{
validate_mode(mode);
}

/// <summary>
/// Constructor
/// </summary>
basic_container_buffer(_CollectionType data, std::ios_base::openmode mode)
: streambuf_state_manager<typename _CollectionType::value_type>(mode),
m_data(std::move(data)),
m_current_position((mode & std::ios_base::in) ? 0 : m_data.size())
{
validate_mode(mode);
}

static void validate_mode(std::ios_base::openmode mode)
{
// Disallow simultaneous use of the stream buffer for writing and reading.
Expand Down Expand Up @@ -520,7 +518,7 @@ namespace Concurrency { namespace streams {
/// <param name="mode">The I/O mode that the buffer should use (in / out)</param>
container_buffer(_CollectionType data, std::ios_base::openmode mode = std::ios_base::in)
: streambuf<typename _CollectionType::value_type>(
std::shared_ptr<details::basic_container_buffer<_CollectionType>>(new streams::details::basic_container_buffer<_CollectionType>(std::move(data), mode)))
utility::make_shared<streams::details::basic_container_buffer<_CollectionType>>(std::move(data), mode))
{
}

Expand All @@ -530,7 +528,7 @@ namespace Concurrency { namespace streams {
/// <param name="mode">The I/O mode that the buffer should use (in / out)</param>
container_buffer(std::ios_base::openmode mode = std::ios_base::out)
: streambuf<typename _CollectionType::value_type>(
std::shared_ptr<details::basic_container_buffer<_CollectionType>>(new details::basic_container_buffer<_CollectionType>(mode)))
utility::make_shared<details::basic_container_buffer<_CollectionType>>(mode))
{
}

Expand Down Expand Up @@ -579,7 +577,7 @@ namespace Concurrency { namespace streams {
/// The stringstream allows an input stream to be constructed from std::string or std::wstring
/// For output streams the underlying string container could be retrieved using <c>buf-&gt;collection().</c>
/// </summary>
typedef container_stream<std::basic_string<char>> stringstream;
typedef container_stream<utility::basic_string<char>> stringstream;
typedef stringstream::buffer_type stringstreambuf;

typedef container_stream<utility::string_t> wstringstream;
Expand Down
Loading