diff --git a/README b/README index 66ca2765..6ca10d6a 100644 --- a/README +++ b/README @@ -19,12 +19,12 @@ Binary-based efficient data interchange format. $ make $ sudo make install - To install Ruby binding, run ./gengem.sh script on ruby/ directory and install + To install Ruby binding, run ./makegem.sh script on ruby/ directory and install generated gem package. $ cd ruby - $ ./gengem.sh - $ gem install gem/pkg/msgpack-*.gem + $ ./makegem.sh + $ gem install msgpack-*.gem *Usage @@ -54,7 +54,7 @@ Binary-based efficient data interchange format. API Document is available at http://msgpack.sourceforge.jp/. -Copyright (C) 2008-2009 FURUHASHI Sadayuki +Copyright (C) 2008-2010 FURUHASHI Sadayuki Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License. diff --git a/c/Makefile.am b/c/Makefile.am index 23995a51..f84759a1 100644 --- a/c/Makefile.am +++ b/c/Makefile.am @@ -23,6 +23,6 @@ check_PROGRAMS = \ msgpackc_test_SOURCES = test.cpp msgpackc_test_CXXFLAGS = -I$(top_srcdir) -I$(top_srcdir)/c -msgpackc_test_LDFLAGS = libmsgpackc.la -lgtest_main +msgpackc_test_LDADD = libmsgpackc.la -lgtest_main TESTS = $(check_PROGRAMS) diff --git a/c/msgpack b/c/msgpack deleted file mode 120000 index 945c9b46..00000000 --- a/c/msgpack +++ /dev/null @@ -1 +0,0 @@ -. \ No newline at end of file diff --git a/c/object.h b/c/msgpack/object.h similarity index 98% rename from c/object.h rename to c/msgpack/object.h index 27b593ef..9a014be7 100644 --- a/c/object.h +++ b/c/msgpack/object.h @@ -19,7 +19,6 @@ #define MSGPACK_OBJECT_H__ #include "msgpack/zone.h" -#include "msgpack/sysdep.h" #include #ifdef __cplusplus diff --git a/c/pack.h b/c/msgpack/pack.h similarity index 100% rename from c/pack.h rename to c/msgpack/pack.h diff --git a/c/sbuffer.h b/c/msgpack/sbuffer.h similarity index 100% rename from c/sbuffer.h rename to c/msgpack/sbuffer.h diff --git a/c/unpack.h b/c/msgpack/unpack.h similarity index 100% rename from c/unpack.h rename to c/msgpack/unpack.h diff --git a/c/vrefbuffer.h b/c/msgpack/vrefbuffer.h similarity index 100% rename from c/vrefbuffer.h rename to c/msgpack/vrefbuffer.h diff --git a/c/zone.h b/c/msgpack/zone.h similarity index 99% rename from c/zone.h rename to c/msgpack/zone.h index e07e7624..475ae514 100644 --- a/c/zone.h +++ b/c/msgpack/zone.h @@ -18,6 +18,7 @@ #ifndef MSGPACK_ZONE_H__ #define MSGPACK_ZONE_H__ +#include "msgpack/sysdep.h" #include #include diff --git a/c/vrefbuffer.c b/c/vrefbuffer.c index b970ece5..b528874d 100644 --- a/c/vrefbuffer.c +++ b/c/vrefbuffer.c @@ -30,7 +30,7 @@ bool msgpack_vrefbuffer_init(msgpack_vrefbuffer* vbuf, vbuf->chunk_size = chunk_size; vbuf->ref_size = ref_size; - // glibcは72バイト以下のmallocが高速 + // glibcは72バイト以下のmallocが高速 size_t nfirst = (sizeof(struct iovec) < 72/2) ? 72 / sizeof(struct iovec) : 8; diff --git a/c/zone.c b/c/zone.c index 2d8bc589..3d0634ea 100644 --- a/c/zone.c +++ b/c/zone.c @@ -104,7 +104,6 @@ static inline void init_finalizer_array(msgpack_zone_finalizer_array* fa) static inline void call_finalizer_array(msgpack_zone_finalizer_array* fa) { - // 逆順に呼び出し msgpack_zone_finalizer* fin = fa->tail; for(; fin != fa->array; --fin) { (*(fin-1)->func)((fin-1)->data); @@ -132,9 +131,6 @@ bool msgpack_zone_push_finalizer_expand(msgpack_zone* zone, size_t nnext; if(nused == 0) { - // 初回の呼び出し:fa->tail == fa->end == fa->array == NULL - - // glibcは72バイト以下のmallocが高速 nnext = (sizeof(msgpack_zone_finalizer) < 72/2) ? 72 / sizeof(msgpack_zone_finalizer) : 8; diff --git a/configure.in b/configure.in index f9f29180..259ed377 100644 --- a/configure.in +++ b/configure.in @@ -36,16 +36,18 @@ AC_CHECK_HEADERS(tr1/unordered_set) AC_LANG_POP([C++]) AC_CACHE_CHECK([for __sync_* atomic operations], msgpack_cv_atomic_ops, [ - AC_TRY_LINK([ - int atomic_sub(int i) { return __sync_sub_and_fetch(&i, 1); } - int atomic_add(int i) { return __sync_add_and_fetch(&i, 1); } - ], [], msgpack_cv_atomic_ops="yes") - ]) + AC_TRY_LINK([ + int atomic_sub(int i) { return __sync_sub_and_fetch(&i, 1); } + int atomic_add(int i) { return __sync_add_and_fetch(&i, 1); } + ], [], msgpack_cv_atomic_ops="yes") + ]) if test "$msgpack_cv_atomic_ops" != "yes"; then - AC_MSG_ERROR([__sync_* atomic operations are not supported. + AC_MSG_ERROR([__sync_* atomic operations are not supported. + Note that gcc < 4.1 is not supported. -If you are using gcc-4.1 and the CPU architecture is x86, try to add -CFLAGS"--march=i686" and CXXFLAGS="-march=i668" options to ./configure as follows: + +If you are using gcc >= 4.1 and the default target CPU architecture is "i386", try to +add CFLAGS="--march=i686" and CXXFLAGS="-march=i668" options to ./configure as follows: $ ./configure CFLAGS="-march=i686" CXXFLAGS="-march=i686" ]) diff --git a/cpp/Makefile.am b/cpp/Makefile.am index 99f4a322..d4de1612 100644 --- a/cpp/Makefile.am +++ b/cpp/Makefile.am @@ -39,6 +39,6 @@ check_PROGRAMS = \ msgpack_test_SOURCES = test.cpp msgpack_test_CXXFLAGS = -I$(top_srcdir) -I$(top_srcdir)/c -I$(top_srcdir)/cpp -msgpack_test_LDFLAGS = libmsgpack.la -lgtest_main +msgpack_test_LDADD = libmsgpack.la -lgtest_main TESTS = $(check_PROGRAMS) diff --git a/cpp/msgpack b/cpp/msgpack deleted file mode 120000 index 945c9b46..00000000 --- a/cpp/msgpack +++ /dev/null @@ -1 +0,0 @@ -. \ No newline at end of file diff --git a/cpp/object.hpp b/cpp/msgpack/object.hpp similarity index 100% rename from cpp/object.hpp rename to cpp/msgpack/object.hpp diff --git a/cpp/pack.hpp b/cpp/msgpack/pack.hpp similarity index 100% rename from cpp/pack.hpp rename to cpp/msgpack/pack.hpp diff --git a/cpp/sbuffer.hpp b/cpp/msgpack/sbuffer.hpp similarity index 100% rename from cpp/sbuffer.hpp rename to cpp/msgpack/sbuffer.hpp diff --git a/cpp/type.hpp b/cpp/msgpack/type.hpp similarity index 100% rename from cpp/type.hpp rename to cpp/msgpack/type.hpp diff --git a/cpp/type/bool.hpp b/cpp/msgpack/type/bool.hpp similarity index 100% rename from cpp/type/bool.hpp rename to cpp/msgpack/type/bool.hpp diff --git a/cpp/type/define.hpp.erb b/cpp/msgpack/type/define.hpp.erb similarity index 100% rename from cpp/type/define.hpp.erb rename to cpp/msgpack/type/define.hpp.erb diff --git a/cpp/type/deque.hpp b/cpp/msgpack/type/deque.hpp similarity index 100% rename from cpp/type/deque.hpp rename to cpp/msgpack/type/deque.hpp diff --git a/cpp/type/float.hpp b/cpp/msgpack/type/float.hpp similarity index 100% rename from cpp/type/float.hpp rename to cpp/msgpack/type/float.hpp diff --git a/cpp/type/int.hpp b/cpp/msgpack/type/int.hpp similarity index 100% rename from cpp/type/int.hpp rename to cpp/msgpack/type/int.hpp diff --git a/cpp/type/list.hpp b/cpp/msgpack/type/list.hpp similarity index 100% rename from cpp/type/list.hpp rename to cpp/msgpack/type/list.hpp diff --git a/cpp/type/map.hpp b/cpp/msgpack/type/map.hpp similarity index 100% rename from cpp/type/map.hpp rename to cpp/msgpack/type/map.hpp diff --git a/cpp/type/nil.hpp b/cpp/msgpack/type/nil.hpp similarity index 100% rename from cpp/type/nil.hpp rename to cpp/msgpack/type/nil.hpp diff --git a/cpp/type/pair.hpp b/cpp/msgpack/type/pair.hpp similarity index 100% rename from cpp/type/pair.hpp rename to cpp/msgpack/type/pair.hpp diff --git a/cpp/type/raw.hpp b/cpp/msgpack/type/raw.hpp similarity index 100% rename from cpp/type/raw.hpp rename to cpp/msgpack/type/raw.hpp diff --git a/cpp/type/set.hpp b/cpp/msgpack/type/set.hpp similarity index 100% rename from cpp/type/set.hpp rename to cpp/msgpack/type/set.hpp diff --git a/cpp/type/string.hpp b/cpp/msgpack/type/string.hpp similarity index 100% rename from cpp/type/string.hpp rename to cpp/msgpack/type/string.hpp diff --git a/cpp/type/tr1/unordered_map.hpp b/cpp/msgpack/type/tr1/unordered_map.hpp similarity index 100% rename from cpp/type/tr1/unordered_map.hpp rename to cpp/msgpack/type/tr1/unordered_map.hpp diff --git a/cpp/type/tr1/unordered_set.hpp b/cpp/msgpack/type/tr1/unordered_set.hpp similarity index 100% rename from cpp/type/tr1/unordered_set.hpp rename to cpp/msgpack/type/tr1/unordered_set.hpp diff --git a/cpp/type/tuple.hpp.erb b/cpp/msgpack/type/tuple.hpp.erb similarity index 100% rename from cpp/type/tuple.hpp.erb rename to cpp/msgpack/type/tuple.hpp.erb diff --git a/cpp/type/vector.hpp b/cpp/msgpack/type/vector.hpp similarity index 87% rename from cpp/type/vector.hpp rename to cpp/msgpack/type/vector.hpp index 754cdc05..385d070f 100644 --- a/cpp/type/vector.hpp +++ b/cpp/msgpack/type/vector.hpp @@ -29,11 +29,15 @@ inline std::vector& operator>> (object o, std::vector& v) { if(o.type != type::ARRAY) { throw type_error(); } v.resize(o.via.array.size); - object* p = o.via.array.ptr; - object* const pend = o.via.array.ptr + o.via.array.size; - T* it = &v.front(); - for(; p < pend; ++p, ++it) { - p->convert(it); + if(o.via.array.size > 0) { + object* p = o.via.array.ptr; + object* const pend = o.via.array.ptr + o.via.array.size; + T* it = &v[0]; + do { + p->convert(it); + ++p; + ++it; + } while(p < pend); } return v; } diff --git a/cpp/unpack.hpp b/cpp/msgpack/unpack.hpp similarity index 100% rename from cpp/unpack.hpp rename to cpp/msgpack/unpack.hpp diff --git a/cpp/vrefbuffer.hpp b/cpp/msgpack/vrefbuffer.hpp similarity index 100% rename from cpp/vrefbuffer.hpp rename to cpp/msgpack/vrefbuffer.hpp diff --git a/cpp/zone.hpp.erb b/cpp/msgpack/zone.hpp.erb similarity index 100% rename from cpp/zone.hpp.erb rename to cpp/msgpack/zone.hpp.erb diff --git a/cpp/test.cpp b/cpp/test.cpp index b152e6d3..113914ab 100644 --- a/cpp/test.cpp +++ b/cpp/test.cpp @@ -438,7 +438,7 @@ TEST(MSGPACK_STL, simple_buffer_multiset) #ifdef HAVE_TR1_UNORDERED_MAP #include -#include "cpp/type/tr1/unordered_map.hpp" +#include "cpp/msgpack/type/tr1/unordered_map.hpp" TEST(MSGPACK_TR1, simple_buffer_unordered_map) { for (unsigned int k = 0; k < kLoop; k++) { @@ -499,7 +499,7 @@ TEST(MSGPACK_TR1, simple_buffer_unordered_multimap) #ifdef HAVE_TR1_UNORDERED_SET #include -#include "cpp/type/tr1/unordered_set.hpp" +#include "cpp/msgpack/type/tr1/unordered_set.hpp" TEST(MSGPACK_TR1, simple_buffer_unordered_set) { for (unsigned int k = 0; k < kLoop; k++) { diff --git a/msgpack/sysdep.h b/msgpack/sysdep.h index 106158ea..c69c69ac 100644 --- a/msgpack/sysdep.h +++ b/msgpack/sysdep.h @@ -48,6 +48,17 @@ typedef unsigned int _msgpack_atomic_counter_t; #ifdef _WIN32 #include + +#ifdef __cplusplus +/* numeric_limits::min,max */ +#ifdef max +#undef max +#endif +#ifdef min +#undef min +#endif +#endif + #else #include /* __BYTE_ORDER */ #endif diff --git a/msgpack_vc8.vcproj b/msgpack_vc8.vcproj new file mode 100644 index 00000000..5daec015 --- /dev/null +++ b/msgpack_vc8.vcproj @@ -0,0 +1,275 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/python/README b/python/README index 2b2ebe98..a7e8c53a 100644 --- a/python/README +++ b/python/README @@ -2,7 +2,7 @@ MessagePack Python Binding =========================== -:author: Naoki INADA +:author: INADA Naoki :version: 0.1.0 :date: 2009-07-12 @@ -32,7 +32,11 @@ MinGW GCC. TEST ---- -MessagePack uses nosetest for testing. +MessagePack uses `nosetest` for testing. Run test with following command: $ nosetests test + + +.. + vim: filetype=rst diff --git a/python/setup.py b/python/setup.py index c48be14e..66cf27e8 100755 --- a/python/setup.py +++ b/python/setup.py @@ -1,16 +1,41 @@ #!/usr/bin/env python # coding: utf-8 -from distutils.core import setup, Extension -#from Cython.Distutils import build_ext import os +from glob import glob +from distutils.core import setup, Extension +from distutils.command.sdist import sdist + +try: + from Cython.Distutils import build_ext + import Cython.Compiler.Main as cython_compiler + have_cython = True +except ImportError: + from distutils.command.build_ext import build_ext + have_cython = False version = '0.2.0dev' +# take care of extension modules. +if have_cython: + sources = ['msgpack/_msgpack.pyx'] + + class Sdist(sdist): + def __init__(self, *args, **kwargs): + for src in glob('msgpack/*.pyx'): + cython_compiler.compile(glob('msgpack/*.pyx'), + cython_compiler.default_options) + sdist.__init__(self, *args, **kwargs) +else: + sources = ['msgpack/_msgpack.c'] + + Sdist = sdist + msgpack_mod = Extension('msgpack._msgpack', - #sources=['msgpack/_msgpack.pyx'] - sources=['msgpack/_msgpack.c'] + sources=sources, ) +del sources + desc = 'MessagePack (de)serializer.' long_desc = desc + """ @@ -26,14 +51,15 @@ What's MessagePack? (from http://msgpack.sourceforge.jp/) """ setup(name='msgpack', - author='Naoki INADA', + author='INADA Naoki', author_email='songofacandy@gmail.com', version=version, - #cmdclass={'build_ext': build_ext}, + cmdclass={'build_ext': build_ext, 'sdist': Sdist}, ext_modules=[msgpack_mod], packages=['msgpack'], description=desc, long_description=long_desc, + url="http://msgpack.sourceforge.jp/", classifiers=[ 'Development Status :: 4 - Beta', 'Intended Audience :: Developers', diff --git a/python/setup_dev.py b/python/setup_dev.py deleted file mode 100755 index 4efc7696..00000000 --- a/python/setup_dev.py +++ /dev/null @@ -1,41 +0,0 @@ -#!/usr/bin/env python -# coding: utf-8 - -from distutils.core import setup, Extension -from Cython.Distutils import build_ext -import os - -version = '0.2.0dev' - -msgpack_mod = Extension('msgpack._msgpack', - sources=['msgpack/_msgpack.pyx'] - ) - -desc = 'MessagePack (de)serializer.' -long_desc = desc + """ - -MessagePack_ (de)serializer for Python. - -.. _MessagePack: http://msgpack.sourceforge.jp/ - -What's MessagePack? (from http://msgpack.sourceforge.jp/) - - MessagePack is a binary-based efficient data interchange format that is - focused on high performance. It is like JSON, but very fast and small. -""" - -setup(name='msgpack', - author='Naoki INADA', - author_email='songofacandy@gmail.com', - version=version, - cmdclass={'build_ext': build_ext}, - ext_modules=[msgpack_mod], - packages=['msgpack'], - description=desc, - long_description=long_desc, - classifiers=[ - 'Development Status :: 4 - Beta', - 'Intended Audience :: Developers', - 'License :: OSI Approved :: Apache Software License', - ] - ) diff --git a/ruby/gem/README b/ruby/README similarity index 100% rename from ruby/gem/README rename to ruby/README diff --git a/ruby/gem/Rakefile b/ruby/gem/Rakefile deleted file mode 100644 index f2fd6846..00000000 --- a/ruby/gem/Rakefile +++ /dev/null @@ -1,133 +0,0 @@ -require 'rubygems' -require 'rake' -require 'rake/clean' -require 'rake/testtask' -require 'rake/packagetask' -require 'rake/gempackagetask' -require 'rake/rdoctask' -require 'rake/contrib/rubyforgepublisher' -require 'rake/contrib/sshpublisher' -require 'fileutils' -include FileUtils - -NAME = "msgpack" -AUTHOR = "FURUHASHI Sadayuki" -EMAIL = "frsyuki _at_ users.sourceforge.jp" -DESCRIPTION = "Binary-based efficient data interchange format." -RUBYFORGE_PROJECT = "msgpack" -HOMEPATH = "http://msgpack.sourceforge.jp/" -BIN_FILES = %w( ) -VERS = "0.3.2" - -#REV = File.read(".svn/entries")[/committed-rev="(d+)"/, 1] rescue nil -REV = nil -CLEAN.include ['**/.*.sw?', '*.gem', '.config'] -RDOC_OPTS = [ - '--title', "#{NAME} documentation", - "--charset", "utf-8", - "--opname", "index.html", - "--line-numbers", - "--main", "README", - "--inline-source", -] - -task :default => [:test] -task :package => [:clean] - -Rake::TestTask.new("test") do |t| - t.libs << "test" - t.pattern = "test/**/*_test.rb" - t.verbose = true -end - -spec = Gem::Specification.new do |s| - s.name = NAME - s.version = VERS - s.platform = Gem::Platform::RUBY - s.has_rdoc = false - s.extra_rdoc_files = ["README", "ChangeLog", "AUTHORS"] - s.rdoc_options += RDOC_OPTS + ['--exclude', '^(examples|extras)/'] - s.summary = DESCRIPTION - s.description = DESCRIPTION - s.author = AUTHOR - s.email = EMAIL - s.homepage = HOMEPATH - s.executables = BIN_FILES - s.rubyforge_project = RUBYFORGE_PROJECT - s.bindir = "bin" - s.require_path = "ext" - s.autorequire = "" - s.test_files = Dir["test/test_*.rb"] - - #s.add_dependency('activesupport', '>=1.3.1') - #s.required_ruby_version = '>= 1.8.2' - - s.files = %w(README ChangeLog Rakefile) + - Dir.glob("{bin,doc,test,lib,templates,generator,extras,website,script}/**/*") + - Dir.glob("ext/**/*.{h,c,rb}") + - Dir.glob("examples/**/*.rb") + - Dir.glob("tools/*.rb") + - Dir.glob("msgpack/*.h") - - s.extensions = FileList["ext/**/extconf.rb"].to_a -end - -Rake::GemPackageTask.new(spec) do |p| - p.need_tar = true - p.gem_spec = spec -end - -task :install do - name = "#{NAME}-#{VERS}.gem" - sh %{rake package} - sh %{sudo gem install pkg/#{name}} -end - -task :uninstall => [:clean] do - sh %{sudo gem uninstall #{NAME}} -end - - -#Rake::RDocTask.new do |rdoc| -# rdoc.rdoc_dir = 'html' -# rdoc.options += RDOC_OPTS -# rdoc.template = "resh" -# #rdoc.template = "#{ENV['template']}.rb" if ENV['template'] -# if ENV['DOC_FILES'] -# rdoc.rdoc_files.include(ENV['DOC_FILES'].split(/,\s*/)) -# else -# rdoc.rdoc_files.include('README', 'ChangeLog') -# rdoc.rdoc_files.include('lib/**/*.rb') -# rdoc.rdoc_files.include('ext/**/*.c') -# end -#end - -desc "Publish to RubyForge" -task :rubyforge => [:rdoc, :package] do - require 'rubyforge' - Rake::RubyForgePublisher.new(RUBYFORGE_PROJECT, 'frsyuki').upload -end - -desc 'Package and upload the release to rubyforge.' -task :release => [:clean, :package] do |t| - v = ENV["VERSION"] or abort "Must supply VERSION=x.y.z" - abort "Versions don't match #{v} vs #{VERS}" unless v == VERS - pkg = "pkg/#{NAME}-#{VERS}" - - rf = RubyForge.new - puts "Logging in" - rf.login - - c = rf.userconfig -# c["release_notes"] = description if description -# c["release_changes"] = changes if changes - c["preformatted"] = true - - files = [ - "#{pkg}.tgz", - "#{pkg}.gem" - ].compact - - puts "Releasing #{NAME} v. #{VERS}" - rf.add_release RUBYFORGE_PROJECT, NAME, VERS, *files -end diff --git a/ruby/gengem.sh b/ruby/gengem.sh deleted file mode 100755 index 359debf3..00000000 --- a/ruby/gengem.sh +++ /dev/null @@ -1,21 +0,0 @@ -#!/bin/sh - -mkdir -p gem/ext -mkdir -p gem/msgpack -cp extconf.rb gem/ext/ -cp pack.c gem/ext/ -cp pack.h gem/ext/ -cp rbinit.c gem/ext/ -cp unpack.c gem/ext/ -cp unpack.h gem/ext/ -cat test_case.rb | sed "s/require ['\"]msgpack['\"]/require File.dirname(__FILE__) + '\/test_helper.rb'/" > gem/test/msgpack_test.rb -cp ../AUTHORS gem/AUTHORS -cp ../ChangeLog gem/ChangeLog -cp ../msgpack/pack_define.h gem/msgpack/ -cp ../msgpack/pack_template.h gem/msgpack/ -cp ../msgpack/unpack_define.h gem/msgpack/ -cp ../msgpack/unpack_template.h gem/msgpack/ -cp ../msgpack/sysdep.h gem/msgpack/ - -cd gem && rake --trace package - diff --git a/ruby/makegem.sh b/ruby/makegem.sh new file mode 100755 index 00000000..fd0db790 --- /dev/null +++ b/ruby/makegem.sh @@ -0,0 +1,21 @@ +#!/bin/sh + +mkdir -p ext +mkdir -p msgpack +cp extconf.rb ext/ +cp pack.c ext/ +cp pack.h ext/ +cp rbinit.c ext/ +cp unpack.c ext/ +cp unpack.h ext/ +cp ../AUTHORS ./ +cp ../ChangeLog ./ +cp ../msgpack/pack_define.h msgpack/ +cp ../msgpack/pack_template.h msgpack/ +cp ../msgpack/unpack_define.h msgpack/ +cp ../msgpack/unpack_template.h msgpack/ +cp ../msgpack/sysdep.h msgpack/ +cat msgpack_test.rb | sed "s/require ['\"]msgpack['\"]/require File.dirname(__FILE__) + '\/test_helper.rb'/" > test/msgpack_test.rb + +gem build msgpack.gemspec + diff --git a/ruby/msgpack.gemspec b/ruby/msgpack.gemspec old mode 100755 new mode 100644 index 59186a4c..7273881c --- a/ruby/msgpack.gemspec +++ b/ruby/msgpack.gemspec @@ -1,12 +1,16 @@ -Gem::Specification.new do |s| - s.platform = Gem::Platform::CURRENT - s.name = "msgpack" - s.version = "0.3.2" - s.summary = "MessagePack" - s.author = "FURUHASHI Sadayuki" - s.email = "frsyuki@users.sourceforge.jp" - s.homepage = "http://msgpack.sourceforge.jp/" - s.rubyforge_project = "msgpack" - s.require_paths = ["lib", "ext"] - s.files = ["lib/**/*", "ext/**/*"].map {|g| Dir.glob(g) }.flatten +Gem::Specification.new do |s| + s.platform = Gem::Platform::RUBY + s.name = "msgpack" + s.version = "0.3.3" + s.summary = "MessagePack, a binary-based efficient data interchange format." + s.author = "FURUHASHI Sadayuki" + s.email = "frsyuki@users.sourceforge.jp" + s.homepage = "http://msgpack.sourceforge.jp/" + s.rubyforge_project = "msgpack" + s.has_rdoc = false + s.extra_rdoc_files = ["README", "ChangeLog", "AUTHORS"] + s.require_paths = ["lib", "ext"] + s.files = Dir["lib/**/*", "ext/**/*", "msgpack/**/*", "test/**/*"] + s.test_files = Dir["test/test_*.rb"] + s.extensions = Dir["ext/**/extconf.rb"] end diff --git a/ruby/test_case.rb b/ruby/msgpack_test.rb similarity index 100% rename from ruby/test_case.rb rename to ruby/msgpack_test.rb diff --git a/ruby/gem/test/test_helper.rb b/ruby/test/test_helper.rb similarity index 100% rename from ruby/gem/test/test_helper.rb rename to ruby/test/test_helper.rb diff --git a/ruby/test_format.rb b/ruby/test_format.rb deleted file mode 100644 index 99a27d1b..00000000 --- a/ruby/test_format.rb +++ /dev/null @@ -1,122 +0,0 @@ -require 'msgpack' - -@up = MessagePack::Unpacker.new - -def check(bytes, should) - puts "----" - @up.reset - src = bytes.pack('C*') - ret = @up.execute(src, 0) - if ret != src.length - puts "** EXTRA BYTES **" - end - puts bytes.map{|x|"%x"%x}.join(' ') - data = @up.data - p data - if data != should - puts "** TEST FAILED **" - p should - end -end - -# SimpleValue -check([ - 0x93, 0xc0, 0xc2, 0xc3, -], [nil,false,true]) - -# Fixnum -check([ - 0x92, - 0x93, 0x00, 0x40, 0x7f, - 0x93, 0xe0, 0xf0, 0xff, -], [[0,64,127], [-32,-16,-1]]) - -# FixArray -check([ - 0x92, - 0x90, - 0x91, - 0x91, 0xc0, -], [[],[[nil]]]) - - -# FixRaw -check([ - 0x94, - 0xa0, - 0xa1, ?a, - 0xa2, ?b, ?c, - 0xa3, ?d, ?e, ?f, -], ["","a","bc","def"]) - -# FixMap -check([ - 0x82, - 0xc2, 0x81, - 0xc0, 0xc0, - 0xc3, 0x81, - 0xc0, 0x80, -], {false=>{nil=>nil}, true=>{nil=>{}}}) - -# unsigned int -check([ - 0x99, - 0xcc, 0, - 0xcc, 128, - 0xcc, 255, - 0xcd, 0x00, 0x00, - 0xcd, 0x80, 0x00, - 0xcd, 0xff, 0xff, - 0xce, 0x00, 0x00, 0x00, 0x00, - 0xce, 0x80, 0x00, 0x00, 0x00, - 0xce, 0xff, 0xff, 0xff, 0xff, -], [0, 128, 255, 0, 32768, 65535, 0, 2147483648, 4294967295]) - -# signed int -check([ - 0x99, - 0xd0, 0, - 0xd0, 128, - 0xd0, 255, - 0xd1, 0x00, 0x00, - 0xd1, 0x80, 0x00, - 0xd1, 0xff, 0xff, - 0xd2, 0x00, 0x00, 0x00, 0x00, - 0xd2, 0x80, 0x00, 0x00, 0x00, - 0xd2, 0xff, 0xff, 0xff, 0xff, -], [0, -128, -1, 0, -32768, -1, 0, -2147483648, -1]) - -# raw -check([ - 0x96, - 0xda, 0x00, 0x00, - 0xda, 0x00, 0x01, ?a, - 0xda, 0x00, 0x02, ?a, ?b, - 0xdb, 0x00, 0x00, 0x00, 0x00, - 0xdb, 0x00, 0x00, 0x00, 0x01, ?a, - 0xdb, 0x00, 0x00, 0x00, 0x02, ?a, ?b, -], ["", "a", "ab", "", "a", "ab"]) - -# array -check([ - 0x96, - 0xdc, 0x00, 0x00, - 0xdc, 0x00, 0x01, 0xc0, - 0xdc, 0x00, 0x02, 0xc2, 0xc3, - 0xdd, 0x00, 0x00, 0x00, 0x00, - 0xdd, 0x00, 0x00, 0x00, 0x01, 0xc0, - 0xdd, 0x00, 0x00, 0x00, 0x02, 0xc2, 0xc3 -], [[], [nil], [false,true], [], [nil], [false,true]]) - -# map -check([ - 0x96, - 0xde, 0x00, 0x00, - 0xde, 0x00, 0x01, 0xc0, 0xc2, - 0xde, 0x00, 0x02, 0xc0, 0xc2, 0xc3, 0xc2, - 0xdf, 0x00, 0x00, 0x00, 0x00, - 0xdf, 0x00, 0x00, 0x00, 0x01, 0xc0, 0xc2, - 0xdf, 0x00, 0x00, 0x00, 0x02, 0xc0, 0xc2, 0xc3, 0xc2, -], [{}, {nil=>false}, {true=>false, nil=>false}, {}, {nil=>false}, {true=>false, nil=>false}]) - - diff --git a/ruby/test_pack.rb b/ruby/test_pack.rb deleted file mode 100644 index 6873d574..00000000 --- a/ruby/test_pack.rb +++ /dev/null @@ -1,58 +0,0 @@ -require 'msgpack' - -def check(data) - puts "---" - pack = data.to_msgpack - p data - puts pack.unpack('C*').map{|x|"%02x"%x}.join(' ') - re = MessagePack::unpack(pack) - if re != data - p re - puts "** TEST FAILED **" - end -end - -check 0 -check 1 -check 127 -check 128 -check 255 -check 256 -check 65535 -check 65536 -check -1 -check -32 -check -33 -check -128 -check -129 -check -32768 -check -32769 - -check 1.0 - -check "" -check "a" -check "a"*31 -check "a"*32 - -check nil -check true -check false - -check [] -check [[]] -check [[], nil] - -check( {nil=>0} ) - -check (1<<23) -__END__ - -ary = [] -i = 0 -while i < (1<<16) - ary << i - i += 1 -end -check ary - diff --git a/ruby/unpack.c b/ruby/unpack.c index e9d6494e..0f1af38f 100644 --- a/ruby/unpack.c +++ b/ruby/unpack.c @@ -18,10 +18,16 @@ #include "ruby.h" #include "msgpack/unpack_define.h" +static ID s_sysread; typedef struct { int finished; VALUE source; + size_t offset; + size_t parsed; + VALUE buffer; + VALUE stream; + VALUE streambuf; } unpack_user; @@ -144,6 +150,9 @@ static void MessagePack_Unpacker_free(void* data) static void MessagePack_Unpacker_mark(msgpack_unpack_t *mp) { unsigned int i; + rb_gc_mark(mp->user.buffer); + rb_gc_mark(mp->user.stream); + rb_gc_mark(mp->user.streambuf); for(i=0; i < mp->top; ++i) { rb_gc_mark(mp->stack[i].obj); rb_gc_mark(mp->stack[i].map_key); /* maybe map_key is not initialized */ @@ -164,14 +173,32 @@ static VALUE MessagePack_Unpacker_reset(VALUE self) UNPACKER(self, mp); template_init(mp); init_stack(mp); - unpack_user u = {0, Qnil}; - mp->user = u; + mp->user.finished = 0; return self; } -static VALUE MessagePack_Unpacker_initialize(VALUE self) +static VALUE MessagePack_Unpacker_initialize(int argc, VALUE *argv, VALUE self) { - return MessagePack_Unpacker_reset(self); + VALUE stream; + switch(argc) { + case 0: + stream = Qnil; + break; + case 1: + stream = argv[0]; + break; + default: + rb_raise(rb_eArgError, "wrong number of arguments (%d for 0)", argc); + } + + MessagePack_Unpacker_reset(self); + UNPACKER(self, mp); + mp->user.offset = 0; + mp->user.parsed = 0; + mp->user.buffer = rb_str_new("",0); + mp->user.stream = stream; + mp->user.streambuf = rb_str_new("",0); + return self; } @@ -249,6 +276,87 @@ static VALUE MessagePack_Unpacker_data(VALUE self) } +static VALUE MessagePack_Unpacker_feed(VALUE self, VALUE data) +{ + UNPACKER(self, mp); + StringValue(data); + rb_str_cat(mp->user.buffer, RSTRING_PTR(data), RSTRING_LEN(data)); + return Qnil; +} + +static VALUE MessagePack_Unpacker_stream_get(VALUE self) +{ + UNPACKER(self, mp); + return mp->user.stream; +} + +static VALUE MessagePack_Unpacker_stream_set(VALUE self, VALUE val) +{ + UNPACKER(self, mp); + return mp->user.stream = val; +} + +static VALUE MessagePack_Unpacker_fill(VALUE self) +{ + UNPACKER(self, mp); + + if(mp->user.stream == Qnil) { + return Qnil; + } + + size_t len; + if(RSTRING_LEN(mp->user.buffer) == 0) { + rb_funcall(mp->user.stream, s_sysread, 2, LONG2FIX(64*1024), mp->user.buffer); + len = RSTRING_LEN(mp->user.buffer); + } else { + rb_funcall(mp->user.stream, s_sysread, 2, LONG2FIX(64*1024), mp->user.streambuf); + len = RSTRING_LEN(mp->user.streambuf); + rb_str_cat(mp->user.buffer, RSTRING_PTR(mp->user.streambuf), RSTRING_LEN(mp->user.streambuf)); + } + + return LONG2FIX(len); +} + +static VALUE MessagePack_Unpacker_each(VALUE self) +{ + UNPACKER(self, mp); + int ret; + +#ifdef RETURN_ENUMERATOR + RETURN_ENUMERATOR(self, 0, 0); +#endif + + while(1) { + if(RSTRING_LEN(mp->user.buffer) <= mp->user.offset) { + do_fill: + { + VALUE len = MessagePack_Unpacker_fill(self); + if(len == Qnil || FIX2LONG(len) == 0) { + break; + } + } + } + + mp->user.source = mp->user.buffer; + ret = template_execute(mp, RSTRING_PTR(mp->user.buffer), RSTRING_LEN(mp->user.buffer), &mp->user.offset); + mp->user.source = Qnil; + + if(ret < 0) { + rb_raise(eUnpackError, "parse error."); + } else if(ret > 0) { + VALUE data = template_data(mp); + template_init(mp); + init_stack(mp); + rb_yield(data); + } else { + goto do_fill; + } + } + + return Qnil; +} + + static VALUE MessagePack_unpack_impl(VALUE args) { msgpack_unpack_t* mp = (msgpack_unpack_t*)((VALUE*)args)[0]; @@ -292,7 +400,7 @@ static VALUE MessagePack_unpack_limit(VALUE self, VALUE data, VALUE limit) msgpack_unpack_t mp; template_init(&mp); init_stack(&mp); - unpack_user u = {0, Qnil}; + unpack_user u = {0, Qnil, 0, 0, Qnil, Qnil, Qnil}; mp.user = u; rb_gc_disable(); @@ -313,17 +421,22 @@ static VALUE MessagePack_unpack(VALUE self, VALUE data) void Init_msgpack_unpack(VALUE mMessagePack) { + s_sysread = rb_intern("sysread"); eUnpackError = rb_define_class_under(mMessagePack, "UnpackError", rb_eStandardError); cUnpacker = rb_define_class_under(mMessagePack, "Unpacker", rb_cObject); rb_define_alloc_func(cUnpacker, MessagePack_Unpacker_alloc); - rb_define_method(cUnpacker, "initialize", MessagePack_Unpacker_initialize, 0); + rb_define_method(cUnpacker, "initialize", MessagePack_Unpacker_initialize, -1); rb_define_method(cUnpacker, "execute", MessagePack_Unpacker_execute, 2); rb_define_method(cUnpacker, "execute_limit", MessagePack_Unpacker_execute_limit, 3); rb_define_method(cUnpacker, "finished?", MessagePack_Unpacker_finished_p, 0); rb_define_method(cUnpacker, "data", MessagePack_Unpacker_data, 0); rb_define_method(cUnpacker, "reset", MessagePack_Unpacker_reset, 0); + rb_define_method(cUnpacker, "feed", MessagePack_Unpacker_feed, 1); + rb_define_method(cUnpacker, "fill", MessagePack_Unpacker_fill, 0); + rb_define_method(cUnpacker, "each", MessagePack_Unpacker_each, 0); + rb_define_method(cUnpacker, "stream", MessagePack_Unpacker_stream_get, 0); + rb_define_method(cUnpacker, "stream=", MessagePack_Unpacker_stream_set, 1); rb_define_module_function(mMessagePack, "unpack", MessagePack_unpack, 1); rb_define_module_function(mMessagePack, "unpack_limit", MessagePack_unpack_limit, 2); } -