Le Wed, Aug 01, 2018 at 06:42:30PM +0200, Bram Moolenaar a écrit :
Patch 8.1.0232
Problem: Ruby error does not include backtrace.
Solution: Add an error backtrace. (Masataka Pocke Kuwabara, closes #3267)
Files: src/if_ruby.c
[...]
+ bt = rb_funcallv(error, rb_intern("backtrace"), 0, 0);
+ for (i = 0; i < RARRAY_LEN(bt); i++)
+ msg_attr((char_u *)RSTRING_PTR(RARRAY_AREF(bt, i)), attr);
It is safe to use RARRAY_AREF() here?
A quick (and not testted...) patch to illustrate the problem.
diff --git a/src/if_ruby.c b/src/if_ruby.c
--- a/src/if_ruby.c
+++ b/src/if_ruby.c
@@ -946,7 +946,7 @@ static int ensure_ruby_initialized(void)
return ruby_initialized;
}
-static void error_print(int state)
+static VALUE _error_print(VALUE _state)
{
#ifndef DYNAMIC_RUBY
#if !(defined(RUBY_VERSION) && RUBY_VERSION >= 19) \
@@ -961,6 +961,7 @@ static void error_print(int state)
int attr;
char buff[BUFSIZ];
long i;
+ int state = (int)_state;
#define TAG_RETURN 0x1
#define TAG_BREAK 0x2
@@ -1018,12 +1019,22 @@ static void error_print(int state)
attr = syn_name2attr((char_u *)"Error");
# ifdef RUBY21_OR_LATER
bt = rb_funcallv(error, rb_intern("backtrace"), 0, 0);
+ Check_Type(bt, T_ARRAY); /* Can be nil in real world ? */
for (i = 0; i < RARRAY_LEN(bt); i++)
- msg_attr((char_u *)RSTRING_PTR(RARRAY_AREF(bt, i)), attr);
+ {
+ VALUE p = RARRAY_AREF(bt, i);
+ Check_Type(p, T_STRING);
+ msg_attr((char_u *)RSTRING_PTR(p), attr);
+ }
# else
bt = rb_funcall2(error, rb_intern("backtrace"), 0, 0);
+ Check_Type(bt, T_ARRAY);
for (i = 0; i < RARRAY_LEN(bt); i++)
- msg_attr((char_u *)RSTRING_PTR(RARRAY_PTR(bt)[i]), attr);
+ {
+ VALUE p = RARRAY_PTR(bt)[i];
+ Check_Type(p, T_STRING);
+ msg_attr((char_u *)RSTRING_PTR(p), attr);
+ }
# endif
break;
default:
@@ -1031,6 +1042,15 @@ static void error_print(int state)
EMSG(buff);
break;
}
+ return Qtrue;
+}
+
+static void error_print(int state)
+{
+ int curstate;
+ rb_protect(_error_print, (VALUE)state, &curstate);
+ if (curstate)
+ EMSG("Call stack not available...");
}
static VALUE vim_message(VALUE self UNUSED, VALUE str)
diff --git a/src/testdir/test_ruby.vim b/src/testdir/test_ruby.vim
--- a/src/testdir/test_ruby.vim
+++ b/src/testdir/test_ruby.vim
@@ -364,3 +364,16 @@ func Test_p()
let messages = split(execute('message'), "\n")
call assert_equal('"Just a test"', messages[-1])
endfunc
+
+func Test_broke_exc()
+ ruby <<--ruby
+ $_ = [
+ Class.new(Exception) { def backtrace() raise 'Quoi ?' end },
+ Class.new(Exception) { def backtrace() 42 end },
+ Class.new(Exception) { def backtrace() 0..42.to_a end },
+ ]
+--ruby
+ for i in range(2)
+ call assert_fails('ruby raise $_.pop.new', '...')
+ endfor
+endfunc
Regards.
Damien
--
--
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php
---
You received this message because you are subscribed to the Google Groups "vim_dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.