diff options
Diffstat (limited to 'lib')
-rwxr-xr-x | lib/rubygems/core_ext/kernel_warn.rb | 45 | ||||
-rw-r--r-- | lib/rubygems/ext/builder.rb | 8 | ||||
-rw-r--r-- | lib/rubygems/ext/ext_conf_builder.rb | 5 | ||||
-rw-r--r-- | lib/rubygems/ext/rake_builder.rb | 21 | ||||
-rw-r--r-- | lib/rubygems/installer.rb | 21 | ||||
-rw-r--r-- | lib/rubygems/test_case.rb | 21 |
6 files changed, 83 insertions, 38 deletions
diff --git a/lib/rubygems/core_ext/kernel_warn.rb b/lib/rubygems/core_ext/kernel_warn.rb index 319fdfe606..3e531441ed 100755 --- a/lib/rubygems/core_ext/kernel_warn.rb +++ b/lib/rubygems/core_ext/kernel_warn.rb @@ -1,28 +1,45 @@ # frozen_string_literal: true +# `uplevel` keyword argument of Kernel#warn is available since ruby 2.5. if RUBY_VERSION >= "2.5" + module Kernel - path = "#{__dir__}/" + path = "#{__dir__}/" # Frames to be skipped start with this path. + + # Suppress "method redefined" warning original_warn = instance_method(:warn) Module.new {define_method(:warn, original_warn)} + original_warn = method(:warn) module_function define_method(:warn) {|*messages, uplevel: nil| - if uplevel - uplevel, = [uplevel].pack("l!").unpack("l!") - if uplevel >= 0 - start = 0 - begin - loc, = caller_locations(start, 1) - break start += uplevel unless loc - start += 1 - end while (loc.path.start_with?(path) or (uplevel -= 1) >= 0) - uplevel = start + unless uplevel + return original_warn.call(*messages) + end + + # Ensure `uplevel` fits a `long` + uplevel, = [uplevel].pack("l!").unpack("l!") + + if uplevel >= 0 + start = 0 + while uplevel >= 0 + loc, = caller_locations(start, 1) + unless loc + # No more backtrace + start += uplevel + break + end + + start += 1 + + unless loc.path.start_with?(path) + # Non-rubygems frames + uplevel -= 1 + end end - original_warn.call(*messages, uplevel: uplevel) - else - original_warn.call(*messages) + uplevel = start end + original_warn.call(*messages, uplevel: uplevel) } end end diff --git a/lib/rubygems/ext/builder.rb b/lib/rubygems/ext/builder.rb index b3b9033962..93be458cd8 100644 --- a/lib/rubygems/ext/builder.rb +++ b/lib/rubygems/ext/builder.rb @@ -56,6 +56,7 @@ class Gem::Ext::Builder end def self.redirector + warn "#{caller[0]}: Use IO.popen(..., err: [:child, :out])" '2>&1' end @@ -63,7 +64,6 @@ class Gem::Ext::Builder verbose = Gem.configuration.really_verbose begin - # TODO use Process.spawn when ruby 1.8 support is dropped. rubygems_gemdeps, ENV['RUBYGEMS_GEMDEPS'] = ENV['RUBYGEMS_GEMDEPS'], nil if verbose puts("current directory: #{Dir.pwd}") @@ -71,9 +71,11 @@ class Gem::Ext::Builder system(command) else results << "current directory: #{Dir.pwd}" - results << command - results << `#{command} #{redirector}` + results << (command.respond_to?(:shelljoin) ? command.shelljoin : command) + results << IO.popen(command, "r", err: [:child, :out], &:read) end + rescue => error + raise Gem::InstallError, "#{command_name || class_name} failed#{error.message}" ensure ENV['RUBYGEMS_GEMDEPS'] = rubygems_gemdeps end diff --git a/lib/rubygems/ext/ext_conf_builder.rb b/lib/rubygems/ext/ext_conf_builder.rb index 18e300d8c2..97bb789fb8 100644 --- a/lib/rubygems/ext/ext_conf_builder.rb +++ b/lib/rubygems/ext/ext_conf_builder.rb @@ -7,6 +7,7 @@ require 'fileutils' require 'tempfile' +require 'shellwords' class Gem::Ext::ExtConfBuilder < Gem::Ext::Builder FileEntry = FileUtils::Entry_ # :nodoc: @@ -38,7 +39,9 @@ class Gem::Ext::ExtConfBuilder < Gem::Ext::Builder destdir = ENV["DESTDIR"] begin - cmd = [Gem.ruby, "-I", File.expand_path("../../..", __FILE__), "-r", get_relative_path(siteconf.path), File.basename(extension), *args].join ' ' + cmd = Gem.ruby.shellsplit << "-I" << File.expand_path("../../..", __FILE__) << + "-r" << get_relative_path(siteconf.path) << File.basename(extension) + cmd.push(*args) begin run cmd, results diff --git a/lib/rubygems/ext/rake_builder.rb b/lib/rubygems/ext/rake_builder.rb index 890803aaef..f41e5618dc 100644 --- a/lib/rubygems/ext/rake_builder.rb +++ b/lib/rubygems/ext/rake_builder.rb @@ -11,22 +11,23 @@ class Gem::Ext::RakeBuilder < Gem::Ext::Builder def self.build(extension, dest_path, results, args=[], lib_dir=nil) if File.basename(extension) =~ /mkrf_conf/i then - cmd = "#{Gem.ruby} #{File.basename extension}".dup - cmd << " #{args.join " "}" unless args.empty? - run cmd, results + run([Gem.ruby, File.basename(extension), *args], results) end rake = ENV['rake'] - rake ||= begin - "#{Gem.ruby} -rrubygems #{Gem.bin_path('rake', 'rake')}" - rescue Gem::Exception - end - - rake ||= Gem.default_exec_format % 'rake' + if rake + rake = rake.shellsplit + else + begin + rake = [Gem.ruby, "-rrubygems", Gem.bin_path('rake', 'rake')] + rescue Gem::Exception + rake = [Gem.default_exec_format % 'rake'] + end + end rake_args = ["RUBYARCHDIR=#{dest_path}", "RUBYLIBDIR=#{dest_path}", *args] - run "#{rake} #{rake_args.shelljoin}", results + run(rake + rake_args, results) results end diff --git a/lib/rubygems/installer.rb b/lib/rubygems/installer.rb index 298a7053c7..7587c259dc 100644 --- a/lib/rubygems/installer.rb +++ b/lib/rubygems/installer.rb @@ -771,33 +771,38 @@ TEXT # return the stub script text used to launch the true Ruby script def windows_stub_script(bindir, bin_file_name) - rb_bindir = RbConfig::CONFIG["bindir"] - # All comparisons should be case insensitive - if bindir.downcase == rb_bindir.downcase + rb_config = RbConfig::CONFIG + rb_topdir = RbConfig::TOPDIR || File.dirname(rb_config["bindir"]) + + # get ruby executable file name from RbConfig + ruby_exe = "#{rb_config['RUBY_INSTALL_NAME']}#{rb_config['EXEEXT']}" + ruby_exe = "ruby.exe" if ruby_exe.empty? + + if File.exist?(File.join bindir, ruby_exe) # stub & ruby.exe withing same folder. Portable <<-TEXT @ECHO OFF @"%~dp0ruby.exe" "%~dpn0" %* TEXT - elsif bindir.downcase.start_with?((RbConfig::TOPDIR || File.dirname(rb_bindir)).downcase) - # stub within ruby folder, but not standard bin. Not portable + elsif bindir.downcase.start_with? rb_topdir.downcase + # stub within ruby folder, but not standard bin. Portable require 'pathname' from = Pathname.new bindir - to = Pathname.new rb_bindir + to = Pathname.new "#{rb_topdir}/bin" rel = to.relative_path_from from <<-TEXT @ECHO OFF @"%~dp0#{rel}/ruby.exe" "%~dpn0" %* TEXT else - # outside ruby folder, maybe -user-install or bundler. Portable + # outside ruby folder, maybe -user-install or bundler. Portable, but ruby + # is dependent on PATH <<-TEXT @ECHO OFF @ruby.exe "%~dpn0" %* TEXT end end - ## # Builds extensions. Valid types of extensions are extconf.rb files, # configure scripts and rakefiles or mkrf_conf files. diff --git a/lib/rubygems/test_case.rb b/lib/rubygems/test_case.rb index 718571ea57..fc9456709f 100644 --- a/lib/rubygems/test_case.rb +++ b/lib/rubygems/test_case.rb @@ -1319,9 +1319,26 @@ Also, a list: end end + class << self + # :nodoc: + ## + # Return the join path, with escaping backticks, dollars, and + # double-quotes. Unlike `shellescape`, equal-sign is not escaped. + private + def escape_path(*path) + path = File.join(*path) + if %r'\A[-+:/=@,.\w]+\z' =~ path + path + else + "\"#{path.gsub(/[`$"]/, '\\&')}\"" + end + end + end + @@ruby = rubybin - @@good_rake = "#{rubybin} \"#{File.expand_path('../../../test/rubygems/good_rake.rb', __FILE__)}\"" - @@bad_rake = "#{rubybin} \"#{File.expand_path('../../../test/rubygems/bad_rake.rb', __FILE__)}\"" + gempath = File.expand_path('../../../test/rubygems', __FILE__) + @@good_rake = "#{rubybin} #{escape_path(gempath, 'good_rake.rb')}" + @@bad_rake = "#{rubybin} #{escape_path(gempath, 'bad_rake.rb')}" ## # Construct a new Gem::Dependency. |