This is the mail archive of the java-patches@sourceware.cygnus.com mailing list for the Java project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Patch: iconv()-based encoding and decoding


I'm committing the appended patch.  It changes libgcj to use iconv()
as a fallback when looking for character set encoders.  This code
hasn't yet been tested, because for some reason (that I have yet to
investigate) my system doesn't have iconv() in libc.

2000-01-30  Tom Tromey  <tromey@cygnus.com>

	* include/config.h.in: Rebuilt.
	* acconfig.h (HAVE_ICONV): Define.
	* configure: Rebuilt.
	* configure.in: Check for `iconv' function.
	* gnu/gcj/convert/BytesToUnicode.java (getDecoder): Try iconv if
	no specific encoder exists.
	* gnu/gcj/convert/UnicodeToBytes.java (getEncoder): Try iconv if
	no specific encoder exists.
	* Makefile.in: Rebuilt.
	* Makefile.am (convert_source_files): Mention Input_iconv.java and
	Output_iconv.java.
	(nat_source_files): Added natIconv.cc.
	* gnu/gcj/convert/natIconv.cc: New file.
	* gnu/gcj/convert/Input_iconv.java: New file.
	* gnu/gcj/convert/Output_iconv.java: New file.

Tom

Index: acconfig.h
===================================================================
RCS file: /cvs/java/libgcj/libjava/acconfig.h,v
retrieving revision 1.17
diff -u -r1.17 acconfig.h
--- acconfig.h	2000/01/22 21:15:57	1.17
+++ acconfig.h	2000/01/31 04:41:55
@@ -134,3 +134,6 @@
 
 /* Define if g++ has a bug preventing us from inlining math routines.  */
 #undef __NO_MATH_INLINES
+
+/* Define if you have working iconv() function.  */
+#undef HAVE_ICONV
Index: configure.in
===================================================================
RCS file: /cvs/java/libgcj/libjava/configure.in,v
retrieving revision 1.51
diff -u -r1.51 configure.in
--- configure.in	2000/01/22 21:15:57	1.51
+++ configure.in	2000/01/31 04:42:01
@@ -372,7 +372,7 @@
 else
    AC_CHECK_FUNCS(strerror ioctl select fstat open fsync sleep)
    AC_CHECK_FUNCS(gmtime_r localtime_r readdir_r getpwuid_r getcwd)
-   AC_CHECK_FUNCS(access stat mkdir rename rmdir unlink realpath)
+   AC_CHECK_FUNCS(access stat mkdir rename rmdir unlink realpath iconv)
    AC_CHECK_FUNCS(inet_aton inet_addr, break)
    AC_CHECK_FUNCS(inet_pton uname inet_ntoa)
    AC_CHECK_FUNCS(backtrace fork execvp pipe)
Index: Makefile.am
===================================================================
RCS file: /cvs/java/libgcj/libjava/Makefile.am,v
retrieving revision 1.44
diff -u -r1.44 Makefile.am
--- Makefile.am	2000/01/28 20:00:21	1.44
+++ Makefile.am	2000/01/31 04:42:10
@@ -447,11 +447,13 @@
 gnu/gcj/convert/Input_JavaSrc.java \
 gnu/gcj/convert/Input_SJIS.java \
 gnu/gcj/convert/Input_UTF8.java	\
+gnu/gcj/convert/Input_iconv.java \
 gnu/gcj/convert/Output_8859_1.java \
 gnu/gcj/convert/Output_EUCJIS.java \
 gnu/gcj/convert/Output_JavaSrc.java \
 gnu/gcj/convert/Output_SJIS.java \
 gnu/gcj/convert/Output_UTF8.java \
+gnu/gcj/convert/Output_iconv.java \
 gnu/gcj/convert/UnicodeToBytes.java
 
 ## List of all .java files for which the .h file is maintained by
@@ -787,6 +789,7 @@
 gnu/gcj/convert/JIS0208_to_Unicode.cc \
 gnu/gcj/convert/JIS0212_to_Unicode.cc \
 gnu/gcj/convert/Unicode_to_JIS.cc \
+gnu/gcj/convert/natIconv.cc \
 gnu/gcj/convert/natInput_EUCJIS.cc \
 gnu/gcj/convert/natInput_SJIS.cc \
 gnu/gcj/convert/natOutput_EUCJIS.cc \
Index: gnu/gcj/convert/BytesToUnicode.java
===================================================================
RCS file: /cvs/java/libgcj/libjava/gnu/gcj/convert/BytesToUnicode.java,v
retrieving revision 1.4
diff -u -r1.4 BytesToUnicode.java
--- BytesToUnicode.java	2000/01/19 18:39:24	1.4
+++ BytesToUnicode.java	2000/01/31 04:42:10
@@ -1,4 +1,4 @@
-/* Copyright (C) 1999  Red Hat, Inc.
+/* Copyright (C) 1999, 2000  Red Hat, Inc.
 
    This file is part of libgcj.
 
@@ -69,8 +69,15 @@
       } 
     catch (Throwable ex) 
       { 
-	throw new java.io.UnsupportedEncodingException(encoding
-						       + " (" + ex + ')');
+	try
+	  {
+	    return new Input_iconv (encoding);
+	  }
+	catch (Throwable _)
+	  {
+	    throw new java.io.UnsupportedEncodingException(encoding
+							   + " (" + ex + ')');
+	  }
       }
   }
 
Index: gnu/gcj/convert/Input_iconv.java
===================================================================
RCS file: Input_iconv.java
diff -N Input_iconv.java
--- /dev/null	Tue May  5 13:32:27 1998
+++ Input_iconv.java	Sun Jan 30 20:42:15 2000
@@ -0,0 +1,42 @@
+// Input_iconv.java -- Java side of iconv() reader.
+
+/* Copyright (C) 2000  Red Hat, Inc.
+
+   This file is part of libgcj.
+
+This software is copyrighted work licensed under the terms of the
+Libgcj License.  Please consult the file "LIBGCJ_LICENSE" for
+details.  */
+
+package gnu.gcj.convert;
+import gnu.gcj.RawData;
+import java.io.UnsupportedEncodingException;
+
+/**
+ * Convert bytes in some iconv-supported encoding to Unicode.
+ * @author Tom Tromey <tromey@redhat.com>
+ * @date January 30, 2000
+ */
+
+public class Input_iconv extends BytesToUnicode
+{
+  public Input_iconv (String encoding) throws UnsupportedEncodingException
+  {
+    this.encoding = encoding;
+    this.handle = null;
+    init (encoding);
+  }
+
+  public String getName() { return encoding; }
+
+  public native void finalize ();
+  private native void init (String encoding)
+    throws UnsupportedEncodingException;
+  public native int read (char[] outbuffer, int outpos, int count);
+
+  // The encoding we're using.
+  private String encoding;
+
+  // The iconv handle.
+  private RawData handle;
+}
Index: gnu/gcj/convert/Output_iconv.java
===================================================================
RCS file: Output_iconv.java
diff -N Output_iconv.java
--- /dev/null	Tue May  5 13:32:27 1998
+++ Output_iconv.java	Sun Jan 30 20:43:30 2000
@@ -0,0 +1,42 @@
+// Output_iconv.java -- Java side of iconv() writer.
+
+/* Copyright (C) 2000  Red Hat, Inc.
+
+   This file is part of libgcj.
+
+This software is copyrighted work licensed under the terms of the
+Libgcj License.  Please consult the file "LIBGCJ_LICENSE" for
+details.  */
+
+package gnu.gcj.convert;
+import gnu.gcj.RawData;
+import java.io.UnsupportedEncodingException;
+
+/**
+ * Convert Unicode to bytes in some iconv-supported encoding.
+ * @author Tom Tromey <tromey@redhat.com>
+ * @date January 30, 2000
+ */
+
+public class Output_iconv extends UnicodeToBytes
+{
+  public Output_iconv (String encoding) throws UnsupportedEncodingException
+  {
+    this.encoding = encoding;
+    this.handle = null;
+    init (encoding);
+  }
+
+  public String getName() { return encoding; }
+
+  public native void finalize ();
+  private native void init (String encoding)
+    throws UnsupportedEncodingException;
+  public native int write (char[] inbuffer, int inpos, int count);
+
+  // The encoding we're using.
+  private String encoding;
+
+  // The iconv handle.
+  private RawData handle;
+}
Index: gnu/gcj/convert/UnicodeToBytes.java
===================================================================
RCS file: /cvs/java/libgcj/libjava/gnu/gcj/convert/UnicodeToBytes.java,v
retrieving revision 1.3
diff -u -r1.3 UnicodeToBytes.java
--- UnicodeToBytes.java	2000/01/19 18:39:24	1.3
+++ UnicodeToBytes.java	2000/01/31 04:43:30
@@ -1,4 +1,4 @@
-/* Copyright (C) 1999  Red Hat, Inc.
+/* Copyright (C) 1999, 2000  Red Hat, Inc.
 
    This file is part of libgcj.
 
@@ -67,8 +67,16 @@
       } 
     catch (Throwable ex) 
       { 
-	throw new java.io.UnsupportedEncodingException(encoding + " ("
-						       + ex + ')');
+	try
+	  {
+	    return new Output_iconv (encoding);
+	  }
+	catch (Throwable _)
+	  {
+	    // Put the original exception in the throwable.
+	    throw new java.io.UnsupportedEncodingException(encoding + " ("
+							   + ex + ')');
+	  }
       }
   }
 
@@ -105,5 +113,4 @@
     str.getChars(inpos, srcEnd, work, 0);
     return write(work, inpos, inlength);
   }
-
 }
Index: gnu/gcj/convert/natIconv.cc
===================================================================
RCS file: natIconv.cc
diff -N natIconv.cc
--- /dev/null	Tue May  5 13:32:27 1998
+++ natIconv.cc	Sun Jan 30 20:46:08 2000
@@ -0,0 +1,142 @@
+// Input_iconv.java -- Java side of iconv() reader.
+
+/* Copyright (C) 2000  Red Hat, Inc.
+
+   This file is part of libgcj.
+
+This software is copyrighted work licensed under the terms of the
+Libgcj License.  Please consult the file "LIBGCJ_LICENSE" for
+details.  */
+
+/* Author: Tom Tromey <tromey@redhat.com>.  */
+
+#include <config.h>
+
+#include <gcj/cni.h>
+#include <jvm.h>
+
+#include <gnu/gcj/convert/Input_iconv.h>
+#include <gnu/gcj/convert/Output_iconv.h>
+#include <java/io/UnsupportedEncodingException.h>
+
+#ifdef HAVE_ICONV
+#include <iconv.h>
+#endif
+
+void
+gnu::gcj::convert::Input_iconv::init (jstring encoding)
+{
+#ifdef HAVE_ICONV
+  jsize len = _Jv_GetStringUTFLength (encoding);
+  char buffer[len];
+  _Jv_GetStringUTFRegion (encoding, 0, len, buffer);
+
+  iconv_t h = iconv_open ("UCS-2", buffer);
+  if (h == (iconv_t) -1)
+    JvThrow (new java::io::UnsupportedEncodingException);
+
+  JvAssert (h != NULL);
+  handle = reinterpret_cast<gnu::gcj::RawData *> (h);
+#else /* HAVE_ICONV */
+  // If no iconv, just throw an exception.
+  JvThrow (new java::io::UnsupportedEncodingException);
+#endif /* HAVE_ICONV */
+}
+
+void
+gnu::gcj::convert::Input_iconv::finalize (void)
+{
+#ifdef HAVE_ICONV
+  if (handle == NULL)
+    {
+      iconv_close ((iconv_t) handle);
+      handle = NULL;
+    }
+#endif /* HAVE_ICONV */
+}
+
+jint
+gnu::gcj::convert::Input_iconv::read (jcharArray outbuffer,
+				      jint outpos, jint count)
+{
+#ifdef HAVE_ICONV
+  jint origpos = outpos;
+
+  jbyte *bytes = elements (inbuffer);
+  jchar *out = elements (outbuffer);
+  size_t inavail = inlength - inpos;
+  size_t old_in = inavail;
+  size_t outavail = count;
+  size_t old_out = outavail;
+
+  size_t r = iconv ((iconv_t) handle,
+		    &bytes[inpos], &inavail,
+		    &out[outpos], &outavail);
+  // FIXME: what if R==-1?
+
+  inpos += old_in - inavail;
+  return old_out - outavail;
+#else /* HAVE_ICONV */
+  return -1;
+#endif /* HAVE_ICONV */
+}
+
+void
+gnu::gcj::convert::Output_iconv::init (jstring encoding)
+{
+#ifdef HAVE_ICONV
+  jsize len = _Jv_GetStringUTFLength (encoding);
+  char buffer[len];
+  _Jv_GetStringUTFRegion (encoding, 0, len, buffer);
+
+  iconv_t h = iconv_open (buffer, "UCS-2");
+  if (h == (iconv_t) -1)
+    JvThrow (new java::io::UnsupportedEncodingException);
+
+  JvAssert (h != NULL);
+  handle = reinterpret_cast<gnu::gcj::RawData *> (h);
+#else /* HAVE_ICONV */
+  // If no iconv, just throw an exception.
+  JvThrow (new java::io::UnsupportedEncodingException);
+#endif /* HAVE_ICONV */
+}
+
+void
+gnu::gcj::convert::Output_iconv::finalize (void)
+{
+#ifdef HAVE_ICONV
+  if (handle == NULL)
+    {
+      iconv_close ((iconv_t) handle);
+      handle = NULL;
+    }
+#endif /* HAVE_ICONV */
+}
+
+jint
+gnu::gcj::convert::Output_iconv::write (jcharArray inbuffer,
+					jint inpos, jint count)
+{
+#ifdef HAVE_ICONV
+  jint origpos = outpos;
+
+  jchar *chars = elements (inbuffer);
+  jbyte *out = elements (buf);
+
+  size_t inavail = count;
+  size_t old_in = count;
+
+  size_t outavail = buf->length - count;
+  size_t old_out = outavail;
+
+  size_t r = iconv ((iconv_t) handle,
+		    &chars[inpos], &inavail,
+		    &out[count], &outavail);
+  // FIXME: what if R==-1?
+
+  count += old_out - outavail;
+  return old_in - inavail;
+#else /* HAVE_ICONV */
+  return -1;
+#endif /* HAVE_ICONV */
+}

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]