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

ruby-changes:42590

From: naruse <ko1@a...>
Date: Fri, 22 Apr 2016 05:09:30 +0900 (JST)
Subject: [ruby-changes:42590] naruse:r54664 (trunk): * gc.c (rb_alloc_tmp_buffer_with_count): added like xmalloc2 to

naruse	2016-04-22 05:59:40 +0900 (Fri, 22 Apr 2016)

  New Revision: 54664

  https://svn.ruby-lang.org/cgi-bin/viewvc.cgi?view=revision&revision=54664

  Log:
    * gc.c (rb_alloc_tmp_buffer_with_count): added like xmalloc2 to
      avoid duplicated check of size.
    
    * gc.c (ruby_xmalloc2): added to keep separate layers.
    
    * include/ruby/ruby.h (rb_alloc_tmp_buffer2): added to check
      the size more statically.

  Modified files:
    trunk/ChangeLog
    trunk/gc.c
    trunk/include/ruby/ruby.h
Index: include/ruby/ruby.h
===================================================================
--- include/ruby/ruby.h	(revision 54663)
+++ include/ruby/ruby.h	(revision 54664)
@@ -1615,6 +1615,7 @@ rb_num2char_inline(VALUE x) https://github.com/ruby/ruby/blob/trunk/include/ruby/ruby.h#L1615
 #define ALLOCA_N(type,n) ((type*)alloca(sizeof(type)*(n)))
 
 void *rb_alloc_tmp_buffer(volatile VALUE *store, long len) RUBY_ATTR_ALLOC_SIZE((2));
+void *rb_alloc_tmp_buffer_with_count(volatile VALUE *store, size_t len,size_t count) RUBY_ATTR_ALLOC_SIZE((2,3));
 void rb_free_tmp_buffer(volatile VALUE *store);
 NORETURN(void ruby_malloc_size_overflow(size_t, size_t));
 static inline size_t
@@ -1625,21 +1626,38 @@ ruby_xmalloc2_size(const size_t count, c https://github.com/ruby/ruby/blob/trunk/include/ruby/ruby.h#L1626
     }
     return count * elsize;
 }
+static inline void *
+rb_alloc_tmp_buffer2(volatile VALUE *store, long count, size_t elsize)
+{
+    size_t cnt = (size_t)count;
+    if (elsize % sizeof(VALUE) == 0) {
+	if (UNLIKELY(cnt > LONG_MAX / sizeof(VALUE))) {
+	    ruby_malloc_size_overflow(cnt, elsize);
+	}
+    }
+    else {
+	if (UNLIKELY(cnt > (LONG_MAX - sizeof(VALUE)) / elsize)) {
+	    ruby_malloc_size_overflow(count, elsize);
+	}
+	cnt = (cnt * elsize + sizeof(VALUE) - 1) / sizeof(VALUE);
+    }
+    return rb_alloc_tmp_buffer_with_count(store, cnt * sizeof(VALUE), cnt);
+}
 /* allocates _n_ bytes temporary buffer and stores VALUE including it
  * in _v_.  _n_ may be evaluated twice. */
 #ifdef C_ALLOCA
 # define RB_ALLOCV(v, n) rb_alloc_tmp_buffer(&(v), (n))
 # define RB_ALLOCV_N(type, v, n) \
-    ((type*)RB_ALLOCV((v), ruby_xmalloc2_size((n), sizeof(type))))
+     rb_alloc_tmp_buffer2(&(v), (n), sizeof(type))))
 #else
 # define RUBY_ALLOCV_LIMIT 1024
 # define RB_ALLOCV(v, n) ((n) < RUBY_ALLOCV_LIMIT ? \
 		       (RB_GC_GUARD(v) = 0, alloca(n)) : \
 		       rb_alloc_tmp_buffer(&(v), (n)))
 # define RB_ALLOCV_N(type, v, n) \
-    ((type*)(ruby_xmalloc2_size((n), sizeof(type)) < RUBY_ALLOCV_LIMIT ? \
+    ((type*)(((size_t)(n) < RUBY_ALLOCV_LIMIT / sizeof(type)) ? \
 	     (RB_GC_GUARD(v) = 0, alloca((n) * sizeof(type))) : \
-	     rb_alloc_tmp_buffer(&(v), (n) * sizeof(type))))
+	     rb_alloc_tmp_buffer2(&(v), (n), sizeof(type))))
 #endif
 #define RB_ALLOCV_END(v) rb_free_tmp_buffer(&(v))
 
Index: ChangeLog
===================================================================
--- ChangeLog	(revision 54663)
+++ ChangeLog	(revision 54664)
@@ -1,3 +1,13 @@ https://github.com/ruby/ruby/blob/trunk/ChangeLog#L1
+Fri Apr 22 04:57:01 2016  NARUSE, Yui  <naruse@r...>
+
+	* gc.c (rb_alloc_tmp_buffer_with_count): added like xmalloc2 to
+	  avoid duplicated check of size.
+
+	* gc.c (ruby_xmalloc2): added to keep separate layers.
+
+	* include/ruby/ruby.h (rb_alloc_tmp_buffer2): added to check
+	  the size more statically.
+
 Fri Apr 22 04:54:40 2016  NARUSE, Yui  <naruse@r...>
 
 	* include/ruby/ruby.h (LIKELY): moved from internal.h.
Index: gc.c
===================================================================
--- gc.c	(revision 54663)
+++ gc.c	(revision 54664)
@@ -7850,6 +7850,12 @@ objspace_xfree(rb_objspace_t *objspace, https://github.com/ruby/ruby/blob/trunk/gc.c#L7850
     objspace_malloc_increase(objspace, ptr, 0, old_size, MEMOP_TYPE_FREE);
 }
 
+static void *
+ruby_xmalloc0(size_t size)
+{
+    return objspace_xmalloc0(&rb_objspace, size);
+}
+
 void *
 ruby_xmalloc(size_t size)
 {
@@ -7972,24 +7978,31 @@ ruby_mimfree(void *ptr) https://github.com/ruby/ruby/blob/trunk/gc.c#L7978
 }
 
 void *
-rb_alloc_tmp_buffer(volatile VALUE *store, long len)
+rb_alloc_tmp_buffer_with_count(volatile VALUE *store, size_t size, size_t cnt)
 {
     NODE *s;
-    long cnt;
     void *ptr;
 
-    if (len < 0 || (cnt = (long)roomof(len, sizeof(VALUE))) < 0) {
-	rb_raise(rb_eArgError, "negative buffer size (or size too big)");
-    }
-
     s = rb_node_newnode(NODE_ALLOCA, 0, 0, 0);
-    ptr = ruby_xmalloc(cnt * sizeof(VALUE));
+    ptr = ruby_xmalloc0(size);
     s->u1.value = (VALUE)ptr;
     s->u3.cnt = cnt;
     *store = (VALUE)s;
     return ptr;
 }
 
+void *
+rb_alloc_tmp_buffer(volatile VALUE *store, long len)
+{
+    long cnt;
+
+    if (len < 0 || (cnt = (long)roomof(len, sizeof(VALUE))) < 0) {
+	rb_raise(rb_eArgError, "negative buffer size (or size too big)");
+    }
+
+    return rb_alloc_tmp_buffer_with_count(store, len, cnt);
+}
+
 void
 rb_free_tmp_buffer(volatile VALUE *store)
 {

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

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