kern/134249: [iconv] ignore case for character set names

Dmitry Marakasov amdmi3 at FreeBSD.org
Tue May 5 23:50:01 UTC 2009


>Number:         134249
>Category:       kern
>Synopsis:       [iconv] ignore case for character set names
>Confidential:   no
>Severity:       non-critical
>Priority:       low
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          change-request
>Submitter-Id:   current-users
>Arrival-Date:   Tue May 05 23:50:00 UTC 2009
>Closed-Date:
>Last-Modified:
>Originator:     Dmitry Marakasov
>Release:        FreeBSD 8.0-CURRENT i386
>Organization:
>Environment:
System: FreeBSD hades.panopticon 8.0-CURRENT FreeBSD 8.0-CURRENT #0: Thu Apr 30 06:41:20 MSD 2009 root at hades.panopticon:/async/obj/usr/src/sys/HADES i386


>Description:
Currently kernel iconv facility is sensitive to character set names, which is both ineffective and confusing: for example, each of this commands:

mount_cd9660 -C koi8-r /dev/acd0 /mnt
mount_cd9660 -C KOI8-r /dev/acd0 /mnt
mount_cd9660 -C KOI8-R /dev/acd0 /mnt
mount_cd9660 -C Koi8-r /dev/acd0 /mnt

will result in loading a separate copy of KOI8-R <-> UTF-16BE conversion tables, using 4x more memory than needed.

Also users who want to mount media with charset cnversion enabled and as non-root (i.e. with vfs.usermount=1) and thus use sysutils/kiconvtool to preload needed conversion tables on system boot will have to carefully check that encodings are specified in the same case everywhere, or the mount will fail.

The simple patch attached
- makes charset name comparisons case insensitive
- coverts charset names to uppercase when storing

>How-To-Repeat:
>Fix:

--- iconv-case-insensitive.patch begins here ---
Index: sys/libkern/iconv.c
===================================================================
--- sys/libkern/iconv.c	(revision 191469)
+++ sys/libkern/iconv.c	(working copy)
@@ -33,6 +33,7 @@
 #include <sys/cdefs.h>
 __FBSDID("$FreeBSD$");
 
+#include <sys/ctype.h>
 #include <sys/param.h>
 #include <sys/systm.h>
 #include <sys/kernel.h>
@@ -171,8 +172,8 @@
 	struct iconv_cspair *csp;
 
 	TAILQ_FOREACH(csp, &iconv_cslist, cp_link) {
-		if (strcmp(csp->cp_to, to) == 0 &&
-		    strcmp(csp->cp_from, from) == 0) {
+		if (strcasecmp(csp->cp_to, to) == 0 &&
+		    strcasecmp(csp->cp_from, from) == 0) {
 			if (cspp)
 				*cspp = csp;
 			return 0;
@@ -207,12 +208,16 @@
 	if (!ucsto) {
 		strcpy(cp, to);
 		csp->cp_to = cp;
-		cp += strlen(cp) + 1;
+		for (; *cp; cp++)
+			*cp = toupper(*cp);
+		cp++;
 	} else
 		csp->cp_to = iconv_unicode_string;
 	if (!ucsfrom) {
 		strcpy(cp, from);
 		csp->cp_from = cp;
+		for (; *cp; cp++)
+			*cp = toupper(*cp);
 	} else
 		csp->cp_from = iconv_unicode_string;
 	csp->cp_data = data;
--- iconv-case-insensitive.patch ends here ---

>Release-Note:
>Audit-Trail:
>Unformatted:


More information about the freebsd-bugs mailing list