update readme (#21797)
[mono-project.git] / mono / metadata / marshal-windows.c
blob8631a829393737b46cbbad19cefa7a2f726af3c0
1 /**
2 * \file
3 * Windows marshal support.
5 * Copyright 2016 Microsoft
6 * Licensed under the MIT license. See LICENSE file in the project root for full license information.
7 */
8 #include <config.h>
9 #include <glib.h>
11 #if defined(HOST_WIN32)
12 #include <mono/utils/mono-compiler.h>
13 MONO_PRAGMA_WARNING_PUSH()
14 MONO_PRAGMA_WARNING_DISABLE (4115) // warning C4115: 'IRpcStubBuffer': named type definition in parentheses
15 #include <winsock2.h>
16 #include <windows.h>
17 #include <objbase.h>
18 MONO_PRAGMA_WARNING_POP()
19 #include "mono/metadata/marshal-internals.h"
20 #include <mono/utils/w32subset.h>
21 #include "icall-decl.h"
23 #if HAVE_API_SUPPORT_WIN32_GLOBAL_ALLOC_FREE
25 void*
26 mono_marshal_alloc_hglobal (size_t size)
28 return GlobalAlloc (GMEM_FIXED, size);
31 gpointer
32 mono_marshal_realloc_hglobal (gpointer ptr, size_t size)
34 return GlobalReAlloc (ptr, size, GMEM_MOVEABLE);
37 void
38 mono_marshal_free_hglobal (gpointer ptr)
40 GlobalFree (ptr);
42 #elif !HAVE_EXTERN_DEFINED_WIN32_GLOBAL_ALLOC_FREE
43 void *
44 mono_marshal_alloc_hglobal (size_t size)
46 return HeapAlloc (GetProcessHeap (), 0, size);
49 gpointer
50 mono_marshal_realloc_hglobal (gpointer ptr, size_t size)
52 return HeapReAlloc (GetProcessHeap (), 0, ptr, size);
55 void
56 mono_marshal_free_hglobal (gpointer ptr)
58 HeapFree (GetProcessHeap (), 0, ptr);
60 #endif /* HAVE_API_SUPPORT_WIN32_GLOBAL_ALLOC_FREE */
62 void*
63 mono_marshal_alloc_co_task_mem (size_t size)
65 return CoTaskMemAlloc (size);
68 void
69 mono_marshal_free_co_task_mem (void *ptr)
71 CoTaskMemFree (ptr);
74 gpointer
75 mono_marshal_realloc_co_task_mem (gpointer ptr, size_t size)
77 return CoTaskMemRealloc (ptr, size);
80 char*
81 ves_icall_System_Runtime_InteropServices_Marshal_StringToHGlobalAnsi (const gunichar2 *s, int length);
83 char*
84 ves_icall_System_Runtime_InteropServices_Marshal_StringToHGlobalAnsi (const gunichar2 *s, int length)
86 // FIXME pass mono_utf16_to_utf8 an allocator to avoid double alloc/copy.
88 ERROR_DECL (error);
89 size_t len = 0;
90 char* ret = NULL;
91 char* tres = mono_utf16_to_utf8 (s, length, error);
92 if (!tres || !is_ok (error))
93 goto exit;
96 * mono_utf16_to_utf8() returns a memory area at least as large as length,
97 * even if it contains NULL characters. The copy we allocate here has to be equally
98 * large.
100 len = MAX (strlen (tres) + 1, length);
101 ret = (char*)mono_marshal_alloc_hglobal_error (len, error);
102 if (ret)
103 memcpy (ret, tres, len);
104 exit:
105 g_free (tres);
106 mono_error_set_pending_exception (error);
107 return ret;
110 gpointer
111 mono_string_to_utf8str_impl (MonoStringHandle s, MonoError *error)
113 char *as, *tmp;
114 glong len;
115 GError *gerror = NULL;
117 if (MONO_HANDLE_IS_NULL (s))
118 return NULL;
120 if (!mono_string_handle_length (s)) {
121 as = (char*)CoTaskMemAlloc (1);
122 g_assert (as);
123 as [0] = '\0';
124 return as;
127 // FIXME pass g_utf16_to_utf8 an allocator to avoid double alloc/copy.
129 MonoGCHandle gchandle = NULL;
130 tmp = g_utf16_to_utf8 (mono_string_handle_pin_chars (s, &gchandle), mono_string_handle_length (s), NULL, &len, &gerror);
131 mono_gchandle_free_internal (gchandle);
132 if (gerror) {
133 mono_error_set_argument (error, "string", gerror->message);
134 g_error_free (gerror);
135 return NULL;
136 } else {
137 as = (char*)CoTaskMemAlloc (len + 1);
138 g_assert (as);
139 memcpy (as, tmp, len + 1);
140 g_free (tmp);
141 return as;
145 #endif /* HOST_WIN32 */