]> git.ipfire.org Git - thirdparty/gettext.git/commitdiff
Fix a bug in the last commit.
authorBruno Haible <bruno@clisp.org>
Thu, 15 Jun 2023 21:33:50 +0000 (23:33 +0200)
committerBruno Haible <bruno@clisp.org>
Thu, 15 Jun 2023 22:08:02 +0000 (00:08 +0200)
* gettext-tools/src/write-mo.c (write_table): Include the number of system
dependent string pairs in the computation of the hash table's size.
* gettext-tools/tests/msgfmt-20: New file.
* gettext-tools/tests/Makefile.am (TESTS): Add it.

gettext-tools/src/write-mo.c
gettext-tools/tests/Makefile.am
gettext-tools/tests/msgfmt-20 [new file with mode: 0755]

index 1809549a8c435ac069deddc2af3e7898fb37a5b4..06c7cff0a82836961206a88815919e476c00482c 100644 (file)
@@ -765,7 +765,10 @@ write_table (FILE *output_file, message_list_ty *mlp)
                 Sorting and Searching, 1973, Addison Wesley]  */
   if (!omit_hash_table)
     {
-      hash_tab_size = next_prime ((nstrings * 4) / 3);
+      /* N is the number of static string pairs (filled in here, below)
+         plus the number of system dependent string pairs (filled at runtime,
+         in loadmsgcat.c).  */
+      hash_tab_size = next_prime (((nstrings + n_sysdep_strings) * 4) / 3);
       /* Ensure M > 2.  */
       if (hash_tab_size <= 2)
         hash_tab_size = 3;
index 04a61264a14581701f9e5d5db6ae5dc45d3306ed..f39459e79859c6c53cb94954c80faf7e18078b05 100644 (file)
@@ -51,7 +51,7 @@ TESTS = gettext-1 gettext-2 \
        msgfilter-sr-latin-1 msgfilter-quote-1 \
        msgfmt-1 msgfmt-2 msgfmt-3 msgfmt-4 msgfmt-5 msgfmt-6 msgfmt-7 \
        msgfmt-8 msgfmt-9 msgfmt-10 msgfmt-11 msgfmt-12 msgfmt-13 msgfmt-14 \
-       msgfmt-15 msgfmt-16 msgfmt-17 msgfmt-18 msgfmt-19 \
+       msgfmt-15 msgfmt-16 msgfmt-17 msgfmt-18 msgfmt-19 msgfmt-20 \
        msgfmt-properties-1 \
        msgfmt-qt-1 msgfmt-qt-2 \
        msgfmt-desktop-1 msgfmt-desktop-2 msgfmt-desktop-3 \
diff --git a/gettext-tools/tests/msgfmt-20 b/gettext-tools/tests/msgfmt-20
new file mode 100755 (executable)
index 0000000..4751ce9
--- /dev/null
@@ -0,0 +1,100 @@
+#! /bin/sh
+. "${srcdir=.}/init.sh"; path_prepend_ . ../src
+
+# Test .mo file with many system dependent string pairs.
+# Cf. <inttypes.h> format string directives support as in msgfmt-12, format-c-3,
+# and the 'I' format directive flag as in format-c-5.
+
+# This test used to trigger an endless loop in loadmsgcat.c, because
+# hash_tab_size was too small and the "open addressing" collision resolution
+# leads to an endless loop when the hash table is full.
+
+cat <<\EOF > mf-20.po
+msgid ""
+msgstr "Content-Type: text/plain; charset=UTF-8\n"
+
+msgid "The trees are green."
+msgstr "Les arbres sont verts."
+
+#, c-format
+msgid "A meter has %d millimeters."
+msgstr "Un mètre a %Id millimètres."
+
+#, c-format
+msgid "A pig has %d legs."
+msgstr "Un cochon a %Id pattes."
+
+#, c-format
+msgid "The French revolution took place in %d."
+msgstr "La révolution française eut lieu en %Id."
+
+#, c-format
+msgid "Abraham died at the age of %d."
+msgstr "Abraham mourut à l’âge de %Id ans."
+
+#, c-format
+msgid "Everyone has %d fingers at each hand."
+msgstr "Chacun a %Id doigts à chaque main."
+
+msgid "Sunshine heats."
+msgstr "Le soleil tape."
+
+#, c-format
+msgid "Most cars have %d wheels."
+msgstr "La plupart des voitures a %Id roues."
+
+#, c-format
+msgid "The oldest person is %d years old."
+msgstr "La personne la plus vieille a %Id ans."
+
+#, c-format
+msgid "Cesar tool %d years to conquer Gaul."
+msgstr "César mit %Id ans à conquérir la Gaule."
+
+#, c-format
+msgid "There are %d pyramids in Egypt."
+msgstr "Il y a %Id pyramides en Égypte."
+
+#, c-format
+msgid "The number %d causes bad luck."
+msgstr "Le nombre %Id porte malheur."
+EOF
+
+test -d fr || mkdir fr
+test -d fr/LC_MESSAGES || mkdir fr/LC_MESSAGES
+
+: ${MSGFMT=msgfmt}
+${MSGFMT} -o fr/LC_MESSAGES/mf-20.mo mf-20.po || Exit 1
+
+cat <<EOF > mf-20.ok
+Le soleil tape.
+EOF
+
+: ${LOCALE_FR=fr_FR}
+: ${LOCALE_FR_UTF8=fr_FR.UTF-8}
+: ${GETTEXT=gettext}
+: ${DIFF=diff}
+if test $LOCALE_FR != none; then
+  prepare_locale_ fr $LOCALE_FR
+  LC_ALL=$LOCALE_FR LANGUAGE= TEXTDOMAINDIR=. TEXTDOMAIN=mf-20 \
+  ${GETTEXT} -s 'Sunshine heats.' > mf-20.tmp
+  LC_ALL=C tr -d '\r' < mf-20.tmp > mf-20.out
+  ${DIFF} mf-20.ok mf-20.out || Exit 1
+fi
+if test $LOCALE_FR_UTF8 != none; then
+  prepare_locale_ fr $LOCALE_FR_UTF8
+  LC_ALL=$LOCALE_FR_UTF8 LANGUAGE= TEXTDOMAINDIR=. TEXTDOMAIN=mf-20 \
+  ${GETTEXT} -s 'Sunshine heats.' > mf-20.tmp
+  LC_ALL=C tr -d '\r' < mf-20.tmp > mf-20.out
+  ${DIFF} mf-20.ok mf-20.out || Exit 1
+fi
+if test $LOCALE_FR = none && test $LOCALE_FR_UTF8 = none; then
+  if test -f /usr/bin/localedef; then
+    echo "Skipping test: no french locale is installed"
+  else
+    echo "Skipping test: no french locale is supported"
+  fi
+  Exit 77
+fi
+
+Exit 0