diff --git a/Library/Homebrew/brew.sh b/Library/Homebrew/brew.sh index e2303765d3..d6bc2450f8 100644 --- a/Library/Homebrew/brew.sh +++ b/Library/Homebrew/brew.sh @@ -897,9 +897,6 @@ then unset HOMEBREW_AUTO_UPDATE_CASK_TAP fi -# Disable Ruby options we don't need. -export HOMEBREW_RUBY_DISABLE_OPTIONS="--disable=gems,rubyopt" - if [[ -z "${HOMEBREW_RUBY_WARNINGS}" ]] then export HOMEBREW_RUBY_WARNINGS="-W1" diff --git a/Library/Homebrew/cmd/setup-ruby.sh b/Library/Homebrew/cmd/setup-ruby.sh index e39d893909..7c65cf4824 100644 --- a/Library/Homebrew/cmd/setup-ruby.sh +++ b/Library/Homebrew/cmd/setup-ruby.sh @@ -5,9 +5,7 @@ #: command. #: -# HOMEBREW_LIBRARY is from the user environment. -# HOMEBREW_RUBY_PATH is set by utils/ruby.sh -# RUBY_DISABLE_OPTIONS is set by brew.sh +# HOMEBREW_LIBRARY is set by brew.sh # HOMEBREW_BREW_FILE is set by extend/ENV/super.rb # shellcheck disable=SC2154 homebrew-setup-ruby() { @@ -37,13 +35,7 @@ homebrew-setup-ruby() { fi fi - GEM_VERSION="$("${HOMEBREW_RUBY_PATH}" "${HOMEBREW_RUBY_DISABLE_OPTIONS}" /dev/stdin <<<'require "rbconfig"; puts RbConfig::CONFIG["ruby_version"]')" - echo "${GEM_VERSION}" - GEM_HOME="${HOMEBREW_LIBRARY}/Homebrew/vendor/bundle/ruby/${GEM_VERSION}" - BUNDLE_GEMFILE="${HOMEBREW_LIBRARY}/Homebrew/Gemfile" - - export GEM_HOME - export BUNDLE_GEMFILE + setup-gem-home-bundle-gemfile if ! bundle check &>/dev/null then diff --git a/Library/Homebrew/dev-cmd/rubocop.sh b/Library/Homebrew/dev-cmd/rubocop.sh index db26803b15..6c30ac10a9 100644 --- a/Library/Homebrew/dev-cmd/rubocop.sh +++ b/Library/Homebrew/dev-cmd/rubocop.sh @@ -4,25 +4,19 @@ # HOMEBREW_LIBRARY is from the user environment. # HOMEBREW_RUBY_PATH is set by utils/ruby.sh -# RUBY_DISABLE_OPTIONS is set by brew.sh # HOMEBREW_BREW_FILE is set by extend/ENV/super.rb # shellcheck disable=SC2154 homebrew-rubocop() { source "${HOMEBREW_LIBRARY}/Homebrew/utils/ruby.sh" setup-ruby-path + setup-gem-home-bundle-gemfile - GEM_VERSION="$("${HOMEBREW_RUBY_PATH}" "${HOMEBREW_RUBY_DISABLE_OPTIONS}" /dev/stdin <<<'require "rbconfig"; puts RbConfig::CONFIG["ruby_version"]')" - GEM_HOME="${HOMEBREW_LIBRARY}/Homebrew/vendor/bundle/ruby/${GEM_VERSION}" - BUNDLE_GEMFILE="${HOMEBREW_LIBRARY}/Homebrew/Gemfile" BUNDLE_WITH="style" - - export GEM_HOME - export BUNDLE_GEMFILE export BUNDLE_WITH if ! bundle check &>/dev/null then - "${HOMEBREW_BREW_FILE}" install-bundler-gems --add-groups=style + "${HOMEBREW_BREW_FILE}" install-bundler-gems --add-groups="${BUNDLE_WITH}" fi export PATH="${GEM_HOME}/bin:${PATH}" diff --git a/Library/Homebrew/utils/lock.sh b/Library/Homebrew/utils/lock.sh index 545845b910..17e43e00e6 100644 --- a/Library/Homebrew/utils/lock.sh +++ b/Library/Homebrew/utils/lock.sh @@ -1,6 +1,7 @@ # create a lock using `flock(2)`. A name is required as first argument. # the lock will be automatically unlocked when the shell process quits. # Noted due to the fixed FD, a shell process can only create one lock. +# HOMEBREW_LIBRARY is by brew.sh # HOMEBREW_PREFIX is set by extend/ENV/super.rb # shellcheck disable=SC2154 lock() { @@ -16,7 +17,7 @@ Fix permissions by running: sudo chown -R ${USER-\$(whoami)} ${HOMEBREW_PREFIX}/var/homebrew EOS fi - # 200 is the file descriptor used in the lock. + # 200 is the file descriptor (FD) used in the lock. # This FD should be used exclusively for lock purpose. # Any value except 0(stdin), 1(stdout) and 2(stderr) can do the job. # Noted, FD is unique per process but it will be shared to subprocess. @@ -37,26 +38,25 @@ EOS } _create_lock() { - local lock_fd="$1" + local lock_file_descriptor="$1" local name="$2" local ruby="/usr/bin/ruby" local python="/usr/bin/python" [[ -x "${ruby}" ]] || ruby="$(type -P ruby)" [[ -x "${python}" ]] || python="$(type -P python)" - # Use /dev/stdin, otherwise Ruby can error if uid != euid. - # Can't use "-" as that's also blocked: - # https://github.com/ruby/ruby/blob/e51435177e88fc845528dff7cf2bc2b75dd36144/ruby.c#L2333-L2335 - if [[ -x "${ruby}" ]] && "${ruby}" /dev/stdin <<<"exit(RUBY_VERSION >= '1.8.7')" + local utils_lock_sh="${HOMEBREW_LIBRARY}/Homebrew/utils/lock_sh" + local oldest_ruby_with_flock="1.8.7" + if [[ -x "${ruby}" ]] && "${ruby}" "${utils_lock_sh}/ruby_check_version.rb" "${oldest_ruby_with_flock}" then - "${ruby}" /dev/stdin <<<"File.new(${lock_fd}).flock(File::LOCK_EX | File::LOCK_NB) || exit(1)" + "${ruby}" "${utils_lock_sh}/ruby_lock_file_descriptor.rb" "${lock_file_descriptor}" + elif [[ -x "$(type -P flock)" ]] + then + flock -n "${lock_file_descriptor}" elif [[ -x "${python}" ]] then "${python}" -c "import fcntl; fcntl.flock(${lock_fd}, fcntl.LOCK_EX | fcntl.LOCK_NB)" - elif [[ -x "$(type -P flock)" ]] - then - flock -n "${lock_fd}" else - onoe "Cannot create ${name} lock, please avoid running Homebrew in parallel." + onoe "Cannot create ${name} lock due to missing/too old ruby/flock/python, please avoid running Homebrew in parallel." fi } diff --git a/Library/Homebrew/utils/lock_sh/ruby_check_version.rb b/Library/Homebrew/utils/lock_sh/ruby_check_version.rb new file mode 100644 index 0000000000..c6d11b5a1e --- /dev/null +++ b/Library/Homebrew/utils/lock_sh/ruby_check_version.rb @@ -0,0 +1,5 @@ +# typed: strict +# frozen_string_literal: true + +ruby_version_to_check = ARGV.first +exit(ruby_version_to_check < RUBY_VERSION) diff --git a/Library/Homebrew/utils/lock_sh/ruby_lock_file_descriptor.rb b/Library/Homebrew/utils/lock_sh/ruby_lock_file_descriptor.rb new file mode 100644 index 0000000000..d271162224 --- /dev/null +++ b/Library/Homebrew/utils/lock_sh/ruby_lock_file_descriptor.rb @@ -0,0 +1,6 @@ +# typed: strict +# frozen_string_literal: true + +file_descriptor = ARGV.first.to_i +file = File.new(file_descriptor) +file.flock(File::LOCK_EX | File::LOCK_NB) || exit(1) diff --git a/Library/Homebrew/utils/ruby.sh b/Library/Homebrew/utils/ruby.sh index 2e9e090082..5fca54f1d8 100644 --- a/Library/Homebrew/utils/ruby.sh +++ b/Library/Homebrew/utils/ruby.sh @@ -2,6 +2,9 @@ # When bumping to a new major/minor version, also update the bounds in the Gemfile export HOMEBREW_REQUIRED_RUBY_VERSION=3.1 +# Disable Ruby options we don't need. +export HOMEBREW_RUBY_DISABLE_OPTIONS="--disable=gems,rubyopt" + # HOMEBREW_LIBRARY is from the user environment # shellcheck disable=SC2154 test_ruby() { @@ -145,3 +148,12 @@ If there's no Homebrew Portable Ruby available for your processor: export HOMEBREW_RUBY_PATH [[ -n "${HOMEBREW_LINUX}" && -n "${TERMINFO_DIRS}" ]] && export TERMINFO_DIRS } + +setup-gem-home-bundle-gemfile() { + GEM_VERSION="$("${HOMEBREW_RUBY_PATH}" "${HOMEBREW_RUBY_DISABLE_OPTIONS}" "${HOMEBREW_LIBRARY}/Homebrew/utils/ruby_sh/ruby_gem_version.rb")" + GEM_HOME="${HOMEBREW_LIBRARY}/Homebrew/vendor/bundle/ruby/${GEM_VERSION}" + BUNDLE_GEMFILE="${HOMEBREW_LIBRARY}/Homebrew/Gemfile" + + export GEM_HOME + export BUNDLE_GEMFILE +} diff --git a/Library/Homebrew/utils/ruby_sh/ruby_gem_version.rb b/Library/Homebrew/utils/ruby_sh/ruby_gem_version.rb new file mode 100644 index 0000000000..a8538eabf1 --- /dev/null +++ b/Library/Homebrew/utils/ruby_sh/ruby_gem_version.rb @@ -0,0 +1,5 @@ +# typed: strict +# frozen_string_literal: true + +require "rbconfig" +puts RbConfig::CONFIG["ruby_version"]