#!/usr/bin/env bash # vi: ft=sh # # © 2019 Konstantin Gredeskoul, Inc., All rights reserved. # MIT LICENSE # # ———————————————————————————————————————————————————————————————— # This script verifies that the current ruby (in PATH) is linked # with libjemalloc library for efficient memory utilization. # It works identically on Linux and Mac OSX. # # Ruby versions 2.5 and earlier had a simpler method, typically # running the following command and expecting the output to # contain something like '-ljemalloc -lm ... ' # # ruby -r rbconfig -e "puts RbConfig::CONFIG['LIBS']" # # Unfortunately, this method no longer works with Ruby 2.6 # and later, nor did it ever work with Linux. # # For this reason, the following script is provided to verify # if your Ruby is using jemalloc memory allocator or not. # # USAGE: # download the script into a file, then # chmod 755 ruby-jemalloc-check.sh # ./ruby-jemalloc-check.sh # # ———————————————————————————————————————————————————————————————— set +e export JM_Quiet=false export JM_Ruby=false export JM_Stats=false export ColorRed="\e[1;31m" export ColorGreen="\e[1;32m" export ColorYellow="\e[1;33m" export ColorBlue="\e[1;34m" export ColorReset="\e[0m" # prints the info about current version of ruby jm::ruby::report() { printf "Ruby version being tested:\n → ${ColorBlue}$(which ruby) ${ColorYellow}$(jm::ruby::detect)${ColorReset}\n" } # returns a string such as "/usr/local/bin/ruby 2.6.4 (x86darwin)" jm::ruby::detect() { local ruby_loc if [[ -n $(which rbenv) ]] ; then ruby_loc=$(rbenv versions | grep '*' | awk '{print $2}') [[ -n ${ruby_loc} ]] && ruby_loc="(rbenv) ${ruby_loc}" else ruby_loc="$(which ruby) $(ruby -e 'puts "#{RUBY_VERSION} (#{RUBY_PLATFORM})"')" fi printf "%s" "${ruby_loc}" } # prints jemalloc statistics if jemalloc is available jm::jemalloc::stats() { jm::jemalloc::detect-quiet || { printf "No Jemalloc was found for the curent ruby $(jm::ruby::detect)\n" return 1 } MALLOC_CONF=stats_print:true ruby -e "exit" 2>&1 | less -S } jm::jemalloc::detect-quiet() { MALLOC_CONF=stats_print:true ruby -e "exit" 2>&1 | grep -q "jemalloc statistics" return $? } jm::jemalloc::detect-loud() { jm::jemalloc::detect-quiet local code=$? local local_ruby=$(jm::ruby::detect) printf "${ColorBlue}Checking if ruby ${local_ruby} is linked with jemalloc... \n\n " if [[ ${code} -eq 0 ]]; then printf " ✅ ${ColorGreen} — jemalloc was detected.\n" else printf " 🚫 ${ColorRed} — jemalloc was not detected.\n" fi printf "${ColorReset}\n" return ${code} } usage() { printf " USAGE: $0 [ -q/--quiet ] [ -r/--ruby ] [ -s/--stats ] [ -h/--help ] DESCRIPTION: Determines whether the currently defined in the PATH ruby interpreter is linked with libjemalloc memory allocator. OPTIONS -q/--quiet Do not print output, exit with 1 if no jemalloc -r/--ruby Print which ruby is currently in the PATH -s/--stats Print the jemalloc stats -h/--help This page. " exit 0 } # Parse additional flags while :; do case $1 in -q|--quiet) shift export JM_Quiet=true ;; -r|--ruby) shift export JM_Ruby=true ;; -s|--stats) shift jm::jemalloc::stats exit $? ;; -h|-\?|--help) shift usage exit 0 ;; --) # End of all options; anything after will be passed to the action function shift break ;; *) break ;; esac done ${JM_Ruby} && { jm::ruby::report; exit 0; } ${JM_Quiet} && { jm::jemalloc::detect-quiet; code=$?; exit ${code}; } jm::jemalloc::detect-loud