summaryrefslogtreecommitdiff
path: root/libraries
diff options
context:
space:
mode:
authorHallvard Furuseth <hallvard@openldap.org>2016-09-06 18:12:01 +0200
committerHallvard Furuseth <hallvard@openldap.org>2016-09-25 15:40:08 +0200
commit67fb3c746a43bf2d2ce4834ede5fba940c9286a5 (patch)
tree2313267bb2097703b0e07af1cb8a2370e6697731 /libraries
parentd87ee20e0bf7fc751f75412082df307647165d56 (diff)
downloadlmdb-67fb3c746a43bf2d2ce4834ede5fba940c9286a5.tar.gz
lmdb-67fb3c746a43bf2d2ce4834ede5fba940c9286a5.tar.bz2
lmdb-67fb3c746a43bf2d2ce4834ede5fba940c9286a5.zip
ITS#7992 Tighter utf8_to_utf16(), fix errcodes
The 0xFFFD check seems due to misleading MultiByteToWideChar() doc. Bad UTF-8 gives 0xFFFD in the output string, not the return value.
Diffstat (limited to 'libraries')
-rw-r--r--libraries/liblmdb/mdb.c42
1 files changed, 24 insertions, 18 deletions
diff --git a/libraries/liblmdb/mdb.c b/libraries/liblmdb/mdb.c
index 087cb98..b0da385 100644
--- a/libraries/liblmdb/mdb.c
+++ b/libraries/liblmdb/mdb.c
@@ -10886,25 +10886,31 @@ mdb_mutex_failed(MDB_env *env, mdb_mutexref_t mutex, int rc)
return rc;
}
#endif /* MDB_ROBUST_SUPPORTED */
-/** @} */
#if defined(_WIN32)
-static int utf8_to_utf16(const char *src, int srcsize, wchar_t **dst, int *dstsize)
-{
- int need;
- wchar_t *result;
- need = MultiByteToWideChar(CP_UTF8, 0, src, srcsize, NULL, 0);
- if (need == 0xFFFD)
- return EILSEQ;
- if (need == 0)
- return EINVAL;
- result = malloc(sizeof(wchar_t) * need);
- if (!result)
- return ENOMEM;
- MultiByteToWideChar(CP_UTF8, 0, src, srcsize, result, need);
- if (dstsize)
- *dstsize = need;
- *dst = result;
- return 0;
+static int ESECT
+utf8_to_utf16(const char *src, int srcsize, wchar_t **dst, int *dstsize)
+{
+ int rc, need = 0;
+ wchar_t *result = NULL;
+ for (;;) { /* malloc result, then fill it in */
+ need = MultiByteToWideChar(CP_UTF8, 0, src, srcsize, result, need);
+ if (!need) {
+ rc = ErrCode();
+ free(result);
+ return rc;
+ }
+ if (!result) {
+ result = malloc(sizeof(wchar_t) * need);
+ if (!result)
+ return ENOMEM;
+ continue;
+ }
+ if (dstsize)
+ *dstsize = need;
+ *dst = result;
+ return MDB_SUCCESS;
+ }
}
#endif /* defined(_WIN32) */
+/** @} */