On 20.07.2016 20:03, Simon Josefsson wrote:
> Evgeny Grin <k...@yandex.ru> writes:
> 
>> Hi!
>>
>> While debugging cURL on Windows x64 crash with simple run of "curl -v
>> http://яндекс.рф";, I discovered that crash caused by calling
>> tld_check_lz(). Further investigations reveal pointer to size_t is cast
>> to pointer to long in stringprep_utf8_to_ucs4() which in invalid on
>> Win64. As result - very high number is stored in items_written and in
>> tld_get_4() dereferenced an invalid pointer.
>> I can't make a minimal example to illustrate it as in minimal example
>> initial nullifying hides the problem. Hope that invalid casting is
>> obvious problem.
> 
> Hello.  Does this problem still exist with 1.32?  What size does
> 'size_t' and 'long' have on Windows x64?

Yes, the same bug is present in 1.32, 1.33 and in current git master.
Currently libidn keep crashing on Windows.
MinGW package includes my patches to prevent crashing:
https://github.com/Alexpux/MINGW-packages/blob/master/mingw-w64-libidn/0003-nfkc.c-Fix-Win64-crash.patch
https://github.com/Alexpux/MINGW-packages/blob/master/mingw-w64-libidn/0004-nfkc.c-Fixed-invalid-var-types.patch

Generally, you can't assume that sizeof(int) == sizeof(long) or
sizeof(long) == sizeof(long long) or sizeof(long) == sizeof(void*)
https://en.wikipedia.org/wiki/64-bit_computing#64-bit_data_models

On Windows x64 sizeof(int) == 4, sizeof(long) == 4, sizeof(long long) ==
8, sizeof(void*) == 8.

But casting pointer to one type to pointer to other type is bad idea in
general, unless you 100% sure that such casting is ALWAYS and ANYWHERE
valid.
I sent already some patches for fixing this bug.
http://lists.gnu.org/archive/html/help-libidn/2016-04/msg00002.html

Additional (unrelated) fixes attached.

--
Best Wishes,
Evgeny Grin
From 6bee19896058d61da53d464b105cc4d7d2fb4f09 Mon Sep 17 00:00:00 2001
From: Karlson2k <k...@narod.ru>
Date: Tue, 29 Mar 2016 17:21:53 +0300
Subject: [PATCH 1/7] .gitattributes: Preserve LF line endings for *.gperf. Fix
 Msys2 builds

---
 .gitattributes | 1 +
 1 file changed, 1 insertion(+)
 create mode 100644 .gitattributes

diff --git a/.gitattributes b/.gitattributes
new file mode 100644
index 0000000..257f2da
--- /dev/null
+++ b/.gitattributes
@@ -0,0 +1 @@
+*.gperf eol=lf
-- 
2.8.0.windows.1

From 4b862808859b5d7f8c3640eba9d5d2d0c242d8a1 Mon Sep 17 00:00:00 2001
From: Karlson2k <k...@narod.ru>
Date: Tue, 29 Mar 2016 17:49:14 +0300
Subject: [PATCH 2/7] doc/gdoc.mk: fix out-of-tree building

---
 doc/gdoc.mk | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/doc/gdoc.mk b/doc/gdoc.mk
index b494009..a51edc3 100644
--- a/doc/gdoc.mk
+++ b/doc/gdoc.mk
@@ -32,7 +32,7 @@ Makefile.gdoc: $(top_builddir)/configure Makefile.am gdoc.mk 
$(GDOC_SRC)
          echo "gdoc_TEXINFOS += $(GDOC_TEXI_PREFIX)$$shortfile.texi" >> 
Makefile.gdoc; \
          echo "$(GDOC_TEXI_PREFIX)$$shortfile.texi: $$file" >> Makefile.gdoc; \
          echo 'TABmkdir -p `dirname $$@`' | sed "s/TAB/        /" >> 
Makefile.gdoc; \
-         echo 'TAB$$(PERL) $(GDOC_BIN) -texinfo $$(GDOC_TEXI_EXTRA_ARGS) $$< > 
$$@' | sed "s/TAB/      /" >> Makefile.gdoc; \
+         echo 'TAB$$(PERL) $$(GDOC_BIN) -texinfo $$(GDOC_TEXI_EXTRA_ARGS) $$< 
> $$@' | sed "s/TAB/     /" >> Makefile.gdoc; \
          echo >> Makefile.gdoc; \
          functions=`$(PERL) $(srcdir)/gdoc -listfunc $$file`; \
          for function in $$functions; do \
@@ -40,12 +40,12 @@ Makefile.gdoc: $(top_builddir)/configure Makefile.am 
gdoc.mk $(GDOC_SRC)
            echo "gdoc_TEXINFOS += $(GDOC_TEXI_PREFIX)$$function.texi" >> 
Makefile.gdoc; \
            echo "$(GDOC_TEXI_PREFIX)$$function.texi: $$file" >> Makefile.gdoc; 
\
            echo 'TABmkdir -p `dirname $$@`' | sed "s/TAB/      /" >> 
Makefile.gdoc; \
-           echo 'TAB$$(PERL) $(GDOC_BIN) -texinfo $$(GDOC_TEXI_EXTRA_ARGS) 
-function'" $$function"' $$< > $$@' | sed "s/TAB/   /" >> Makefile.gdoc; \
+           echo 'TAB$$(PERL) $$(GDOC_BIN) -texinfo $$(GDOC_TEXI_EXTRA_ARGS) 
-function'" $$function"' $$< > $$@' | sed "s/TAB/  /" >> Makefile.gdoc; \
            echo >> Makefile.gdoc; \
            echo "gdoc_MANS += $(GDOC_MAN_PREFIX)$$function.3" >> 
Makefile.gdoc; \
            echo "$(GDOC_MAN_PREFIX)$$function.3: $$file" >> Makefile.gdoc; \
            echo 'TABmkdir -p `dirname $$@`' | sed "s/TAB/      /" >> 
Makefile.gdoc; \
-           echo 'TAB$$(PERL) $(GDOC_BIN) -man $$(GDOC_MAN_EXTRA_ARGS) 
-function'" $$function"' $$< > $$@' | sed "s/TAB/        /" >> Makefile.gdoc; \
+           echo 'TAB$$(PERL) $$(GDOC_BIN) -man $$(GDOC_MAN_EXTRA_ARGS) 
-function'" $$function"' $$< > $$@' | sed "s/TAB/       /" >> Makefile.gdoc; \
            echo >> Makefile.gdoc; \
          done; \
          echo >> Makefile.gdoc; \
-- 
2.8.0.windows.1

From 4a2147b9a2efd0c81b9d2dcdffd5b1b5b34681a3 Mon Sep 17 00:00:00 2001
From: Karlson2k <k...@narod.ru>
Date: Fri, 1 Apr 2016 20:36:14 +0300
Subject: [PATCH 3/7] nfkc.c: do not use UTF-8 codes longer then 4 bytes, do
 not use UCS-4 codes > 0x10FFFF (non-UTF-32)

---
 lib/nfkc.c | 28 +++-------------------------
 1 file changed, 3 insertions(+), 25 deletions(-)

diff --git a/lib/nfkc.c b/lib/nfkc.c
index edc62c4..a843a2b 100644
--- a/lib/nfkc.c
+++ b/lib/nfkc.c
@@ -171,25 +171,13 @@ GNormalizeMode;
       Len = 4;                                 \
       Mask = 0x07;                             \
     }                                          \
-  else if ((Char & 0xfc) == 0xf8)              \
-    {                                          \
-      Len = 5;                                 \
-      Mask = 0x03;                             \
-    }                                          \
-  else if ((Char & 0xfe) == 0xfc)              \
-    {                                          \
-      Len = 6;                                 \
-      Mask = 0x01;                             \
-    }                                          \
   else                                         \
     Len = -1;
 
 #define UTF8_LENGTH(Char)                      \
   ((Char) < 0x80 ? 1 :                         \
    ((Char) < 0x800 ? 2 :                       \
-    ((Char) < 0x10000 ? 3 :                    \
-     ((Char) < 0x200000 ? 4 :                  \
-      ((Char) < 0x4000000 ? 5 : 6)))))
+    ((Char) < 0x10000 ? 3 : 4)))
 
 #define UTF8_GET(Result, Chars, Count, Mask, Len)                            \
   (Result) = (Chars)[0] & (Mask);                                            \
@@ -337,21 +325,11 @@ g_unichar_to_utf8 (gunichar c, gchar * outbuf)
       first = 0xe0;
       len = 3;
     }
-  else if (c < 0x200000)
+  else
     {
       first = 0xf0;
       len = 4;
     }
-  else if (c < 0x4000000)
-    {
-      first = 0xf8;
-      len = 5;
-    }
-  else
-    {
-      first = 0xfc;
-      len = 6;
-    }
 
   if (outbuf)
     {
@@ -498,7 +476,7 @@ g_ucs4_to_utf8 (const gunichar * str,
       if (!str[i])
        break;
 
-      if (str[i] >= 0x80000000)
+      if (str[i] > 0x10FFFF)
        goto err_out;
 
       result_length += UTF8_LENGTH (str[i]);
-- 
2.8.0.windows.1

Attachment: signature.asc
Description: OpenPGP digital signature

_______________________________________________
Help-libidn mailing list
Help-libidn@gnu.org
https://lists.gnu.org/mailman/listinfo/help-libidn

Reply via email to