From da4329ca1e3609607c3c2a702005e5574fbc711a Mon Sep 17 00:00:00 2001 From: shyouhei Date: Tue, 12 Dec 2017 11:56:25 +0000 Subject: Add uplevel keyword to Kernel#warn and use it If uplevel keyword is given, the warning message is prepended with caller file and line information and the string "warning: ". The use of the uplevel keyword makes Kernel#warn format output similar to how rb_warn formats output. This patch modifies net/ftp and net/imap to use Kernel#warn instead of $stderr.puts or $stderr.printf, since they are used for printing warnings. This makes lib/cgi/core and tempfile use $stderr.puts instead of warn for debug logging, since they are used for debug printing and not for warning. This does not modify bundler, rubygems, or rdoc, as those are maintained outside of ruby and probably wish to remain backwards compatible with older ruby versions. rb_warn_m code is originally from nobu, but I've changed it so that it only includes the path and lineno from uplevel (not the method), and also prepends the string "warning: ", to make it more similar to rb_warn. From: Jeremy Evans code@jeremyevans.net Signed-off-by: Urabe Shyouhei shyouhei@ruby-lang.org git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@61155 b2dd03c8-39d4-4d8f-98ff-823fe69b080e --- error.c | 35 ++++++++++++++++++++++++++++++++--- 1 file changed, 32 insertions(+), 3 deletions(-) (limited to 'error.c') diff --git a/error.c b/error.c index 4b921f99ff..075cb1dfb1 100644 --- a/error.c +++ b/error.c @@ -327,10 +327,39 @@ warning_write(int argc, VALUE *argv, VALUE buf) static VALUE rb_warn_m(int argc, VALUE *argv, VALUE exc) { - if (!NIL_P(ruby_verbose) && argc > 0) { + VALUE opts, uplevel = Qnil; + + if (!NIL_P(ruby_verbose) && argc > 0 && + (argc = rb_scan_args(argc, argv, "*:", NULL, &opts)) > 0) { VALUE str = argv[0]; - if (argc > 1 || !end_with_asciichar(str, '\n')) { - str = rb_str_tmp_new(0); + if (!NIL_P(opts)) { + static ID kwds[1]; + if (!kwds[0]) { + CONST_ID(kwds[0], "uplevel"); + } + rb_get_kwargs(opts, kwds, 0, 1, &uplevel); + if (uplevel == Qundef) { + uplevel = Qnil; + } + else if (!NIL_P(uplevel)) { + uplevel = LONG2NUM((long)NUM2ULONG(uplevel) + 1); + uplevel = rb_vm_thread_backtrace_locations(1, &uplevel, GET_THREAD()->self); + if (!NIL_P(uplevel)) { + uplevel = rb_ary_entry(uplevel, 0); + } + } + } + if (argc > 1 || !NIL_P(uplevel) || !end_with_asciichar(str, '\n')) { + if (NIL_P(uplevel)) { + str = rb_str_tmp_new(0); + } + else { + VALUE path; + path = rb_funcall(uplevel, rb_intern("path"), 0); + str = rb_sprintf("%s:%li: warning: ", + rb_string_value_ptr(&path), + NUM2LONG(rb_funcall(uplevel, rb_intern("lineno"), 0))); + } RBASIC_SET_CLASS(str, rb_cWarningBuffer); rb_io_puts(argc, argv, str); RBASIC_SET_CLASS(str, rb_cString); -- cgit v1.2.3