[前][次][番号順一覧][スレッド一覧]

ruby-changes:22504

From: drbrain <ko1@a...>
Date: Sat, 11 Feb 2012 09:37:59 +0900 (JST)
Subject: [ruby-changes:22504] drbrain:r34553 (trunk): * ext/zlib/zlib.c (rb_inflate_add_dictionary): Added

drbrain	2012-02-11 09:37:44 +0900 (Sat, 11 Feb 2012)

  New Revision: 34553

  http://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=rev&revision=34553

  Log:
    * ext/zlib/zlib.c (rb_inflate_add_dictionary):  Added
      Zlib::Inflate#add_dictionary to allow users to pre-specify
      for using during #inflate.  [ruby-trunk - Feature #5937]

  Modified files:
    trunk/ChangeLog
    trunk/ext/zlib/zlib.c
    trunk/test/zlib/test_zlib.rb

Index: ChangeLog
===================================================================
--- ChangeLog	(revision 34552)
+++ ChangeLog	(revision 34553)
@@ -1,3 +1,9 @@
+Sat Feb 11 08:34:42 2012  Eric Hodel  <drbrain@s...>
+
+	* ext/zlib/zlib.c (rb_inflate_add_dictionary):  Added
+	  Zlib::Inflate#add_dictionary to allow users to pre-specify
+	  for using during #inflate.  [ruby-trunk - Feature #5937]
+
 Sat Feb 11 08:23:02 2012  Eric Hodel  <drbrain@s...>
 
 	* ext/zlib/zlib.c (do_inflate):  Inflate more data if buffered data
Index: ext/zlib/zlib.c
===================================================================
--- ext/zlib/zlib.c	(revision 34552)
+++ ext/zlib/zlib.c	(revision 34553)
@@ -56,6 +56,8 @@
 
 #define sizeof(x) ((int)sizeof(x))
 
+static ID id_dictionaries;
+
 /*--------- Prototypes --------*/
 
 static NORETURN(void raise_zlib_error(int, const char*));
@@ -875,6 +877,15 @@
 	    if (z->stream.avail_in > 0) {
 		zstream_append_input(z, z->stream.next_in, z->stream.avail_in);
 	    }
+	    if (err == Z_NEED_DICT) {
+		VALUE self = (VALUE)z->stream.opaque;
+		VALUE dicts = rb_ivar_get(self, id_dictionaries);
+		VALUE dict = rb_hash_aref(dicts, rb_uint2inum(z->stream.adler));
+		if (!NIL_P(dict)) {
+		    rb_inflate_set_dictionary(self, dict);
+		    continue;
+		}
+	    }
 	    raise_zlib_error(err, z->stream.msg);
 	}
 	if (z->stream.avail_out > 0) {
@@ -965,6 +976,7 @@
     obj = Data_Make_Struct(klass, struct zstream,
 			   zstream_mark, zstream_free, z);
     zstream_init(z, funcs);
+    z->stream.opaque = (voidpf)obj;
     return obj;
 }
 
@@ -1602,12 +1614,12 @@
  * dup) itself.
  */
 
-
-
 static VALUE
 rb_inflate_s_allocate(VALUE klass)
 {
-    return zstream_inflate_new(klass);
+    VALUE inflate = zstream_inflate_new(klass);
+    rb_ivar_set(inflate, id_dictionaries, rb_hash_new());
+    return inflate;
 }
 
 /*
@@ -1737,6 +1749,25 @@
     }
 }
 
+/* Document-method: Zlib::Inflate#add_dictionary
+ *
+ * call-seq: add_dictionary(string)
+ *
+ * Provide the inflate stream with a dictionary that may be required in the
+ * future.  Multiple dictionaries may be provided.  The inflate stream will
+ * automatically choose the correct user-provided dictionary based on the
+ * stream's required dictionary.
+ */
+static VALUE
+rb_inflate_add_dictionary(VALUE obj, VALUE dictionary) {
+    VALUE dictionaries = rb_ivar_get(obj, id_dictionaries);
+    VALUE checksum = do_checksum(1, &dictionary, adler32);
+
+    rb_hash_aset(dictionaries, checksum, dictionary);
+
+    return obj;
+}
+
 /*
  * Document-method: Zlib::Inflate#inflate
  *
@@ -4018,6 +4049,8 @@
 
     mZlib = rb_define_module("Zlib");
 
+    id_dictionaries = rb_intern("@dictionaries");
+
     cZError = rb_define_class_under(mZlib, "Error", rb_eStandardError);
     cStreamEnd    = rb_define_class_under(mZlib, "StreamEnd", cZError);
     cNeedDict     = rb_define_class_under(mZlib, "NeedDict", cZError);
@@ -4086,6 +4119,7 @@
     rb_define_singleton_method(mZlib, "inflate", rb_inflate_s_inflate, 1);
     rb_define_alloc_func(cInflate, rb_inflate_s_allocate);
     rb_define_method(cInflate, "initialize", rb_inflate_initialize, -1);
+    rb_define_method(cInflate, "add_dictionary", rb_inflate_add_dictionary, 1);
     rb_define_method(cInflate, "inflate", rb_inflate_inflate, 1);
     rb_define_method(cInflate, "<<", rb_inflate_addstr, 1);
     rb_define_method(cInflate, "sync", rb_inflate_sync, 1);
Index: test/zlib/test_zlib.rb
===================================================================
--- test/zlib/test_zlib.rb	(revision 34552)
+++ test/zlib/test_zlib.rb	(revision 34553)
@@ -185,6 +185,23 @@
       assert_equal("foo", z.finish)
     end
 
+    def test_add_dictionary
+      dictionary = "foo"
+
+      deflate = Zlib::Deflate.new
+      deflate.set_dictionary dictionary
+      compressed = deflate.deflate "foofoofoo", Zlib::FINISH
+      deflate.close
+
+      out = nil
+      inflate = Zlib::Inflate.new
+      inflate.add_dictionary "foo"
+
+      out = inflate.inflate compressed
+
+      assert_equal "foofoofoo", out
+    end
+
     def test_inflate
       s = Zlib::Deflate.deflate("foo")
       z = Zlib::Inflate.new

--
ML: ruby-changes@q...
Info: http://www.atdot.net/~ko1/quickml/

[前][次][番号順一覧][スレッド一覧]