Untitled - tombo.in

Transcription

Untitled - tombo.in
rvm
1. rvm
1.1. HACKING.md
# How to hack on RVM
## Fetch and try test suite on your rvm installation
Note that the [`vboxtest`](docs/vm_tests.md) approach is now outdated.
It's better to use the
[`rvm-test`](https://github.com/wayneeseguin/rvm-test/) test suite
which lives in a separate git submodule. (It's separate in order to
allow reuse when hacking on rvm2).
$ git submodule init
$ git submodule update
# Register the rvm-test submodule in .git/config
# Check out the rvm-test submodule
Now read [`rvm-test`'s
README.md](https://github.com/wayneeseguin/rvm-test/blob/master/README.md)
and follow those instructions to make sure you can successfully run
the tests (you will need rvm already installed).
## Set up test installation of rvm
You need a test rvm install to run the test suite against:
$
$
$
$
$
git clone https://github.com/wayneeseguin/rvm
export rvm_path=~/path/to/rvm/test/install
export rvm_bin_path=$rvm_path/bin
cd rvm
./install
# or your own github fork
# choose a path here
This will create a test installation of rvm in
`~/path/to/rvm/test/install`, and as long as `$rvm_path` points to it,
this will be used when running the tests. This means you can safely
break the test installation without risking breaking your main rvm
installation.
If you want to do manual testing on the CLI against this test installation,
you also need to do:
$ rvm reload
## Hacking RVM via TDD (Test-Driven Development)
First write a test for the behaviour you expect. For details on how
to write new tests, see [`rvm-test`'s
README.md](https://github.com/wayneeseguin/rvm-test/blob/master/README.md).
Then run the test:
$ tf --text rvm-test/fast/foo_comment_test.sh
It should fail.
Now repeat the following steps until the test passes:
1. hack the changes in your rvm src tree
2. run `./install`
3. re-run the test (you can also manually test via rvm commands on the CLI)
Now `git commit`, `git push` to your github fork, then issue a pull
request, and if it is accepted then your place in hacker heaven is
secured.
## Getting help
If you get stuck, you should ask on `#rvm-test` or `#rvm` on Freenode.
1.2. install
scripts/install
1.3. README.txt
README
1.4. .gitmodules
[submodule "rvm-test"]
path = rvm-test
url = git://github.com/wayneeseguin/rvm-test.git
1.5. LICENCE
Copyright (c) 2009-2011 Wayne E. Seguin
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
1.6. README.rdoc
README
1.7. .gems
travis-lint
1.8. VERSION
1.14.10
1.9. .travis.yml
language: ruby
rvm:
- 1.9.3
install: gem install tf
before_script:
- rvm alias delete default
- hash -r
- ./install
- rvm-smile
- git submodule init
- git submodule update
script: tf --text rvm-test/fast/*
notifications:
irc:
channels:
- "irc.freenode.org#rvm-test"
- "irc.freenode.org#rvm"
email:
recipients:
- [email protected]
- [email protected]
on_failure: change
1.10. History.txt
= RVM History, thanks be to Git.
== Release 1.7.1
* Remove playful jab.
* Merge pull request #369 from thinkerbot/vbox-test
* added vm test scaffold
* Merge pull request #368 from benmoss/patch-1
* Fix some typos
* I have to stop doing so many things at once. ... Nah... who am I fooling? :)
== Release 1.7.1
* Merge branch 'master' of git.overnothing.com:rvm
* Rake is now stable at 0.9.2, good default there.
* Perhaps this will help solidus-river.
* Merge pull request #366 from deryldoucette/master
* Made NOTE: part green as well just to ensure people see it.
* Fixed and color coded per-project rvmrc example.
* Added information to 'rvm notes' about the >= 1.7.0 per-project .rvmrc toggle.
* Account for Lion default clang in packages also.
* Bugfix for zsh, array indexing differences are always good for a certain kind of chuckle.
* Turns out we already had a History.txt file :)
* Merge pull request #365 from burningTyger/rdoc
* rdoc instead of markdown
* space cadet.
* The redundency bothered me.
* On long reflection, 90% of the issues I have seen are to do with rvm_path setting. If you are root, /usr/local/rvm If you
are a user, $HOME/.rvm
== Release 1.7.0
* Since this is not read anyway, I might as well have some fun with it!
* Default rvm_project_rvmrc to off, set rvm_project_rvmrc=1 in ~/.rvmrc to enable. Oh wow, you mean you could toggle it???
Yes. Always could. Wow I should have asked!! Yes... yes you should have... Amazing how much you learn by simply asking a
question...
* Added missing example.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* RVM History, thanks be to Git.
* Merge pull request #364 from jfredett/master
* fix typo (doubled 'bison') in arch bootstrap script and in script/notes
* Merge pull request #363 from aghecht/master
* Adding missing shell functions
* Merge pull request #362 from ognevsky/fix-typo-in-implode
* Fixed typo in implode
* Correcting install messages.
* fix local arrays in trusting
* fix trusting on zsh
* Merge pull request #361 from zaadjis/master
* Fixed untrusting rvmrcs.
* Copy paste can get you into trouble sometimes ;)
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Swiped md5 code from BDSM
* Merge pull request #359 from agibralter/master
* Allow hooks directory or hooks to be symlinked.
* Merge pull request #358 from chrismealy/master
* Added automake (to get aclocal) to dependencies for Ubuntu.
* Merge pull request #357 from tabletcorry/master
* Merge branch 'master' of github.com:wayneeseguin/rvm
* prevent duplicate suffixing
* cleanup.
* Cleanly return in case of not in a git repository tree.
* Add a check to FQ rvm_path
* Merge pull request #356 from dsedivec/master
* Allow irb switches to set the prompt mode
* Merge pull request #354 from lribeiro/master
* Merge pull request #355 from ncreuschling/master
* removed duplicate dependency from installation notes
* we dont need to depend ant dist to build jruby, ant jar is enough and a lot faster
* Merge pull request #353 from MagLev/MagLev-26355
* do not require double -- after --name
* do not pass args before -* Merge branch 'master' of github.com:wayneeseguin/rvm
* do not pass args before -* Updated to MagLev-26355
* Merge pull request #352 from meqif/master
* Fixed zsh bug when glob_subst is set.
* use a local for the file looping over.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Added popd hijack.
* Merge pull request #351 from goncalossilva/master
* added gcdata patch for 1.9.3-preview1
* added gcdata patch for 1.9.2-p290
* Merge branch 'master' of github.com:wayneeseguin/rvm
* cleaning mri detection for other rubies
* Merge pull request #349 from deryldoucette/master
* remove test output
* manual printf as find not allways supports it
* fix detection mri rubies
* Some cli cleanup.
* Fixed errant help message. Was displaying 'rvm package' rather than 'rvm pkg' as it should.
* flipNzBit!
* Merge pull request #347 from mblair/master
* so it's like the others
* tyop.
* Really? Homebrew? Have another...
== Release 1.6.32
* Ruby 1.9.3-preview1 is now default 1.9.3
* Merge pull request #346 from amarshall/rbx-1.2.4
* Rubinius 1.2.4
* Merge branch 'master' of github.com:wayneeseguin/rvm
* fix --no-tcmalloc on OSX when user provided options
* Initial groundwork for "rvm group" feature, untested
* Merge pull request #345 from tricknotes/master
* Changed package to pkg on README
* make rbx work
* Merge pull request #344 from tsykoduk/master
* Merge branch 'master' of github.com:wayneeseguin/rvm
* fix bunzip2 error
* changed package to pkg on help text to correctly reflect real command
== Release 1.6.31
* git it done man, git it done.
* NO Effin Comment. I am with @joedamato on this one.
* Allow 1.9 in dependency check for Rubinius, requiring MRI.
== Release 1.6.30
* RubyGems 1.8.6 as default, w00t!!!
== Release 1.6.29
* claening
* restore jruby hook code, it is already disabled by default
* Merge branch 'master' of github.com:wayneeseguin/rvm
* no default jruby/ng on install, persist hooks x flag on install
* make 1.9.3-head working
* fix reading db
* Dismount.
== Release 1.6.28
* "rvm refresh ..." => "rvm reinstall" as suggested by v0n
* Feature: rvm refresh 1.9.2 ~ equivalent to rvm remove 1.9.2 ; rvm install 1.9.2
== Release 1.6.27
* Removed ebuilds.
* Also set CC on Darwin for 1.9 Rubies, for now.
* Updated ebuild for latest release.
== Release 1.6.26
* export CC="/usr/bin/gcc-4.2" if darwin11
* Merge pull request #343 from telemachus/lion
* Add a note/warning about gcc vs llvm on Lion
* Merge branch 'master' of github.com:wayneeseguin/rvm
* fix installer to not make jruby hook +x when it was -x once
* No comment.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* improved jruby support, allow to set per project options (in .rvmrc)
* Merge pull request #342 from MagLev/MagLev-26231
* Updated to MagLev-26231
* update support for ubuntu
* Merge pull request #341 from anl/master
* Merge remote-tracking branch 'rvm/master'
* Adjusted logic.
* Merge pull request #340 from joshuacronemeyer/master
* Merge remote branch 'upstream/master'
* change fetch script to account for the fact that curl wasn't giving an error when it got a 404.
case use -f switch to ensure it.
* Merge pull request #339 from psanford/fix_global_rvm_path
* Fix "grep: Invalid range end" messages on FreeBSD.
* Fixed rvm.sh setting path for global installs.
* Fix FreeBSD "pw groupadd" syntax.
* Merge pull request #337 from MagLev/MagLev-26197
* Wrestling the ZSH beastiality beast.
* Updated to MagLev-26197
* Fixed incorrect formatting and inconsistency.
* Adjusted testing for teardown.
* Merge pull request #321 from darren-fhf/master
* Bugfix in rvmrc generator.
* Updated ebuild for latest release.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* fix after
== Release 1.6.25
* Merge branch 'master' of github.com:wayneeseguin/rvm
* fix removing jruby functions
* jruby hook enabled by default
* note about after_use hooks
* fix hooks installation
* Let us not forget about zsh :)
* after_use hooks must be executable to be turned on now.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Added rubygems diretory.
* Fixing unsets.
* Merge pull request #336 from jzacsh/master
* Merge branches 'master' and 'master' of git://github.com/wayneeseguin/rvm
* Fixing bug introduced in 203257a by pull request #333, case-modification is a bash4ism [1].
* More .gitignore files.
* pkg
* pkg!!!
fetch should fail in that
* hooksssssssssssssssss
* Minor tweaking of awesome work by mpapis.
* Merge pull request #335 from mpapis/ng
* fix after_use hooks, add jruby --ngserver support
* Good cop. Bad cop.
* Why... whatever could I be up to?
* Merge branch 'master' of github.com:wayneeseguin/rvm
* package :)
* Merge branch 'master' of github.com:wayneeseguin/rvm
* pkg :)
* Merge pull request #333 from jzacsh/master
* Missed one.
* Bombs away!!!
* pull #333: implified logic for user simply hitting [enter] key.
* using case in place of if for possible "yes" or "no" in user-response.
* taking advantage of the printf that was already there; a whee-bit nicer.
* making sure that the while condition actually make sense. utilizing boolean-ish~ness with bash arithmetic, ease of
reasdability. lower-casing response immediately.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge pull request #334 from t-nagamatsu/patch-1
* Updated ebuild for latest release.
* Hook code cleanup.
* Updated ebuild for latest release.
== Release 1.6.24
* Merge pull request #331 from jrep/master
* Always store project .rvmrc trust keyed by the full, only slightly munged, path Prune old-style md5-keyed entries during
install Mention all this in notes
* changed each option sequence. unexpected error won't occur to run 'package install zlib' on Mac OS X 10.6. "ERROR: Error
running '/*/make install', please read /*/make.install.log"
* Merge pull request #330 from griff/master
* simplified prompt for rvmrc trust, infinate loop not a threat, as user can interrupt script at any time.
* updated copy to no longer reference `less` pager, as it seems cat is used now for security purposes.
* simplified checking of params.
* yoda~ish logic from [not, else] to [if, then]
* Updated ebuild for latest release.
== Release 1.6.23
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Ruby 1.9.2 p290 is now default.
* Recall the checksum of a trusted project .rvmrc.
* Added code to set rvm_user_install_flag in scripts/initialize
* Merge pull request #328 from gabemc/master
* Merge pull request #329 from biow0lf/master
* Merge branch 'master' of github.com:wayneeseguin/rvm
* rvmsudo: fix vairable values with spaces
* Add ruby-1.9.3-head
* Making md5sum the default executable, to fix an issue on Cygwin, which doesn't have a correctly formatted MACHTYPE.
* Merge pull request #327 from nibrahim/master
* Escape grep
* update instructions for reload
* fix variable values containing spaces
* yaml v0.1.4
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Installer adjustment.
* Merge pull request #326 from arunagw/jruby163_test
* Tests added for JRuby-1.6.3
* Merge pull request #325 from terabyte/master
* Fixed error message when you 'gemset create' before 'use ruby'.
* Updated ebuild for latest release.
== Release 1.6.22
* JRuby 1.6.3
* Merge pull request #323 from andrew/master
* Merge pull request #324 from mhorbul/master
* use TMPDIR value or /tmp by default. This will allow to update rvm when /tmp is mounted with noexec flag
* Updated rails bootstrap script to install rails 3.0.9
* Merge branch 'master' of github.com:wayneeseguin/rvm
* inform user about reload\!
* reworked rvmsudo: forward all rvm variables (and possibly more)
* fix loading/reloading rvm
* Merge pull request #322 from MagLev/maglev-newMac
* Handle pre-installed gems for MagLev
* add libxslt for yum: needed in CentOS 5.6
* Merge branch 'master' of github.com:wayneeseguin/rvm
* fix capistrano :system for rvm 1.6.21
* Updated ebuild for latest release.
== Release 1.6.21
* Merge pull request #320 from koraktor/ruby-1.8.7-p352
* Merge branch 'master' of github.com:wayneeseguin/rvm
* make rvm ruby lib work properly with 1.9.2
* Ruby 1.8.7 has been updated to patch level 352
* Merge pull request #319 from kbrock/master
* rvm wrapper now properly symlinks to a command with an absolute path
* fix zsh installation (process env persistance)
* always export rvm_path (sourced from .rvmrc)
* silence pushd/popd
* Merge pull request #318 from danhealy/master
* rvm_prefix does not have a trailing slash
* Merge pull request #317 from dplummer/patch-1
* Fix skipping extract step for REE
* fix root 'user' installation
* Merge pull request #316 from tylerhunt/patch-1
* Fixed a typo in the gemset_empty() warning.
* Merge pull request #314 from griff/master
* Merge branch 'master' of https://github.com/wayneeseguin/rvm
* Restructured how the - separator gets inserted in rvm-prompt to remove the need for sed editing at the end
* fix defaults to root
* fix rvm self contained feature
* Merge pull request #313 from griff/master
* Found a few log calls that was missed when logging was pulled internal
* Merge pull request #312 from cobracmder/master
* made minor grammar changes
* Merge pull request #311 from cobracmder/patch-1
* Minor grammar changes
* Merge pull request #310 from MagLev/MagLev-26063
* Updated to MagLev-26063
* Merge pull request #307 from threedaymonk/master
* Merge pull request #309 from MagLev/maglev-newMac
* Merge pull request #308 from justinko/master
* Fix problem causing selector to download/compile curl
* Merge pull request #306 from MagLev/maglev-newMac
* spellcheck
* Correct spelling of possessive its
* Fix up GemStone version for "rvm install maglev-head"
* rvm_gemstone_version
* Merge pull request #305 from MagLev/maglev-newMac
* Fix bad location for uncompressed GemStone directory
* Array! Yay!
* Merge pull request #304 from iangreenleaf/master
* Missed a spot! Spot! There you are lil guy!!!
* Anyone else hear circus musik?
* Cleanup, aisle MagLev.
* scripts/base in maglev.
* Only add users to group if thy aren't members
* Check users against passwd file
* Merge pull request #303 from MagLev/maglev-newMac
* Change so RVM doesn't override preinstalled RubyGems for MagLev
* Merge branch 'master' of github.com:wayneeseguin/rvm
* bashrc
* Merge pull request #302 from szTheory/master
* fixed issue where Result#initialize would blow up if status was false, giving (NoMethodError: undefined method '[]' for
false:FalseClass) on result.rb:14
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Try exporting rvm_path.
* Merge pull request #301 from Spaceghost/master
* Merge pull request #300 from MagLev/maglev-newMac
* Made rvm always create a hooks directory.
* Handled case where MagLev arch was x86-64 but file is i386
* Merge pull request #298 from mpapis/master
* Merge pull request #299 from MagLev/MagLev-25987
* Updated to MagLev-25987
* fix macport manage script
* Merge pull request #296 from buysse/improve_rvmsudo
* Merge pull request #295 from geemus/master
* Merge pull request #294 from gstark/fix_logging_output_tput_styling
* Merge pull request #293 from HeSYINUvSBZfxqA/master
* Merge pull request #297 from remear/master
* Added strings option to gemset listings. rvm gemset list strings
* Added support for sudo flags (such as -H) to the rvmsudo script
* [help] add use docs
* [help] add uninstall docs
* [help] add remove docs
* Removed the unset for rbxopt, allow it for all rbx installs.
* Detect interactive shell by looking at STDOUT for colorized logging.
* quote --no-same-owner option with tar command for ree/maglev
* 2.0.0pre @tmorini :)
* Merge pull request #292 from mblair/master
* typo fix
* Use RVM path.
* Updated ebuild for latest release.
== Release 1.6.20
* Updated ebuild for latest release.
* Truncate logs so that logs reflect last run.
* A tweaking we will go, a tweaking we will go...
* rvm_install_args
* rbx is not compatible with rbx :-p
* For rbx allow args to be passed through directly to configure.
* Account for name case.
* rbx counts too ;)
* rvm install rbx-2.0.0pre will work tomorrow ;)
* Updated ebuild for latest release.
== Release 1.6.19
* Bugfix, we have ruby at this point, might as well use it to generate a yaml output of the env ;).
* Try that rboyd...
* Move --no-same-owner inside.
* Put back an empty file.
* Merge pull request #291 from indirect/master
* Only track the latest of each point release in known.
* Stop forcibly setting BUNDLE_GEMFILE for now, because it stays set forever.
* Remove bundle shell function for now
* Added missing sources.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Cleaning up manage script by breaking it out into files.
* Merge pull request #290 from swhitt/master
* Running "bundle" by itself is the same thing as running "bundle install".
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Bugfix in installer thanks to yonahw.
* Merge pull request #289 from mpapis/master
* fix BUNDLE-INSTALL(1)
BUNDLE-INSTALL(1)
* Merge branch 'master' of github.com:wayneeseguin/rvm
* ignore RybMine configuration
* handle BUNDLE_GEMFILE, added default for projects that do not provide it
* Merge pull request #288 from shtirlic/patch-1
* Fix for zsh.
* ensure not finding the function.
* Altered rvm loading.
* better handling bundler, do not generatecomments for PATH
* do not create separate bin dir for bundler, let it overwrite gem
* "life" is the better word than "work" ;)
* Some manage cleanup.
* Merge!
* stars.
* Acting on comment suggestion from githuh.
* Merge pull request #287 from mpapis/master
* fix bundle binstubs
* Merge pull request #286 from mpapis/master
* improved bundle commnad
* Helps to actually git add the file.
* Account for bundler in rvm itself now.
* Merge pull request #284 from docwhat/master
* Merge pull request #285 from mattalbright/master
* This fixes the bug where system-installed RVM on Mac doesn't properly add the users to the rvm group. To properly add Mac
users to the rvm group, list all users that are in the "staff" group, which seems to mean can login.
* Typo in example rvmrc
* Merge pull request #283 from ncreuschling/master
* Escape! Escape!
* Merge branch 'master' of github.com:wayneeseguin/rvm
* bump version defaults in bootstrap script.
* fixed typo
* Merge pull request #282 from MagLev/MagLev-25913
* Updated ebuild for latest release.
== Release 1.6.18
* Added lines for bundler users to generated rvmrc (rvm --create --rvmrc use X@Y)
* Added a comment.
* Updated ebuild for latest release.
== Release 1.6.17
* More robust generated rvmrc files, better error handling.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* The proper thing to do is to use autoreconf, not autoconf. Learning autotools proper usage is highly recommended.
* Updated to MagLev-25913
* Merge pull request #281 from nwjsmith/master
* Fix typo
* Merge pull request #280 from mpapis/master
* Merge branch 'master' of github.com:wayneeseguin/rvm
* memory note for Rubinius
* added instructions for opensuse
* Merge pull request #279 from ajburton/md5_fix
* fixes test syntax
* vbatts is correct.
* Properly denote the default version of JRuby.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Updated ebuild for latest release.
== Release 1.6.16
* Source packages at the top.
* Such tender love went into the making of this feature :)
* Merge pull request #277 from arunagw/jruby_tests
* Tests added for jruby-1.6.2 #jruby
* Minor cleaning.
* Do not switch rubygems on JRuby.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* JRuby 1.6.2, w00t!
* Updated ebuild for latest release.
== Release 1.6.15
* Merge pull request #276 from ilikepi/fix_missing_then
* Add missing "then" to scripts/rubygems
* Added DESTDIR
* rubygems script cleanup.
* Updated ebuild for latest release.
== Release 1.6.14
* More installer fixes.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* I see stars!
* Merge pull request #275 from mpapis/master
* fix compilation with openssl 1.8.6
* I never thought that I would be doing this :)
* Updated ebuild for latest release.
== Release 1.6.13
* WHY was that not executable???
* More progress cleaning up installer.
* Look, the cure for stupidity consists of space!
* Gotcha you lil buggar!
* More installer refactorings, trying to get to the bottom of that annoying issue.
* Some cleanup of the rvm-installer.
* Only append to profile file if it exists.
* Array start bugfix and gemset script cleanup.
*
*
*
*
*
*
Somehow it managed to elude me.
Ensure that scripts that should be executable are.
Bugfix?
Bugfix?
If not connected to an interactive session, return.
Updated ebuild for latest release.
== Release 1.6.12
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Updated ebuild for latest release.
== Release 1.6.11
* Merge pull request #271 from adevadeh/patch-1
* Merge pull request #272 from yonahw/bad_taste_in_branch_naming_accepted_NOT_encouraged
* Merge pull request #273 from MagLev/MagLev-25876
* Merge pull request #274 from thomasjachmann/master
* fixes installer bug introduced in 10.6.10
* I blame gitflow for this atrocity
* split bunzip into 2 lines, the one-liner fails in RHEL4 for some reason. 2 lines works for RHEL4, RHEL5, Ubuntu, and
MacOS, have not tested anything else
* Updated to MagLev-25876
* Updated ebuild for latest release.
* 1.6.10
* Merge branch 'master' of github.com:wayneeseguin/rvm into rbx
* Bugfix: unbound variable in cli.
* Merge pull request #270 from ahamid/master
* add switch for explicit user install setting; helpful with root
* Merge branch 'master' of github.com:wayneeseguin/rvm
* More housecleaning.
* Merge pull request #269 from pvande/master
* Fixed postinstall note output.
* More cleanup.
* only call the command if it is loaded, first install should not error.
* Low hanging fruit plucking.
* Adjusted __rvm_18_compat_ruby to exclude rbx, since we do not want rbx to build rbx.
* Always load the .rvmrc if in an interactive shell (open new tab in same dir).
* Clean up some RubyGems-related duplication.
* Merge pull request #268 from CraigCottingham/rvmselect
* Merge branch 'master' into rvmselect
* Merge branch 'rvmselect'
* Add scripts/functions/developer, from https://gist.github.com/984bd56424be200532d0
* Merge pull request #267 from CraigCottingham/cleanup-bin
* Fix call to match() in __rvm_remove_binaries()
* Began cleaning up the installer.
* Cleaned up wrapper code some.
* Thank yøu bhenderson.
* Updated ebuild for latest release.
== Release 1.6.9
* Fixed an assinine bug thanks to stepheneb.
* Properly test for interactive mode.
* Removed no longer necessary code.
* Updated ebuild for latest release.
* The LOFL I am sick of this shit release!
* Merge branch 'master' of github.com:wayneeseguin/rvm
* LOFL!
* Merge pull request #266 from MagLev/MagLev-25838
* Switch to antialias.
* Corrected ordering.
* Updated ebuild for latest release.
== Release 1.6.7
* Synchronizing the code repetition blocks.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Level the playing field.
* Merge pull request #265 from gabebw/dollar-dollar
* Use cp -f and rm -f when dealing with /tmp/$$
* Updated ebuild for latest release.
== Release 1.6.6
* Updated to MagLev-25838
* Only if prefix is nonempty.
* Adjusted __rvm_project_rvmrc()
* Merge pull request #264 from derekprior/help-updates
* Works with 1.9.* as well. Added bit about 'rvm rubygems remove' from the rvm website.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* set -fu
* Merge pull request #263 from meineerde/setup_rvm_group_users-with-no-users
* Fix setup_rvm_group_users for the case when there are no additional users.
* Tweaked recursive copy.
* Add a reset --hard HEAD on rbx build.
* handle get specially.
* resolution
* s/aptitude/apt-get/g Many users of Debian certainly and probably other Debian-derived distros prefer 'apt-get' to
'aptitude'. For whatever reasons [Ubuntu has actually stopped shipping with 'aptitude' by
default](http://www.webupd8.org/2010/06/aptitude-removed-from-ubuntu-1010.html). Without debating the technical merits of
either tool, I would say this:
* Merge pull request #259 from matschaffer/patch-1
* More set -u fun.
* set -u should be outlawed :-p
* Bugfix: scripts/functions.
* Removeperpetual d call to display_osx_hint.
* Adjusted rvm path setting.
* Merge pull request #260 from rosenfeld/master.
* Merge pull request #261 from alec-c4/master.
* Added hint for OSX users
* Add example for tweaking Gem options
* Loading cleanup, adjusting more for zsh.
* Bugfix: ZSH random declare. Adjusted rvm_user_install with _flag postfix as that is what it is. Corrected usage of
rvm_user_install_flag.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Bugfix: do not allow missetting of rvm pretty print flag to blow up.
* Merged pull request #258 from pweldon/fix_config_user_mv.
* Ensure aptitude is installed.
* fix logic for moving config/user -> user/db
* Merge branch 'master' of github.com:wayneeseguin/rvm
* --no-same-owner is back!!! :)
* Merged pull request #256 from ConradIrwin/sha1-simplification.
* Merged pull request #257 from utkarshkukreti/patch-1.
* Add newline after the error message on running `rvm update`.
* Further simplify SHA1 extraction.
* Merged pull request #253 from bergalath/master.
* Merged pull request #254 from pweldon/fix_user_db.
* Merged pull request #255 from ConradIrwin/master.
* Tidy up, and comment option setting.
* Yeah... I see you too zsh...
* extglobbing fun :)
* Merge branch 'master' of git.overnothing.com:rvm
* Ying, meet Yang.
* Fix user db overrides to use $rvm_user_path/db consistently.
* Updated ebuild for latest release.
== Release 1.6.5
* Using `git rev-parse` instead of `git log --no-color -1` to get the last sha1 commit on current branch so we can remove
some treatment.
* Ubuntu sucks arse through a straw.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Merged pull request #251 from ConradIrwin/fix-nonomatch.
* --no-same-owner thanks to ngan.
* Merged pull request #252 from kaerast/master.
* Return on error.
* Removed duplicated flags, thnk you very much arrix.
* added missing dependencies for Centos
* Updated install line in readme, thanks to crankharder for pointing it out.
* -o...
* Correct and clarify resetting of zsh options.
* Updated ebuild for latest release.
== Release 1.6.4
* Wow... that was a brainfart.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Select if not selected.
* More cleanup prompted by last pull request.
* fixed my brain
* We found you, you little snot
* Trying to do too many things at once :/
* Added rvm_rbx_opts to example rvmrc with comments.
* This part needs more thought.
* More cleanup.
* ...
* ...
* Merge branch 'master' of git.overnothing.com:rvm
* Syntactical Cleanup.
* Added RBXOPT to environment file recording. Cleaned up environment files and code some.
* Defaut RBXOPT to -Xrbc.db and -Xagent.start, overrides by setting rvm_rbx_opt in rvmrc.
* Merge branch 'add_jruby_161_to_known' of https://github.com/sferik/rvm into sferik-add_jruby_161_to_known
* Missed a q.
* Add JRuby 1.6.1 to the list of known rubies
* Merge branch 'fix-install-errors' of https://github.com/chrislwade/rvm into chrislwade-fix-install-errors
* Default to Jruby-1.6.1
* Fix typos.
* Fix errors reported during install.
* Updated ebuild for latest release.
* People define "stable" by version numbers, so here I give them another #daft.
* Added rvm-exec to binscripts installation thanks to arrix.
* Removed eval from end of rvm-exec.
* Stick with builtin.
* Some cleanup.
* Merge branch 'issues/fix-missing-escape' of https://github.com/meineerde/rvm into meineerde-issues/fix-missing-escape
* Merge branch 'MagLev-25716' of https://github.com/MagLev/rvm into MagLev-MagLev-25716
* rvm-installer: fix typo in "--version latest" switch
* Added rvm-exec as per suggestion by Arrix Zhou.
* Updated to MagLev-25716
* Fix another typo
* Fix missing escape
* Slight cleanup of new function.
* Feature: rvm gemset search <gem name> strings
* Feature: rvm gemset search <gemname>
* Updated ebuild for latest release.
== Release 1.6.2
* Adjusted ps1_titlebar as recommended by @chrislwade.
* Merge branch 'MagLev-25681' of https://github.com/MagLev/rvm into MagLev-MagLev-25681
* F'n Solaris.
* already gone!
* Bugfix: rvm_make_flags_flag
* Adjusted ps1_titlebar
* Updated to MagLev-25681
* Merge branch 'master' of https://github.com/skaes/rvm into skaes-master
* Take rubygems to 1.6.2 until I can complete the new feature.
* Fixes bug with calling shopt with ZSH
* run autoconf if the configure script is older than configure.in
* Updated ebuild for latest release.
== Release 1.6.1
* Merge branch 'master' of https://github.com/MagLev/rvm into MagLev-master
* Merge branch 'ps1_titlebar' of https://github.com/thecatwasnot/rvm into thecatwasnot-ps1_titlebar
* Merge branch 'codegnome/issue-001' of https://github.com/CodeGnome/rvm into CodeGnome-codegnome/issue-001
* Merge branch 'codegnome/issue-002' of https://github.com/CodeGnome/rvm into CodeGnome-codegnome/issue-002
* Defaulting Rubygems version to 1.4.2 based on Evan Phoenix's recommendation.
== Release MagLev-25665
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Updated ebuild for latest release.
== Release 1.6.0 - https only.
* https AAAAARRRRRGGGGGGHHHHHHHHHHHHHHH
* __rvm_ask_to_trust(): Aligned 'yes or no' prompt.
* Better user messages for __rvm_ask_to_trust().
* Bumped minor version for HEAD.
* Updated ebuild for latest release.
== Release 1.5.4
* rvm use 1.2.3 => rbx-1.2.3
* Ensure extglob is on for r()
* Updated ebuild for latest release.
== Release 1.5.3
* Adding titlebar back for xterm in contrib/ps1_functions
* Altered new git status ps1 feature to minimize external calls.
* Merge branch 'git_status' of https://github.com/carlosgaldino/rvm into carlosgaldino-git_status
* Update to MagLev-25646
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bugfix: adjusted printf.
* Adjusted rm_rf
* nn
* Fixed regression in 'require'
* Update to MagLev-25568. Fixes SEGV in MagLev FFI code on Linux
* show git status
* Removed extra escape.
* Updated branching logic thanks to prompting by hiroshi.
* Merge branch 'fix_branch_select_patterns' of https://github.com/hiroshi/rvm into hiroshi-fix_branch_select_patterns
* Fix patterns for $(git branch)
* Merge branch 'master' of https://github.com/wayneeseguin/rvm into macruby_repo_url_github
* Changed macruby_repo_url to github
* Merge branch 'master' of https://github.com/ashgti/rvm into ashgti-master
* Bugfix: call gemset_import in import(), thanks to hedge-hog.
* Update the ps1_set to escape all of the coloring parts so you can use a separator that is not a new line and not mess up
your prompt. See contrib/ps1_functions for more detail.
* Create and add $rvm_bin_path if necessary
* Removed extra fi from removed test.
* Alter calculation of user_install detection.
* Go through full RVM path initialization in rvm-shell.
* Merge branch 'untar-ownership' of https://github.com/meineerde/rvm into meineerde-untar-ownership
* Merge branch 'cleanup_192_pre' of https://github.com/sferik/rvm into sferik-cleanup_192_pre
* Remove all 1.9.2 pre-releases now that 1.9.2 is final and stable
* Add -o parameter to all tar extractions to not use existing users and groups when running as root
* Set $rvm_prefix to actually allow to override the target $rvm_path
* Allow to actually set an install path other than /usr/local/rvm
* Add missing shift to allow '--version latest'
* if exec is called bypass loading libs.
* Merge https://github.com/arunagw/rvm into arunagw-56b6e97
* Merge branch 'master' of https://github.com/goncalossilva/rvm into goncalossilva-master
* Sanity check for the case we are not in a git branch.
* Merge remote-tracking branch 'upstream/master'
* Initialize the variables to make sure they are set.
* Updated ruby186gc for the latest patchlevels. RVM applies patches with -p1, changed patch headings accordingly.
* added the "ruby186gc" and "ruby187gc" patches
* Bugfix: remove symlink if it exists.
* Updated ps1_functions based on discussion with @0x44
* Fixed gems to gemset
* Only chown as root.
* Bugfix: if the hooks files are the same, only run once.
* More replacement of 'gems" to "gemset"
* Replacing gems to gemset in test/unit/gemset_test
* Modified PS4 again.
* Test for jruby 1.6.0. Default is jruby-1.6.0
* added working gcdata patch for mri 1.9.2-p180
* removed non-functional 1.9.3 gcdata patch
* Updated PS4 to a more readable version.
* s/exec/eval/:(
* I am so insanely daft that I make my pet rock look smart :/
* Adjusting rvmsudo for debugging.
* Bugfix: Globbing now works properly in zsh.
* Bugfix: Preserve arguments to rvmsudo.
* Bugfix: Keep bin path default scripts in sync. Copy instead of symlink.
* Bugfix: account for multiple digits and up to three.
* LOFL
* Adjusted binscripts methods.
* Bugfix: version detecting for macruby.
* Adjust for possibility that path is nil?
* Adjust cap integration for the removal of system-wide.
* Updated ebuild for latest release.
== Release 1.5.2
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Ensure etc_profile_file is assigned.
Empty check.
Missed gems, environments and wrappers.
Ensure rvm path dirs exist.
Explicit instead of implicit.
vra tyop.
Rebuild instead of migrate.
Close if, silly!
s/rvm_selfcontained/rvm_user_install/g
More work on profiles.
tyop
Are we there yet?
Automatic user profile setup, Yehuda might yell at me for putting this back ;)
Always call setup_rvmrc
Improved default rvmrc logic.
Respect --path.
More fine tweaking.
New tactic, only load the associated rvmrc file :)
Forcable AND direct!
be more direct with setting rvm_path.
dassinine - verb - daft and assinine
Ahhh it is the token!
Allow for rvm-installer x.y.z
chmod +x !
Determining install path comes first.
More work on the installer.
Turn on extended globbing.
Added new rvm-installer script which combines all functionality of the install-latest install-head and get API.
Merge branch 'master' of https://github.com/nerdyc/rvm into nerdyc-master
profile.d scripts must be executable.
LOL!
Working on better profile.d logic.
Update rvm ruby selector script to support MacRuby 0.10.
.sh :(, thanks bradland !
Symlink to prefix path bin, not hardcoded to /usr/local/bin
Use /etc/profile.d if it exists, otherwise fall back on /etc/profile.
Bugfix: I was a bit overzealous when escaping things :)
Use the rubygems API as part of manage.
Give the user more information during root installation.
Merge branch 'master' of https://github.com/zendesk/rvm into zendesk-master
Loading rvmrc fits better in install_setup.
== Release 1.5.1 - rvmrc files are now respected during installs.
* Respect main rvmrc files.
== Release 1.5.0, anything less is UNSUPPORTED :)
* Sneeky buggars!
* Updated update head script.
* FI fi fo fum!
* Fun with function names, w00t!
* So how about we actually append to the file, yes? :)
* What is in a name?
* Keep on drillin!
* Move parse args for clarity.
* More root canal work.
* RVM built in installer now handles root installation.
== Release 1.3.2
* MacRuby 0.10, w00t!
* Fixed an insanely daft bug.
== Release 1.3.1
* Fuck you system wide, fuck you.
* Explicitly do not load rvm.
* Determine paths separately from loading RVM.
* Use printf, rvm_error has not yet been loaded yet at this point.
* Lock and load.
* fixing rvm get x.y.z
* Merge branch 'purple-directory' of https://github.com/carlosgaldino/rvm into carlosgaldino-purple-directory
* Merge branch 'master' of https://github.com/zendesk/rvm into zendesk-master
* Refactored Install script, it is now much more readable and maintainable.
* turn off die on error in tmp cleanup trap for shell scripts that enable set -e
* Missed a spot :/
== Release 1.3.0
* Switching to a far superior rubygems download url, w00t!!! Thanks kotique!
* directory is now purple
* Escape as we do not mean a unicode sequence :)
* Added contrib to installer.
* Added ps1_functions to contrib/
* More trailing slash guards.
* Account for odd trailing slashes in install script.
* Remove i386 CPU_TYPE check since new macs return x86_64 Update to version 25506
* Switched from external calls to using $UID as suggested by methods.
* Finishing touches for kiji interpreter thanks to initiative by Blue Box Group.
* Merge branch 'master' of https://github.com/blueboxgroup/rvm into bbg
* Merge branch 'master' of https://github.com/yura/rvm into yura-master
* Merge branch 'master' of https://github.com/erikh/rvm into erikh-master
* Completely removed rvm_interactive_flag, checking directly each time as per recommendation by e2 for zsh.
* Autodetect rvm_interactive_flag every time
* Found a few more places...
* First flushout to add kiji.
* Fix ri generation
* don't need to emerge libxml since it's ruby package in gentoo and required ruby 1.8.7 to be emerged
== Release 1.2.9
* JRuby 1.6.0 is now default.
* Added rbx-1.2.3
* Update to MagLev-25439. Seaside works again.
* Added a project specific hook check.
* Bugfix: hooks :)
* Default to user install.
* Rubygems 1.6.2.
* Bugfix: Ensure we are in the correct directory during git operations for macruby-head
* 1.2.8
* JRuby 1.6.0.RC3
* Added default value for rvm_path.
* Merge branch 'master' of https://github.com/anl/rvm into anl-master
* Fix zsh completion
* correcting the man files installation locations
* ignoring .DS_Store files
* Merge branch 'mkdir_usr_local_lib' of https://github.com/hiroshi/rvm into hiroshi-mkdir_usr_local_lib
* Merge branch 'master' of https://github.com/re5et/rvm into re5et-master
* packages script was broken, typo fixed.
* in case of missing /usr/local/lib directory
* Updated docs for get.
* Added rvm get master which does the same as rvm get head for sensitive people. Moved packaging script functions into
functions dir.
* Updated MagLev to 25375 after fixing C-extension problems
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Added RubyGems 1.6.1 URL and md5.
* Update to MagLev 25370
* Remove hard-coded /usr/local.
* More progress on expanding the rails_routes script, r() also.
* Added scripts/extras.
* Moved rails CLI helper functions script from contrib to scripts/extras.
* Added rails_routes to rails helper function r() script.
* Added screen test when sourcing rvm .
* Bugfix: zsh cd loading.
* Remove warning from gemset copy.
* Added a comment.
* More cleanup in gemsets.
* Ensure that rvm_gemset_name is unset for gemset copy.
* Unset gemset name.
* Respect PAGER while still protecting from .rvmrc based attacks.
* ZSH auto_name_dirs feature is troublesome :)
* Added comments and a sanity check to the trap.
* Shut your trap!
* Merge branch 'disk_usage_symlink' of https://github.com/ilikepi/rvm into ilikepi-disk_usage_symlink
* fixed gemset completion function .
* Explicit match.
* Directory check on ruby gem home.
* Set current to 1.6.0
* Added md5 and URL for RubyGems 1.6.0.
* Adjust __rvm_fetch_ruby based on suggestions by brixen.
* Add trailing '/' so disk-usage can handle symlinks
* --disable-install-doc flag set by default.
* Merge branch 'master' of https://github.com/pedz/rvm into pedz-master
* Load __rvm_db as part of base.
* Bugfix: The patchlevel tried to run away!!!
* Remove GEM_HOME and GEM_PATH from initialize export.
* Bugfix: load rvm reset where used.
* Merged back in all my previous changes
* Export rvm_ruby_repo_branch
* Silence silly messages.
* Removed no longer necessary n* case from selector.
* Install 1.8.7 dep with a clean env
* Ruby name now propigates in selector.
* te hee!!! You see nothing!
* Remove empty extract target directory.
* Feature: Named rubies can now be any alphanumeric sequence at the end of the ruby string, no more -n necessary. In fact -n
will be removed "soon".
* Feature: -n/--name [name] to name a ruby, in addition to -n in ruby string.
* Removed leftover function call.
* Cleanup setup & initialize some more.
* Take that ye variable leech!
* Bugfix: keep exports in cd until the last second.
* Ensuring all vars are set for project rvmrc loading.
* Reorganization and cleanup. scripts/utility => scripts/functions/*
* Missed an exit.
* Added help for install
* Bugfix: hard exit when error occurs during ruby install.
* Bugfix: Proper globbing for rvm gemset import.
* Seperate returned list from rubies list.
* Check for matches first.
* Added ncurses-dev to ruby dependencies on apt based systems.
* Alter __rvm_18_compat_ruby to explicitely exclude macruby,goruby,jruby,anything not matching.
* Added ~amd64 to KEYWORDS in ebuild templates.
* Missed a flag for unset, simplified match()
* Missed a variable for env cleanup.
* Type based removal.
* Removed a bit of redundancy.
* Adjusted installer script sourcing.
* Install check should not be quoted.
* Only install 1.3.7 for Ruby 1.8.6.
* Be far more precise when copying install files and directories over.
* Merge branch 'rbx-1.2.2' of https://github.com/sferik/rvm into sferik-rbx-1.2.2
* Add rubygems 1.5.3
* Add rubinius 1.2.2
* Cleanup unused checksums
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Merge branch 'master' of git.overnothing.com:rvm
Rename $path to $target in __rvm_rm_rf
Add in a patch level for rubinius 1.2.2
Bugfix: stupididity.
Rebase when pulling.
Tyop.
Missed a ;
All rm -rf calls now use a _slightly_ safer __rvm_rm_rf with some sanity checks in place. Thanks Sven!
Adding some sanity checks around rms
Added sanity check to rm for tmp cleanup, suggested by sven schwyn.
Merge branch 'master' of https://github.com/caius/rvm
Bugfix: Manage script variable truncation.
Stop ZSH warning about unmatched globs by setting an option.
Revert "Supress a warning when cleaning up ./tmp under ZSH"
Merge branch 'master' of https://github.com/ferrous26/rvm
Supress a warning when cleaning up ./tmp under ZSH
Began revising get to be able to specify a specific revision.
cd will need some work to be configurable for scripts.
MacRuby latest release is now version 0.9
More cleanup.
Bugfix: missing variable name. Thanks tilthouse.
arg*v!
rvm tmp path.
Properly cleanse rvm environment.
Ignore .rvmrc :)
Add pkg/ to gitignore.
Added functions.
Rollback cd.
Wrappers and environments.
Temp path configurable.
Cleanup, aisle _
Config path configurable.
gemsets & hooks.
rvm_scripts_path configuration variables.
Added in rvm_archives_path config.
Missed a "
Initialize variables.
Where did they go?!
Consistently use rvm_rubies_path for ruby installation path setting.
Merge branch 'master' of https://github.com/MagLev/rvm into MagLev-master
Removed VERSION.yml symlink.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Added comment to leave the eval.
Call__rvm_rvmrc_tools for escaping
Bump head version to 1.2.8
Updated manifest.
Merge branch 'master' of git.overnothing.com:rvm
Updated manifest for only the gem release files.
Make scripts/migrate deal correctly with the base gemset
use -eq insetad of = for an integer test
New release - MagLev 25239
Merge branch 'system-installer-rev-fix' of https://github.com/fnichol/rvm into fnichol-system-installer-rev-fix
Fetch more history in install-system-wide when called with --revision.
Use correct gemset file name.
Merge branch 'gemsets-import' of https://github.com/docwhat/rvm into docwhat-gemsets-import
Merge branch 'master' of https://github.com/ferrous26/rvm into ferrous26-master
Merge branch 'master' of https://github.com/sferik/rvm into sferik-master
Merge branch 'master' of https://github.com/sikachu/rvm into sikachu-master
Merge branch 'master' of https://github.com/xing/rvm into xing-master
Merge branch 'master' of https://github.com/wt/rvm into wt-master
Update for MagLev 23515
REE 2011.03 now default for ree.
fixed typo that prevents cloning ruby via https
Update installation procedure in README
Swap find args so that find doesn't complain.
Unset rvm_ruby_name when cleaning up.
MacRuby nightly builds are now on version 0.10
Add 1.9.1-p431 as default 1.9.1
Non-awk way to import configuration files for gems.
No grep for you sed I!
Act on Christian's suggestion to use new current_gemset function in info script.
Added Christian's function to utility.
Formatting.
'rvm gemset list' now has a '=>' for the currently used gemset
Updated usage and help.
SANITYFIX: rvm upgrade [source] [destination]
added full path to usermod
Fix bug where "rvm gemdir" was throwing an "unknown action" error
New ree release, fixed a tyop.
Use a case for argument parsing in alias.
Bugfix: rvm help get works as intended now.
MagLev 25289.
Annotations and consolidation.
Removed update added get to usage output.
Merge branch 'master' of https://github.com/spastorino/rvm into spastorino-master
Add 1.9.2-p180
Add 1.8.6-p420
Fix to add rvm/environment/wrapper to RVM::Environment.
Bugfix: allow 'rvm @gemsetname' to switch gemsets
Bugfix: test for ree version #
Added extra arg check.
Default action to use.
Moved usage from flags section into command section.
alnum fool!
Refactored argument parsing for more efficiency / less checking to reach end goal.
* Reordered ruby check.
* Reordered checks in cli parse args
* Removed old matcher case.
* sgr0 is safer than setaf 9.
* Altered logging function definitions.
* Bugfix: Adjust pattern match, thanks to thomasfedb for pointing this out.
* 1.8.7-p334 is now default.
* bye bye now!
* Pulled logging internal.
* Squeaked even more performance into the selector straight shell builtin case.
* Performance improvement centered around the selector.
* Merge branch 'speed-up-cd-hook' of https://github.com/tastapod/rvm into tastapod-speed-up-cd-hook
* Replaced call to grep with case match to speed things up. Replaced for loop with 'env|while read' to protect env vars with
spaces.
* Fix call to unset causing the real result of rvmrc trustworthiness to be lost.
* Minor version bump.
* Added an ERROR message with an exit when JAVA 1.3 / 1.4 detected for jruby install
* Added warning when java version is old when installing JRuby.
* Merge branch 'master' of https://github.com/fnichol/rvm
* Fixed syntax.
* Merge branch 'master' of https://github.com/victorluft/rvm into victorluft-master
* Merge branch 'master' of https://github.com/cr0t/rvm into cr0t-master
* Extract install dir from rbconfig.
* Account for Rubinius when altering rubygems versions.
* Tyop fix.
* Added Rubinius 1.2.1 to known list.
* Allow Rubinius to change rubygems versions.
* Fixed rvm_ree_options autosetter to --no-tcmalloc on Darwin systems
* Added emerge line for notes.
* Bugfix: when using --ree-options be sure to use the parameters passed in. Thanks to dmilith for catching this.
* Update group modification support in install-system-wide for SuSE.
* WTF??? Seriously? A new Repo? Save a tree, use branches!
* Default ree is now ree-1.8.7-2011.01.
* Rubygems 1.5.2 is now default.
* Removed old maglev md5 sums
* Maglev version 25223 is now default
* Added jruby-1.6.0.RC2 to known list.
* Setting a default ruby now creates ~/.rvm/bin/<binary> for each binary in the default wrapper directory.
* Rubygems 1.5.1 is now default.
* Fix gemset copy to be able to use non-complete gemset name. (I.E. @gemset or 1.9.2@gemset instead of ruby-1.9.2p136@gemset)
* Fix API method typo (gemset_intial -> gemset_initial).
* Merge branch 'master' of https://github.com/aef/rvm into aef-master
* Reverted JRuby 1.6.0.RC1 to be the default choice for JRuby
* Merge branch 'master' of https://github.com/Innova/rvm into Innova-master
* Merge branch 'rvmrc_fixes' of https://github.com/tpope/rvm into tpope-rvmrc_fixes
* README.
* Removed unsetting of rvm_path and rvm_prefix since these are required in several scenarios to be pre-set.
* Separated out RVM version from RVM API version.
* Added a version file back in.
* Added files back into API gem.
* Damn I suck... no more lisp and ruby at the same time. brain gone
* Oops! Needed to deal with VERSION.yml going away
* Added jruby-1.6.0.RC1 to the known rubies
* Fixed licence annotation at the end of README thanks to zenspider.
* Moved from jeweler to hoe (mostly... needs check my wayneeseguin)
* Moved pkg to meta
* Fixed variable initialization problems in scripts/rvm
* MagLev 25186
* Fixed typo in utility script
* Fix typo
* Prevent false matches on gems in .rvmrc bundling
* Clean up run-on sentences in .rvmrc
* Don't output bundle binary path from .rvmrc
* Bugfix: odd tyop in help script.
* Reworded rubygems line in README.
* Feature: rvm RTFM
* Bugfix: rvm gemset copy now works as intended.
* Create destination gemset if it does not exist.
* Removed contentious comment.
* Updated ebuild for latest release.
== Release 1.2.6
* Feature: rvm rubygems remove.
* Removed obsoltete items from README.
* Bugfix: correct path to log.
* If revision is "head" then recenter to "master" for a git fetch.
* Use builtin rubygems command to update to current during manage install.
* Updated ebuild for latest release.
== Release 1.2.5
* Added Rubygems 1.5.0 md5
* Rubygems 1.5.0 is 1.9 compatible, w00t!!!
* How the Eff did that happen???
* Its SunOS not Solaris-x86
* Bugfix: Default rvm_promptless to 0.
* Merge branch 'solaris' of https://github.com/kylef/rvm into kylef-solaris
* Merge branch 'solaris-install' of https://github.com/kylef/rvm into kylef-solaris-install
* jruby-head needs ant and a jdk to install (updated for Ubuntu).
* Bootstrap script should pass --default flag, good catch Sutto.
* RVM uses the Apache Licence v2.0.
* Added "ls" as an alis for the list command, ala pik.
* Make install-system-wide support SunOS
* Properly detect if its a 64bit Solaris-x86 machine or not
* always pull from remote repo when installing from head
*
*
*
*
*
*
*
*
*
*
*
*
Bugfix: tyop, thanks to rsim for pointing it out.
Added info message when trying http url.
Fixing macruby-head bug.
Create destination during a copy.
Merge branch 'master' of https://github.com/timfel/rvm into timfel-master
Slight refactoring in rvm-prompt.
Allow to use characters in prompt like virtualenv for python
Bugfix: logic error, thanks to lfalcao for pointing this out.
Fixed a tyop thanks to telemachus.
Added bootstrap_rails_environment contrib script.
force re-setting of GemStone url, otherwise downloads won't work, if the URL has already been set in the env
Updated ebuild for latest release.
== Release 1.2.4
* WTSyntax?
* Updated ebuild for latest release.
== Release 1.2.3
* Added libxslt/libyaml to usage output.
* Merge branch 'master' of https://github.com/sunteya/rvm into sunteya-master
* Bugfix: tyop.
* Added libyaml package.
* Maglev 25051 is now default.
* The 'rvm remove' will re-delete environments and binaries
* Merge branch 'base-typo' of https://github.com/jcf/rvm into jcf-base-typo
* Merge branch 'rvm-current' of https://github.com/jcf/rvm into jcf-rvm-current
* Second patch by lordzork + slight syntax cleanup twards the project standard.
* Applied patch by lordzork.
* Removed =~ usage for older shells, thanks to cosine.
* Correct a typo in a comment within scripts/base
* rvm current
* Default rvm_path and rvm_prefix to exported environment variables then empty string. Thanks to agreif for pointing out the
issue.
* Updated ebuild for latest release.
* Defaulting RubyGems to 1.4.2 for allowed interpreters (MRI 1.8.X).
* Doublejump!
* Also escape forward slashes for awk match.
* Reorder our escape sequence :)
* Awww.. c'mon ... you saw them too?!
* But I *like* backslashes :(
* It is amazing how much one lil dot can affect things :)
* Adjusted trust check logic.
* Adjust for when USER is not set.
* Use escape when checking trustworthiness
* Version bump to 1.2.2
* Adding a packaged version of rvm and a new rvm-install script which uses the version packaged in the gem. Thanks to
vkushner for the conversation :)
* Missed a file.
* Feature: use a user directory in order to store user settings instead of the config/ dir. This also fixes the
"disappearing rvmrc" bug.
* Support JRuby's .RCX kinkyness.
* Added escape flag for db.
* Escaping keys in the db :)
* Added rvm_always_trust_rvmrc_flag to examples.
* Only for ruby interpreter use svn like branch calculation.
* Applying zenspider's patch
* Account for possibility that rvm_path is not set.
* Trust a .rvmrc file if rvm_always_trust_rvmrc=1 is set in ~/.rvmrc or /etc/rvmrc regardless of contents if it is trusted
once. Thanks to yonahw for this!
* Remove file before writing to it in gemset export.
== Release 1.2.1
* Altering loading of override_gem.
* Clear all traps upon successful teardown. Call rvm teardown on trap.
* Merge branch 'master' of https://github.com/adammck/rvm into adammck
* Added a check to ensure /etc/rvmrc exists before sourcing it, thanks to pedz for the heads up.
* Bugfix: account for unset variables, thanks to zenspider for pointing it out.
* add rvmrc test.
* fix trailing space bug, and improve tests.
* add minimal unit tests for 'rvm [un]export'.
* add minimal docs for [un]export.
* add 'rvm export' and 'rvm unexport' actions.
* Make sure \n is literally printed in the .rvmrc file, as opposed to being interpolated
* Bugfix: escape quotes inside .rvmrc template.
* Updated ebuild for latest release.
== Release 1.2.0
* Bugfix: ensure that .rvmrc files are output exactly as they are ignoring escape sequences.
* Updated ebuild for latest release.
== Release 1.1.13
* Fixed a daft tyop, thanks to El_Picador for pointing this out.
* Be more verbose by default for users.
* Increased verbosity and clarity of the .rvmrc file, also made it more DRY.
* Revert to printf since log has been removed. Thanks to khasse for bringing this up
* Bugfix: Nono RVM, Bad touch!
* Updated ebuild for latest release.
== Release 1.1.12
* Bugfix: tyop with syntax.
* Ruby repository uses 'trunk' as 'master'
* Install -head MRI Rubies via github.
* Removed legacy rvm-install
* Bugfix: Ensure archives directory exists for latest.
* Removed configure env setup from manage, leaving for libraries
* Added libc6-dev to aptitude installation notes.
* Updated ebuild for latest release.
== Release 1.1.11
* Added *.rbc to gitignore.
* Comment out archflags for now.
* Updated rvm-get-latest
* Bugfix: rvm get latest, variable correction.
* Updated ebuild for latest release.
== Release 1.1.10
* Merge branch 'archflags'
* Swithed install head script to use https, install latest script now checks md5.
* Archflags working on packages, not quite yet on rubies.
* Added some varaibles to cleanup.
* Removed extra trailing slashes
* Updated ebuild for latest release.
== Release 1.1.9
* Rubygems 1.4.1
* Added newline as requested by daniely.
* Merge branch 'master' of git.overnothing.com:rvm
* Do not unconditionally call project rvmrc when cli is loaded, this is taken care of when RVM is loaded in scripts/rvm
* Add in zlib-gc-fix for 1.8.7 and ree, Fixing issues with bundler installing gems.
* Updated ebuild for latest release.
* Adjusted rvm notes for JRuby on aptitude hosts.
== Release 1.1.8
* Bugfix: rvm remove --gems X now uses full paths to avoid any possible CWD issues. Thanks to agrimm for bringing this to
our attention.
* Bugfix: unbound variable in cli.
* Use rvm_promptless for the rvm-auto-ruby and the like to avoid hangs in things like TextMate
* libruby osx arch patch for 1.9.1 and 1.9.2
* Added openssl-devel to yum distro notes.
* Updated ebuild for latest release.
== Release 1.1.7
* ruby-1.9.2-p136
* ruby-1.8.7-p330
* MagLev 24924
* Merge branch 'fix_test_suite' of https://github.com/txus/rvm into txus-fix_test_suite
* Fix: test suite refers to unknown dir
* Fix typo on rbx-1.2.0
* rbx-1.2.0-20101221
* Missed 2 sed's, thanks to gabebw for pointing this out.
* Merging in patch by iLikePi.
* Practice safe sed :)
* Merge branch 'master' of https://github.com/cdunn2001/rvm into cdunn2001-master
* Merge branch 'fix-191-version' of https://github.com/gabebw/rvm into gabebw-fix-191-version
* Zsh completion of gemsets trailing rubies (#84)
* What, you mean you actually want to compile something???
* config/known now shows correct ruby-1.9.1-p378
* Append to file, again thanks for the heads up cdunn2001.
* Change over-write to append; same as previous change by wayne, different line.
* Append to file, thanks for the heads up cdunn2001.
* Updated ebuild for latest release.
== Release 1.1.6
* Updated post intsall message for the gem releases.
* Solaris, why can you not play nice with others???
* Altered the way PATH is cleaned to get things working on Solaris.
* Make implode take into account other items including wrappers
* Bugfix: Macruby gem command now respects gemsets.
* MagLev 24864
* standardise the display of known rubies and their defaults eg.
macruby[-0.8] rather than
* Updated ebuild for latest release.
macruby-[0.8]
== Release 1.1.5
* MacRuby 0.8 is now default.
* Added informational output when --static is used.
* Bugfix: Allow rvm_static_flag to pass through.
* Feature: --static for statically built MRI Rubies. Removed RVM installation from RVM API gem.
* Switched to https.
* Added line numbers to the default irbrc prompt
* Temporary fix for the project rvmrc bug w/ path-identifier
* Escape aliases in the shell wrapper, correctly export the shell variables in environment.rb
* Escape a grep in selector.
* Tweaked version check / exporting rvm_version.
* Removed unused extra variable.
* Updated ebuild for latest release.
== Release 1.1.4
* Feature: 'rvm gemset list_all'. Thanks to jedmtnman.
* Merge branch 'master' of https://github.com/blueboxgroup/rvm into blueboxgroup-master
* Patch to resolve issues experienced with a missing rvm_path command.
* Handle md5 in fetch on OpenBSD. Thanks to Andrew Gwozdz
* Bugfix: When NOT root :) thanks jonathonstorer.
* Switch from whoami to id for POSIX compatibility as suggested by rockyb.
* gem install jruby-launcher after installing any jruby.
* Added jruby-launcher to JRubys global gemset.
* Further quoting fixes.
* Bugfix: Properly quote when -e is called.
* Added libxslt to the recommended dependencies list, thanks laomao!.
* Bugfix: Clear defaults and delete alias when system is set as default. Do not output the alias deletion (twice even!)
Thanks to dreamcat4 for this.
* rake install macruby via rvmsudo.
* Updated ebuild for latest release.
== Release 1.1.3
* Merged in a tweaked version of robotarmy's OPenBSD patch.
* JRuby 1.5.6 is now default.
* Acted upon Dreamcat4's recommendation.
* Load rvmrc when rvm is sourced.
* Allow setting of rvm_tmp_path in ~/.rvmrc
* Updated ebuild for latest release.
== Release 1.1.2
* Merge branch 'master' of https://github.com/wingrunr21/rvm into wingrunr21-master
* Merge branch 'darwin_notes_abandon_system_ruby' of https://github.com/billgathen/rvm into billgathendarwin_notes_abandon_system_ruby
* rvm install goruby
* Update system wide installer for Darwin support
* Bugfix: 'rvm --default system' now works as expected
* Reset when system is set as default.
* Allow selecting git branches via --branch when installing a Ruby.
* Bugfix: setting default now properly creates an alias again. rvm list default also works again.
* Tyop fix, thanks to nirvdrum.
* Added rvm_ruby_name to variable unset section thanks to rocky.
* I usually run rvm interactively logged in as myself, but got a confusing error when I tried to have my webserver running
as www-data source it to use in a setup script. Hopefully this change will make it clearer to anyone trying to do the same
thing.
* Updated ebuild for latest release.
== Release 1.1.1
* Egg enhancement.
* Ensure that when using an RVM Ruby BUNDLE_PATH is unset.
* rvm gemset import output is a bit nicer.
* Merge error & log files into a single log file.
* libreadline5 => libreadline6
* s/git/git-core/ for ubuntu packages.
* Added libyaml-dev to ruby deps on Ubantos.
* Added after cd hook to latest zsh.
* Added before & after do hooks.
* Added before_install / after_install hooks.
* Revert "a few more quotes"
* When installing as user always install to ~/.rvm
* a few more quotes
* A quoting we will go!
* Added notice upon script entry.
* Yeah... I'm going to pretend that I did not just do that, join me please.
* Bugfix: rvm install 1.8.7,1.9.2
* Silence grep for BUNDLE_PATH.
* Bugfix: only adjust environments files if the directory exists.
* I *love* it when interpreter authors are highly responsive, go brixen!!!
* Check for BUNDLE_PATH before replacing.
* Bugfix: remove the prefix path before configuring for rbx.
* Bugfix: Remove the destination prefix path for rbx install.
* Bugfix: Clean BUNDLE_PATH from environments on install.
* Removed shyouhei/mputs interpreter install as it is no longer necessary or maintained given the official ruby github
mirror.
* Bugfix: Remove destination path when updating from github.
* Updated ebuild for latest release.
== Release 1.1.0 (aka 1.0.23) discontinues use of BUNDLE_PATH and global gems are now picked up by Bundler (1.0.5+).
* Updated ebuild for latest release.
== Release 1.0.23. Bundlercats ho!!!
* No longer use BUNDLE_PATH. Three cheeers for team Bundler! w00t! w00t! w00t!
* Indicated that rbx-head is default for rbx.
* Add Rubinius 1.1.1
* Fix build of macruby-nightly
* Bugfix: default rvm_cd_complete_flag to 0
* Changed rvm_trust_rvmrcs to rvm_trust_rvmrcs_flag=1, as it is a flag. Take Note Folks!
* Updated ebuild for latest release.
== Release 1.0.22 - The quirkey release.
* Feature: rvm_cd_complete_flag for ~/.rvmrc.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Add bug fix for rvm tools path-identifier (and hence support in passenger).
* Default rbx version is now head.
* Bugfix: Detect rvm function load.
* Bugfix: properly call "less -X" as default PAGER, thanks to lmarburger for the heads up.
* Bugfix: Working function load test for both sh and bash/zsh.
* Tyop Fix: it appears that visually rvm and ruby interchange when reading quickly... Thanks again to aspiers.
* Adjusted wording for more clarity, thanks to aspiers.
* Bugfix: Allow RVM loading detection to work with sh, thanks to David Black.
* call less -X to stop the screen from clearing.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Tweaked the nice patch by James Blanding.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* More traditional behavior for './install --help'
* Another string readability tweak.
* See the diff, rvm install ree -C --with-readline-dir=$rvm_path/usr,--with-iconv-dir=$rvm_path/usr,--with-zlibdir=$rvm_path/usr,--with-openssl-dir=$rvm_path/usr was oldskool, now it is rvm install ree --with-readline-dir=$rvm_path/usr
--with-iconv-dir=$rvm_path/usr --with-zlib-dir=$rvm_path/usr --with-openssl-dir=$rvm_path/usr
* bumping jruby to 1.5.5
* Some cleanup of selector.
* Bugfix: gemset name persisting after failed use issue. https://gist.github.com/607116 Thanks be to george.
* Bugfix: "rvm 1.8.7 test.rb" now works as expected, Thanks to Alex Chaffee
* Merge branch 'master' of git.overnothing.com:rvm
*
*
*
*
*
*
*
*
Bugfix: do not include /bin in GEM_PATH. Thanks to cube!
Bugfix: error when "1.8" or "1.9" is used.
Thanks valeri_ufo!
Merge branch 'master' of github.com:wayneeseguin/rvm
Addressing the concerns of portsnap.
Adjust handling of CDPATH to honor new IFS value
Make sure you use the unaliased grep
Updated ebuild for latest release.
== Release 1.0.21
* Bugfix: "rvm install 2.9.2" now fails as expected
* Fixed possible format string vulnerability.
* Fixes a problem where tab completion didn't work when a directory in the path contained a space.
* Updated ebuild for latest release.
== Release 1.0.20
* Bugfix: remove src dir if it already exists before moving extracted dir over.
* Bugfix: unset rvm_ruby_package_file as well.
* Patch by Darcy Laycock <[email protected]> "Convert to an array correctly."
* Bugfix: properly return bison check code. Thanks to joukokar for this.
* Convert to an array correctly
* Suppose (and not Supose)
* Added instructions for abandoning Snow Leopard system ruby.
* Handle /D<Tab> cases so they don't try 'Documents'.
* Fix cd tab-completion.
* Added instructions for abandoning Snow Leopard system ruby.
* Just finish to put comments to better docs
* Put some comments in info and add comments in the #use method
* Add some example in list informations about environments
* The #env_contents should return a array
* Added some comments in env methods (It's better for rdoc =-)
* Bugfix: 'rvm rubygems 1.3.7' thanks to Matthew McEachen (mrm_adgrok) w00t!
* MagLev 24566
* Stick to the most standard tool for Ruby in RVM default gemsets, users can add their own.
* Backed out rvm_export_if_set, sorry teleological too big of a performance hit. There must be another way.
* Enable alias complettion for zsh
* Fixed: s/rvm update --head/rvm get head/, thanks to Nathan Youngman.
* Updated update-head script
* Updated ebuild for latest release.
== Release 1.0.19
* Added scripts/get.
* Bugfix: Turn off error tracing when done.
* Features: 'rvm get latest' and 'rvm get head', Depreciated: 'rvm update' and 'rvm update --head'
* Tweaking for when USER is undefined.
* Hardcode location of sysctl on OSX, thanks to [email protected]
* Updated ebuild for latest release.
== Release 1.0.18
* Merge branch 'master' of github.com:wayneeseguin/rvm
* unsetting RUBYLIB / RUBYOPT thanks to suggestion by khaase
* SHA should be short not long
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Updated ebuild for latest release.
== Release 1.0.17
* I believe this is a bug fix
* Further tweaked fetching user name.
* Switched user name retrieval to "git config user.name", thanks cypher23
* re-comment cd completion code.
* Manually applied patch by teleological. http://github.com/teleological/rvm/commit/21d6083db3fffc5fa92b9ea8814f3f28f7e48c7f
* Bugfix: unset rvm_head_flag with ruby variables, thanks koraktor.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Bugfix thanks to mbarnett: Fixes an issue where cd completion will fail completely if any directories in CDPATH do not
exist.
* Fixes rvm update problem on zsh.
* Fix Ubuntu notes.
* Updated md5 file.
* Commented out _rvm_cd_complete for now, unsure as to the purpose of it.
* Bugfix: Account for rvm_ruby_version being empty.
* Bugfix: properly compute next token for --branch
* Updated ebuild for latest release.
== Release 0.1.16: The NYC.rb Release.
* flags should be tested as integers and be sure to account for nil
* Only trigger loading of rvmrc if in an interactive shell when sourced.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Feature: --branch for use with git head repositories.
* Moved cd autocompletion so it will really run.
* More updates for --repo
* Dumb dumb dumb dumb....
* Bugfix: we have the first user using --repo :)
* Tweaked rvm notes a bit more
* Tweaked rvm notes output for clarity.
* Added a .nil? guard in case rvm_path is not set in the environment.
* Fixing rvm update.
* Updated ebuild for latest release.
== Release 0.1.15
* Trigger any cd hooks when sourced.
* Removed rubyforge as a source for rubygems and the latest ruby enterprise.
* Change git-core to git; git-core now deprecated in Ubuntu repo
* Fixed a silly tyop, thanks dipnlik.
* Rescue LoadError explicitely for Readline failure, thanks to Alexey Antipov.
* MacRuby 0.7.1
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Bugfix: nonzero exit code when unrecognized command.
Allow gemset to pass through the variable clearing.
Addressed Yehudas rvm-prompt slowness query.
Adjusting order of operations for ruby string calculation.
slightly reverted user patch.
Removed patches from openssl for now, until someone tells me WTF happened to them.
Feature: rvm gemset rename X Y (for currently selected ruby)
Getting this to work: rvm my_alias@my_gemset. Previously only e.g. rvm 1.8.7@my_gemset worked.
Worked a bit on the integration tests.
Maglev 24407.
Added notice about re-setting default if user sees the error message.
Bugfix: do not blindly chmod +x, thanks egyp7!
Blasted formatting issues, thanks for the kick in the arse jacquesc.
Updated ebuild for latest release.
== Release 1.0.14
* Added man/ to gem files.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Merged in patch by deliciousrobots, domo arrigato!!!
* Clean up.
* Add a short hand to install all dependencies for ree in appropriate order.
* Revert "Reamin rvm_ruby_interpreter to show current ruby on rprompt."
* Ask readline to use ncurses in ~/.rvm/usr
* Reamin rvm_ruby_interpreter to show current ruby on rprompt.
* FIX: fail to build readline-5.2 on Snow Leopard, and may be on Leopard
* FIX: wrong path to patch
* FIX: missing codes to apply patches
* FIX: rvm_project_rvmrc_default doesn't work
* no need for -d on rm, -f ignores non existent
* no need for -d on mkdir -p: checks that automatically
* Copied over latest install head script.
* Reversed the order of git url attempts.
* MacRuby 0.7 is now default.
* Updated ebuild for latest release.
== Release 1.0.13
* Bugfix: postpend not prepend rvm_path for selector for system case.
* Slightly tweaked conditionally add bin path.
* Missed a spot with rvm_gems_path.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Updated ebuild for latest release.
== Release 1.0.12
* grab revision from the right argument
* fix path bug in wrapper wrap()
* make is also required by arch
* Sing along with me now folks, 'I'm a dumbass after all, I'm a dumbass after all, I'm a....'
* I have been convinced of the readability difference between function declaration styles.
* Merged in bash cd completion patch by albus522, thanks!
* Bugfix: account for empty binary list.
* Bugfix: upgrade, thanks kevwil.
* Further separate out destination calculation.
* Removed extra \\
* Reformatting code.
* only 1.9+ requires a 1.8 compatible ruby to build.
* Tweaking gemsets calculation for telemachus.
* JRuby 1.5.3 is now default.
* Fix disk usage and cleanup to work again with the newly refactored code. Thanks to tomyum for the patch
* Fixed a tyop, thanks piclez.
* Installer will now exit on any unhandled nonzero return status.
* Bugfix: fixed unbound variables in installer.
* Bugfix: no more "pretty slash trails"
* Refactored 'rvm repair gemsets'.
* Feature: rvm repair gemsets
* Bugfix: Ensure that gems/@global and gems/*@ no longer appear.
* Rubinius now defaults to 1.1.0, thanks for the heads up spastorino
* Bugfix: rvm-prompt when jruby is used.
* Bugfix: s/--/-/
* Bugfix: allow bash to list the directories for find to search.
* Bugfix: Fixed order of parameters for older versions of find in post cd completion code, Thanks for the heads up
telemachus.
* Cleaned up upgrade script thanks to feedback from jatan.
* Ensure that bin path exists.
* Whoops, forgot the env!
* Look ma, I am flexible!
* Swap command order.
* Going for the throat.
* Wrap rvmsudo eval command in quotes.
* Tweaked wrapper to display usage when no arguments are supplied.
* Added rvm list ruby_svn_tags to help output.
* Removed call to regenerate_wrappers, thanks jmhodges.
* Bugfix: rvm 1.9.2 gemset create testes now works as expectd, thanks cjbottaro!
* Updated ebuild for latest release.
== Release 1.0.11
* Added rvm_path/bin to mkdir list for install.
* Added NOTE to --passenger flag about Passenger 3.
* NEVER use backticks.
* use $PAGER
* Tab-complete through a chain of dirs works as normal
* Maintain CDPATH tab-completion with RVM's cd
* Tweaked rvm repair output.
* Merged in wrapper regeneration into repair.
* Attempting to debug the wrapper regeneration.
* Use full path for wrappers :/. This means that after rsync users will have to do an "rvm repair all".
* Bugfix: rvm gemset copy X Y now works properly (tyop)
* Set errtrace for installer at the top.
* Default rvm_ruby_string to empty string.
* adjusted wrappers regeneration
* Account for possibility of no rvm_ruby_string in __rvm_run.
* Some cleanup on installer, now runs under shell options noclobber, nounset, errtrace. Now respects --trace as part of args
parsing.
* Add gemset support to aliases
* Fix bug with sourcing items in alias
* Forgot the version number, lol!
* Updated ebuild for latest release.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Applied patch from Christopher Roach, Thanks!
* Outline case statements. Removed another 'echo' statement.
* Removed echo statement for os_type.
* Updated install-system-wide script with support for FreeBSD (tested with FreeBSD 8.1).
* Merge branch 'master' of git.overnothing.com:rvm
* Simple refactoring
* Add rvm_ruby_api env variable to make detection in .rvmrc files possible
* Hook wrapper regeneration into the upgrade process
* Add wrappers to repair
* List fixes, regenerate for gemsets
* Add utility to regenerate all wrappers
* Improved shell escaping for env
* Implement a more advanced method of detecting the default rvm_path in the ruby library
* Added rvm_path to env file exports.
* Bugfix: --trace actually produces a trace once again. Bugfix: automatically regenerate wrapper scripts if missing.
* Adjusted rbx compile to use the wrapper script for the 18 compatible ruby.
* Defaulting rvm_ignore_rvmrc, thanks Cicloid.
* Bugfix: Testing for directory in .rvmrc, thanks bjencks!
* Initialize rvm_ruby_interpreter to first part of rvm_ruby_string if not set when entering the selector.
* More cleanup.
* Bugfix: rvm 1.8.7,1.9.2 gem install X
* Bugfix: escape any / characters in in the match regex.
* Bugfix: symlinks for default, etc now get created again!
* Some more cleanup.
* Bugfix: rvm 1.8.7,1.9.2 exec ruby -v
* PIBRQBAS
* Replaced .nitems with .compact.length
* Bugfix: cleanup tracing on exit.
* Bugfix: rvm 1.8.7 exec ls
* Do not load completion if readline failed.
* Bugfix: move maxhistsize within the scope of Kernel::at_exit
* fix % to %% substitution in log script for older bash
* use an alternate method to save irb history until irb/ext/save-history is fixed
* Applied patch by bjencks.
* Bugfix: rvm gemset delet cucumber now does what is expected.
* Check in irb fix which shouldn't be needed
* Bugfix: rvm package install zlib.
* Whilst putting the cart before the horse can be quite amusing, reality sets in after we do not get to our destination.
* Bugfix: rvm system now correctly appends instead of prepending rvm bin path.
* Apply patches after running ant dist if installing JRuby Head.
* Array!
* Cleanup any swap files found in rvm_path, if they exist.
* Missed a few variables during teardown, thanks bjencks!
* Bugfix: Adjusted loading detection to accommodate for ZSH. Thanks eregon.
* Added ~/.rvm/hooks/after_cd hook ability to RVM.
* Simplified rvm function detection.
* RVM now detects whether it is loaded in the current shell as a function when sourced.
* Altered the way that rvm_loaded_flag is set for byrnejb.
* Updated ebuild for latest release.
== Release 1.0.9
* Bugfix: Initial gemsets are now behaving.
* Bugfix: Default log path to rvm_path/log
* Still working on fixing initial gemset import, commented out while debugging.
* Bugfix: needed the extra level of interpolation.
* Fork! Fork! *BOOM*
* Bugfix: rvm alias list. rvm X --default. rvm list default.
* Bugfix in alias creation, will no longer duplicate.
* Bugfix: Removed [[ keyword from around md5 comand test.
* Going for the throat, explicitely.
* Moved tests in preparation for the separation.
* Bugfix: jruby cp issue.
* Explicitely export all RVM variables inside scripts.
* Bugfix: Removed extra line from PATH parsing.
* Removed start of line from awk, only doing a single export now.
* Quote out actual_file
* Do not unset result.
* Updated ebuild for latest release.
== Release 1.0.8
* Fixed double or nothing bug.
* Almost there, double or nothing eh?
* This time I have ZSH to thank for finding a bug.
* Cleaned up upgraded/migrate usage().
* Missed a spot.
* Bugfix: rvm gemset list. Thanks ianw!
* Maglev 24209 -- Rails 3.0.0 Support
* Defaulting rvm_gems_path
* Ensure bin_path has defaults
* Grumble.
* Environment is much cleaner new. More code cleanup.
* Bufix: solved the case of the missing line.
* Bugfix: Fixed typo, setting defaults now works.
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Missed a spot.
Bugfix: prefix set in env no longer carries through to wrappers.
I am an arse. I know better than to use find/replace :/
Setting source directory explicitely.
Merge branch 'master' of github.com:wayneeseguin/rvm
Find and replace? Yes. It is that technique where you take perfectly working code and replace it with bugs.
Bugfix: location of rvm_ruby_src_path was not set.
Fix zsh completion for gemset commands
Fixing zsh completion syntax
rvm_tmp_path no longer defaulted in global namespace.
rvm_docs_path no longer default in global namespace.
rvm_log_path is no longer in the global namespace
Removed rvm_src_path from global exports.
rvm_archives_path, some more code cleanup.
rvm_config_path and rvm_rubies_path
Removed rvm_environments_path and rvm_wrappers_path.
Removed rvm_hooks_path from configurable.
Run in parallel, saves a few seconds or more depending on the # of gems in a gemset.
Removed 'info: ' prefix from info, now labels only show for other levels.
Feature: rvm gemset unpack Bugfix: ruby_string() now correctly grabs the current ruby string.
Removed redundant libs, as requested by the department of redundancy department.
Added --trace and --verbose options to rvmsudo.
bugfix: rvm --shebang inspect gem
Safely strip rvm elements from the PATH.
Updated ebuild for latest release.
== Release 1.0.7
* Bugfix: rvm gemset create X
* Bugfix: ensure rvm reload you know... reloads?
* Cleaned up installer some.
* Bugfix: rvm_pretty_print_flag now actually prints with colors in rvm list.
* Visual cleanup on list.
* Bugfix: find -iname ordering, thanks matti
* Missed a spot!
* Trimming down more, s#rvm_gemsets_path#rvm_path/gemsets#g
* Trimming down more, s#rvm_scripts_path#rvm_path/scripts#g
* Unset head_flag when an rvm call completes.
* Reflect that p378 is the default in list known.
* Modify default annotation based on suggestion from gitmate on github.
* Set empty binaries correctly
* Bugfix: rvm gemset empty now works (tyop). Added extendedglob to zsh.
* The good news is I think I found the culprit. The bad news is I have to recompile 1.9.2 again to test this.
* More cleanup on scripts/manage.
* Carefully handle binaries array.
* Fun with find, Scene I, Take III.
* More fun with find and seek!
* I just *love* the way CentOS keeps their systems up to date :/
* Bugfix: bashd zsh.
* I need to go back to kindergarden and learn how to type.
* More fun with ZSH.
* Removed -G, --archives, --src path options in preparation for consolidation and "system vs user".
* Removed exit on cleanup.
* Some people like consistency too much :/
* removed gemset separator from global initialize.
* Updated ebuild for latest release.
== Release 1.0.6
* Tweak bison detection.
* Another performance tweak, this time to selector which is called neigh every time.
* Much work with the loco locals.
* Allow ruby-1.8 in 1.8 compatible rubies.
* Slight cleanup on gemset_snapshot
* Went one level too deep.
* rvm list much faster feedback now.
* Bugfix: "rvm use/install/... jruby-head" no longer inserts the version.
* Added simple CLI parsing to install-system-wide
* Use rvm_revision to specify a particular git revision of rvm to install
* Turns out maxdepth 1 is MUCH faster than simply specifying the depth.
* ls > /dev/null
* Change to an array
* Account for extra spaces.
* Much faster version gathering.
* Explicitely remove default from set operations.
* * wayneeseguin sprays aliasbgone
* Ensure ruby string is set.
* Ever so slowly spreading my cheeks to remove my head...
* Who stole my bloody quote? Cheap bastard...
* Removing usages of =~ so as to not be "idiotic", by the power of GreyCat!!!
* Altered git detection.
* Make configure flags immune to the mass cleanse.
* Explicitely set rvm_ruby_configure_flags when possibly first used.
* Bugfix: do not quote args of the regex.
* Slight cleanup of rvm binscript.
* Simplification thanks to ashb.
* Bugfix: RVM.tools_strings('1.9.2')
* Bugfix: rvm update
* Updated ebuild for latest release.
== Release 1.0.5
* More hashtags
* tyop fix, thanks eduardohl
* The world is not yet ready for hardcore bondage...
* I comand thee!!! ... Why do you not listen?!
* Balls out...
* Push... Pop... *Poof*!!!
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Put back in the cwd :)
Fixing an issue caused by me not having a clue about bash programming.
Bugfix: Space strippers to the rescue!!!
Bugfix: rvm gemset copy a@b c@d
Got the lil bastard that time!
'1.8.7@rvm-site gem env gemdir' works as expected
Made ruby specific variables more consistent.
Working on Remears request, hash tagging the installations.
More progress.
Merged --trace and --debug, respecting differences with zsh.
Merge branch 'master' of git.overnothing.com:rvm
More consolidation.
Update tools with a minor fix
Bugfix: __rvm_environment_identifier now returns proper env id again.
Bugfix: Adjusted the way CLI arguments are parsed.
Updated ebuild for latest release.
== Release 1.0.4
* Bugfix: rvm gemset use X
* More installer cleanup.
* Removed spinner and sleep from install. While they were neat, non-interactive installs did not like them ;)
* Tweaking install messages.
* Bugfix: rvm gemset use <gemsetname>, thanks owen1
* Bugfix: tyop in CLI, thanks to RichGuk!
* Updated ebuild for latest release.
== Release 1.0.3
* Bugfix: Gemsets are now working as expected again.
* Added pretty print to Upgrade notes.
* Added rvm_pretty_print to rvm notes, thanks eregon.
* Bugfix: Bandaids go sticky side down. (gemset sticky flag now set when expected).
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Bugfix: global cache return value.
* Quote $PATH when used with printf to defined $new_path. This allows spaces in $PATH.
* Fix ZSH completion for the new command disk-usage
* Fixed tyop, added consistency
* Bugfix: default gemsets now import.
* Let us be more direct, shall we?
* Thanks to Sutto (Darcy) for pointing out the obvious.
* Turns out older bash shells could not handle the redirect operator :/
* Added error handling around the sourcing of primary scripts when loading RVM.
* Bugfix: ZSH did not like unset/declare.
* ZSH goosed me.
* Finally got around to fixing scripts/log ;)
* Forgot to export PS4, thanks thewoolleyman!
* Bugfix: rvm default gemsets now load properly.
* Ten Thousand Lines... will give you such a crick in the neck!
* Returns are now through utility and some of gemsets
* More slow progress making things more robust.
* Added "rvm strings" into CLI. More returns. More cleanup.
* Tweaked rvmrc trust message wording. Added variable name and explicit returns to a few functions for clarity.
* Speed up scripts/log by using builtins. Removed stray xtrace off.
* Added command locations for bash/zsh in rvm info.
* __rvm_environment_identifier() is now using strictly shell builtins, should also work in more cases now.
* Default all logging to terminal to not use colors. set "export rvm_pretty_print=1" in ~/.rvmrc to override this.
* Make that more of a sanity check until I track this bug.
* Skip patching if it is not a file.
* More headway with --patch.
* Bugfix: rvm info
* Arrays make me feel shifty... Disco Fever!
* Bugfix: extract gem_prefix properly. Thank you sikachu!
* We want to eliminate all spaces.
* Ensure we are calling a binary for gem in gem_install
* Updated ebuild for latest release.
== Release 1.0.2
* Bash completion for help subcommand.
* Escape newlines for old shells.
* Add known rubies completion for install subcommand
* Add bundler to ree global gemset.
* Yet another space stripper... How drunk was I last night? ...
* Simplifying space strippers, I was over thinking things.
* Removed scripts/manpages, turns out that manpath finds it based on PATH, reduced complexity yay!!!
* Commented out manpages, should be found based on PATH by manpath
* Bugfix: Arg parsing in package
* Turns out the match, was not a match.
* wow... I really need to go back to gradeschool...
* Dodge Z alias!!!!!!!
* Found two more squealers
* Someday the subtle differences between zsh and bash are going to drive me batty :-p
* Patch splitting moved to internal.
* Begone relic of the past.
* Bugfix: Account for missing gemset.
* BugFix: Bugfix Fixed.
* Bugfix: matching in 18 compatible ruby based on new grep. Plus more cleanup.
* Very slowly cleaning everything up.
* Clarified the .rvmrc trust message a bit.
* Suddenly, I feel like watching LeekSpin for an extended period of time... ( http://leekspin.com/ )
* Merge branch 'master' of github.com:wayneeseguin/rvm
* More space $HOME friendly.
* Remade symbolic links of 1.9.{1,2} global gemsets to that of 1.8.7.
* Updated gemsets to use final release of Bundler.
* Make __rvm_update_rvm extract correct, with thanks to loumz for pointing out the source of the problem
* Bugfix: because some people are perfectionists ::cough:: dbussink ::cough::
* Updated ebuild for latest release.
== Release 1.0.1
* Missed a few spots.
* Consolidated path cleanup code, removed paste as it is a high profile alias target. Some minor tweaks.
* Copy across bundled gems as part of the jruby install process
* Merge branch 'zsh-warning-fix'
* Actually commit the damn file
* Merge remote branch 'origin/happy-fun-docs-time'
* Update load-rvmrc reference
* Add more docs
* Merge remote branch 'origin/path-fix'
* Simple fix to make sure rvm is added to the path, even with system loaded
* Typo broke rvm list known
* I encourage you to learn more about your shell every day, it will be beneficial.
* A debugging we will NOT go...
* Properly detect interactive sessions.
* Improve ruby api trust-checking, primarily for passenger stuff
* Removed the 'fun with perl' items, some people have no sense of humor.
* Prevent unintentional exit code 1 when sourcing scripts/rvm
* alias why dost thou hateth me so...
* s/$(pwd)/$PWD/g
* Add gem hook
* Manually rehash whenever path is set
* Merge remote branch 'origin/better-path-handling'
* Handle conditionally adding rvm to the path
* Updated ebuild for latest release.
* RVM 1.0.0
* Fix set operations
* Check trustworthiness around whole thing
* Implement rvmrc loading security
* Merge remote branch 'origin/switch-to-bzip'
* Add bundler to rvm gemset
* make rvm use bz2 for mri rubies
* Merge remote branch 'origin/auto-install-bundler'
* Merge remote branch 'origin/head-installer-fix'
* Add check for 1.8.7 on 1.9.2-head
* Make rvm automatically install bundler as needed
* Rehash binaries on switch, forcing it to forget seen executables / lookup new path
* Add zsh completion script
* Problem with installing glib on mac os x snow leopard. Fixed by adding a -I compiler flag and setting the path for pkgconfig. Also added installation of pkg-config and gettext to glib function instead of mono function
* JRuby 1.5.2 is now default for JRuby. Thanks for the heads up stepheneb.
* And lo we fight the evil alias Hydra wherever a head may rear.
* Updated ebuild for latest release.
== Release 0.1.47
* Merge remote branch 'origin/generate-default-wrappers'
* Merge remote branch 'origin/set-warning'
* Make it generate default wrappers as expected
* Fix rvm_project_rvmrc_default
* Show a warning on set operations when passed what look like options
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Merge remote branch 'origin/xargs-fix-dangit'
* Merge remote branch 'origin/revert-set-all'
* Change the default behaviour of the set operations, fix the rubies option
* Make basename have the argument seperator
* Add uninstall to the blacklisted action
* Make manage receive the correct arguments, pass correct string
* Don't allow $rvm_gemset_separator in gemset names (e.g. "my@gemset@rocks"): It works fine when you create the gemset, but
fails in interesting ways when trying to delete it.
* Merge remote branch 'origin/hudson-plugins'
* Adjusted notes for apt based systems, thanks jmettraux.
* Added 1.9.2 rc1/rc2 to known.
* Add plugins to the repo
* Updated ebuild for latest release.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* 1.9.2-p0 is now default, w00t!!!
* Typo in github url.
* Add install system wide fixes for xargs
* Bugfix: Fixed a *very* irritating bug related to cd "hanging" on exit sometimes.
* fix -G, --archives, -source options
* Altered rvm info to report both zsh and bash versions.
* Correct restrict basename argument count
* Fix installer showing the source line
* Merge remote branch 'origin/rvm_bin_path-fix'
* Correctly calculate paths to remove double-slashes
* Add default-with-rvmrc / rvmrc for rvm set operations.
* Fix minor issue with rm -rf
* Blasted aliases.
* 1.8.7-p302 is now default (Security Vulnerability Patch Level).
* Merge remote branch 'origin/system-wide-tweaks'
* Add system wide rvm tweaks
* Merge remote branch 'origin/set-exec-fix'
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Maglev 24067.
* Fix set exec options
* Use default rvm for rvm-auto-ruby
* Updated ebuild for latest release.
== Release 0.1.45
* Fix rvm_prefix correction logic
* Refactor rvm migrate to take into account aliases and wrappers
* Implement rvm upgrade
* Merge branch 'rvm-migrate'
* Implement item+alias as shorthand on rvm use for creating aliases
* Cleanup how rvm_prefix works
* Merge remote branch 'origin/no-hardcoded-env-path'
* Implement rvm migrate
* Don't hardcode rvm_environments_path inside the rvmrc
* Make rvm gemset copy actually work correctly again
* Added missing file append (>>) in ebuilds.
* Use grep to suppress some noise when running a root installation as non-root.
* Typo fix: __rvm_ensure_has_enviroment_files -> __rvm_ensure_has_environment_files
* Apply ebuild changes from 99999 to template.
* Remove broken and unnecessary installation of "environments/system" file from ebuild.
* Added some informative comments to the ebuild.
* Moved some ebuild template lines around to minimize differences between git-based ebuild and regular ebuild.
* Rename variable: rvm_sandboxed -> rvm_selfcontained .
* A little more cleanup. Also, please use two spaces no tabs for this project. Thanks!
* Minor cleanup.
* added code to fallback to http:// if git:// or ftp:// fails. This allows rvm to work behind corporate firewalls with http
only access to the internet
* Fixed system var not getting set correctly in scripts/maglev for OpenSolaris environment.
* Apply recent ebuild template changes to rvm-99999.ebuild .
* Removed "touch system" from ebuild, since rvm itself should take care of this.
* Merge branch 'set-operation-tweaks'
* Add optional targets for the set operations
* Updated ebuild for latest release.
== Release 0.1.44
* Updated ebuild for latest release.
* Implement rvm_ignore_rvmrc, to do installs without rvmrc files
* Move __rvm_environment_identifier back to utility to avoid conflicts.
* Correctly expand rubies
* Make rvm gemset copy correctly report the err with no args
* Fix the ebuild
* Misc tweaks to the sandbox installer
* First set of work on implementing rvm_sandboxed
* Fix __rvm_quote_args_with_shift
* Totally not the droids you are looking for.
* Merged converter by Darcy.
* sh safe environment files.
* Fixed ree named install
* What... you want MORE?
* Cleanup, aisle 3! Named installs actually compile now :)
* correctly use rvm_ruby_name in blank selector
* Adjust package name for ruby when name is used.
* StripNzN
* Feature: Named installs.
* Fix rvm update --rubygems
* Misc code tweaks, including converting not -z to -n
* Properly expand the path for install
* Install current rubygems correctly
* Rename textmate_ruby to rvm-auto-ruby since it's universally useful
* Fix rvm update --rubygems
* MANPATH gets clobbered after rvm loads. Reversing the variables seems to help.
* Bugfix: when cd fails properly report the exit status.
* A single textmate_ruby for all!
* update rvm opts and add snapshot command to completion
* Added some sanity checks to file removals.
* Default rvm flags before first use when loading.
* Added no-default option to rvm-prompt
* Prevent an alias of "tr" from "breaking" RVM
* Removing rdoc from global and default gems.
* Allowing the aliasing of digits directly.
* MagLev 23913
* Added an extra line detailing what MRI/ree/rbx stand for to notes, thanks douglascamata.
* Added a warning message with a pointer to docs for when irb cant load readline. Thanks douglascamata.
* Temporarily reverting rvmsudo until we talk things out with thewoolleyman.
* Added sanity to the patchsets installer.
* Refactor how alias, docs and rubygems are invoked to be consistent
* Ensure we set the path
* Clarified a generating message, Thanks cehoffman!
* Fyxed a tyop, Thanks cehoffman!
* Improve rvm-shell to take into account .rvmrc
* Implement rvm-repair
* Set path variables with a check for valid path.
* Updated ebuild for latest release.
== Release 0.1.43
* Merging Darcys record-install-commands branch.
* rvm_patches_path will be created by following lines
* Implement strings on 'rvm tools'
* Implement rvm snapshot {save,load}
* Updated ebuild for latest release.
== Release 0.1.42
* Add missing info functionality to api, fix list_strings output
* Implement rvm load-rvmrc
* Merge remote branch 'origin/rvm-usage'
* Make rvmsudo use -E
* Implement rvm disk-usage
* Merge branch 'master' of git.overnothing.com:rvm
* Feature: May now switch gemsets for the current interpreter via 'rvm use @gemsetname'
* Refactor the way clang integration works
* Escape percentages in the message
* Implement --clang option when install rubies.
* MagLev Palindrome Release.
* Use the actual environment identifier
* Revert the code to force 32bit, simplify 64 bit checks
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Merge remote branch 'origin/multiple-ruby-management'
Merge remote branch 'origin/man-fixes'
Merge remote branch 'origin/install-tweaks'
Fix invocation of scripts/manage with multiple rubies
Correct set the default rvm_prefix
Tweaks to how rvm_prefix is handled in scripts/initialize
Miscellaneous tweaks to the install proce
Removed notice about 1.8.7 patchlevel now that it is back to latest. Thanks blowmage.
Fix the install process for man pages, generate both versions
Replace readline fix with one that doesn't need a patchlevel
Remove archives if interrupted mid-download
Add install-system-wide
Add is-at-least check
Refactor the way rvmrc is checked to make it reusable outside of cd
Revert "Installer seems to be a bit jacked up somehow... fixing."
Installer seems to be a bit jacked up somehow... fixing.
Added an empty scripts/man to prevent silly error messages.
Modify rvm-shell to take the optional first argument as a ruby string
Fix the check on for arg count in scripts/wrapper
Nice... missed the debugging comments & code from the contribution.
Added mkdir of rvm_patches_path during install, thanks niw!
Fix and improve openssl options
FIX: spaces, missing options
Merge remote branch 'pistos/respect-rvm-prefix-3'
Fix implode spelling error in completion
Adding manpage
Fixed a tyop.
Merge branch 'wrapper-tweaks'
Merge of Darcy's work on rvm-shell
Tweaks to wrapper generation
Add backported openssl fixes to a patch
Merge branch 'master' into respect-rvm-prefix-3
Miscellaneous bug fixes, namely related to exception
1.9.2 is now defaulted to rc2, w00t!!! Thanks Pistos!
Tweak for the rvm install process
Use correct item
Simplify the md5 code
md5 should have more info
Make scripts/md5 work correctly on ubuntu, add md5 sum for the latest ree
Add ability to override the command check in certain situations
Bug fixes galore - also, use_from_path!
Implement tools in the ruby api, fix a few misc bugs
Add scripts/tools, implement identifier and path-identifier
Since we are breaking out of the loop, this does not actually do anything on reflection.
Initial Ruby API, written by Darcy!!!
Updated ebuild for latest release.
== Release 0.1.41
* Feature: Added 'rvm list known_strings', thanks to lenary for the idea.
* Maglev 23767.
* Do *not* use 1.9.1-p429. http://redmine.ruby-lang.org/issues/show/2404
* Respect $rvm_prefix when checking for root user.
* corrected grammar (no comma necessary) and made consistent with other "info:" statements
* Fix for wrong working dir showed on prompt when project .rvmrc is loaded.
* Commented out dos2unix for now.
* More misc work on fixing the build process, nameling detecting rubies
* Don't mangle the supplied path in __rvm_ruby_string_paths_under
* Defaulting 1.9.1 to p429
* rc1 is now default for 1.9.2, thanks for the heads up bcg.
* better fix to allow users to specify patches with absolute path
* Fix rvm_ruby_configure_flags so that it only replaces commas with spaces when they precede another option, thus allowing
option values to contain commas.
* Patch to facilitate building Ruby for a specific architecture on Snow Leopard
* Use patchlevel default of 1
* Merge conflict resolved.
* Copy files in to the correct man path
* Simplify doc building process to remove docbook2x requirement, update docs
* [WIP] Work on tweaking the build process for docs
* Add progress details to the docbook process
* manpath initialization a bit corrected
* manpage itself corrected
* installation script updated to install manpages
* Basic manpage for rvm implemented.
* Expand patch name support
* Start of refactoring on patches support, including patchsets
* Implement --patch{,es} support in rvm.
* Ruby 1.8.7-p299, w00t!!!
* Fix trailing s in the prompt
* fixes pkgconfig bad url for curl
* fixes iconv bad url for curl
* Updated ebuild for latest release.
== Release 0.1.40
* Merge remote branch 'origin/list-fixes'
* Fix rvm list for architecture wrt gemsets
* Reimplement the global cache, controlled via rvm gemset globalcache
* Merge remote branch 'origin/gemset-update-and-tweaks'
* Add rvm gemset update to the usage
* Implement rvm gemset update and add a bit more info to set output
* Refactor script/gemsets to have a usage message
* Correctly generate an irb wrapper for rubinius
* Use 'rbx irb' on rubinius
* Start of refactoring for rbx-irb
* Implement rvm cleanup
* Refactor scripts/info
* Start replacing common inclusion patterns with $rvm_scripts_path/base
* Remove ruby binaries with rvm remove along with aliases
* Check for 1.8 compatible rubies and use them if available.
* Call __rvm_become before single exec.
* Merge branch 'warn-on-rubyopt'
* Show warning on upgrade as well as install
* Warn if RUBYOPT is present as part of the install.
* Merge remote branch 'origin/ruby-head-fix'
* Make ruby-head install rubygems correctly
* Merge branch 'install-message-fixes'
* Clarify the message regarding sourcing rvm
* Fix rvm use --default
* Make rvm reset really unset all of the old env vars
* Added libyaml-devel libffi-devel to yum based distros, thanks rosenfeld for the suggestion!
* Bugfix: when disk and loaded versions differ, the message now makes more sense.
* Record packages when they are installed.
* Feature: package urls are now read from config/db
* added rvm list gemsets, which is like rvm list rubies, but shows every gemset eh
* MagLev 23673
* make rvm update respect the head flag, use http for updating from head
* Merge remote branch 'origin/rvmrc_cd_refactor'
* Tickets https://www.pivotaltracker.com/story/show/3870044 (rvm should revert back to the last manually set (or default
version) when cd'ing to a directory that doesn't have a .rvmrc file above it.) and
https://www.pivotaltracker.com/story/show/3869970 (.rvmrc should not be re-sources when cd'ing under the same project)
* Version bump, 0.1.39
* Updated ebuild for latest release.
* Let users configure the rubygems version to install for a given interpreter
* Prevent it from trying on rubinius or jruby
* Make installing different rubygems versions work
* Added rubygems control script and CLI.
* Fix bad variable naming
* Use eval instead of calling exec directly
* Work on adding rvm exec
* When showing info for system, don't show the ruby section
* Fix rvm gemset copy
* rvm alias create name ruby should check that name isn't a ruby string
* Fix set action exit code, make benchmark correctly work with sets
* Fix build options for ree-head
* Modified rvm-prompt to support using unicode format parameter in conjunction with other format paramters. For instance
"rvm ree ; rvm-prompt u v" will now return "-1.8.7". Previously, the unicode parameter would short circuit all other
formatting.
* Bugfix: 'gem' command in rbx now works.
* Actually fix match
* Fix issues with unterminated regular expressions in scripts/match
* Fixed a bug in BTU, added db_test file.
* Bugfix: scripts/match now works properly again, and the tests are running again!!!
* Feature: More compatibility with all shells for scripts/match. Thanks to Brian Jones for the motiviation :)
* corrected patch-prefix presence checking
* Merged in changes by Yoshimasa Niwa (niw). Thanks!
* patch prefix handling added; README updated accordingly
* vim temporary (swap) files ignorance
* Bugfix: explicitely use the 1.8.7 wrapper for rbx install.
* Half tolken for a half wit?
* Feature: Allow common configure options to pass directly through the RVM CLI Example: rvm install 1.8.7 --enable-shared -enable-pthreads
* Bugfix: gemset_pristine
* Added/fixed typos for alias and fetch help docs
* updated test cases for new "s" switch used to add "system" to the prompt when system ruby is in use.
* Require s (system) switch to return "system" when system ruby is in use.
* Bugfix: --passenger now regen's wrappers every time.
* Remove invalid (it seems) rvm_debug_flag stuff in scripts/cli
* Removed --jit from usage, thanks tmorini
* Updated ebuild for latest release.
* Let users configure the rubygems version to install for a given interpreter
* Prevent it from trying on rubinius or jruby
* Make installing different rubygems versions work
* Added rubygems control script and CLI.
* Fix bad variable naming
* Merge remote branch 'origin/set-exec'
* Use eval instead of calling exec directly
* Work on adding rvm exec
* Merge remote branch 'origin/system-info-fix'
* When showing info for system, don't show the ruby section
* Merge remote branch 'origin/gemset-copy-fix'
* Fix rvm gemset copy
* rvm alias create name ruby should check that name isn't a ruby string
* Fix set action exit code, make benchmark correctly work with sets
* Fix build options for ree-head
* Modified rvm-prompt to support using unicode format parameter in conjunction with other format paramters. For instance
"rvm ree ; rvm-prompt u v" will now return "-1.8.7". Previously, the unicode parameter would short circuit all other
formatting.
* Bugfix: 'gem' command in rbx now works.
* Actually fix match
* Fix issues with unterminated regular expressions in scripts/match
* Fixed a bug in BTU, added db_test file.
* Bugfix: scripts/match now works properly again, and the tests are running again!!!
* Feature: More compatibility with all shells for scripts/match. Thanks to Brian Jones for the motiviation :)
* corrected patch-prefix presence checking
* Merged in changes by Yoshimasa Niwa (niw). Thanks!
* patch prefix handling added; README updated accordingly
* vim temporary (swap) files ignorance
* Bugfix: explicitely use the 1.8.7 wrapper for rbx install.
* Half tolken for a half wit?
* Feature: Allow common configure options to pass directly through the RVM CLI Example: rvm install 1.8.7 --enable-shared -enable-pthreads
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Bugfix: gemset_pristine
Added/fixed typos for alias and fetch help docs
updated test cases for new "s" switch used to add "system" to the prompt when system ruby is in use.
Require s (system) switch to return "system" when system ruby is in use.
Bugfix: --passenger now regen's wrappers every time.
Remove invalid (it seems) rvm_debug_flag stuff in scripts/cli
Removed --jit from usage, thanks tmorini
Remove type rvm from info, does not apply anymore.
JRuby 1.5.1
Changed apt-get check to aptitude, overwhelming response that it is far superior.
Commenting out rvm_history until we can make the solution more robust.
John Trupianos *awesome* contribution to RVM, rvm remove now works properly w00t!!!
Use ree 2010.02
Fix for zsh wrapper error
Refactor the generated wrappers
Misc tweaks to the install process
Misc fixes and integration for __rvm_run_with_env
new rvm env inherits trace flag
Introduce utility functions to run stuff in a given env
Rearrange where the gem import is run
Bugfix: Actually add the code lines to the wrapper file.
Added error checking around environment loading in wrappers.
Bugfix: sh has '.' not 'source'.
Added PATH to rvm info.
Bugfix: If default flag is set when wrapper is called as root, link binaries to bin path.
When root, default the bin path to /usr/local/rvm
Updated ubuntu 'rvm notes' message.
rbx-1.0.1-20100603
MagLev 23577
Merge branch 'repo-folder-tweaks'
Refactor the watch rubies are fetched
Make test/suites exit code reflect the result
Updated ebuild for latest release.
== Release 0.1.38
* Tweak md5 slightly.
* Update the order of calls that create the .rvmrc
* Beginnings of .rvmrc create refactor.
* Merge branch 'gemset-ruby-strings'
* Use mkdir -p instead of mkdir
* Allow importing gemsets into multiple envs
* Ensure we have the directory first
* General alias / selector bug fixes.
* Use subshells directly to import the gemset stuff
* Fix recursion in alias - thanks to fermion for the bug report
* Use --alias instead of --aliases
* Add --aliases option to rvm install
* Record each rvm command to ~/.rvm_history
* Promote 'rvm notes' message to the top of upgrade notes.
* Removed install_source_path for gemsets
* Ensure remove correctly deals with the alias, ensure system has a blank environment file
* Updated ebuild for latest release.
* Implement 'rvm gemset prune'
* Generate wrapper by default, fix shift for wrapper arguments
* Use find and misc enhancements in scripts/install
* Fix default and system on sets
* Added header in 'rvm list known' for MRI Rubies
* Refactor the way wrappers are used internally
* Make that a quad espresso.
* Bugfix: I need more caffene :/
* I will be attending remedial commit training next week.
* Bugfix: initial gemsets pathing.
* How did that happen???
* Merged Darcy's repo directory changes.
* Bugfix: No longer spew errors on Importing gemsets part of install.
* Bugfix: filesystem key-value db now properly handles kinky values.
* Feature: May now specify default configure flags for MRI Rubies. Set in ruby_configure_flags in ~/.rvm/config/user.
* grr...
* Feature: Nested {default/global/gemset_name}.gems files from ~/.rvm/gemsets.
* Minor version bump.
* Updated ebuild for latest release.
* 1.9.2 defaults to preview3
* Updated install notes for p174 switch.
* 0.1.36 version bump.
* Default 1.8.7 p174: 2010-05-31 13:47 <@wayneeseguin> drako: OK .. what are you suggesting to put 174 as default? 2010-0531 13:47 < drako> wayneeseguin: yes 2010-05-31 13:48 < drako> because is a p248 related bug 2010-05-31 13:48 < drako> in
1.9.1 and head-ruby rails3 works ok 2010-05-31 13:48 < drako> but rails 2.3.x wont work ok with ruby 1.8.7 >= p248 2010-0531 13:48 < drako> and since its still the stable branch
* Add in log levels to shell log output lines.
* allow for installing with a prefix
* Merge branch 'gem-install-fixes'
* Make rvm gem install act as expected, don't call out to rvm gemset install
* Merge branch 'docs-in-install'
* Remove trailing semicolon
* Call cd . after rvm reload, casuing it to reload rvmrc
* Allow users to install docs as a part of the install process
* Update rvm_environment_identifier to respect system and the current state of ruby
* Correct negate the bison command
* Re-add the trailing newline for logging. Check for no bison and return from install.
* Check for bison when installing ruby head
* Remove extra commented lines
* Updated ebuild for latest release.
== Release 0.1.35
* Merge branch 'set_refactoring'
*
*
*
*
*
*
*
*
Add newline after use statements
Refactor the way set works, using rvm_ruby_strings
Minor refactoring to how __rvm_environment_identifier works
Typo fix in installer, thanks to noocx.
unset rvm_ruby_strings inside of __rvm_teardown
Refactor rvm_ruby_version's use for multiple rubies to be rvm_ruby_strings
Use rvm_ruby_strings in set and clean up the variable
Updated ebuild for latest release.
== Release 0.1.34
* Change the way info is called, use the correct environment identifier
* Fix the way ri generates doc, installing them into system
* Update the notice for downloading rvm
* Removed extra line on log output.
* Clean up rvm install message more.
* Added config/known file.
* Features: 'rvm list known' now returns immediately and does not include svn. 'rvm list ruby_svn_tags' now lists the ruby
svn tags available. 'rvm list known' alters behavior based on context.
* Alter log output for better consumption by external tools without loosing the level.
* Bugfix: If you do not have a system ruby installed rvm should load the default properly.
* Added contrib/gemset_snapshot script.
* Removed global gem caching. Excellent idea, however, it does not work for all use cases.
* Feature: __rvm_setup / __rvm_teardown Thanks to amikula:
http://github.com/amikula/rvm/commits/790cfa052702be6c3d7874af6b6646ec321b843a
* Fix scripts/info wrt printf
* Updated ebuild for latest release.
* Feature: MRI Ruby URLs are now configurable from config/{user,db}.
* Fix for __rvm_gemset_gemdir
* Bugfix: Set rvm_ruby_gem_path in selector.
* Tell users in rvm notes that they need 1.8.7 for 1.9.2-head / rbx. Thanks jmettraux!
* Bugfix: Be much more assertive about loading the default environment.
* Feature: 'rvm gempath', 'rvm gemhome', similar for gemsets.
* Unset rvm_ruby_string if rvm has not yet been loaded.
* Reimplement --default using alias and handle migration
* Bugfix: Account for multiple lines being in the default file.
* Bump version #.
* Add rvm_gemsets_path fix
* Initial post-install gemsets code.
* Allowed gemset to pass through on empty action.
* Made the post-help message more helpful.
* Made post-help message more concise.
* Added scripts/list.
* Remove System from list.
* Bugfix: 'rvm info' now reports correct environment information.
* Logging output now feeds a newline at the end.
* 'rvm list known' shows 1.0.0 for rbx- default. Thanks Defiler.
* Bugfix: 'rvm install rbx' now properly downloads the source when the archive is not correct.
* Added a missing line break.
* Changed 'echo -e' to 'printf'.
* Proper quoting for echo of parameters.
* rvm info without parameters now runs in current env.
* For Rubinius call configure with ruby configure.
* MagLev 23530
* Bugfix: missing test operator
* Add initialize to scripts/info
* Add rmv env (with option --path) to get environment info
* Add documentation built into rvm for wrapper
* Implement environment files and switch symlinks for wrapper scripts
* Silencing if GEM_HOME does not exist. Thanks Sutto.
* Append to file instead of overwrite.
* Feature: generate ri-site / ri for real this time.
* Sticking with the default -client for jruby tarcieri.
* Correct the json output for successful and errors, ensuring it wraps the rubies correctly
* Added 'rvm help info'
* Extra space after ruby version in output
* 'rvm info' is now an external script callable by sections and can specify rubies..
* Adjusted rvm-prompt sed based on Sutto's comment.
* Remainder of our changes from pairing this morning with Sutto.
* Bugfix: rvm-prompt double dash bug in rbx, thanks be to Sutto.
* Bugfix: rvm-prompt double dash bug, thanks be to Sutto.
* Bugfix: rvm 1.8.7,ruby-head ruby -e 'p :t' works properly.
* MagLev 23508.
* Bugfix: JRuby gemsets now work properly, including 'rvm gemset list'. 'rvm gemset list' also is much improved.
* Updated ebuild for latest release.
== Release 0.1.32
* Added 1.9.2-head to list known now that there is a branch for it. Thanks altogether!
* Bugfix: removed /bin from autoconf install path.
* Beware the user aliases... Thanks be to ice799!!!
* Default rbx built to use --skip-system for LLVM, thanks postmodern.
* Prevent 'bad things from happening' when specifying 'rubinius', thanks tmm1.
* patchlevel tweak.
* You see nothing...
* Rubinius 1.0.0 refactoring.
* Rubygems 1.3.7 is now default.
* Missed a variable change with last commit.
* Hooks may now alter the current environment. Please be very careful what you place in them :)
* Updated ebuild for latest release.
== Release 0.1.31 - JRuby 1.5.0 fix for readers of RubyInside.
* Sortof Bugfix: Adjust rake for a minor relase issue. Thanks to haruki_zaemon for notifying me of this issue.
* Updated ebuild for latest release.
== Release 0.1.30
* JRuby 1.5.0 w00t!!!
* Updated install message for && return. Thanks to panaggio.
* Updated ArchLinux MRI deps.
* 'rvm gemset pristine', thanks be to jschoolcraft.
* Added initial 'rvm help ruby' text.
* Added initial 'rvm help rake'
* Rubinius rc5
* Bugfix: Account for parse args now arg quoting.
* Pass rvm_ruby_configure_flags through to rbx, thanks goes to khaase.
* Maglev 23464.
* Handle command line args with spaces (e.g., REE build options).
* Run an 'svn switch' when updating a svn repo.
* 1.9.3 is now 'ruby-head'
* Removed --no-dev-docs from ree install. use ree-options instead.
* MRI 1.8.7-p249
* Export rvm_ree_options.
* Minor tweak to rdoc generation.
* Bugfix: 'rvm use X' now prefixes gems bin directories to path also. Thanks erikh.
* PATH order: gem bin:global gem bin:ruby bin:... Thanks for the great idea erikh!!!
* JRuby 1.5.0RC3
* Removed --verbose from rdoc call.
* Updated ebuild for latest release.
* MacRuby 0.6
* Made installation message regarding && return more clear.
* Minor version bump.
* Beginnings of 'rvm help'
* Bugfix: 'rvm gemset use X' now works properly again.
* Do not unset rvm_ruby_string everywhere, it is meant to be used for scripting.
* Cleaned up package.
* Bugfix: package install autoconf.
* Bugfix: Account for rvm_symlink_path not existing.
* MagLev 23400
* Added zlib1g to rvm notes for apt hosts.
* MacRuby nightlies should come from macruby.org
* :) lets make this a three step process hmm?
* Account for spaces at the beginning of the line also with rvmrc sanity check.
* Bugfix, old exports.
* Thank you Maz for your sharp eye.
* Overzealous.
* Better export handling in CLI, moving towards sh compatibilty.
* Added Sanity checks to two more locations.
* Check for users that do not read the documentation before loading /etc/rvmrc and/or ~/.rvmrc, thanks iotaion9.
* Don't copy and paste folks, it gets you into trouble. Pure typing is the way to be :)
* Feature: after_install hook :) Look Ma, it's already documented.
* MagLev 23351.
* Be silent if no system ruby is found.
* Bugfix: Display system ruby correctly in rvm list when it is a symlink.
* Removed extra $dir
* Bugfix: rvm gemset copy.
* djanowski.
* Openssl version bump -> 0.9.8n
* Removed creation of rvm_symlink_path and .gem/cache
* Added RUBYOPT to 'rvm info' output.
* Bugfix: Squished an oompa loompa.
* Scaling back alias, went overboard last night :)
* Time to go back to bed.
* Bugfix: xdg-open detection now proper, removed OS type test.
* Added xdg-open for systems which have it.
* Bugfix: Don't you wish we could mute some people the same way? ::grin::
* Bugfix: rvm-prompt for system rubies, corrected awk.
* Bugfix: gemsets line 311, thank you mgutz.
* Features: 'rvm alias create [ruby] [name]' 'rvm alias delete [name]' 'rvm alias list'
* Added docs feature. Thank you Paul Barry (pjb3)!!! w00t!!!
* Logical negations are fun!!!
* s/which/POSIX command -v/g
* Bump zlib version to 1.2.5
* Bugfix: Adjust monitor for new set extraction.
* Added libreadline6-dev and subversion as dependencies for apt.
* Made rvm gem install output slightly more clear.
* What do you mean you need to specify ./configure?
* Might possibly add libxml2 to package.
* Bugfix: Account for LoadError in irbrc, thanks to Shinzui!
* More IR progress.
* IronRuby 1.0 just about functional.
* Maglev Update.
* Fun with java.
* Updated ebuild for latest release.
* Bump version #.
* JRuby 1.5.0.RC1 is now JRuby default.
* Silence grep when not found.
* damn copy paste
* --ree-options --no-dev-docs default now for ree
* Updated for cent 5.4 iconv-devel MIA.
* Bugfix: do some more sanity checks when using a gemset.
* Bugfix: Fixing the last bugfix.
* Bugfix: Switch gemsets when already using one.
* If gemset name was specified, explicitely use it.
* Add more detail to the post-install gem installations (eg, where they are installing to).
* Bugfix: 'rvm answer' now uses perl, since the universe is written in Perl. As it is obvious... the universe has bugs, and
perl is the only language that can have bugs not even god could sort out.
* Bugfix: 'rvm question'
* 'rvm question'
* 'rvm answer' now answers the question: What is the Answer to the Ultimate Question of Life, the Universe, and Everything?
* Improved rvm info output.
* Added zlib to notes.
* Account for term type 'unknown', thanks Chad Woolley.
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Adjustment to gem for rbx-head.
Bugfix: Rubinius is now able to use gemsets also :) Thank you luislavena!
Dumbass. It's like you never awk'd before...
When called with only one ruby, allow no args.
Now can set rvm_verbose_flag=0 to silence set log.
Made progress on IronRuby during coderpath interview.
Bugfix: don't relink caches anymore.
Improved output for gemset empty.
Bugfix: Don't select if gem_home set.
Install autoconf to rvm bin path / symlink path.
Sometimes I wonder why we have copy/paste...
Added variable.
Added autoconf package url.
Feature: 'rvm package install autoconf'
Bugfix, grab the gemdir properly for destination in copy.
Updated ebuild for latest release.
== Release 0.1.27
* Remove .ext/rdoc if it exists, for those having trouble with it when installing 1.9.2-head.
* Applied jhsu's patch.
* Updated rvm-prompt tests to run rvm prompt in correct directory. Also updated 1.9.1 and 1.8.6 tests to use the correct
'head' versions
* initial bash completion
* I'll think about this more.
* Bugfix: only warn when using sytem.
* Do not store system ruby as root.
* Added nice warning message about using gemsets with System rubies.
* Be sure to practice safe sed...
* Updated Maglev version to 23191.
* Reconfigure always.
* Bugfix: don't unset rvm_gem_name during installs.
* Updated ebuild for latest release.
* Minor CLI cleanup.
* Added rvm-update-{head,latest}
* Bumped minor version.
* What? sed is not actually clairvoyant???
* rdoc/rake now install both to interpreter gemset and interpreter global gemset.
* Change % to @ during update in default file.
* Updated scripts/install.
* Fixed rvm_bin_path in example rvmrc, thanks uxp.
* Adjusted ncurses url, thanks agibralter.
* Install rdoc/rake with no rdoc/ri option.
* Install rdoc before rake.
* Added 'system' output to rvm-prompt, thanks workmad3.
* How'd that sneak in there?
* 'rvm install rbx' now installs rc4.
* Ignore dependencies when loading a gem.
* Updated installer to output differently for install vs upgrade.
* Bugfix: Improved check for no gem command.
* Updated ebuild for latest release.
* Bugfix ;)
* Updated ebuild for latest release.
== Release 0.1.25
* Feature: gemset now displays in info. Bugfix: 'rvm gemset clear' now works as expected.
* Added unicode char for head. Thanks khaase!
* Bugfix: install gemset renaming ready for next release.
* Bugfix: % separator for migration of gemsets.
* Maglev version 23101.
* Now using @ as separator :/ ::twitch::
* Bugfix: Bugfix fixed.
* Bugfix: If rvm_ruby_gem_home is not set, attempt to set it.
* Bugfix: Removed extraneous }
* Bugfix: Properly extract the ruby string for gemset use.
* Feature: rvm_gemset_separator. Now with '+' as default. Install renames old gemsets. To keep old '%' then export
rvm_gemset_separator='%' in ~/.rvmrc.
* Bugfix: slow the insane logic down.
* Performance: Use GEM_HOME instead of going through gem in rvm-prompt to gain gemset. Thanks priit!
* Bugfix: 'rvm benchmark myscript.rb' works again.
* Added --gems flag for uninstall/remove.
* Updated ebuild for latest release.
== Release 0.1.24
* Bugfix: Available packages are now detected correctly, thanks apotonick && NilsH for letting me know about it.
* Removed global caching scheme in preparation for something sweet.
* MagLev now 1.8.7 w00t! (23082)
* Merge branch 'master' of git.overnothing.com:rvm
* Updated zlib version. Thanks bierbaum.
* Added a use to rubygems setup.
* Crossing my legs and hoping not to get screwed.
* Bugfix: unset rvmrc flag after create.
* Thanks Wilson!!!
* 'rvm gemset string' for consistency
* Display gemset by default in rvm-prompt.
* Added initial unicode concept for rvm-prompt. Thanks burke!
* Removed --all.
* Improved gemset and usage messages.
* Bugfix: when use --create flag gemsets no longer complain.
* Comment out some legacy cli items. Cleaned up the CLI help a bit. Thanks dreamcat4.
* Fix typo in list known for 1.8.6 version. Thanks drewolson.
* Merged in hellopatrick's patch for MacRuby. Thanks hellopatrick.
* For JRuby s/kenai/org.s3.amazonaws/g. Thanks nicksieger.
* Added ruby-head to 'rvm list known'. Thanks takkanm.
* Rubinius rc3. Thanks Renaud (Nel) Morvan.
* We have to practice safe sed now that BSD is out there.
*
*
*
*
*
*
Better non-interactive operation (color terminal interaction).
Try this one Pistos.
The spaces for 'readability' have annoyed me long enough.
Try that Pistos.
Bugfix: only chmod when installed as user.
Updated ebuild for latest release.
== Release 0.1.23
* Bugfix: Ensure PATH includes gemset path when gemset is used.
* Bumped MagLev version.
* Moved the root check up higher.
* Less agressive with the cache linking.
* Only do the gem cache dance if a user.
* Bugfix: Reflect on the action for packages.
* Fix 1.8.7, ensure pathname2 is installed.
* Tarball not zipball.
* Updated ebuild for latest release.
== Release 0.1.22
* Bugfix: Check for rvm_ruby_gem_home and set accordingly. Additionlly don't append %gemset to the existence check, it will
already be in the gem home. Thanks mattdenner.
* Updated ebuild for latest release.
== Release 0.1.21 - Many gemset bugfixes.
* Bugfix: rvm gemset delete now works as expected.
* Bugfix: 'rvm gems use X' now properly sets up all env vars.
* Bugfix: 'rvm gemset delete X' now works again.
* Bugfix: 'rvm gems use X' uses X again :)
* Bugfix: 'rvm gemset use X' will not double X. Bugfix: 'rvm gemset use Y' will no longer display an error message about the
ruby string.
* Feature: rvm_gemset_create_on_use_flag=1 in ~/.rvmrc
* Bugfix: s/gems/gemset/ in error messages.
* More ironruby progress.
* Or maybe not.
* Ironruby might work now.
* Progress with ironruby...
* This is the way it *should* be however ... no comment...
* Bumped ironruby's version to 1.0-rc2
* Bugfix: libraries has been moved to package.
* Cleaned up CLI readme slightly.
* Added full path to md5 on Darwin in fetch. Thanks shigeya.
* err ::cough:: /usr/ ::cough::
* Full path to OSX installer for macruby. Thanks shigeya.
* Updated ebuild for latest release.
* Bugfix: Fix /sbin/md5 for Darwin based systems. Thank you very much shigeya!
* Bugfix: 'rvm package ....' under zsh.
* Updated ebuild for latest release.
== Release 0.1.19
* Updated mono package function.
* Rounded out new package feature.
* New API: 'rvm package {install,uninstall} {openssl,zlib,readline,iconv,etc...}'
* Found that blasted missing 's'.
* Bugfix: gemset not gems in set script. Thanks drewolson.
* Initialize.
* Source the utility functions.
* Bugfix: Function naming error.
* chmod certain scripts during install.
* Make libraries executable.
* Export in the examples.
* Check for existance before grepping.
* For root installs, use the rvm_path for global gem cache.
* Bugfix: Libraries output no longer occurs when rvm is sourced.
* Bugfix: Don't source libraries, it's now external. Thanks Jimmy Baker.
* Merged Pisto's ebuild update.
* Adjust where rvmrc gets loaded for package managers.
* Advise users to get head often via 'rvm update --head'.
* Fixed a tyop in examples/rvmrc.
* Only do 'make' not configure for JRuby < 1.4.
* Bugfix: For set/do actions if only one ruby is specified only do that ruby. Bugfix: when -S is used don't quote the args,
thanks to aslakhellesoy.
* Bugfix: missed a spot.
* MagLev version 22907.
* Added 'rvm seppuku' in honor of tsykoduk who can't spell so it saved his life.
* Bugfix: 'rvm_gems_select' -> rvm_gemset_select
* s/gems/gemset/g Thanks everyone for such a decisive vote.
* Defaulting 'rvm list' to 'rvm list rubies'.
* Do not try and use log script during implode after removal :).
* Bugfix: global gems cache setting is now exported.
* Enhanced the error message.
* Bugfix: exit not return from script. Thanks TecnoBrat.
* Added tracability to extracted set actions.
* Added tags file to gitignore.
* Heh... might need that.
* tyop fix for preifx.
* Made install message about the return statement more clear.
* Moved 'do' actions to external script (set). Refactored to allow for rvm_prefix for package managers.
* Bugfix: Show gemset for do actions.
* Adding ebuild for rvm-0.1.18
== Release 0.1.18
* Renamed sticky-gems to sticky
* Removed rvm_path code from installer which should not be set during install. Install is 'black and white'
* Feature: Now you can empty any gem dir, not just for a gemset.
* Was too agressive with last commit. We still want to use gemsets :-p
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Bugfix: GEM_PATH now gets correctly set for rubies without an actual 'version'.
Removed warning message, was in the wrong place.
Corrected caps of GemStone in readme.
More work on gems actions. Fixed capitization of GemStone. Added maglev-head to 'rvm list known'
Bugfix: removed double negation.
Bugfix: properly detect a ruby string interpreter component.
Feature: 'rvm gems create'
Added error handling to __rvm_strings (thanks dreamcat4). Began working on the new gemset interface.
Adjusted wording from --all to known for rvm install.
Feature: New list functionality. Feature new strings functionality.
Upgrade installers to rubygems 1.3.6
Make the rvm rubies subcommand more helpful
Added installation warning when 'return' is detected in .bashrc.
Adding ebuild for rvm-0.1.17
== Release 0.1.17
* Added latest maglev md5's
* Bump maglev version to 22891.
* Do not install rubygems for ruby-head.
* What is with me and my inability to spell?
* Tweak path logic slightly.
* 'rvm update' no longer attempts to install from a gem. Now downloads and installsthe latest stable release tarball.
* Adding ebuild for rvm-0.1.16
== Release 0.1.16
* Bugfix for the last Bugfix ;)
* Bugfix: Search global path for 'do' actions.
* FreeBSD deviates from the norm just like OSX :)
* 'rvm gems import/export' instead of 'rvm gems dump/load'
* Feature: 'rvm gems copy X Y', thanks to my UnderpantsGnome.
* Bugfix: Installer fixed again.
* dirname of course!
* change to the location of the install file.
* Added loading of rvmrc before path calculation.
* Removed source_path using $0
* Adding ebuild for rvm-0.1.15
* RVM Release 0.1.15
* Allow --sticky_gems from command line.
* Bugfix: better gem command detection.
* Adding ebuild for rvm-0.1.14
== Release 0.1.14
* Bugfix: careful now.
* Stricter checking.
* Bugfix: Missed a spot for global gem cache.
* Ensure symlinks are correct.
* Refactored global gems cache to be located in $HOME/.gem/cache/
* Bugfix: Remove archive if it fails checks. Feature: Initial bundler support.
* Bugfix: rvm gems delete.
* Updated yum based notes. Thanks RubyPanther.
* Feature: 'rvm X --rvmrc'.
* Adding ebuild for rvm-0.1.13
== Release 0.1.13
* Adjusted install message to be more explicit about the return. Adjusted rbx's installer.
* Turns out it was the previous 1.8.7 install that was jacked, not the rbx installer.
* Bugfix: remove spaces in filenames for rvm gems load.
* Tweaking rbx install.
* Slowly improving gemset functionality.
* court3nay is correct, we want \s
* Bugfix: rvm gem install t* now works again ;)
* Removed empty file.
* Install now exits on failed patch. Error command output tweaked.
* Adding ebuild for rvm-0.1.12
* Patch with p0
* Bugfix: rvm install X --patch Y now patches :)
* Feature: Cleaned up 'rvm list'
* Add some more output so that you know what's going on when a gem is already installed.
* Bugfix: 'rvm gems load X' as well as 'rvm gem install Y'.
* Oh man, that was a very sneaky lil buggar...
* Sometimes I am so dense that I myself don't realize that I'm completely daft :/
* I suffer from accute mental deficiency :(
* Need more caffene...
* A refactoring we will go... A refactoring we will go...
* Perhaps it's better to just let things go sometimes.
* Two installs for the price of one
* Bugfix: 'rvm gem install X' should now actually install X
* Altering how gem path & home are passed for gem install.
* Switch the unsetting of the patch specification to the global variables.
* Refactored libraries code. Added rvm_ruby_patch exports.
* Removed completion script.
* Bugfix: rvm reset now clears default properly.
* Bugfix for 'rvm gem install X' dealing with GEM_PATH setting.
* Added proxy ability for rubies fetching. Thanks Jadefalkner.
== Release 0.1.11
== Release 0.1.10
* Bugfix: Fixed tyop in variable name. Fixed extra space issue.
* Bugfix: PATH correction. Thanks UnderpantsGnome.
* Bugfix: Fixing the last Bugfix correctly.
* Bugfix for zsh on gems load. Began adding 'rvm install mono' - not done.
* Bugfix: Macruby 0.5
== Release 0.1.9
*
*
*
*
*
*
Bugfix: 'rvm install macruby' now installs 0.5 instead of nightly build.
Is a direcotory and not a symlink.
Fixed pathing for mput.
Added test if directory is empty.
Bugfix: globbing in zsh is unsettling.
Documentation updates.
== Release 0.1.8
* Bugfix: Separate directory and symlink logic.
* 1.8.6-p399 now default.
* Removed tracing.
* Bugfix in site docs, thanks to wmadden.
* Bugfix: rvm gems load now properly skips gems that are already installed.
* Wow, that was a challenging bugger to track down.
* Updated CLI help with more information. Bugfix: rvm gems load now works again. Feature: rvm gems load now installs gems
very fast from cache.
* Added shell to output.
== Release 0.1.7
* p398 is now default for 1.8.6. Thanks Kirk Haines.
* Removed '--no-rdoc --no-ri' as default. Set rvm_gem_options in .rvmrc if desired.
* Added ebuild for 0.1.6.
* Added GEM_PATH to info output.
* Bugfix: Use the proper variable for global gems paths.
* Bugfix: Removed extra slash from shebang for hooks, thanks haruki_zaemon
== Release 0.1.6
* Update default 1.8.7 to p249.
* Thank you Pete Nicholls.
* Bugfix: Ensure that cache directory exists.
* Added ebuild for version 0.1.5 .
* Merge branch 'master' into ebuilds-nice
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
== Release 0.1.5
* Careful not to nuke system gems cache.
* No! the other left!
* Bugfix: So system rubies matter? ;)
* Updates to all ebuilds, including 0.1.3, 0.1.4 and "edge" (git) versions.
* Updates to all ebuilds, including 0.1.3, 0.1.4 and "edge" (git) versions.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master' of github.com:Pistos/rvm
* Update maglev's version to 22816.
* Bugfix: fun with zsh ;)
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
== Release 0.1.4
* Added filesystem permissions check to rvm debug.
* Ensure that %global gets into path.
* Tweaked verbage.
* Bugfix: global gems dir, no blind move.
* Feature: cache md5 sums on successful download.
* Global gem cache :)
* Features: %global default gem set. symlink of each ruby's interpreter default gem set to ruby_string/lib/ruby. Thanks
UnderpantsGnome for the %global idea.
* Site update.
* rvm now creates symlinks to gem directories in rvm_ruby_home/lib/ruby/1.8 for example.
* Add patch dependency notice.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bump LLVM version.
* More tweaking of rvm_path for Pistos.
* Mental Breakdowns for fun and profit.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* putting it back :)
* Merge branch 'master' of github.com:Pistos/rvm
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Adjusted default path again.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Adjust order of defaults loading.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Moved scripts detection code, added defaults.
* Thanks Justin Smestad
* Thank you Justin Smestad for your support!
* Trying adding in a default fallback for rvm_path.
* Upgrade MagLev version.
* Run notes from cwd.
* Added rvm_scripts_path to install block.
* Site updates.
* Honor rvm path for irbrc.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Ensure log directory exists for nested logs.
* Added rvm irbrc processing to post_install.
* Merge branch 'master' of github.com:wayneeseguin/rvm
== Release 0.1.3
* Added ebuild for version 0.1.2.
* Added Maglev 22780 checksums.
* Added MagLev 22780 Added rubygems update when new ruby gem home is created.
* Feature: 'rvm install ruby-head'.
* chose MRI SVN repository when install with head option
* Merge branch 'master' of github.com:Pistos/rvm
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
== Release 0.1.2
* Site update.
* Bugfix: better handle ruby log paths.
* Bugfix: Append to log when running a command.
* Bugfix: directory creation during installer.
* Added comments for all utility functions.
* Added 'rvm rubies' for use with scripting.
* Use the redist-libs as the source folder for Ruby libraries when copying IronRuby files after building.
* Fixed a mistake in the manual merge performed in commit d471bb9.
* Fixed a regression introduced after commit 12221fe that broke the recognition of a proper mono version to build IronRuby
from the Git repository.
* updated to Ruby Enterprise Edition 1.8.7 2010.01
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Adjusted wrapper scripts.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* MagLev update, symlink gemstone dir.
* Pedantic formatting for jruby in rvm list.
* Consistent formatting.
* maglev is *always* x86_64
* Bugfix: don't exit out when mostly done with MagLev install.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
== Release 0.1.1 - bugfixes.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Removed sourcing of .rvmrc / etc/rvmrc.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Tweaking init for install.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Add env vars to install trace.
* Enable install tracing.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bugfix: destinkerifying.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bugfix: smelly elif.
* rm -rf rm -rf.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Moved stored system/default into config/ from rvm_path
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Only show manual instructions if not installing as root.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Quick, pull your pants up the boss is comming
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Added another sanity check.
* Updated binscripts/rvm
* Bugfix: 'rvm install jruby' actually works now :)
* Bugfix: 'rvm install jruby' now sets the correct archive extension.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master' of github.com:Pistos/rvm
* Bugfix: maglev-head added demo key.
* Site update.
* Updated sha1's for MagLev on Linux.
* Copied /usr/portage/skel.ebuild for first ebuild. No changes yet.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Updated rvm-prompt to be more 'bare'. Thanks Pistos :)
* Bugfix: issue a warning and point to docs when 'rvm gems' without arguments is used.
* Added gems to help output, thanks technicalpickles.
* Minor installer tweaks.
* Added 'rvm_sticy_gems' setting for ~/.rvmrc file. Tweaked maglev-head.
* Updated directory creations.
* More updates for maglev-head.
* Added new GemStone sha1. Fixed a logical bug with maglev-head install.
* More MagLev tweaking. Now workign on getting 'maglev-head' working proper.
* Added maglev-22725 sha1.
== Release 0.1.0
* Added maglev to usage output and list.
* Updated installation notice
* Silly rabbit... debugs are for developers...
* Shebang adjustment. Site update.
* Added migration piece for rubies so that people aren't caught off guard like with the gem directory change.
* Updated MagLev version. Fixed a few items I missed with last commit.
* Initial refactoring of rubies into $rvm_path/rubies
* Final pre 0.1.0 release allowing for full MagLev functionality with gem install.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Minor tweak for Pistos.
* Silence gemstone check for MagLev.
* Bugfix: Only start stone for maglev once.
* Updated MagLev verison.
* Bugfix: 'rvm gems load' now works under zsh as well :/
* Fixed a tyop
* 'rvm install ree' now properly extracts with the correct extension.
* More work on MagLev support. Added check for running gemstone. Added check for setting version based on ruby string digits
piece.
* Tweaked notes to include release name on Linux.
* Update 1.9.1 to default to p378.
* Bugfix: removed z in tar's where piping through gunzip. Thanks to jfsworld.
* Added 1.8.7-p248 md5.
* If rvm_project_rvmrc=0 then don't even hijack cd.
* Fixed maglev gemstone extraction
* For now always nab gemstone.
* Removed extra }
* Updated to new MagLev url scheme.
* Updated maglev urls.
* Changed maglev to download tar.gz
* Switched tar extractions to work on Solaris. Updated install doc.
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Added start to use maglev.
Missing [
Only extract gemstone on head.
Only download gemstone for -head version.
Minor bugfix.
Initial working maglev, no head.
MagLev precheck script working.
added maglev prereq script.
Initial working 'rvm install maglev'. Several things need to be done before releasing maglev.
Bugfix: syntax error, daft man coding.
Bugfix: Extract on force if already extracted. Beginning maglev code.
grr.
Bugfix: rvm gems load for path to gem file no longer emits an awk error.
Thank you very much, Robert Hunter!
== Release 0.999, getting very close to 0.1.0
* Added some exit points to rbx install for error cases.
* Site updates.
* Upgraded rbx. Several other fixes and patches. Thanks awesome users!
* Site Updates.
* Removed the --jit from usage which is no longer used. Use --enable-llvm instead.
* Feature: sticky gem sets are now disabled by default. Set 'rvm_sticky_gemsets=1' in ~/.rvmrc to enable.
* Bugfix: rvm gems delete should now work. Thanks jfsworld!
* Bugfix: MY_RUBY_HOME in default file greps were adjusted since export was moved to beginning of line. Thanks jfsworld.
* Bugfix: rvm install rbx/rbx-head.
* Updated install message for zshrc instead of zshenv.
* Altered rbx llvm code based on feedback from Evan. llvm is now default so the option for rbx is --disable-llvm.
* Bugfix: 'rvm default' now works as intended. Thanks rolfb.
* Switched to using match script inside mono install section so that older bash shells can still run. Thanks tibra.
* Bugfix: Don't fetch version when --head is specified for macruby.
* Abort macruby-head installation if install_source exited with error code.
* Make llvm building opt-in for macruby via --enable-llvm flag (for now).
* Add libraries to manage script.
* How'd that get in there?
* Propigate default through selector.
* Propigate default from CLI.
* Bugfix: install to exit upon encoutering it's first error.
* Tweaked install message slightly.
* Bugfix: rvm gems delete now works again.
* Bugfix: 'rvm gems name' works now.
* Feature: 'rvm gems clear'
* Bugfix: rvm gems list. Thanks jpalardy.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Added export of rvm_hooks_path. Thanks jpalardy.
* Corrected a few typos in the site's content
* Bugfix: s/rvm_dir/rvm_path/g
* Thank you Jack Dempsey.
* Bugfix: always hit ruby for version string instead of current binary for 'do' actions.
* Updated 1.8.7 in rvm-list
* Changed default 1.8.7 to p248.
* Changed default 1.8.7 to p248.
* Thank you Jonathan Palardy.
* Added git-core to apt based hosts notes message. Thanks racan.
== Release 0.0.99
* Added rvm source script test for website.
* Adjusted formatting of 'rvm list'.
* More tweaks to install message.
* Feature: './install' no longer touches rc files. Pass --auto to installer in order to have it touch the rc files. Thanks
agib.
* Option: rvm_gem_options ; default: --no-rdoc --no-ri
* added extra sanity check to gem install
* When root created default AND symlink both. Fall back to /usr/local/rvm/default when selecting default.
* Extracted hoooks to external script. Improved cd logic.
* Added warning to install & documentation not to return from .bashrc.
* Bugfix: jruby-* in rvm list now correctly does -v on the ruby itself.
* Bugfix: if a file name is given during dump, honor it.
* changed exec to eval for rvmsudo.
* Bugfix: only create ./log if using it.
* Bugfix: whoops, those are variables?
* corrected variable placement.
* Adjusted prefixing for rvmsudo.
* Added line padding around 'rvm --version'
* Bugfix: when no gem home set rvmsudo should not fail.
* Return to original directory after update.
* Added spaces before & after logging messages based on Yehuda's recommendation.
* Merge branch 'master' of git.overnothing.com:rvm
* Detect interactive vs non-interactive and adapt logging output based on interactivity. Thanks agib & egyp7.
* HOME rvm overrides system.
* Don't mkdir on specs
* Let's try initializing rvm's variables.
* Switching to a different tactic.
* Silence errors when detecting.
* Merged.
* Attempting to fix the detection of an installed gem.
* Tweaked gem installed test.
== Release 0.0.98
* Added optional trailing slash. Thanks dreamcat4.
* Removed quotes from regex.
* Working on adjusting the installer with dreamcat4
* merged an extract of dreamcat4's commit
* Manually merged nrk's patch for BASH_REMATCH check.
* Manually merged nrk's patch for pwd fix.
* Manually merged fistfvck's commit 949ca1402f1d8fb491e7eafdf661205da388123a.
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Added a missing LF for notes related to JRuby on systems running pacman.
Tweaked initializer based on dreamcat4 suggestions and some cleanup.
Added messages for IronRuby to install notes.
Added IronRuby to the README.
Support for building and installing IronRuby from the official git repository (Mono >= 2.6 is required).
Merge branch 'master' of git.overnothing.com:rvm
Feature: rvmsudo X for executing X in context of current rvm selection.
Bugfix: adding HOME .profile to correct zshenv.
Added mkdir -p to install script for rvm paths.
Bugfix: 'rvm gems load' works again as well.
Bugfix: no more double extraction for jruby.
Bugfixes: rvm install jruby.
switching more back ...
Added message to 'ant dist' build line. Reverted more items.
Bugfix: ant dist on jruby-head.
Put back rvm-prompt :/
Bugfix: jruby always run ant.
Added JRuby message to install notes.
Added --{disable,enable}-{llvm,jit} cli flags.
Bugfix: JIT logic.
More tweaks to rvm rbx install.
Nuked some unnecessary codez.
That should about do it for 'rvm install rbx'
Progress with rbx however... how do you specify install target for package?
Trying a different install on use approach.
Trying a different install on use approach.
Take that Scyllinice!
Well this is fun, switching back around.
What trace? I see no trace?
Bugfix: Adjusted ruby string interpreter matcher.
Added debug messages to gems actions.
Bugfix: properly restore rbx's ruby string.
Bugfix: rvm_install_on_use_flag=1 in ~/.rvmrc works again.
switch from $interpreter/$versin to $ruby_string for gem dirs.
== Release 0.0.97
* Documentatino updates.
* Bugfix: 'rvm X gem install Y' now works, w00t
* Yes folks, zsh IS better at emitting a stack trace :)
* Bugfix: Installing gems via 'rvm gem install X'
* Bugfix: I just found out the which command on OSX has different options than on Linux :/
* Merge branch 'fix_rvm_ruby_do'
* Removed debug statements.
* Bugfix: account for plain old ruby in the ruby string :)
* Bugfix: variable has regained its $
* Bugfix: 'rvm remove reeee' no longer tries to remvoe all rubies.
* Feature: Use default set in $HOME first then ruby path.
* Bugfix: only run exract for jruby if not installing jruby-head.
* unset loaded flag during reload.
* switch .profile and rvm sourcing order
* re-feature: Added back the sourcing of .profile if it exists. Began cleaning up bash scripts.
== Release 0.0.96
* Features: rvm X --editor : creates rvm_path/bin/editor_X symlinks rvm X --passenger : creates rvm_path/bin/passenger_X
symlinks rvm X --symlinks smurf : creates rvm_path/bin/smurf_X symlinks
* Merge remote branch 'origin/fix_rvm_ruby_do' into fix_rvm_ruby_do
* fixed 'File Not Exist' error, when rvm_do.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Removed --enable-shared as default on recommendation of Aman Gupta (tmm1).
* Rubinius: LLVM is enabled by default; flip --enable-llvm to --disable-llvm
* Initial support for IronRuby's binaries. NOTE: the current download URL is temporary and it might change in the future.
* The user might not have curl installed, so we should prompt to install curl in the notes section
* Bugfix: rvm -e 'puts 6 + 7' should now work.
* Bugfix: silence error output from ls.
* Thank you Scott Clausen!
== Release 0.0.95
* Feature: rvm now behaves the same way when logged in as root and user. To set a system wide default ruby now do 'rvm X -default' when logged in as root
* Bugfix: --enable-shared not --enable_shared, thanks saimon!
* Minor version bump.
* No longer run irbrc on select.
* Minor adjustment, --enable-shared.
* Default compile flag is now --enable-shared=yes unless overridden with -C ...
* Bugfix: 'rvm list' now shows proper architecture strings.
* Bugfix: silence another which ruby call and also test for executable on system ruby.
* Bugfix: Check proper directory and script for root install, additionally ensure rvm_path is a directory before attempting
to load rvm.
* Minor version bump.
* Set PATH after symlinks for zsh to rehash.
* Bugfix: 'rvm gem install X' works again after extracting gem actions to a external script.
* Have gems load use current set / exported environment.
== Release 0.0.92
* red is the new green ;)
* Only call colors once per color. Set rvm_ruby_gem_home if it is not set.
* Set gem_args.
* Missed a rename with last commit.
* Properly reflect on the gems(et) file.
* the external gems methods should use the environmental ruby.
* Sometimes, I see dumb people. Then I realize I'm looking in the mirror. :/
* Who commented out that shift? :)
* re-added load action
* Bugfix: 'rvm gems load' once again loads the gems(et).
* Bugfix: export configure flags for manage script.
* Added code to get 1.8.5 to compile on all systems, including ones with newer readline & openssl :) Thanks khaase!
* Feature: Added post-gem-install message. Thanks tmm1!
* Default Change: per-project rvmrc code to switch to default/system on exit is now opt-in instead of opt-out.
== Release 0.0.91
* Bugfix: 'rvm update' now tries current ruby first. Bugfix: 'rvm install' does not imbecillically use the same code as
initialize and startup.
== Release 0.0.90
* Bugfix: rvm gems(et) commands now work again.
* Site Updates.
* Bugfix: rvm install X for libraries now works again, broken in 0.0.89
* I am so incredibly daft sometimes :(
* Over zealous
* Attempting to improve rvm_path logic.
== Release 0.0.89
* Feature: Monitor files in lib/ and app/ directories. This might need some more polish.
* Feature: md5 checksums now happen so that archives are not re-downloaded.
* Bugfix: rvm scripts path looks around now before gettings set if not already set.
* Site updates.
* Added user tag ability to rvm ruby strings for future requirement.
* Site updates.
* Site updates.
* Feature: gem actions are now in external scripts.
* libraries are now uninstallable.
* Bugfix: check if not null, not for equals 1
* Added rvm/usr path detection.
* Added 1.9.1-p376 to rvm list --all
* fixed 'File Not Exist' error, when rvm_do.
* If rvm_archflags=1 then set rvm_make_flags_flag.
* Bugfix: rvm runs extract even if archive already exists.
* Made __rvm_make_flags opt-in via rvm_make_flags_flag
* Updated 1.9.1 default patchlevel to 376.
* Add curl to 'rvm notes'
* Moved do all case to use shell builtin glob instead of ls.
* Adjusted for config/user during install.
* fixed __rvm_update_rvm
* Bugfix: nailgun now compiles for jruby.
* Bugfix: JRuby rake & gem now work as expected out of the box.
* Bugfix: Run extract after package fetches only.
* Bugfix: moved 'rvm_remove_ruby' into the external manage script.
* Committing Rolf's mute button :-p
* Site update.
* Thank you Konstantin Haase!
* Removed trap for zsh.
* Finished extracting installer to separate script.
* Site Update.
* Site update, thanks Erik Hansson!
* Feature: 'rvm fetch X,Y,Z' works.
* Minor version bump in preparation for a release.
* rvm_fetch improvements
* Began working on 'rvm fetch' function.
* Site update.
* Bugfix: Install message no longer shows awk output, notes cleaned up.
* Adjustment: rvm gems load switched colors and message around to make it more natural.
* Bugfix: jruby install now correctly symlinks the jbinaries to regular and no longer alter's their shebangs.
* Removed the run flag.
* Adjusted the version output during install.
* Removed a failed attempt at a self aware script ;)
* Evil slash... begone!
* Tweaked installer for new binscript.
* script vs run logic.
* Clear!.
* Knit three yank six.
* Try one pull two.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Provide more information during the installation.
* In Darwin, explicitly use system's "basename" command.
* Feature: rvm_symlink_path now overridable and defaults to /usr/local/bin
* Extracted cd to sorced script.
* Feature: Project specific rvmrc files now switch back to default and/or system rubies when exiting a project directory.
Additionally they can now be toggled off by placing 'rvm_project_rvmrc_default=0' and/or 'rvm_project_rvmrc=0' in the
~/.rvmrc file
* Bugfix: rbx_url
* Site updates.
* Removed debugging flags.
* Tweaked monitor with a file check.
* Added monitor page to site.
* Bugfix: rvm reload now correctly reloads and does not go loopy.
* Bugfix: break in case? Really? ...
* Initial thoughts on patch support.
== Release 0.0.86
* Added a simple bootstrap script to the documentation.
* scripts/hash now executable in preparation for future use.
* Bugfix: system for rvm list now shows up properly when exists.
* Feature: ~/.rvm/config/user now available for user defined settings and defaults.
* Site updates.
* Adding config/md5 sum file.
* Updated examples/rvmrc file to be current for the project. Fixed 'rvm_temp_path' to be 'rvm_tmp_path' as expected.
* Bugfix: More tweaking of the rvm load.
* Bugfix: scripts/rvm does not re-source if rvm is already loaded.
* Bugfix: added missing ; then
* Site update, thank you Vladimir Sizikov.
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Added tracability to monitor.
Minor version bump after 0.0.84 release.
Minor version bump.
Bugfix: Be sure to include files right in the test/ and spec/ directory also.
Bugfix: 'rvm reload' now works again :)
Feature: 'rvm <ruby string> monitor' now works for: rspec,shoulda,test/unit,...
Feature: 'rvm <ruby strings> monitor' now works for spec/
Feature: 'rvm install rbx' now installs Rubinius 1.0.0-rc1.
Bugfix: 'rvm install mput/shyouhei' now clones the proper url
Bugfix: shebang line now sets correctly.
Bugfix: Correctly set rvm_path for system only installations.
Missed a spot for CFLAGS adjustment.
Allow CFLAGS and LDFLAGS to be specified by environment.
Bugfix: silence error messages from the command.
Site updates.
Bugfix: Logic was negated for finding gem command.
Bugfix: Silent gems select.
Bugfix: subshell not string :/
Adjusted spacing for 'rvm notes'
Feature: 'rvm notes' now outputs the same notes as spit out during rvm install.
We really are not interested in the output of 'which gem' for testing purposes :)
Adjusted install message for ubuntu.
Added message for list when no system ruby installed.
gems select should silently return if gem missing.
Added gem check to gems select
Alter checks.
If ruby & gem do not exist, skip default setting.
Skip gem actions with an error message if no gem command found.
Bugfix: Added check for source directory during install. Added check for gem existing for the case when no ruby exists.
Bugfix: Account for the case where there is no current ruby.
Bugfix: Account for the case where there is no current ruby.
== Release 0.0.82
* Added site/tmp/dependencies to gitignore.
* Bugfix: installer loading logic.
* Site updates.
* Added XCode version & update message to install.
* Send error & fail messages to stderr.
* Added array functions.
* Extracted monitor to external script, will finish implementation later.
* Feature: Added a few hooks, most importantly ~/.rvm/hooks/after_use
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Altered 'rvm list' output to be more clear.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Removed subshell after nice command.
* Bugfix: properly copy binscripts to $rvm_path/bin/
* Bugfix: running -v against an existing script.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Feature: rvm_ruby_mode now propigates to the ruby -v output on the do line as well as the ruby string output.
* Bugfix: Properly pass mode, do not store in rvm_ruby_args.
* Feature: Ability to specify a ruby string 'jruby-m1.9' in order to startup jruby with --1.9 mode.
* Tracing is like divining with entrails!
* Bugfix: do not unset all variables. Bugfix: Adjust the rvm loading logic.
* buahahahaah found you you lil bugger! bug ! bug ! ... SQUISH
* Bugfix: Initialize issue during install.
* Removed debugging line.
* Bugfix: Installer actually works now when no rvm is present :)
* Bugfix: Better return logic on failure from fetch.
* Much refactoring see PT...
* Significantly cut down on trace noise.
* Bugfix: Removed extra /rvm/ in scripts path. Removed external --prefix option.
* Refactored initialize out of several places into a common script and improved it's logic for handling root installs.
* Bugfix: adjust rvm_prefix_path and rvm_path to be user overridable and have consistent defaults in both initialize() and
install()
* Applied my new found education on the naming of JRuby :) Thanks VVSiz
* Minor version bump post 0.0.80 release.
* Feature: 'rvm list --all' now outputs ruby strings and indicates defaults and has a few extra comments.
* Support Heroku style '.gems' files.
* Bugfix: rvm do actions now work with 'system' ruby. Example: 'rvm 1.9.1,system,ree rake spec'
* Minor version bump after release 0.0.79.
* Switch to rvm_path instead of hardcoded ~/.rvm.
* Bugfix: 'rvm gems load' now works for system rubies as well.
* Strip preceding whitespace.
* Select 2nd field from output of sysctl.
* ppc pre-empts 64 bit check.
* Adjusting make_flags for PPC
* Don't call make_flags for ree releases, it computes things with it's own installer.
* Adjusted macruby_nightly latest url.
* Bugfix: 'rvm specs/tests/rake spec/rake test' now work proper.
* Bugfix: Strip off trailing 's' for specs/tests when passing to rake.
* Bugfix: specs/tests CLI.
* Honor user .rvmrc and /etc/rvmrc settings during rvm install.
* Lop off path when collecting gem names for gemsync
* Properly unset vars for rbx install and only call make_flags for 1.[8-9]* rubies.
* Minor version number bump.
* Remove ParseTree requirement for rbx, additionally remove %rbx gem set.
* Bugfix: strip off the t for tag when checking out repo.
* Bugfix: correct tag selector.
* site updates.
* Bugfix: add -eq 1 to test for zsh.
* Disabling Installer code from rbx for now.
* Added export of rvm_ruby_string and gem_set_name for selected default rubies.
* Feature: Export ruby string and gem set name for extrnal scripts to take advantage of them.
* Feature: Source a .rvmrc file in a directory after changing to it, if it exists.
* Bugfix: Honor -C configure flags passed via command line.
* Added back the --host and --build configure options.
* Bugfix: (sorta) ignore calling self when $* matches completion* Minor version bump.
== Release 0.0.77
* Bugfix: 'rvm gem uninstall X' no longer errors on --no-rdoc
* Feature: 'rvm install ree-1.8.6' on Darwin now injects --no-tcmalloc
* Removed usage of =~ for now :/
* Switched shebang lines to use /usr/bin/env.
* Feature: 'rvm install curl'. (For use with curb for example: 'rvm ree ; rvm install curb -- --with-curldir=/Users/wayne/.rvm/usr/'). Thanks foca.
* Minor Version Bump.
* Feature: Detection of scripts directory vs rvm path.
* Bugfix: 'rvm gemdir', 'rvm gemdir system', 'rvm gemdir user', etc... now all work as expected.
* Bugfix: rvm 1.9.1,1.8.6 -S spec spec/hash_spec.rb. Thanks dbussink.
* More tweaks to Darwin build architecture detection.
* Bugfix: only honor MacOSX SDK's. Thanks rolfb.
* Prevent \ interpretation.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Site Updates.
* fixed symlink path for default-irb/default-gem
* Feature: Have 'rvm use X' be verbose and output 'now using ruby X' while 'rvm X' not be verbose for scripting (by
default). This can be overridden by placing rvm_verbose_flag=1 in ~/.rvmrc to always be verbose.
* Feature: Cleaned up rvm list, added some color.
* Bugfix: clear all gems flags when cleaning up variables.
* Initial SysAdmin root level support -- specficially targeted to hosting environments.
* Feature: for 'rvm gem install X' add --no-rdoc --no-ri
* Bugfix: --ree-options should now actually take options.
* Bugfix: i686 for x86_64 in --host and --build.
* Skip autoconf step if configure is defined.
* Adjust how we build llvm.
* Build llvm prior to building macruby.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Buahahahahahaahahahahaha...
* Fun with configure.
* Switched function style in installer and utility scripts.
* Improved rubygems install code some.
* Bugfix: 'rvm install 1.9.2' no longer tries to install 'ppreview1' :)
* Minor version bump after 0.0.73 release.
== Release 0.0.73.
* jruby 1.4.0 is now default. macruby now only shows up in all list if system is OSX.
* Minor version bump after 0.0.72 release.
* Initial jruby-head support.
* space fail.
* Fixed up installer based on suggestion by chrisk.
* Feature: Added macruby to 'rvm list'. Adjusted VERSION to latest jeweler release (yay).
* Site update.
* Bugfix: ree installer now a) does not double call make_flags() and b) parses the configure to place -c before each --call.
* Nice basename idea Chris Kampmeier.
* Bugfix: Adjusted 'ls' in order to avoid aliases.
* Make user facing message simpler.
* Bugfix: adjust svn urls for new ruby string logic.
* Minor version bump.
== Release 0.0.71: Added macruby & rbx to rvm list. Initial (simple) ruby support.
* Feature: rbx and macruby now both show up under rvm list.
* rvm Release 0.0.70: Initial macruby support.
* Feature: 'rvm macruby' now defaults to the 'nightly' version.
* Feature: 'rvm install macruby-nightly' now works. Caution: conflicts with beta release, advise using nightly builds.
* Site update.
* Added initial ruby support files.
* Minor version bump.
* Tweaked version difference message a bit, great stuff thanks docwhat :)
* Feature: Checks if rvm needs to be re-synced in the shell.
* Bugfix: 'rvm gemdir' thoughts not completed are best completed.
* Bugfix: Correctly check for the specification file to see if it is already installed :)
* Well that was rather embarassing ...
* Slowly improving gem handling logic.
* Feature: respect the reported architecture of the host OS on Darwin. Additionally allow the user to override via
rvm_archflags in ~/.rvmrc
* Adjusted jruby download url.
* jruby RC1 -> RC3
* Bugfix: We *want* shell expansion of some things :)
* Bugfix: irbrc loading code, thanks yury!
* Bugfix: 'rvm system' now works as expected.
* Site updates.
* Respect any previous configure flags.
* Bugfix: Ruby now compiles more explicitely as i686 on OSX 10.
* Bugfix: 'rvm gemdir' now works again, thank you Tony_.
* Added extra trace output.
* tyop fix. Thanks coderpath.
* s/checkout/update/. Thank you rubys!
* Bugfix: svn checkout is ... fascinating.
* Subversion revision tweak.
* Adjusted download/clone/checkout messages, thank you rubys.
* Bugfix: Check for head flag for download url.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Bugfix: (again) 'rvm 1.9.1 --head'. Thank you rubys.
* Fixed use of RUBY_ENGINE -- doesn't exist in ruby < 1.9
* Rewrote __rvm_ruby_string to be a) flexible b) handle errors better and c) far less complex! Thanks for the idea,
Chrononaut!
* Site update.
== Release 0.0.66
* Bugfix: 'rvm 1.8.7%gemset' now works again (broken in last commit).
* Bugfix: 'rvm 1.8.7-p160' now works.
* Bugfix: 'rvm 1.9.1,ree,jruby benchmark some_code.rb'
* Added missing file scripts/irbrc.
* Moved usage out to readme.
* Patches: Thank you Thomas Ritz. Altered irb files to use env vars.
* Feature: Use a common irbrc for all installations for easy upgrades.
* Bugfix: 'rvm 1.9.1%somegem ; gem install wirble ; rvm 1.8.7 ; rvm gems delete 1.9.1%somegem' now works properly.
* Feature: IRB prompt mode is now stored in :RVM instead of :DEFAULT.
* Bugfix: 'rvm gem install X' now works.
* Put PAGER code back. bad monkey, careo, bad bad bad monky :-p
* Site updates.
* Bugfix: Do not respect the users PAGER setting as it may break rvm help.
* Switch back from bash native subsitution.
* Minor version bump.
* Adjusted rvm debug to output information useful when debugging issues on OSX.
* Added --archflags and --sdk, as well as configurable via ~/.rvmrc
* Switching rbx to use the new installer.
* Bugfix: Use 64 bit for SL and later, 32bit for previous.
* Bugfix: tyop, thank you hsbt
* Use *both* archflags for Darwin.
* Bugfix: Do not rely on 'ls -t' instead use sort and tail.
* Bugfix: -S and -e now work properly again. Removed --script and --execute options as they do not appear in ruby.
* Move reset of configure to all variable reset.
* Bugfix: 'rvm remove X' no longer tries to install after removing. Feature: 'rvm remove X' now takes a full rvm selector
string. Minor version bump.
* Site update, now officially publishing to gemcutter.org only.
* Feature: 'rvm 1.9.1-r25443' now works.
* Site update.
* Upgraded ree default version. 63 commands, 384 assertions, 384 passed, 0 failed..
* Applied patch for shyouhei 'mput' ruby
* Bugfix: 'rvm install 1.9.1 --rev 25443'
* rvm-prompt has been rewritten to be flexible.
* Bugfix: 'rvm 1.9.1-head'
* Site update.
* Bugfix: 'rvm install 1.9.1-head'.
* Minor version bump.
* Bugfix: Removed __rvm_reload
* Feature: Restore cwd after rvm update. Bugfix: 'rvm update' should work again.
* Minor site wording tweak.
* rvm Release 0.0.62 (See PT for information).
* Bugfix: properly extracting of gem names & versions
* Escape paren in regex.
* Logic tweak to gems loading.
* Bugfix: gem name parsing for gemset laod.
* Missed a spot.
* Double entendre :)
* Several bugfixes and features (see pT)
* Site updates.
* Site update.
* Site Update, thank you Brian Hogan!
* Bugfix: Use rvm_path and do not hardcode .rvm DOH.
* Adjust to use actual architecture rather than OSX release version.
* Remember kids, practice safe sed!
* Date bump.
* Bugfix: 1.8.* now properly use rvm's installed openssl/readline/zlib/iconv. Major accomplishment tonight, would do a
backflip if I could ;) w00t
* Version bump. Bugfix in btu.
* Site Update.
* Regex adjustment.
* Switching to safer sed patterns.
== Release 0.0.60: gems(et) and other bugfixes.
* Bugfix: 'rvm 1.8.7-p160' works as intended. 50 tests, 351 assertions, 351 passed, 0 failed
* Bugfix: install should not replace rvm-prompt location :)
* Added 2 tests with assertions to cover the last feature checked in.
* Bugfix: 'rvm gems X' and 'rvm gems clear' now updates the PATH properly for the new gem home.
* Feature: 'rvm gems clear' now clears the current gemset, resulting to the selected ruby's default gem home.
* Bugfix: If gem version is not specified, omit it.
* Bugfix: Respect force flag for rvm gems load if gem is already installed.
* Bugfix: rvm gems once again properly skips gems that are already installed. Feature: rvm gems load now displays red/green
for success/failure of gems loading and surpresses gem's output. Added __color function.
* Adding blank bundler files to site.
* rvm release 0.0.59: gems(ets)
* Site update.
* Site documentation update, added a few more tests.
* gemsets now work with the selector and multi commands, w00t!
* Now have: 40 tests, 339 assertions, 339 passed, 0 failed. Gem Sets working as expected.
* Feature: rvm gems completely functional! Passing test suite, w00t!
* Bugfix: rvm gems load
* Removed debug.
* Site Update.
* Site updates.
* Site update.
* 'rvm install ree' now works without throwing an error.
* Bugfix: nasty recursive gem home bug.
* Bugfix: ree string had an extra ) floating around ...
* use non-prefixed less for pager default.
* Updating FAQ - Textmate Workaround
* So ... I can't count eh?
* release 0.0.58
* Bugfix: GEM_HOME is now handled correcty.
* Switched code to use preferred subshell method.
* Made test clauses safer from bad input.
== Release 0.0.57: Bugfixes.
* Bugfix: 'rvm ruby' and 'rvm gem' with no arguments now properly issue an error message.
* Bugfix: 'rvm update' now works again.
* Remove debug.
* Bugfix: nasty recursive gem home bug.
== Release 0.0.56. 'rvm gems X', X in {<set name>, load,dump,delete,name,dir,list}
* Feature(s): 'rvm gems X'. 52 tests, 443 assertions, 443 passed, 0 failed. ::grin:: w00t
* Bugfix: basename: missing operand.
* Fixed the tests.
* BugFix: ree installer.
* Use signal trap in order to cleanup when done.
* Remove wget support, we're going all curl baby...
* Bugfix: 'rvm --help' no longer tries to shift on an empty array.
* Removed system ps1 from rvm, no longer necessary with rvm-prompt. More work on 'rvm gems ...'
* Site updates.
* Merge branch 'master' of github.com:wayneeseguin/rvm
* Started working on the gemset ui.
* Fixes issues with the display of preformatted code.
* Feature: Partial string matches (for use with do actions). Added btu 0.0.1 and 29/290 tests.
* Switched rbx to latest llvm compilation method (still using --jit from CLI). Renamed rvm_gem_home to rvm_ruby_gem_home for
clarity. Shortened 'ruby-enterprise' to 'ree' for brevity.
* Allow user to set their archflags in ~/.rvmrc.
* Date update.
* Minor config tweak.
* Site update
== Release 0.0.55: Gemset Bugfix.
== Release 0.0.55: Gemset Bugfix.
== Release 0.0.55: Gemset Bugfix.
* Bumped 1.8.5 patchlevel to 231.
* Bugfix: gemsets no longer default to version :-p
* rvm Release 0.0.54: 'rvm jruby 1.4.1' (currently RC1)
* Feature: 'rvm gemset delete X'
* Feature: Detect curent gemset if none given and one exists.
* Feature: Indicate defaults in 'rvm list --all'
* Docfix: Added jruby 1.4.1 to 'rvm list --all'
* Feature: 'rvm install jruby 1.4.1; rvm use jruby 1.4.0. Bugfix: Do not let the dog chase it's tail :)
* Allow exact specification of gemset file during load.
* Add basename extraction to test also.
* Prevent users from specifying full path in gemset.
* Allow --repository and --url and --repo with the CLI
* Pass '--repo-url X' to override the repository url used when installing a ruby.
* If you place 'rvm_ruby_repo_url' or 'rvm_jurby_repo_url' or 'rvm_rbx_repo_url' it will override rvm's urls
* If you place 'rvm_ruby_repo_url' or 'rvm_jurby_repo_url' or 'rvm_rbx_repo_url' it will override rvm's urls
* Show gem sources when 'rvm debug' is used.
* Shift if 'use ruby' sequenece to avoid the ruby triggering do.
* Summary output is now more readable.
== Release 0.0.53
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bugfix: 'rvm benchmark increment.rb' now works with jruby. Site Updates.
* Added Maz's installer patch. Added imajes rvm_loaded_flag idea.
* Shortened output.
* Minor version bump.
* Patch: Maz, fix extraction logic after archive download.
* rvm release 0.0.52: rbx fully functional.
* rbx finally works fully, yay
* Site modification, switch to haml (yay).
* Feature: --json,--yaml only output those. Bugfix: Downloader for installs.
== Release 0.0.51: ree 1.8.7
* ree 1.8.7 is now default.
* Feature: ree 1.8.7.
== Release 0.0.50: Progress.
* Bugfix: rvm list.
* Some more tweaking on macruby.
* Smoothing out the installs & configuring.
* using default with no default set is a warning not an error.
* Bugfix: rvm reset now correctly selects system.
* Minor version bump.
* Bugfix: Logical switch on jruby should be and not or.
* Feature: 'rvm load my.gemset' ; Feature: 'rvm dump my.gemset'
* re-added install symlink.
* Fixed some paths, thanks Pistos.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
== Release 0.0.49.
* Some rubinius tweeks.
* Feature: 'rvm ree 1.8.7 --head'
* Indent notes.
* Symlink rvm-install for next few releases to smooth upgrades.
* Adding ./install
* Beginning final overhaul before 0.1.0.
* Feature: --trace flag to differentiate and augment from --debug flag.
* Site update.
* Initial try to check archives
* patch the remainder of the jruby scripts
* remove old scripts so that links don't lead to weird resutls
* Feature: 'rvm --shebang --env inspect x,y,z' to help me help others.
* Bugfix: system indicator.
* Bugfix: Correctly use bin_script for rubies. THANK YOU smparkes.
* Full path for shebang.
* Back to symlinks.
* Hardlink after install for jfiles.
* hard link jfiles .
* Removed extra chmod.
* Silence errors we don't care about.
* Set environment for jgem.
* Bypass aliases for make.
* use before doing.
* Stick with jruby's own rubygems.
* Skip rubygems and only do update for jruby.
* Installer now allows for non-interactive installs.
* Feature: rvm restores selected ruby after performing a multi action. Bugfix: unset rvm_ruby_selector when cleaning up
variables.
* Site update.
* Site updates.
* Bugfix: s/=true// for --enable-shared. Thanks Maz.
== Release 0.0.48. Site updates.
* Feature: 'rvm install/uninstall/remove X,Y,Z...' Updated usage & CLI.
* Feature: 'rvm system --default'
* Slowly forward with jruby...
* Bugfix: rvm install X,Y
* Removed stray __rvm_select
* Bugfix: rvm install A,B,C now works.
== Release 0.0.47: jruby + rubydo bugfixes.
* jruby ::twitch:: jruby ::twitch:: ... working ...
* After much mental aerobics JRuby is now working.
* Bugfix: jruby shebang now properly set, yay.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bugfix: rvm list for zsh if no rvm sourced in bashrc.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master' of [email protected]:Pistos/rvm
* Bugfix: /bin/bash instead of just 'bash' in case bash is not in path.
== Release: 0.0.46 Essential installer and other bugfixes.
* Removed pointless warnings.
* Patch: For curl, detects if server does not support range command, delete archive, and retry download. Thanks Maz.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bugfix: Ruby installs now have gem_env/path and shebang properly injected.
* Bugfix: Fixed jacked up sed script, thanks Maz
* Finished removing system_path items.
* Feature: Clean PATH of rvm instead of storing system path. Thank you Joseph Hsu (jhsu)!
* Feature: json/yaml to log/summary.json/yaml.
* Bugfix: 1.9.X rubygems install.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* More cleanup.
* Cleaned up visuals of rvm-install.
* Bugfix: Multiple and all for rake X now work. Thank you dbussink
* Single spec case working.
* minor version bump.
* Bugfix: Missing space around test, thanks Maz.
* Bugfix: Install on use flag works now. Bugfix: existence testing and standard file testing for gem path/hme injection.
* Never do things in a hurry :/
* Fix test for 1.9, thanks Maz.
* Feature: Removed path from system snapshot. Bugfix: test for file in post-install.
* s/sync/gemsync/g
== Release 0.0.45
* JSON output reformatted and workign in zsh as well.
* Bugfix: ZSH yaml fix.
* Feature: 'rvm install X,Y,'Z works as intended. Bugfix: 'rvm install jruby'
* Make rvm debug slightly more useful when helping people.
* Bugfix: 'rvm do' === 'rvm rubydo'
* Fun with popsicles.
* Bugfix: gemsync actually works now. Thanks bosie.
* Bugfix: gemsync :)
* Added gemsync utility. Thanks bosie.
* Gem Sync mege with gem dup.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Bugfix: rvm list for system, thanks Pistos/Scyllinice. Initial sync code, thanks bosie.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Silence pushes & pops, thanks darkhelmet & bosie.
* rbx binary wrappers for gem and rake.
== Release 0.0.44: Install Bugfix, thanks Maz.
* cp -Rf /
* cp -Rf :)
* cp -R
== Release 0.0.43. Features: 'rvm benchmark code.rb', 'rvm rake <task>'
* Bugfix: 'rvm system' works again with rvm-prompt.
* Bugfix: 'rvm gemdup system'. Bugfix: 'rvm gemdup user'
* Unearthed gem of a gem, gem features.
* gem wrapper now in place.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Added rake to rbx install.
* Feature: --json Summary.
* Feature: 'rvm benchmark rubyfile.rb' :). Feature: Summary as yaml 'rvm --yaml rake -T'.
== Release 0.0.42.
* Feature: 'rvm rake -T' (doesn't have to be just -T ;))
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
s/--enable-pthread=true/--enable-pthread/g
Bugfix: patchlevel should respect 'head' and 'trunk' values. Thanks Yehuda.
Feature: 'rvm remove' and 'rvm uninstall' are now split.
re-enabled macruby against git head.
LOL bugfix
Moved VERSION.yml to lib/
Copy over lib dir on install.
Install adjustment.
Initial rake/gem code.
Set ARCHFLAGS for Darwin.
Feature: Merge configure options with user's configure options.
minor version bump prepairing for next release.
BugFix: Would you like a variable with that?
Removed -l flag.
Bugfix: patchlevel for ree.
Added VERSION.yml to Rakefile, thanks tswicegood.
::twitch::
grumble... I just pushed a release :/
== Release 0.0.41: Bugfixes. Thank you community awesome.
* Bugfix: rake gets installed to gem_home/bin :)
* Site Updates.
* Bugfix: ruby_string grep should check rev at beginning.
* Remove 'j' from 'jgem' call bin script.
* Bugfix: silence ls. Feature: Extracted duplicate rubydo blocks out to a function.
* Silence error stream for gem list. Remove Readline comment.
* Comment out manual readline build for now.
* Bugfix: unset configure variable. More work on gemset loading.
* Bugfix GEM_PATH. Thanks Jamie.
* run bin_script after rubygems install.
* version bump.
* Show progress indicators for wget/curl when downloading.
* Site Update.
* Feature: skip already installed gem files.
* Thank you Thomas Kern. Bugfix: correct gem file names for gemset load.
* s/daft-wayne/wayne/g
* Subshell output redirect, thanks bosie
* Cleaning up cli. Updating usage. Bugfix: gemset load.
* Fun with flags.
* Search rvm gems cache directories for gem files before hitting the 'series of tubes'.
* Bugfix: gemset load, thanks bosie.
* if [ 'zsh' = 'daft' ] ; then s/parameters/configure_parameters/g
* Send STDERR to /dev/null for cache check with gemset load
* if [ 'zsh' = 'daft' ] ; do sed -i s/status/result/g ; done
* Bugfix: Patchlevel sanity checks, thanks sfpyra.
* rvm Release 0.0.40: Ruby Install Bugfix.
* setn enable-shared=true
* Ensure that --enable-shared is used with configure :/
== Release 0.0.39
* Only use rvm readline if it exists.
* Silence Z grep
* Features: ~/.bin/ruby,gem,irb,default-ruby symlinks on --default.
* Bugfix: patch level. Check for non-existant url and issue error message if so.
* Moved some cli related functions into rvm-cli script.
* Removed --disable-shared, how'd that sneak in there :-p
* Feature: gem update --system after installing 1.9.1
* Feature: rvm built in readline build support now functional. Bugfix: 1.9 installs properly w/rubygems modify instead of
install. Site Updates.
* Removed warning to allow people to run ruby under passenger as root ;)
* Bugfix: Rubygems install for 1.9 was not honoring its test. Setting flags for readline compile.
* Feature: 'rvm update --rubygems' now installs rubygems for the currently selected ruby.
* Bugfix: 'rvm gemdir system user' now works. Site Updates.
== Release: the .38 special.
* moving forward with readline.
* Doc updates, thanks anita-kun.
* flash messages.
* Bugfix: use 'trunk' for 'head' / 'trunk' rev. BugFix: svn update if svn repo already cloned. Feature: 'rvm install
readline'. Feature: 'rvm install iconv'.
* Merge branch 'master' of github.com:Pistos/rvm
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Typo fix, missing |. removed sudo from iconv install.
* Added two (as of yet untested) functions.
* Bugfix: rvm list now shows default ruby correctly.
* 'default_' -> 'system_'
* Bugfix: Only shift params if version supplied.
* Feature: 'rvm update --bin'. Feature: 'rvm update --rubygems'. Bugfix: 'rvm system'. Feature: gemset load/dump extracted
to functions. Feature: rubygems install extracted to function. Feature: gemset load now checks for a cached version in gem
home before installing, accounts for prefix and postfix, setup for eval flag parameter later.
* Initial ruby_string function, not working yet.
* Bugfix: tyop :)
* Feature: 'rvm update --bin.'
* Bugfix: 1.9.1 gem command shebang line now proper.
* Bugfix: missing dollar sign prefix.
* Feature: -r|--require. Bugfix: GEM_PATH in aux scripts. Began setup of status checks for installer.
* Skip rubygems for 1.9.1
* Feature: can now pass 'rvm install 1.9.1 -j 8' to have make -j8 called. Bugfix: shebang line w00t. Added GEM_PATH to aux
binaries.
* Feature: exit status codes propigate out of the rvm command. Feature: -S now eats to the end of the line and works as
expected, example: 'rvm 1.8,1.9,jruby,rbx,ree --summary -S rake -T'
* Added initial -I functionality.
* equivocate arguments ending in '.rb' to -S
* Added symlink rvm-install -> rvm-update
* purty...
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
--summary now works with -S.
Bugfix: 'gemdir' command actually works as intended now :)
BugFix: Do not blindly adjust profiles, test for adjustment condition first.
Bugfix: remove '.orig' sed backup files. Thanks Josh Peek. Now working on --summary for use with -S
Merge branch 'master' of git://github.com/wayneeseguin/rvm
-C should proxy to -c for rvm.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
rvm <selector> -S <scriptname.rb> now works. Bugfix: ree now uses -C args passed in, Thanks chewie71.
Bugfix: irbrc loading.
Feature: use now prompts for install. Feature: Added timestamps + commands to logs.
Feature: 'rvm reboot'. Cleaning up cli into functions.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
rvm list >> multiruby -v :-p
Bugfix: GEM_PATH missed a spot for system. Made version single point of change.
Added GEM_PATH.
Simply load, not copy user's .irbrc, thanks brainopia.
Site Update, prompt.
== Release 0.0.37: Bug! Bug!... Squish!!!
* Made the currently selected ruby more... obvious.
* Updated 'rvm list' to include a '*' in front of the currently selected ruby.
* Inject blank line just before injecting source lines during install.
* Bugfix: default & sytem selector now work properly.
* Bugfix: rbx install. Bugfix: Check if user has unzip for jruby installs and show warning if not. Minor site updates.
* Added prompt to site.
* Fixed wget test, thank you Maz.
* Updated site with --dump & --load
* Remove debug flag.
* Bugfix: gemset --dump correctly separates multiple versions now.
* Bugfix: remove system *file* if it exists and is a file.
* rvm-prompt works when you copy scripts/rvm-prompt to your path now :)
* Feature: rvm-prompt.
* Issue a warning message if rvm binaries are called as root.
* Feature: ~/.rvm/default -> ~/.rvm/system ; ~/.rvm/current -> ~/.rvm/default
* Bugfix: Correctly specify java/ree messages on install.
* Added scripts/rvm-aliases and scripts/rvm-functions for 'extra' features. Added gemdo usage doc. Added rake to binaries
list. Added initial --dump and --load for use with gemsets.
* Site Updates.
== Release 0.0.36
* BugFix: rubydo if interpreter is actually a ruby version number, thanks aaalex.
* Fix for rubydo, all case.
* Use current user path instead of default path.
* Applied PATCH by Chrononaut for install to follow symlink to zshrc.
* Site update.
* Bumped version.
* Fixed an IRBRC bug, thanks danny (dnyy). Updated site faq to advise strongly against using sudo, thanks olegshaldybin.
* Bugfix: IRBRC not getting set with current. Better setting/unsetting behavior for current.
* Adjusted else fork's location to be consistent with if above, thanks olegshaldybin.
* Added GEM_HOME explicit setting to installer, thanks zomb. Site updates.
* rvm gemdir fix.
* Playing touchy-feely with some log files.
* Bugfix: rvm-install not rvm-update.
* Bugfix: Ensure sure that the log directory exists.
* Fixed heredoc subshell for zsh :/ ;)
* Bugfix: ree. Initial rakedo & gemdo, not fully baked yet.
* Update now merged into installer with extra checks. Temporarily commented out actuLfile.
* Removed bin/rvm-update.
* Bugfix: binary install for rake. Began merging update script into the install script.
* Added rbx head --jit to list --all.
* rvm Release 0.0.35:
* Fixed missing binaries issue with Ruby 1.9.2.
* Bugfix: log file name.
* Fixed db entries.
* Site update.
* default_system_ruby fix
* Bumped 1.8.6 back to 383.
* Pushed fix for syntax on Makefile line.
* Added config dir so we get the db.
* Renamed rvm-installer to rvm-ruby-installer.
* Bugfix: missing $, thanks brainopia. Feature: Split out files.
* Bugfix: Correctly unset RUBYOPT for installer if it is *non empty*.
* Feature: --re-configure. Added selected variable export to prepare for install extraction.
* Working on defaults from db hash store.
* Site Updates.
* PATH tweek for binaries.
* Resorting to a semi-colon
* Adding blank space to irbrc.
* Bugfix: Added 'current' to selector.
== Release 0.0.34: Bugfix: log_file_name... is a variable :)
* Syntax check, aisle 3
* Adjusted default system checks to check if ruby is installed, thanks Maz. Bugfix: log_file_name... is a variable :)
== Release 0.0.33: Bugfix: autoconf logic.
* Bugfix: autoconf.
* Bugfix: Correctly handle autoconf.
* Site update.
== Release 0.0.32: Bugfix: PATH to include user's default path now.
* Adjusted binary file paths to include the user's default path.
== Release 0.0.31: Feature: rvm list --all Feature: Adjusted rvm_ruby_configure. Feature: rvm update Feature: reset so that
system ruby (1.8) is used to build rubinius, which requires parsetree. Thanks manveru. Feature: env/path injection to
executables. Feature: Added wget support. Feature: rvm_run function. Added update --head. Bugfix: Exit out of push'd
directory when encountering a failure. Bugfix: Made trimming the last : in the path more shell agnostic. Bugfix: Moved logs
outside eval. Thank you metaskills. Bugfix: Adjusted default configure options. Updated some site docs. Thanks mr-interweb.
Bugfix: don't shift on use if 2nd parameter is empty thanks mr-interweb.
* Feature: rvm list --all
* Bugfix: Exit out of push'd directory when encountering a failure.
* Added wget support.
* Made trimming the last : in the path more shell agnostic.
* Added rvm-run function. Added update --head.
* Moved logs outside eval.
* Trying something with the configure line for metaskills.
* Adjusted default configure options. Updated some site docs. Thanks mr-interweb.
* Bugfix, don't shift on use if 2nd parameter is empty thanks mr-interweb.
* Adjusted rvm_ruby_configure.
* Added 'rvm update' feature.
* Many variable renames/replacements for line shortening and readability.
* Added reset so that system ruby (1.8) is used to build rubinius, which requires parsetree. Thanks manveru.
* Added reset for rubinius which requires 1.8 to install due to parsetree, thanks manveru.
* Working env/path injection.
* Applying patch from ujihisa: Fixed installer's behavior. See the details below.
* Moved svn url block inside the svn if.
== Release 0.0.30 Feature: 1.8.6-p383 is now default. Feature: --set-prompt option for prepending ruby version to prompt
(opt-in). Feature: GEM_HOME/PATH to: gem, irb, erb, ri, rdoc, testrb, rake. Feature: install --force option Feature: git
support to ruby-install-source. Bugfix: unset variables in default file if not set by default. Feature: rvm_prompt added to
defaults file. Bugfix: Path fix. Feature: Ruby Wrapper Script. Bugfix: Log path error messages. Typos in docs. Bugfix: usage
to be more clear for --configure option, thanks mikeg1a. Feature: alias '--trace' for '--debug' for rake lovers :)
* Update 1.8.6 to use 383 as default.
* Added --set-prompt option for prepending ruby version to prompt (opt-in).
* Added GEM_HOME/PATH to: gem, irb, erb, ri, rdoc, testrb, rake.
* Added GEM_HOME to rake binary now.
* Added --force option for install.
* Added git support to ruby-install-source. Bugfix: unset variables in default file if not set by default.
* Adding rvm_prompt to defaults file.
* Path fix. Ruby Wrapper Script.
* Working out the make & make install options for macruby.
* *actually* fixed the log path error messages.
* Fixed quoting issue.
* Fixed rvm_ruby_repo_url for macruby.
* Fixed url for macruby in info.
* Fixed url for macruby
* Typo fixes for docs. Working on MacRuby with help from lukeredpath.
* Updated usage to be more clear for --configure option, thanks mikeg1a. Added alias '--trace' for '--debug' for rake lovers
:)
== Release 0.0.29: rvm Passenger Support. (with a gemspec :)
== Release 0.0.29: rvm Passenger Support.
* Bugfix for $@ with passenger, thanks lukeredpath.
* Added Passenger Support. Bugfix for error log location notification during installs.
== Release 0.0.28: Reverted installation bin scripts. Two bug fixes.
* Bugfix for '--configure' thanks Scyllinice
* Updated site.
* Updated website.
* Added unset of rvm_prompt on reset, thanks zmack
* Reverted the bin/rvm-* scripts to their previous state.
== Release 0.0.27 Feature 'rvm implode' Feature --jit flag to tell Rubinius to build with JIT (RBX_LLVM=1). Bugfix reset
should select system only after doing some cleanup. Feature missing variable namespaces Feature exits when install goes
badly. Feature for use with PS1 Feature support for inclusion of user's irbrc, if it exists.
* Added 'rvm implode'
* Webssite Update.
* Added --jit flag to tell Rubinius to build with JIT (RBX_LLVM=1).
* Reset should select system only after doing some cleanup.
* Added missing variable namespaces
* Adding exits when install goes badly.
* Don't unset rvm_prompt
* Tweaked user's irbrc inclusion to be more efficient (no variable).
* Added support for inclusion of user's irbrc, if it exists.
== Release 0.0.26: Several bugfixes. 'rvm default' now uses the current set default or system. 'rvm system' now uses system.
Adjusted namespace to be even more discreet. Added rbx for rubinius. Cleaned up usage. Removed install all feature. Made
rvm_prompt opt-in via env variable.
* Gem install/update tweak. Updated setdefault docs page.
* 'rvm default' now uses the current set default or system. 'rvm system' now uses system. Added bugfix for install/update,
thanks Maz.
* Adjusted namespace to be even more discreet. Updated site docs some more.
* Add rbx. Adjusted usage.
* Trimmed down 'rvm usage' some. You don't need an 'Installation' section if you are using 'rvm usage' ;)
* Bumped version #'s and updated date. Removed usage for install all.
* Now exporting 'rvm_prompt' env var for use with prompts, use if you like.
* Make prompt feature 'opt-in' :)
* Removing 'install all' feature.
* Third time is a charm? :)
* Another bugfix for install all, thanks Peter Cooper.
* Bugfix for install all, thanks Peter Cooper.
* Tweaked install all. Updated site docs some.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
== Release 0.0.25. 'Major Nerdon'
* jruby HEAD working.
* Finished initial revision of rubydo.
* Added an extra line to the output.
* Path now updates to display currently selected ruby version. Small bugfix in update thanks to Maz.
* Simplifying install & update. Added message for MacRuby.
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
*
Added defatults cache file.
Added rvm-cache for string storage (defaults).
Added ability for more than one --configure option :). More progress with macruby.
Initial Rubinius support. Updated Thanks.
Initial macruby code, had to stop testing because I could not get macruby compiling :)
Named releases, named svn tags, svn revisions, svn head for 1.[8-9].X.
Initial tag usage functional, thank you Kirk Haines.
Bugfix: install all should not try to install 'REE 1.3.1' :), thank you Scyllinice.
Initial tag code. Bugfix for ree: add --no-tcmalloc to install, thank you r38y
Added abillity to remove a named gem set.
Remove gem directories for versions on uninstall.
Added gem set support.
Bugfix in install script. Thank you ddfreyne.
Fix to install script, thanks Tsykoduk
Bugfix, odd typo. Cleaning up code.
Fixed ree (again :)
IRB Support complete.
Added individual ruby IRBRC support.
Shuffled around directories so that things are closer to their final form early on.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Fixed: -h | --help | rvm usage | rvm help
Fixed rvm info. Merged with rvm debug secion. Improved rvm debug output.
Namespaced niceness to rvm_niceness.
Namespaced configure to rvm_ruby_configure
Added patch by Jim Lindley on how to 'install from source'.
You must export what you wish to use :)
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Change test for rvm source file to also check if greater than zero.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
No longer using -f check with curl since we are using the -C - flags.
Slightly improve error handling.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Merge branch 'master' of git://github.com/wayneeseguin/rvm
We are (generally) not psychic, have curl automatically determine where to continue downloading.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Enable 'continue partial downloads' for curl, thanks Pistos\!
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Adjust rvm_{major,minor} version extraction to play nice with zsh...
Running a ruby file against all versions of ruby or just one now works.
Fixed ree install. Site updates.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Merge branch 'master' of [email protected]:Pistos/rvm
Updated thank you's on site.
Adjusted path cleaning to remove trailing :
Refactoring complete. Testing needed.
Removed switching message now that we stay in the same shell.
Repaying technical debt. Refactoring.
Merge branch 'master' of git://github.com/wayneeseguin/rvm
'ls' is now referencing '/bin/ls' to avoid potential alias issues,
thanks Pistos!!!.
Make the about information show up again in the usage :)
Shortened usage and made it more maintainable at the same time, yay
Merge branch 'master' of git://github.com/wayneeseguin/rvm
More cleaning up, namespacing, working on support for 1.8.X
Merge branch 'master' of git://github.com/wayneeseguin/rvm
Added awesome sed-fu patch by Chrononaut.
== Release 0.0.24: Quick, hide before she sees!
== Release 0.0.23: It works!
* Completely separated out rvm's gems from system 1.8.
* Added support for bin_path.
* ree now works with it's own rubygems again. Seeing some oddities with 1.9.2.
* Namespaced log_path. Rubygems now good for 1.8.X, still failing for ree.
* Default variable bugfix. All ruby installs work. Rubygems install needs bugfix (gem isn't going to the correct location).
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Rename default_gem_path to default_user_gem_path
* More namespacing.
* Began the variable namespacing process.
* Add rvm reload option.
* Adjusted install & update based on feedback from Maz on IRC.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Download file check based on archive path.
* Fixed prefix path checking and logic.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Merge branch 'master-upstream'
* Defaulting log path properly to install_path/log
* Changed variable defaults to use :- instead of simply -.
* Added patch for archives, thanks to Pistos.
* Applied niceness patch by Pistos.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* Removed pwd for install & update. Added /log to log path. Thanks Maz.
* Removed lots of trailing whitespace for Pistos.
* Bugfix for zsh in rvm-install. Abstracted log dir.
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
* ~/.rvm/log. Hook into .bashrc also. Install all bugfix. Install script capability testing cleanup.
* Merge branch 'zsh'
* Merge branch 'english-changes'
* Merge branch 'master' of git://github.com/wayneeseguin/rvm
== Release 0.0.22: Let it Snow Leopards
* Merge commit 'a8e55b29195f15b773dd698beb236493f372efdd'; branch 'site'
* Credit Pistos, add patch by Caius Durling.
* Merge branch 'master' into site
== Release 0.0.21. Is there a cure for stupidity?
== Release 0.0.20. Bugfix: zsh using curl. Bugfix: REE Uninstall.
* Fixed ree uninstall bug.
* 'Ignore built gems.' -- Pistos
* 'Added evals to calls, to satisfy zsh' -- Pistos
* Added evals to $curl calls, to satisfy zsh.
* Merge branch 'master' of [email protected]:Pistos/rvm
* freenod -> freenode
* Ignore built gems.
* Added rvm symlinks to generate ~/.rvm/bin/ binary symlinks. Fixed RUBYOPT 'bug' when installing ree.
* Added rvm symlinks
* Fixed documentation error in the installer.
* Updated Site.
* Updated README and website to https://rvm.io/
* Latest site.
* Website initial just about ready.
* Unset GEM_HOME and MY_RUBY_HOME on default switch.
* gemdup getting there...
== Release 0.0.18.
* Adjusted rvm debug.
* Parital gemdup functionality (default & system).
* Added system default ruby to rvm list.
* rvm reset now works proper for hard system reset.
* Adding rvm-update.
* Added rvm reset feature.
== Release 0.0.16. Many documentation typo fixes. Added Install section to usage. Added more thank you's. Added curl
detection (for Ubuntu). Added force to symlinks. Fixed gemdir system/user. Added both shells option to install. Improved
wording of rvm-install script.
* Bugfix on source pat.
* Installer now prompts for manual install and is much more forthcoming and helpful.
== Release 0.0.14. Bitten by RubyGems.
== Release 0.0.13. Bugfix in mkdir for source dirs.
* Namespaced logging functions.
* Refined debug.
== Release 0.0.11. rvm gemdir functional.
* Updated Readme.
* rvm gemdir now functions.
== Release 0.0.10. rvm default and switching now work properly with the path. Began prepairing for abstraction.
* Label gemdup TODO
* Updated README
* Added rvm list.
* Updated README
* Uninstall now works.
* Added sanity check for rvm-install to deny installation as root.
== Release 0.0.8
* Debug switch now works. Added root sanity check.
== Release 0.0.7
* Addded gemdup example. Fixed a rather embarassing typo.
== Release 0.0.6
* Installations are now verbose and clean. REE now works properly. rvm -v|--version alone now displays the version of rvm.
* Updated usage & readme.
* When not specifying implementation and version, set to default.
* Added Credits & Website
* Added version and author line and updated wording for usage/docs. Removed rubinius plans for now.
* Don't depend on uninstall.
* Added default task => :gem
* Updated rake gem
* Added initial zsh support.
* un-DRY curl.
* Properly namespace all rvm functions with rvm-.
* Added 1.9.2 support. Added per interpreter rubygems install (for source installs).
* Added --configure option override. Fixed a typo.
* Typo fix. Merged two variables that were the same except in name.
* gemdir and srcdir now work as advertised.
* Improved usage documentation. Removed path, rvm-setup, leopard (redundant to default).
* Added debug action. Added all install. Added RVM module place holder. Removed package manager option, this should be for
system default control.
* Added LICENCE file to gem build.
* Fixed executable permissions for jruby.
* Prepairing for first release.
* gemdup stil needs some love but we're good to go.
* About to refactor.
* Correctly refer to the bash/rvm-setup script for setup option.
* Added LICENCE File.
* Adjusted the rvm command so that it does not hijack the cwd.
* Initial Gem version.
* Switched source and package to simply prefix.
* Updated path order and installer.
* Added Installer.
* Initial rvm, ruby, jruby, leopard functional.
1.11. Rakefile
#!/usr/bin/env ruby
require "rubygems"
#
# VirtualBox Helpers
#
# Matches a host declaration in a ssh config file.
HOST_REGEXP
= /^\s*Host\s+([^\s#*]+)/
SNAPSHOT
= (ENV['SNAPSHOT'] || 'CURRENT').upcase
SSH_CONFIG_FILE = ENV['SSH_CONFIG_FILE'] || File.expand_path('../config/ssh', __FILE__)
def shell(cmd)
puts "$ #{cmd}"
system(cmd)
end
def hosts
@hosts ||= begin
hosts = []
File.open(SSH_CONFIG_FILE) do |io|
io.each_line do |line|
next unless line =~ HOST_REGEXP
hosts << $1
end
end
hosts
end
end
namespace :vbox do
desc "start each vm"
task :start => :stop do
hosts.each do |host|
shell "VBoxManage -q snapshot #{host} restore #{SNAPSHOT}"
shell "VBoxManage -q startvm #{host} --type headless"
shell "ssh -MNf -F '#{SSH_CONFIG_FILE}' '#{host}' >/dev/null 2>&1 </dev/null"
end
end
desc "stop each vm"
task :stop do
hosts.each do |host|
if `VBoxManage -q list runningvms`.include?(host)
shell "VBoxManage -q controlvm #{host} poweroff"
end
end
end
desc 'Run the tests remotely on each VM'
task :test do
begin
Rake::Task["vbox:start"].invoke
Rake::Task["vbox:remote_test"].invoke
ensure
Rake::Task["vbox:stop"].execute(nil)
end
end
desc 'Run the tests remotely (assuming each VM is running)'
task :remote_test do
local_dir = File.expand_path("..", __FILE__)
remote_dir = "$(pwd)/rvm"
remote_script = "vboxtest/test_suite.sh"
sh "'#{File.expand_path("../vboxtest.sh", __FILE__)}' -L '#{local_dir}' -R '#{remote_dir}' -S '#{remote_script}'
#{hosts.join(' ')}"
end
desc 'Run the tests locally'
task :local_test do
sh File.expand_path("../vboxtest/test_suite.sh", __FILE__)
end
end
1.12. README
{master:<img src="https://secure.travis-ci.org/wayneeseguin/rvm.png?branch=master" alt="Build Status" /> stable:<img
src="https://secure.travis-ci.org/wayneeseguin/rvm.png?branch=stable" alt="Build Status" />}[http://travisci.org/#!/wayneeseguin/rvm/branch_summary]
= rvm
* https://rvm.io/
* https://github.com/wayneeseguin/rvm/
== DESCRIPTION:
RVM is the Ruby enVironment Manager (rvm).
It manages Ruby application environments and switching between them.
== Installation
curl -L get.rvm.io | bash -s stable [--ruby] [--rails] [--trace]
stable :: Install stable RVM, good for servers.
--ruby :: Additionally install latest ruby version (MRI).
--rails :: Install gem rails into default gemset (also installs ruby if not
selected).
--trace :: Print trace of the installation, gist output when you have problems.
More details here: https://rvm.io/rvm/install/
== Usage
rvm [Flags] [Options] Action [Implementation[,Implementation[,...]]
== Flags
--default
--debug
--trace
--force
--summary
--latest
--gems
--docs
--reconfigure
--skip-gemsets
::
::
::
::
::
::
::
::
::
::
with 'rvm use X', sets the default ruby for new shells to X.
Toggle debug mode on for very verbose output.
Toggle trace mode on to see EVERYTHING rvm is doing.
Force install, removes old install & source before install.
Used with rubydo to print out a summary of the commands run.
with gemset --dump skips version strings for latest gem.
with uninstall/remove removes gems with the interpreter.
with install, attempt to generate ri after installation.
Force ./configure on install even if Makefile already exists.
with install, skip the installation of default gemsets.
== Options
-v|--version
-l|--level
--bin
-S
-e
--gems
::
::
::
::
::
::
Emit rvm version loaded for current shell
patch level to use with rvm use / install
path for binaries to be placed (~/.rvm/bin/)
Specify a script file to attempt to load and run (rubydo)
Execute code from the command line.
Used to set the 'gems_flag', use with 'remove' to remove
gems
:: Used to set the 'archive_flag', use with 'remove' to remove
archive
:: With MRI Rubies you may specify one or more full paths to
patches
--archive
--patch
for multiple, specify comma separated:
--patch /.../.../a.patch[%prefix],/.../.../.../b.patch
-C|--configure
'prefix' is an optional argument, which will be bypassed
to the '-p' argument of the 'patch' command. It is separated
from patch file name with '%' symbol.
:: custom configure options. If you need to pass several
configure options then append them comma separated:
-C --...,--...,--...
--nice
--ree-options
--with-rubies
:: process niceness (for slow computers, default 0)
:: Options passed directly to ree's './installer' on the
command line.
:: Specifies a string for rvm to attempt to expand for set
operations.
== Action
(Note: for most actions, 'rvm help action-name' may provide more information.)
*usage*
version
use
reload
implode
::
::
::
::
::
show this usage information
show the rvm version installed in rvm_path
setup current shell to use a specific ruby version
reload rvm source itself (useful after changing rvm source)
(seppuku) removes the rvm installation completely.
This means everything in $rvm_path (~/.rvm || /usr/local/rvm).
This does not touch your profiles. However, this means that you
must manually clean up your profiles and remove the lines which
source RVM.
get
:: {head,stable} upgrades rvm to latest head or stable version.
Check 'rvm help get' for more details.
reset
(If you experience bugs try this first with head version, then
ask for help in #rvm on irc.freenode.net and hang around)
:: remove current and stored default & system settings.
debug
(If you experience odd behavior try this second)
:: show the *current* environment information for current ruby
:: print the *current* ruby version and the name of any gemset
being used.
:: show info plus additional information for common issues
install
:: install one or many ruby versions
uninstall
remove
See also: https://rvm.io/rubies/installing/
:: uninstall one or many ruby versions, leaves their sources
:: uninstall one or many ruby versions and remove their sources
info
current
migrate
upgrade
:: Lets you migrate all gemsets from one ruby to another.
:: Lets you upgrade from one version of a ruby to another, including
migrating your gemsets semi-automatically.
wrapper
:: generates a set of wrapper executables for a given ruby with the
specified ruby and gemset combination. Used under the hood for
passenger support and the like.
cleanup
:: Lets you remove stale source folders / archives and other
miscellaneous data associated with rvm.
:: Lets you repair parts of your environment e.g. wrappers, env
files and and similar files (e.g. general maintenance).
:: Lets your backup / restore an rvm installation in a lightweight
manner.
repair
snapshot
disk-usage
tools
docs
rvmrc
:: Tells you how much disk space rvm install is using.
:: Provides general information about the ruby environment,
primarily useful when scripting rvm.
:: Tools to make installing ri and rdoc documentation easier.
:: Tools related to managing rvmrc trust and loading.
do
tests
specs
monitor
::
::
::
::
gemset
:: gemsets: https://rvm.io/gemsets/
rubygems
:: Switches the installed version of rubygems for the current ruby.
gemdir
srcdir
:: display the path to the current gem directory (GEM_HOME).
:: display the path to rvm source directory (may be yanked)
fetch
list
:: Performs an archive / src fetch only of the selected ruby.
:: show currently installed rubies, interactive output.
pkg
https://rvm.io/rubies/list/
:: Install a dependency package {readline,iconv,zlib,openssl}
notes
https://rvm.io/packages/
:: Display notes, with operating system specifics.
runs an arbitrary command against specified and/or all rubies
runs 'rake test' across selected ruby versions
runs 'rake spec' across selected ruby versions
Monitor cwd for testing, run `rake {spec,test}` on changes.
export
:: Temporarily set an environment variable in the current shell.
unexport
:: Undo changes made to the environment by 'rvm export'.
requirements :: Shows additional OS specific dependencies/requirements for
building various rubies.
== Implementation
*ruby*
jruby
rbx
ree
::
::
::
::
macruby
maglev
ironruby
system
default
::
::
::
::
::
MRI/YARV Ruby (The Gold Standard) {1.8.6,1.8.7,1.9.1,1.9.2...}
JRuby, Ruby interpreter on the Java Virtual Machine.
Rubinius
Ruby Enterprise Edition, MRI Ruby with several custom
patches for performance, stability, and memory.
MacRuby, insanely fast, can make real apps (Mac OS X Only).
GemStone Ruby, awesome persistent ruby object store.
IronRuby, NOT supported yet. Looking for volunteers to help.
use the system ruby (eg. pre-rvm state)
use rvm set default ruby and system if it hasn't been set.
https://rvm.io/rubies/default/
== Resources:
https://rvm.io/
https://www.pivotaltracker.com/projects/26822
== Contributions:
Any and all contributions offered in any form, past present or future, to the
RVM project are understood to be in complete agreement and acceptance with the
Apache Licence v2.0.
== LICENSE:
Copyright (c) 2009-2011 Wayne E. Seguin
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
1.13. .gitignore
gems/
*.gem
site/.sass-cache/
site/tmp/dependencies/
site/tmp/
tags
.*.swp
tmp/
*.rbc
pkg/
.rvmrc
.DS_Store
.idea
aclocal.m4
autom4te.cache/
config.status
configure
install-sh
Makefile
depcomp
missing
.deps/
README.rdoc
install.sh
config/ssh
db/config.yml
config/database.yml
test/rvm_test_suite/ruby/config/database.yml
test/rvm_test_suite/ruby/db/config.yml
test/rvm_test_suite/ruby/db/*.sqlite
1.14. vboxtest.sh
#! /bin/sh
############################################################################
ssh_config_file=${SSH_CONFIG_FILE:-config/ssh}
local_dir=${LOCAL_DIR:-$(pwd)/test}
remote_dir=${REMOTE_DIR:-\$(pwd)/$(basename "$local_dir")}
remote_script=${REMOTE_SCRIPT:-test_suite.sh}
usage="usage: %s [-F SSH_CONFIG_FILE] [-L LOCAL_DIR] [-R REMOTE_DIR] [-S SCRIPT] [-h] HOSTS...\n"
option="
%s
%s\n"
while getopts "F:G:L:R:S:h" opt
do
case $opt in
F ) ssh_config_file=$OPTARG ;;
L ) local_dir=$OPTARG ;;
R ) remote_dir=$OPTARG ;;
S ) remote_script=$OPTARG ;;
h ) printf "$usage" $0
printf "$option" "-F" "the ssh config file"
printf "$option" "-L" "the local dir"
printf "$option" "-R" "the remote dir"
printf "$option" "-S" "the remote script"
printf "$option" "-h" "prints this help"
exit 0 ;;
\? ) printf "$usage" $0
exit 2 ;;
esac
done
shift $(($OPTIND - 1))
############################################################################
#
# transfer tests
#
for host in "$@"
do
ssh -q -T -F "$ssh_config_file" "$host" -- <<SCRIPT
rm -rf "$remote_dir"
if [ "\$(dirname "$remote_dir")" != "" ]
then
mkdir -p "\$(dirname "$remote_dir")"
fi
SCRIPT
scp -q -r -p -F "$ssh_config_file" "$local_dir" "$host:$remote_dir"
status=$?
if [ $status -ne 0 ]
then
echo "[$status] could not scp tests to host: $host" >&2
exit 1
fi
done
#
# run tests
#
for host in "$@"
do
echo "############## $host ##############"
ssh -q -F "$ssh_config_file" "$host" -- "$remote_dir/$remote_script" </dev/null
status=$?
if [ $status -ne 0 ]
then
echo "[$status] $remote_dir/$remote_script" >&2
exit 1
fi
done
############################################################################
1.15. binscripts
1.15.1. rvm-smile
#!/usr/bin/env bash
printf "%b" "
|
|
.:::.
|
....
:::::
|
,;' .;:
:: ..:
\`:::'
|
::.
..:,:;.,:;.
.
::
.::::.
\`:'
|
'''::,
:: :: :: \`::
:: ;:
.::
:
|
,:'; ::; :: :: ::
::
:: ::,::''.
.
|
\`:,,,,;;' ,;; ,;;, ;;, ,;;, ,;;, \`:,,,,:'
:;:
"
..::''''::..
.;''
\`\`;.
::
:: ::
::
::
:: ::
::
:: .:' :: :: \`:. ::
:: :
: ::
:: \`:.
.:' ::
\`;..\`\`::::''..;'
1.15.2. rvm-shell
#!/usr/bin/env bash
export HOME="${HOME%%+(\/)}" # Remove trailing slashes if they exist on HOME
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
for rvmrc in /etc/rvmrc "$HOME/.rvmrc"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "\nError: $rvmrc is for rvm settings only.\nrvm CLI may NOT be called from within $rvmrc. \nSkipping the
loading of $rvmrc"
return 1
else
source "$rvmrc"
fi
fi
done
fi
export rvm_path
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 )) && [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
elif [[ -d "${HOME}/.rvm" ]]
then rvm_path="${HOME}/.rvm"
elif [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
else echo "Can't find rvm install!" 1>&2 ; exit 1
fi
fi
true ${rvm_scripts_path:="$rvm_path/scripts"}
__rvm_shell_lookup_script()
{
local relative_scripts_dir directory
if [[ -L $0 ]]
then relative_scripts_dir="$(dirname -- "$(dirname -- "$( readlink "$0")" )" )/scripts" #"
else relative_scripts_dir="$(dirname -- "$(dirname -- "$0")")/scripts" #"
fi
for directory in "$rvm_scripts_path" "$HOME/.rvm/scripts" "/usr/local/rvm/scripts" "$relative_scripts_dir"
do
if [[ -d "$directory" && -s "$directory/rvm" ]]
then
echo "$directory/rvm"
return
fi
done
}
case $0 in
(*-rvm-env) selected_shell=${0%-rvm-env} ;;
(*)
selected_shell=bash
;;
esac
selected_shell="$(basename "${selected_shell}")"
if [[ -n "$1" && ! -f "$1" && -n "$(echo "$1" | GREP_OPTIONS="" \grep -v '^-')" ]]
then
rvm_shell_ruby_string="$1"
shift
elif [[ "$1" == "--path" && "$2" =~ /* ]]
then
if [[ -d "$2" ]]
then
cd $2
else
rvm_shell_ruby_string="default"
fi
shift 2
fi
rvm_shell_rvm_path="$(__rvm_shell_lookup_script)"
if [[ -n "$rvm_shell_rvm_path" ]]
then
source "$rvm_shell_rvm_path"
# Setup as expected.
if [[ -n "$rvm_shell_ruby_string" ]]
then
if ! rvm "$rvm_shell_ruby_string"
then
echo "Error: RVM was unable to use '$rvm_shell_ruby_string'" 1>&2
exit 1
fi
else
rvm rvmrc load >/dev/null 2>&1
fi
fi
exec ${selected_shell} "$@"
1.15.3. rvm
#!/usr/bin/env bash
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
declare rvmrc
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
for rvmrc in "${rvm_rvmrc_files[@]}"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "
Error:
$rvmrc is for rvm settings only.
rvm CLI may NOT be called from within $rvmrc.
Skipping the loading of $rvmrc
"
exit 1
else
source "$rvmrc"
fi
fi
done
unset rvm_rvmrc_files
unset rvmrc
fi
export rvm_path
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 )) && [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
elif [[ -d "${HOME}/.rvm" ]]
then rvm_path="${HOME}/.rvm"
elif [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
else echo "Can't find rvm install!" 1>&2 ; exit 1
fi
fi
# allow disabling check temporary
: rvm_is_not_a_shell_function:${rvm_is_not_a_shell_function:=1}
# if to prevent fork-bomb
if source "${rvm_scripts_path:="$rvm_path/scripts"}/rvm"
then
rvm "$@"
else
echo "Error sourcing RVM!" 1>&2
exit 1
fi
1.15.4. rvmsudo
#!/usr/bin/env bash
sudo_args=()
while [[ $# -gt 0 ]] ; do
token="${1}"
#rvm trace flag
case "${token}" in
(--trace)
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
set -o xtrace
;;
\${LINENO} > "
#rvm verbose flag
(--verbose)
set -o verbose
;;
#not an rvm option, treat as sudo option
(-*)
sudo_args+=("$token")
#option with value
case "$token" in
(-g|-u|-p|-r|-t|-U|-C)
shift
#read & append the value
sudo_args+=("$1")
;;
esac
;;
#no more options skip processing
(*)
break
;;
esac
#go to next param
shift
done
if [[ $# -gt 0 ]]
then
eval command sudo \"\${sudo_args[@]}\" /usr/bin/env $(/usr/bin/env | GREP_OPTIONS="" \grep -E
'^rvm|^gemset|^http_|^PATH|^IRBRC|RUBY|GEM' | sed 's/=\(.*\)$/="\1"/' ) \"\$@\"
else
printf "%b" "Usage:\n $0 [--trace] [--verbose] [sudo-options] command [command-options]\n"
fi
1.15.5. rvm-exec
#!/usr/bin/env bash
export HOME="${HOME%%+(\/)}" # Remove trailing slashes if they exist on HOME
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
for rvmrc in /etc/rvmrc "$HOME/.rvmrc"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "\n Error:
$rvmrc is for rvm settings only.
rvm CLI may NOT be called from within $rvmrc.
Skipping the loading of $rvmrc
"
exit 1
else
source "$rvmrc"
fi
fi
done
fi
export rvm_path
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 )) && [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
elif [[ -d "${HOME}/.rvm" ]]
then rvm_path="${HOME}/.rvm"
elif [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
else echo "Can't find rvm install!" 1>&2 ; exit 1
fi
fi
true ${rvm_scripts_path:="$rvm_path/scripts"}
__rvm_shell_lookup_script() {
local relative_scripts_dir
relative_scripts_dir="$(dirname -- "$(dirname -- "$0")")/scripts"
for directory in "$rvm_scripts_path" "$HOME/.rvm/scripts" "/usr/local/rvm/scripts" "$relative_scripts_dir"; do
if [[ -d "$directory" && -s "$directory/rvm" ]]; then
echo "$directory/rvm"
return
fi
done
}
if [[ -n "$1" && ! -f "$1" && -n "$(echo "$1" | GREP_OPTIONS="" \grep -v '^-')" ]]; then
rvm_shell_ruby_string="$1"
shift
fi
rvm_shell_rvm_path="$(__rvm_shell_lookup_script)"
if [[ -n "$rvm_shell_rvm_path" ]]; then
source "$rvm_shell_rvm_path"
# Setup as expected.
if [[ -n "$rvm_shell_ruby_string" ]]; then
rvm "$rvm_shell_ruby_string"
if [[ "$?" -gt 0 ]]; then
echo "Error: RVM was unable to use '$rvm_shell_ruby_string'" 1>&2
exit 1
fi
else
rvm rvmrc load >/dev/null 2>&1
fi
fi
exec "$@"
1.15.6. rvm-prompt
#!/usr/bin/env bash
add()
{
token=${1:-""}
eval "${token}_flag=1" ; shift
if [[ -n "$format" ]] ; then
[[ ${previous_is_format_var:-0} == 1 ]] && eval "${token}_prefix_flag=1"
format="${format}\$${token}"
else
format="\$${token}"
fi
previous_is_format_var=1
return 0
}
add_raw_token()
{
previous_is_format_var=0
token=${1:-""}
format="${format:-""}${token}"
return 0
}
rvm_gemset_separator="${rvm_gemset_separator:-"@"}"
ruby=$( builtin command -v ruby | GREP_OPTIONS="" \grep -v $rvm_path/bin/ruby )
if [[ -n "$ruby" && -n "$(echo "$ruby" | awk '/rvm/{print}')" ]] ; then
unset format
while [[ $# -gt 0 ]] ; do
token="$1" ; shift
case "$token" in
i|interpreter)
add "interpreter"
;;
v|version)
add "version"
;;
p|patchlevel)
add "patchlevel"
;;
r|revision)
add "revision"
;;
a|architecture) add "architecture" ;;
g|gemset)
add "gemset"
;;
u|unicode)
add "unicode"
;;
s|system)
;; #skip when in ruby
-d|--no-default) no_default=1
;;
*) add_raw_token "$token" ;;
esac
done
if [[ -z "${format:-""}" ]] ; then
for default in interpreter version patchlevel gemset ; do
add "$default"
done
fi
ruby_string=$(dirname "$ruby" | xargs dirname | xargs basename)
if [[ -n "$no_default" ]]; then
# Do not display anything if no default flag was provided
#
and we are using the default ruby
# Only people who explicitely ask for this will have the
#
slight performance penalty associated.
if [[ "$(rvm tools identifier)" == "$(rvm alias show default)"
]] ; then
exit 0
fi
fi
strings=(${ruby_string//-/ })
if [[ ${interpreter_flag:-0} -gt 0 || -n "$unicode_flag" ]] ; then
interpreter=${strings[0]}
[[ ${interpreter_prefix_flag:-0} -gt 0 ]] && interpreter="-${interpreter}"
fi
if [[ ${version_flag:-0} -gt 0 || -n "$unicode_flag" ]] ; then
version=${strings[1]}
[[ ${version_prefix_flag:-0} -gt 0 ]] && version="-${version}"
fi
if [[ ${#strings[@]} -gt 2 ]] ; then
if [[ ${patchlevel_flag:-0} -gt 0 ]] ; then
patchlevel=${strings[2]}
[[ ${patchlevel_prefix_flag:-0} -gt 0 ]] && patchlevel="-${patchlevel}"
fi
fi
if [[ ${architecture_flag:-0} -gt 0 ]] ; then
architecture="$(echo "$(ruby -v)" | sed 's/^.*\[//' | sed 's/\].*$//')"
[[ ${architecture_prefix_flag:-0} -gt 0 ]] && architecture="-${architecture}"
fi
if [[ ${gemset_flag:-0} -gt 0 ]] ; then
case "${GEM_HOME:-""}" in
*${rvm_gemset_separator:-"@"}*)
gemset="${rvm_gemset_separator:-"@"}${GEM_HOME/*${rvm_gemset_separator:-"@"}/}"
;;
esac
fi
if [[ ${unicode_flag:-0} -gt 0 ]] ; then
case "$interpreter" in
jruby)
unicode="" ;;
rbx)
unicode="❖" ;;
ree)
unicode="" ;;
macruby)
unicode="" ;;
maglev)
unicode="㎖" ;;
ironruby) unicode="♭" ;;
system)
unicode="" ;;
goruby)
unicode="";;
ruby)
case ${version:-""} in
1.8.6)
unicode="❻"
;;
1.8.7)
unicode="❼"
;;
1.8*)
unicode=""
1.9.1)
unicode="❶"
;;
;;
1.9.2)
unicode="❷"
;;
1.9.3)
unicode="❸"
;;
*)
unicode=""
;;
esac ;;
*) unicode="" ;;
esac
if echo "$ruby_string" | GREP_OPTIONS="" \grep '-head' >/dev/null 2>&1 ; then
unicode="${unicode}"
fi
[[ ${unicode_prefix_flag:-0} -gt 0 ]] && unicode="-${unicode}"
fi
eval "echo \"$format\""
else
while [[ $# -gt 0 ]] ; do
token="$1" ; shift
case "$token" in
s|system) echo "system" ;;
esac
done
fi
exit 0
1.15.7. bundle
#!/usr/bin/env bash
function bundle_not_found()
{
printf "%b" "$(tput setaf 1)ERROR: Gem bundler is not installed, run \`gem install bundler\` first.$(tput sgr0)\n"
exit 127
}
# in rvm warn about missing gem
if [[ -n "${GEM_HOME:-}" ]]
then
bundle_not_found
else
current_bundle="$(dirname $(which $0))"
export PATH
PATH=":${PATH}:"
PATH="${PATH//:${current_bundle}:/:}"
PATH="${PATH#:}"
PATH="${PATH%:}"
if [[ -n "${current_bundle}" ]] && builtin command -v bundle >/dev/null 2>&1
then
builtin command bundle "$@"
else
bundle_not_found
fi
fi
1.15.8. rake
#!/usr/bin/env bash
function rake_not_found()
{
printf "%b" "$(tput setaf 1)ERROR: Gem rake is not installed, run \`gem install rake\` first.$(tput sgr0)\n"
exit 127
}
# in rvm warn about missing gem
if [[ -n "${GEM_HOME:-}" ]]
then
rake_not_found
else
current_rake="$(dirname $(which $0))"
export PATH
PATH=":${PATH}:"
PATH="${PATH//:${current_rake}:/:}"
PATH="${PATH#:}"
PATH="${PATH%:}"
if [[ -n "${current_rake}" ]] && builtin command -v rake >/dev/null 2>&1
then
builtin command rake "$@"
else
rake_not_found
fi
fi
1.15.9. rvm-auto-ruby
#!/usr/bin/env bash
export HOME="${HOME%%+(\/)}" # Remove trailing slashes if they exist on HOME
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
for rvmrc in /etc/rvmrc "$HOME/.rvmrc"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "\nError: $rvmrc is for rvm settings only.\nrvm CLI may NOT be called from within $rvmrc. \nSkipping the
loading of $rvmrc"
return 1
else
source "$rvmrc"
fi
fi
done
fi
export rvm_path
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 )) && [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
elif [[ -d "${HOME}/.rvm" ]]
then rvm_path="${HOME}/.rvm"
elif [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
else echo "Can't find rvm install!" 1>&2 ; exit 1
fi
fi
true ${rvm_scripts_path:="$rvm_path/scripts"}
true ${rvm_environments_path:="$rvm_path/environments"}
if [[ -n "$rvm_path" && -s "$rvm_scripts_path/rvm" ]]; then
source "$rvm_scripts_path/rvm" > /dev/null 2>&1
elif [[ -s "$HOME/.rvm/scripts/rvm" ]]; then
source "$HOME/.rvm/scripts/rvm" > /dev/null 2>&1
elif [[ -s "/usr/local/rvm/scripts/rvm" ]]; then
source "/usr/local/rvm/scripts/rvm" > /dev/null 2>&1
else
echo "Unable to detect rvm, please manually set the rvm_path env variable." >&2
exit 1
fi
[[ -s "$rvm_environments_path/default" ]] && source "$rvm_environments_path/default"
rvm_promptless=1 rvm rvmrc load > /dev/null 2>&1
exec ruby "$@"
1.15.10. rvm-installer
#!/usr/bin/env bash
# echo "65536 * 3 + 256 * 2 + 25" | bc
if [[ -n "${BASH_VERSION:-}" ]] &&
(( 65536 * ${BASH_VERSINFO[0]} + 256 * ${BASH_VERSINFO[1]} + ${BASH_VERSINFO[2]} < 197145 ))
then
echo "BASH 3.2.25 required (you have $BASH_VERSION)"
exit 1
fi
shopt -s extglob
PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
export PS4
set -o errtrace
set -o errexit
log()
{ printf "%b\n" "$*" ; return $? ;
\${LINENO} > "
}
fail() { log "\nERROR: $*\n" ; exit 1 ; }
if [[ -z "${rvm_tar_command:-}" ]] && builtin command -v gtar >/dev/null
then
rvm_tar_command=gtar
else
rvm_tar_command=tar
fi
if [[ ! " ${rvm_tar_options:-} " =~ " --no-same-owner " ]] && \
$rvm_tar_command --help | GREP_OPTIONS="" \grep -- --no-same-owner >/dev/null
then
rvm_tar_options="${rvm_tar_options:-} --no-same-owner"
rvm_tar_options="${rvm_tar_options## }"
fi
usage()
{
printf "%b" "
Usage
rvm-installer [options] [action]
Options
[[--]version] <latest|latest-x|latest-x.y|x.y.z> - Install RVM version
[--]branch
<name> - Install RVM head, from named branch
--trace
- used to debug the installer script
Actions
master - Install RVM master branch from wayneeseguin rvm repo (Default).
stable - Install RVM stable branch from wayneeseguin rvm repo.
help
- Display CLI help (this output)
Branches:
branch
branch
branch
branch
<branch>
/<branch>
<repo>/
<repo>/<branch>
Defaults:
branch: master
repo:
wayneeseguin
"
}
#Searches for highest available version for the given pattern
# fetch_version 1.10. -> 1.10.3
# fetch_version 1. -> 1.11.0
# fetch_version "" -> 2.0.1
fetch_version()
{
curl -s https://api.github.com/repos/wayneeseguin/rvm/tags |
sed -n '/"name": / {s/^.*".*": "\(.*\)".*$/\1/; p;}' |
sort -t. -k 1,1n -k 2,2n -k 3,3n -k 4,4n -k 5,5n |
GREP_OPTIONS="" \grep "^${1:-}" | tail -n 1
}
install_release()
{
typeset _version
_version=$1
log "Downloading RVM version ${_version}"
get_and_unpack \
https://github.com/wayneeseguin/rvm/tarball/${_version} \
rvm-${_version}.tar.gz \
wayneeseguin-rvm}
install_head()
{
typeset _repo _branch
case "$1" in
(/*)
_repo=wayneeseguin
_branch=${1#/}
;;
(*/)
_repo=${1%/}
_branch=master
;;
(*/*)
_repo=${1%/*}
_branch=${1#*/}
;;
(*)
_repo=wayneeseguin
_branch=$1
;;
esac
log "Downloading RVM from ${_repo} branch ${_branch}"
get_and_unpack \
https://github.com/${_repo}/rvm/tarball/${_branch} \
${_repo}-rvm-${_branch}.tgz \
${_repo}-rvm}
get_and_unpack()
{
typeset _url _file _patern
_url=$1
_file=$2
_patern=$3
if curl -L ${_url} -o ${rvm_archives_path}/${_file}
then
true
else
typeset ret=$?
case $ret in
(60)
log "
Could not download '${_url}'.
Make sure your certificates are up to date as described above.
To continue in insecure mode run 'echo insecure >> ~/.curlrc'.
"
return 60
;;
(*)
log "
Could not download '${_url}'.
curl returned status '$ret'.
"
return 1
;;
esac
fi
[[ -d "${rvm_src_path}/rvm" ]] || \mkdir -p "${rvm_src_path}/rvm"
if ! builtin cd "${rvm_src_path}/rvm"
then
log "Could not change directory '${rvm_src_path}/rvm'."
return 2
fi
rm -rf ${rvm_src_path}/rvm/*
if ! $rvm_tar_command xzf ${rvm_archives_path}/${_file} ${rvm_tar_options:-}
then
log "Could not extract RVM sources."
return 3
fi
if ! mv ${_patern}*/* .
then
log "Could not move RVM sources path."
return 4
fi
rm -rf ${_patern}*
}
# Tracing, if asked for.
if [[ "$*" =~ --trace ]] || (( ${rvm_trace_flag:-0} > 0 ))
then
set -o xtrace
export rvm_trace_flag=1
fi
# Variable initialization, remove trailing slashes if they exist on HOME
true \
${rvm_trace_flag:=0} ${rvm_debug_flag:=0} ${rvm_user_install_flag:=0}\
${rvm_ignore_rvmrc:=0} HOME="${HOME%%+(\/)}"
if (( rvm_ignore_rvmrc == 0 ))
then
for rvmrc in /etc/rvmrc "$HOME/.rvmrc"
do
if [[ -s "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "
Error: $rvmrc is for rvm settings only.
rvm CLI may NOT be called from within $rvmrc.
Skipping the loading of $rvmrc
"
return 1
else
source "$rvmrc"
fi
fi
done
fi
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 ))
then
rvm_path="/usr/local/rvm"
else
rvm_path="${HOME}/.rvm"
fi
fi
export HOME rvm_path
install_rubies=()
install_gems=()
# Parse CLI arguments.
while (( $# > 0 ))
do
token="$1"
shift
case "$token" in
--trace)
set -o xtrace
export rvm_trace_flag=1
;;
--path)
if [[ -n "${1:-}" ]]
then
rvm_path="$1"
shift
else
fail "--path must be followed by a path."
fi
;;
--branch|branch) # Install RVM from a given branch
if [[ -n "${1:-}" ]]
then
version="head"
branch="$1"
shift
else
fail "--branch must be followed by a branchname."
fi
;;
--user-install|--auto)
token=${token#--}
token=${token//-/_}
export "rvm_${token}_flag"=1
printf "%b" "Turning on ${token/_/ } mode.\n"
;;
--without-gems=*)
export rvm_without_gems="${token#--without-gems=}"
printf "%b" "Installing RVM without gems: ${rvm_without_gems}.\n"
;;
--version|version)
version="$1"
shift
;;
head)
version="head"
branch="master"
;;
stable|master)
version="head"
branch="$token"
;;
latest|latest-*|+([[:digit:]]).+([[:digit:]]).+([[:digit:]]))
version="$token"
;;
--ruby)
install_rubies+=( ruby )
;;
--ruby=*)
token=${token#--ruby=}
install_rubies+=( ${token//,/ } )
;;
--rails)
install_gems+=( rails )
;;
--gems=*)
token=${token#--gems=}
install_gems+=( ${token//,/ } )
;;
help|usage)
usage
exit 0
;;
*)
usage
exit 1
;;
esac
done
case "$rvm_path" in
*[[:space:]]*)
printf "%b" "
It looks you are one of the happy *space* users(in home dir name),
RVM is not yet fully ready for it, use this trick to fix it:
sudo ln -s \"$HOME/.rvm/\" /$USER.rvm
echo \"export rvm_path=/$USER.rvm\" >> \"$HOME/.rvmrc\"
and start installing again.
"
exit 2
;;
esac
if (( ${#install_gems[@]} > 0 && ${#install_rubies[@]} == 0 ))
then
install_rubies=( ruby )
fi
if (( ${#install_rubies[@]} > 0 ))
then
echo "Please read and follow further instructions."
echo "Press ENTER to continue."
builtin read -n 1 -s -r anykey
fi
true "${version:=head}"
if [[ "$rvm_path" != /* ]]
then
fail "The rvm install path must be fully qualified. Tried $rvm_path"
fi
rvm_src_path="$rvm_path/src"
rvm_archives_path="$rvm_path/archives"
rvm_releases_url="https://rvm.io/releases"
for dir in "$rvm_src_path" "$rvm_archives_path"
do
if [[ ! -d "$dir" ]]
then
mkdir -p "$dir"
fi
done
# Perform the actual installation, first we obtain the source using whichever
# means was specified, if any. Defaults to head.
case "${version}" in
(head)
echo "${branch}" > "$rvm_path/RELEASE"
install_head ${branch:-master} || exit $?
;;
(latest)
echo "${version}" > "$rvm_path/RELEASE"
install_release $(fetch_version "") || exit $?
;;
(latest-*)
echo "${version}" > "$rvm_path/RELEASE"
install_release $(fetch_version "${version#latest-}") || exit $?
;;
(+([[:digit:]]).+([[:digit:]]).+([[:digit:]])) # x.y.z
echo "version" > "$rvm_path/RELEASE"
install_release ${version} || exit $?
;;
(*)
fail "Something went wrong, unrecognized version '$version'"
;;
esac
# required flag - path to install
flags=( --path "$rvm_path" )
if (( rvm_trace_flag == 1 ))
then flags+=("--trace")
fi
if (( rvm_debug_flag == 1 ))
then flags+=("--debug")
fi
if (( rvm_auto_flag == 1 ))
then flags+=("--auto")
fi
if [[ -n "${rvm_without_gems:-}" ]]
then flags+=("--without-gems=${rvm_without_gems}")
fi
chmod +x ./scripts/install
./scripts/install "${flags[@]}"
(
source ${rvm_scripts_path:-${rvm_path}/scripts}/rvm
source ${rvm_scripts_path:-${rvm_path}/scripts}/version
__rvm_version
if (( ${#install_rubies[@]} > 0 ))
then
{
echo "Ruby (and needed base gems) for your selection will be installed shortly."
echo "Before it happens, please read and execute the instructions below."
echo "Please use a separate terminal to execute any additional commands."
echo "Press 'q' to continue."
} | less
fi
for _ruby in ${install_rubies[@]}
do
command rvm install ${_ruby} -j 2
done
for _ruby in ${install_rubies[@]}
do
# set the first one as default, skip rest
rvm alias create default ${_ruby}
break
done
for _gem in ${install_gems[@]}
do
rvm all do gem install ${_gem}
done
if (( ${#install_rubies[@]} > 0 ))
then
printf "%b" "
* To start using RVM you need to run \`source $rvm_path/scripts/rvm\`
in all your open shell windows, in rare cases you need to reopen all shell windows.
"
fi
if [[ "${install_gems[*]}" =~ "rails" ]]
then
printf "%b" "
* To start using rails you need to run \`rails new <project_dir>\`.
"
fi
)
1.16. docs
1.16.1. vm_setup.md
Setting up a VM
-----------------------The only real requirement to allow testing of RVM on a VM is that the VM be
reachable by ssh. If you choose to run your VMs on [VirtualBox] and take care
with a few snapshots then you can use some extra rake commands that expedite
testing. Specifically you can reset+start and stop the VMs using:
rake vbox:start
rake vbox:stop
As an example, build a [Ubuntu] VM on [VirtualBox] using the following:
-
name: ubuntu
Linux/Ubuntu
512 MB memory
8 GB dynamically resizing drive
Add the iso to the cd/dvd device under Settings > Storage. Now start the
server and install ubuntu (use default settings unless specified):
- user/password: vboxtest
- select 'OpenSSH server' in packages to install
When the server has rebooted
install iso, take a snapshot
convenience. Port forwarding
and have that be received by
and is ready at the login screen, remove the
and setup port forwarding. The snapshot is for
allows you to ssh to yourself on one port (2220)
the VM on another port (22).
(Devices > CD/DVD Devices > Remove disk from virtual drive)
VBoxManage snapshot ubuntu take RAW
VBoxManage controlvm ubuntu poweroff
# wait to fully power off
VBoxManage modifyvm ubuntu --natpf1 'ubuntu-ssh,tcp,,2220,,22'
VBoxManage -q snapshot ubuntu restore RAW
VBoxManage startvm ubuntu
Transfer your ssh key to the vm. Help to generate ssh keys can be found on
[GitHub](http://help.github.com/key-setup-redirect):
scp -P 2220 -o UserKnownHostsFile=/dev/null ~/.ssh/id_rsa.pub vboxtest@localhost:id_rsa.pub
Setup SSH for your user:
vm:
vm:
vm:
vm:
mkdir .ssh
mv id_rsa.pub .ssh/authorized_keys
chmod 0700 .ssh
chmod 0600 .ssh/authorized_keys
Remove the login banner (cleans up test output) and exit.
vm: sudo rm /etc/motd
vm: exit
Now take some standard snapshots. By taking them at the login screen you can
reset to a running VM, which avoids startup overhead.
VBoxManage snapshot ubuntu take BASE
VBoxManage snapshot ubuntu take CURRENT
VBoxManage controlvm ubuntu poweroff
To cleanup the port forwarding (run later, if ever):
VBoxManage modifyvm ubuntu --natpf1 delete 'ubuntu-ssh'
Now add configs for this VM to config/ssh:
Host ubuntu
HostName localhost
Port 2220
User vboxtest
Note that the Host, Port, and User should match up to the values you used
during the VM setup. To add additional VMs, for instance to test on different
operating systems, choose another name/port and repeat.
[VirtualBox]: http://www.virtualbox.org/
[Ubuntu]: http://www.ubuntu.com/
1.16.2. vm_tests.md
VM Tests
=============================================================================
RVM lives in the shell and so is tested in a shell. To make things easier, RVM
has the ability to test on one or more virtual machines. The setup only
requires that VMs be reachable by ssh, however you get a few helper tasks if
you run your VMs using [VirtualBox].
See below for an overview of the VM test architecture.
Running Locally
-----------------------To run locally (generally not recommended due to possible side effects):
./vboxtest/test_suite.sh
Or, equivalently:
rake vbox:local_test
To add another test suite, make a script in the test directory that ends with
`_test.sh` and ensure it is executable. Then follow this pattern:
#!/bin/sh
########################################################################
TEST_CASE=$(basename "$0")
########################################################################
. ${0%/$TEST_CASE}/../test_helper.sh
test_echo_echos_a_string_to_stdout () {
# The assert_equal method will check that the echo command exits
# with status 0, and that the stdout is 'hello world'.
#
# There are similar assertions to just check the exit status
# or just check stdout.
assert_equal 0 "$(
echo 'hello world'
)" $LINENO <<stdout
hello world
stdout
# Write as many assertions as you please in a given method.
}
run_test_case "$0"
You can write as many test methods as you like... just follow the same
conventions as in Test::Unit (ie start the method with `test_`). See the tests
for more examples.
Running on VMs
-----------------------First set up some virtual machines by following the instructions in
doc/vm_setup. Now to run the tests:
# starts each of the VMs
rake vbox:start
# copies the test scripts to each vm and runs the test suite on each
rake vbox:remote_test
# stops each of the VMs
rake vbox:stop
Or you can run the whole shebang with:
rake vbox:test
If you aren't running your VMs on VirtualBox and as set up in the docs, then the start/stop commands won't work.
can use the `vbox:remote_test` task, you just need to manage your VMs manually.
Overview of VM Test Architecture
==============================================================================
For those interested in the details...
The basic plan is to copy scripts to a VM and then execute one of them to run
the test suite.
The vboxtest.sh script does just that - it makes a directory on each VM,
copies scripts to it, then remotely executes the test runner, all via ssh. As
it does so, output is sent back to your terminal.
The trick is to use ssh with a config file. The config file allows you to
specify the options used by ssh in one place and access them by host name.
That way you can provide a simple list of hosts to vboxtest.sh rather than a
varied and complex set of connection information. As a convenience the
You still
`vbox:remote_test` task runs vboxtest.sh with all hosts in config/ssh.
The beauty of this setup is that it can go anywhere ssh can go to... at the
level of vboxtest.sh, it's pure ssh... and it can do so with a standard ssh
config file.
VirtualBox
-----------------------You don't have to use VirtualBox, but if you do then you can work a few more tricks.
Specifically you can name your VirtualBox VMs the same as each host. So make a VirtualBox VM named 'ubuntu' and add a host
named 'ubuntu', a VM named 'debian' and a host named 'debian'. Then you setup port forwarding so that you can ssh to
localhost:2220 and that goes to ubuntu:22 and localhost:2221 to debian:22.
If you've been consistent about your setup you can reuse a lot of the ssh options giving you a tidy, scalable config file
like this:
Host ubuntu
Port 2220
Host debian
Port 2221
# Defaults used by all hosts
Host *
HostName localhost
User vboxtest
Since your VirtualBox VMs are named the same as the hosts, you can pull them
out and have rake start/stop the VMs for you using the VBoxManage command
(which comes with VirtualBox).
The SSH Config File
-----------------------A couple ssh options can be used to expedite testing:
# loosen up the ssh checks so you just go without being 100% secure
# (good for a test environment)
UserKnownHostsFile /dev/null
StrictHostKeyChecking no
IdentitiesOnly yes
# setup a master socket so that the full ssh exchange doesn't have
# to happen every time you connect (which is 3 times per-host).
ControlMaster auto
ControlPath /tmp/socket-%r@%h:%p
The master socket drastically reduces overhead. Note that the master socket is
cleaned up automatically when the VM is shut down.
[VirtualBox]: http://www.virtualbox.org/
1.16.3. rebuild.sh
#!/usr/bin/env bash
#
# Generating rvm self documents
#
# uncomment for debugging
#set -x
# checking system requirements
[[ `which asciidoc 2> /dev/null` ]] || (echo "'asciidoc' is not installed on your system, exiting..."; exit 1)
[[ `which docbook2man 2> /dev/null` ]] || (echo "'docbook2x' is not installed on your system, exiting..."; exit 1)
DIRNAME=$(dirname $0)
rvm_base_dir=$(cd $DIRNAME/../; pwd)
rvm_docs_src_dir=${rvm_base_dir}/docs
rvm_tmp_dir=${rvm_base_dir}/tmp
rvm_docs_target_man_dir=${rvm_base_dir}/man
\mkdir -p ${rvm_tmp_dir}
\mkdir -p ${rvm_docs_target_man_dir}
echo "Starting doc generation run through."
# processing manpages
find ${rvm_docs_src_dir} -type f -name *.txt | while read rvm_manpage_file; do
#
#
#
#
#
#
trying to detect manpage name automatically
(just for fun, I don't think, that rvm will ever have more than one manpage :)
The name of the generated manpage is initially specified within the source file in asciidoc format,
so we'll do some simple parsing
We assume, that it will be specified at one of the 3 (three) first lines
of the source file.
# it should be something like 'RVM(1)'
rvm_manpage_name_full="$(head -n 3 < "$rvm_manpage_file" | \grep -o '^[^(]*[(][^)]*[)]$')"
if [[ -z "${rvm_manpage_name_full}" ]]; then
echo "Unable to detect manpage name, stopping build process..." 1>&2
exit 1
fi
# we need smth like 'rvm.1'
rvm_manpage_name="$(echo "$rvm_manpage_name_full" | sed "s|(|.|;s|)||" | tr '[[:upper:]]' '[[:lower:]]')"
# we need '1'
rvm_manpage_name_part=$(echo "$rvm_manpage_name" | cut -d '.' -f 2)
# So, the manpage directory will be the following:
rvm_manpage_dir="$rvm_docs_target_man_dir/man$rvm_manpage_name_part"
mkdir -p "$rvm_manpage_dir"
echo "Generating manpage format from source file for $rvm_manpage_name"
a2x -d manpage -f manpage -D "$rvm_manpage_dir" "$rvm_manpage_file" > /dev/null 2>&1
if [[ "$?" -gt 0 ]]; then
echo "Unable to generate manpage for $rvm_manpage_name_full"
else
\rm -f "$( echo "$rvm_manpage_file" | sed 's/.txt$/.xml/')"
# compression is optional, but gzip check added for neatness
if command -v gzip >/dev/null 2>&1; then
echo "gzip compressing the manpage"
gzip < "$rvm_manpage_dir/$rvm_manpage_name" > "$rvm_manpage_dir/$rvm_manpage_name.gz"
fi
fi
done
# vim: ft=sh
1.16.4. rvm.txt
RVM(1)
======
NAME
---rvm - The Ruby Version Manager
SYNOPSIS
-------*rvm* ['FLAGS'] ['OPTIONS'] 'ACTION' ['IMPLEMENTATION'[,'IMPLEMENTATION'[,'...']]
DESCRIPTION
----------RVM is a command line tool which allows us to easily install, manage and work
with multiple ruby environments from interpreters to sets of gems.
FLAGS
----*--head*::
with update, updates rvm to git head version.
*--rubygems*::
with update, updates rubygems for selected ruby
*--default*::
with ruby select, sets a default ruby for new shells.
*--debug*::
Toggle debug mode on for very verbose output.
*--trace*::
Toggle trace mode on to see EVERYTHING rvm is doing.
*--force*::
Force install, removes old install & source before install.
*--summary*::
Used with rubydo to print out a summary of the commands run.
*--latest*::
with gemset --dump skips version strings for latest gem.
*--gems*::
with uninstall/remove removes gems with the interpreter.
*--docs*::
with install, attempt to generate ri after installation.
*--reconfigure*::
Force ./configure on install even if Makefile already exists.
OPTIONS
------*-v, --version*::
Emit rvm version loaded for current shell.
*-l, --level*::
patch level to use with rvm use / install
*--bin*::
path for binaries to be placed ('~/.rvm/bin/')
*--source*::
src directory to use ('~/.rvm/src/')
*--archives*::
directory for downladed files ('~/.rvm/archives/')
*-S*::
Specify a script file to attempt to load and run (rubydo).
*-e*::
Execute code from the command line.
*-G*::
root gem path to use
*--gems*::
Used to set the 'gems_flag', use with 'remove' to remove gems.
*--archive*::
Used to set the 'archive_flag', use with 'remove' to remove archive.
*--patch*, *--patches*::
With any ruby build from source, allows you to specify patch paths
and patch names to be applied prior to building. Values should
be a relative / absolute path to a patch or the name of known
patch / patchset. Optionally, paths or names may be followed by
'%someinteger' - e.g. '--patches mypatch%2' - where the number
following the % specifies the value of the -p argument to patch,
defaulting to two.
*-C, --configure*::
custom configure options. If you need to pass several configure
options then append them comma separated: '-C --...,--...,--...'.
*--nice*::
process niceness (for slow computers, default 0)
*--ree-options*::
Options passed directly to ree's './installer' on the command line.
ACTIONS
------*usage*::
Show this usage information.
*version*::
Show the rvm version installed in rvm_path.
*use*::
Setup current shell to use a specific ruby version.
*reload*::
Reload rvm source itself (useful after changing rvm source).
*env*::
Displays information about an environment specified but the
given ruby string. Useful for getting a sourceable path or an
evaluatable set of shell variable declarations.
*implode*::
(seppuku) removes the rvm installation completely.
This means everything in $rvm_path ('~/.rvm').
This does not touch your profiles. However, this means that
you must manually clean up your profiles and remove the lines
which source RVM.
*update*::
Upgrades rvm to the latest version.
(If you experience bugs try this first with --head).
*reset*::
Remove current and stored default & system settings.
(If you experience odd behavior try this second).
*info*::
Show the *current* environment information for current ruby.
*debug*::
Show info plus additional information for common issues.
*install*::
Install one or many ruby versions.
https://rvm.io/rubies/installing/
*uninstall*::
Uninstall one or many ruby versions, leaves their sources.
*remove*::
Uninstall one or many ruby versions and remove their sources.
*wrapper*::
Generates a set of wrapper executables for a given ruby with the
specified ruby and gemset combination. Used under the hood for
passenger support and the like.
*do \**::
Runs the specified command against specified and/or all rubies.
*tests*::
Runs 'rake test' across selected ruby versions.
*specs*::
Runs 'rake spec' across selected ruby versions.
*monitor*::
Monitor cwd for testing, run 'rake {spec,test}' on changes.
*gemset*::
gemsets: https://rvm.io/gemsets/
*gemdir*::
Display the path to the current gem directory ('$GEM_HOME').
*srcdir*::
Display the path to rvm source directory (may be yanked).
*fetch*::
Performs an archive / src fetch only of the selected ruby.
*list*::
Show currently installed rubies, interactive output.
https://rvm.io/rubies/list/
*pkg*::
Install a dependency package {readline,iconv,zlib,openssl}.
https://rvm.io/packages/
*notes*::
Display notes, with operating system specifics.
*export*::
Temporarily set an environment variable in the current shell.
*unexport*::
Undo changes made to the environment by 'rvm export'.
*requirements*::
Show additional OS specific dependencies/requirements for building various rubies.
IMPLEMENTATION
-------------*ruby*::
MRI/YARV Ruby (The Gold Standard) {1.8.6,1.8.7,1.9.1,1.9.2...}
*jruby*::
JRuby, Ruby interpreter on the Java Virtual Machine.
*rbx*::
Rubinius
*ree*::
Ruby Enterprise Edition, MRI Ruby with several custom
patches for performance, stability, and memory.
*macruby*::
MacRuby, insanely fast, can make real apps (Mac OS X Only).
*maglev*::
GemStone Ruby, awesome persistent ruby object store.
*ironruby*::
IronRuby, NOT supported yet. Looking for volunteers to help.
*system*::
Use the system ruby (eg. pre-rvm state).
*default*::
Use rvm set default ruby and system if it hasn't been set.
https://rvm.io/rubies/default/
RESOURCES
--------https://rvm.io/[Main web site]
https://www.pivotaltracker.com/projects/26822[Online issue-tracker]
COPYING
------Copyright (c) 2009 Wayne E. Seguin
See LICENCE file for details.
////
# vim:ft=asciidoc
////
1.17. lib
1.17.1. rvm.rb
# == Ruby Version Manager - Ruby API
raise "RVM - Ruby integration was extracted to a separate gem, \
it should be installed by default with RVM, \
remove the `$LOAD_PATH.unshift` line and all should be fine again."
1.17.2. rvm
1.17.2.1. capistrano.rb
# Recipes for using RVM on a server with capistrano.
raise "RVM - Capistrano integration was extracted to a separate gem, \
install: `gem install rvm-capistrano` and remove the `$LOAD_PATH.unshift` line, \
note also the 'set :rvm_type, :user' is now the default (instead of :system)."
1.18. scripts
1.18.1. color
#!/usr/bin/env bash
#
#
#
#
#
#
set colors, separate multiple selections with coma, order is not important
using bold in one definition requires resetting it in others with offbold
using background in one color requires resetting it in others with bdefault
example:
rvm_error_color=bold,red
rvm_notify_color=offbold,green
case "${TERM:-dumb}" in
(dumb|unknown) exit 0 ;;
esac
builtin command -v tput >/dev/null && tput sgr0 >/dev/null || exit 0
for color in ${1//,/ }
do
case "${color:-}" in
# regular colors
black)
tput setaf
;;
red)
tput setaf
;;
green)
tput setaf
;;
yellow)
tput setaf
;;
blue)
tput setaf
;;
magenta) tput setaf
;;
cyan)
tput setaf
;;
white)
tput setaf
;;
0
1
2
3
4
5
6
7
# emphasized (bolded) colors
bold)
tput smso
;;
offbold) tput rmso
;;
# background colors
bblack)
tput setab
;;
bred)
tput setab
;;
bgreen)
tput setab
;;
byellow) tput setab
;;
bblue)
tput setab
;;
bmagenta) tput setab
;;
bcyan)
tput setab
;;
bwhite)
tput setab
;;
0
1
2
3
4
5
6
7
# Defaults
default) tput setaf 9
;;
bdefault) tput setab 9
;;
# Reset
*)
tput sgr0
;;
esac
done
1.18.2. package
#/usr/bin/env bash
1.18.3. hook
#!/usr/bin/env bash
# silence ZSH redefinitions
typeset rvm_verbose_flag rvm_debug_flag hooks >/dev/null 2>/dev/null
true ${rvm_verbose_flag:=0} ${rvm_debug_flag:=0} "${rvm_hook:=}"
if [[ -n "$rvm_hook" ]]
then
if [[ "$PWD/.rvm/hooks/$rvm_hook" == "$rvm_hooks_path/$rvm_hook" ]]
then
hooks=( "$rvm_hooks_path/$rvm_hook")
else
hooks=("$PWD/.rvm/hooks/$rvm_hook" "$rvm_hooks_path/$rvm_hook")
fi
for hook in "${hooks[@]}"
do
if [[ -s "$hook" ]]
then
if (( rvm_verbose_flag > 0 )) || (( rvm_debug_flag > 0 ))
then
rvm_log "Running $hook"
fi
source "$hook"
else
continue
fi
done
fi
unset rvm_hook hooks
1.18.4. extract
#/usr/bin/env bash
1.18.5. monitor
#!/usr/bin/env bash
original_ruby_strings=$rvm_ruby_strings
original_ruby_string=$rvm_ruby_string
source "$rvm_scripts_path/base"
rvm_monitor_sleep="${rvm_monitor_sleep:-2}"
timestamp()
{
if [[ "Darwin" == "$(uname)" ]] ; then
echo $(stat -f "%m" $1)
else
echo $(stat -c "%Y" $1)
fi
}
push_if_timestamp_changed()
{
typeset file file_timestamp time
file=$1
file_timestamp=$(timestamp "$file")
eval "time=\$${framework}_timestamp"
if [[ "$file_timestamp" -gt $time ]]
then
array_push "changed_${framework}_files" $file
fi
}
update_timestamp()
{
if [[ -d "${1}/" ]]
then
\touch "$rvm_path/${$}_${1}_timestamp"
eval "${1}_timestamp=\$(timestamp \"$rvm_path/${$}_${1}_timestamp\")"
fi
}
rvm_warn "rvm monitor is deprecated, take a look on autotest, guard, watchr or ruby-inotify"
update_timestamp "test"
update_timestamp "spec"
while : ; do
changed_test_files=() ; changed_spec_files=() ; changed_code_files=()
for file in lib/**/*.rb lib/*.rb app/**/*.rb app/*.rb ; do
if [[ -f "$file" ]] ; then push_if_timestamp_changed $file "code" ; fi
done
for framework in test spec ; do
if [[ -d "$framework/" ]] ; then
for file in ${framework}/**/*_${framework}.rb ${framework}/*_${framework}.rb ; do
if [[ -f "$file" ]] ; then
push_if_timestamp_changed $file $framework
fi
done
if [[ "$(array_length "changed_${framework}_files")" -gt 0 ]] ; then
rvm_ruby_strings=$original_ruby_strings
rvm_ruby_string=$original_ruby_string
if [[ "spec" == "$framework" ]] ; then
rvm_action="spec"
rvm_ruby_args="spec/spec_helper.rb ${changed_spec_files[*]}"
"$rvm_scripts_path/set" $rvm_action $rvm_ruby_args
elif [[ "test" == "$framework" ]] ; then
rvm_action="ruby"
rvm_ruby_args=" -r$(echo "${changed_test_files[*]}" | sed 's/ / -r/g') test/test_helper.rb"
"$rvm_scripts_path/set" $rvm_action $rvm_ruby_args
fi
update=1
fi
if [[ "$(array_length "changed_code_files")" -gt 0 ]] ; then
rvm_ruby_strings=$original_ruby_strings
rvm_ruby_string=$original_ruby_string
if [[ "spec" == "$framework" ]] ; then
rvm_action="spec"
rvm_ruby_args="spec/"
"$rvm_scripts_path/set" $rvm_action $rvm_ruby_args
elif [[ "test" == "$framework" ]] ; then
rvm_action="rake"
rvm_ruby_args="test"
"$rvm_scripts_path/set" "$rvm_action" $rvm_ruby_args
fi
update=1
fi
fi
if [[ "$update" -eq 1 ]] ; then
update_timestamp $framework
fi
done
unset update changed_test_files changed_spec_files
sleep $rvm_monitor_sleep
done
1.18.6. selector
#!/usr/bin/env bash
# __rvm_select implementation version patch_level
__rvm_select()
{
true ${rvm_gemset_name:=}
typeset _original_env_string
_original_env_string=${rvm_env_string}
# Set Variable Defaults
export GEM_HOME GEM_PATH MY_RUBY_HOME RUBY_VERSION IRBRC
export rvm_env_string rvm_action rvm_alias_expanded rvm_archive_extension rvm_bin_flag rvm_bin_path rvm_configure_flags
rvm_debug_flag rvm_default_flag rvm_delete_flag rvm_docs_type rvm_dump_environment_flag rvm_error_message
rvm_expanding_aliases rvm_file_name rvm_gemdir_flag rvm_gemset_name rvm_gemstone_package_file rvm_gemstone_url rvm_head_flag
rvm_hook rvm_install_args rvm_install_on_use_flag rvm_llvm_flag rvm_loaded_flag rvm_make_flags rvm_niceness rvm_nightly_flag
rvm_only_path_flag rvm_parse_break rvm_patch_names rvm_patch_original_pwd rvm_pretty_print_flag rvm_proxy rvm_quiet_flag
rvm_ree_options rvm_reload_flag rvm_remove_flag rvm_ruby_alias rvm_ruby_aliases rvm_ruby_args rvm_ruby_binary rvm_ruby_bits
rvm_ruby_configure rvm_ruby_file rvm_ruby_gem_home rvm_ruby_gem_path rvm_ruby_global_gems_path rvm_ruby_home
rvm_ruby_interpreter rvm_ruby_irbrc rvm_ruby_load_path rvm_ruby_major_version rvm_ruby_make rvm_ruby_make_install
rvm_ruby_minor_version rvm_ruby_mode rvm_ruby_name rvm_ruby_package_file rvm_ruby_package_name rvm_ruby_patch
rvm_ruby_patch_level rvm_ruby_release_version rvm_ruby_repo_url rvm_ruby_require rvm_ruby_revision rvm_ruby_selected_flag
rvm_ruby_sha rvm_ruby_string rvm_ruby_strings rvm_ruby_tag rvm_ruby_url rvm_ruby_user_tag rvm_ruby_version rvm_script_name
rvm_sdk rvm_silent_flag rvm_sticky_flag rvm_system_flag rvm_token rvm_trace_flag rvm_use_flag rvm_user_flag rvm_verbose_flag
rvm_wrapper_name rvm_architectures
if [[ -z "${rvm_ruby_string:-}" ]]
then # First we build rvm_ruby_string from components if it is empty.
if [[ -n "${rvm_ruby_interpreter:-}" ]]
then
rvm_ruby_string="$rvm_ruby_interpreter"
fi
if [[ -n "${rvm_ruby_version:-}" ]]
then
rvm_ruby_string="$rvm_ruby_string-$rvm_ruby_version"
fi
if [[ -n "${rvm_ruby_patch_level:-}" ]]
then
rvm_ruby_string="$rvm_ruby_string-$rvm_ruby_patch_level"
fi
if [[ -n "${rvm_ruby_revision:-}" ]]
then
rvm_ruby_string="$rvm_ruby_string-$rvm_ruby_revision"
fi
if [[ -n "${rvm_ruby_name:-}" ]]
then
rvm_ruby_name="$rvm_ruby_string-$rvm_ruby_name"
fi
fi
__rvm_ruby_string || return $?
rvm_archive_extension="tar.gz"
if [[ -z "${rvm_ruby_interpreter:-}" ]]
then
rvm_ruby_interpreter="${rvm_ruby_string//-*/}"
fi
case "${rvm_ruby_interpreter:-missing}" in
missing)
return 2
;;
macruby)
if [[ "Darwin" == "$(uname)" ]]
then
rvm_ruby_package_name="${rvm_ruby_interpreter}-${rvm_ruby_version}"
if (( ${rvm_head_flag:=0} == 1 ))
then
rvm_ruby_version="" ; rvm_ruby_tag=""
rvm_ruby_revision="head"
__rvm_db "macruby_repo_url" "rvm_ruby_repo_url"
rvm_ruby_url="$rvm_ruby_repo_url"
elif [[ "nightly" == "${rvm_ruby_version:-}" ]]
then
__rvm_db "macruby_nightly_url" "rvm_ruby_url"
rvm_ruby_package_name="${rvm_ruby_interpreter}_nightly-${rvm_ruby_version}"
rvm_ruby_package_file="$rvm_ruby_package_name"
elif [[ -n "${rvm_ruby_version:-}" ]]
then
__rvm_db "macruby_${rvm_ruby_version}_url" "rvm_ruby_url"
[[ -n "${rvm_ruby_url:-}" ]] || __rvm_db "macruby_url" "rvm_ruby_url"
rvm_ruby_package_name="MacRuby%20${rvm_ruby_version}.zip"
rvm_ruby_package_file="$rvm_ruby_package_name"
rvm_ruby_url="$rvm_ruby_url/$rvm_ruby_package_name"
else
__rvm_db "macruby_version" "rvm_ruby_version"
__rvm_db "macruby_url" "rvm_ruby_url"
rvm_ruby_package_name="MacRuby%20${rvm_ruby_version}.zip"
rvm_ruby_package_file="$rvm_ruby_package_name"
rvm_ruby_url="$rvm_ruby_url/$rvm_ruby_package_name"
fi
rvm_ruby_patch_level=""
else
rvm_error "MacRuby can only be installed on a Darwin OS."
fi
;;
rbx|rubinius)
rvm_archive_extension="tar.gz"
rvm_ruby_interpreter="rbx"
rvm_ruby_version=${rvm_ruby_version:-$(__rvm_db "rbx_version")}
rvm_ruby_repo_url=${rvm_rbx_repo_url:-$(__rvm_db "rubinius_repo_url")}
rbx_url=${rbx_url:-$(__rvm_db "rbx_url")}
rvm_ruby_patch_level=""
case "${rvm_ruby_version}" in
(2.0pre)
rvm_ruby_repo_branch="master" ;;
(2.0.testing)
rvm_ruby_repo_branch="${rvm_ruby_version}" ;;
esac
if (( ${rvm_head_flag:=0} == 0 ))
then
rvm_ruby_url="${rbx_url}"
rvm_ruby_package_file="rubinius-${rvm_ruby_version}.${rvm_archive_extension}"
rvm_ruby_url="$rvm_ruby_url/$rvm_ruby_package_file"
else
rvm_ruby_version="head"
fi
if [[ -n "${rvm_rbx_opt:-}" ]]
then
export RBXOPT="${RBXOPT:=${rvm_rbx_opt}}"
fi
;;
jruby)
rvm_ruby_patch_level=""
if (( ${rvm_head_flag:=0} == 1 ))
then
rvm_ruby_version="head"
rvm_ruby_repo_url="${rvm_ruby_repo_url:-$(__rvm_db "jruby_repo_url")}"
rvm_ruby_url="${rvm_ruby_repo_url:-$(__rvm_db "jruby_repo_url")}"
elif [[ ${rvm_18_flag:-0} == 1 || ${rvm_19_flag:-0} == 1 ]]
then
rvm_ruby_repo_url="${rvm_ruby_repo_url:-$(__rvm_db "jruby_repo_url")}"
rvm_ruby_url="${rvm_ruby_repo_url:-$(__rvm_db "jruby_repo_url")}"
rvm_ruby_version="${rvm_ruby_version:-"$(__rvm_db "jruby_version")"}"
rvm_ruby_tag="${rvm_ruby_tag:-${rvm_ruby_version}}"
else
rvm_archive_extension="tar.gz"
rvm_ruby_version="${rvm_ruby_version:-"$(__rvm_db "jruby_version")"}"
jruby_url="$(__rvm_db "jruby_url")"
rvm_ruby_package_file="${rvm_ruby_interpreter}-bin-${rvm_ruby_version}"
rvm_ruby_package_name="${rvm_ruby_interpreter}-${rvm_ruby_version}"
rvm_ruby_url="${jruby_url}/${rvm_ruby_version}/${rvm_ruby_package_file}.tar.gz"
jruby_url=""
fi
alias jruby_ng="jruby --ng"
alias jruby_ng_server="jruby --ng-server"
;;
maglev)
rvm_ruby_patch_level=""
maglev_url="$(__rvm_db "maglev_url")"
system="$(uname -s)"
if [[ "$MACHTYPE" == x86_64-apple-darwin* ]]
then
arch="i386" # Anyone else hear circus musik? ;)
else
arch="$(uname -m)"
fi
if (( ${rvm_head_flag:=0} == 1 )) || [[ "$rvm_ruby_version" == "head" ]]
then
rvm_head_flag=1
rvm_ruby_version="head"
rvm_ruby_repo_url="${rvm_ruby_repo_url:-$(__rvm_db "maglev_repo_url")}"
rvm_ruby_url="${rvm_ruby_repo_url:-$(__rvm_db "maglev_repo_url")}"
rvm_gemstone_version=$(
command curl -s https://raw.github.com/MagLev/maglev/master/version.txt |
GREP_OPTIONS="" \grep ^GEMSTONE | cut -f2 -d)
rvm_gemstone_package_file="GemStone-${rvm_gemstone_version}.${system}-${arch}"
else
rvm_ruby_package_file="MagLev-${rvm_ruby_version}" # removed from 1.0: .${system}-${arch}
rvm_ruby_version="${rvm_ruby_version:-"$(__rvm_db "maglev_version")"}"
rvm_ruby_package_name="${rvm_ruby_interpreter}-${rvm_ruby_version}"
rvm_ruby_url="${rvm_ruby_url:-"$maglev_url/${rvm_ruby_package_file}.${rvm_archive_extension}"}"
rvm_gemstone_version=$(
version_tag_commit=$(
command curl -s http://github.com/api/v2/yaml/repos/show/MagLev/maglev/tags |
awk '/MagLev-'${rvm_ruby_version}':/ {print $2 }'
)
command curl -s https://raw.github.com/MagLev/maglev/$version_tag_commit/version.txt |
GREP_OPTIONS="" \grep ^GEMSTONE | cut -f2 -d)
rvm_gemstone_package_file="GemStone-${rvm_gemstone_version}.${system}-${arch}"
export MAGLEV_HOME="$rvm_rubies_path/$rvm_ruby_string"
fi
rvm_gemstone_url="$maglev_url/${rvm_gemstone_package_file}.${rvm_archive_extension}"
;;
ironruby)
rvm_ruby_patch_level=""
if (( ${rvm_head_flag:=0} == 1 ))
then
rvm_ruby_version="head"
rvm_ruby_package_name="${rvm_ruby_string}"
rvm_ruby_repo_url="${rvm_ruby_repo_url:-$(__rvm_db "ironruby_repo_url")}"
rvm_ruby_url="${rvm_ruby_repo_url:-$(__rvm_db "ironruby_repo_url")}"
else
rvm_archive_extension="zip"
rvm_ruby_version=${rvm_ruby_version:-"$(__rvm_db "ironruby_version")"}
rvm_ruby_package_name="${rvm_ruby_interpreter}-${rvm_ruby_version}"
rvm_ruby_package_file="${rvm_ruby_interpreter}-${rvm_ruby_version}.${rvm_archive_extension}"
rvm_ruby_url="$(__rvm_db "ironruby_${rvm_ruby_version}_url")${rvm_ruby_package_file}"
fi
export rvm_ruby_version rvm_ruby_string rvm_ruby_package_name rvm_ruby_repo_url rvm_ruby_url rvm_archive_extension
;;
ree)
rvm_ruby_interpreter=ree
rvm_ruby_version=${rvm_ruby_version:-"$(__rvm_db "ree_version")"}
case "$rvm_ruby_version" in
1.8.*) true ;; # all good!
*) rvm_error "Unknown Ruby Enterprise Edition version: $rvm_ruby_version" ;;
esac
if [[ -n "${rvm_ruby_patch_level:-0}" ]]
then
rvm_ruby_patch_level="$(echo $rvm_ruby_patch_level | \sed 's#^p##')"
fi
rvm_ruby_package_file="ruby-enterprise-$rvm_ruby_version-$rvm_ruby_patch_level"
rvm_ruby_url="$(__rvm_db "${rvm_ruby_interpreter}_${rvm_ruby_version}_${rvm_ruby_patch_level}_url")"
rvm_ruby_url="${rvm_ruby_url:-$(__rvm_db "${rvm_ruby_interpreter}_${rvm_ruby_version}_url")}"
rvm_ruby_url="${rvm_ruby_url}/$rvm_ruby_package_file.tar.gz"
;;
kiji)
rvm_ruby_interpreter="kiji"
rvm_ruby_version="head"
rvm_head_flag=1
rvm_ruby_string="kiji-head"
rvm_ruby_patch_level=""
rvm_ruby_repo_url=${rvm_mput_repo_url:-"$(__rvm_db "kiji_repo_url")"}
rvm_ruby_url=$rvm_ruby_repo_url
rvm_ruby_configure="" ; rvm_ruby_make="" ; rvm_ruby_make_install=""
;;
goruby)
rvm_ruby_interpreter="goruby"
rvm_ruby_version="head"
rvm_ruby_string="goruby"
rvm_ruby_patch_level=""
rvm_ruby_repo_url=${rvm_mput_repo_url:-"$(__rvm_db "goruby_repo_url")"}
rvm_ruby_url=$rvm_ruby_repo_url
rvm_ruby_configure="" ; rvm_ruby_make="" ; rvm_ruby_make_install=""
;;
tcs)
rvm_ruby_interpreter="tcs"
rvm_ruby_version="head"
rvm_ruby_string="tcs"
rvm_ruby_patch_level=""
rvm_ruby_repo_url=${rvm_tcs_repo_url:-"$(__rvm_db "tcs_repo_url")"}
rvm_ruby_url=$rvm_ruby_repo_url
rvm_ruby_repo_branch="${rvm_ruby_repo_branch:-"$(__rvm_db "tcs_repo_branch")"}"
export rvm_head_flag=1
rvm_ruby_configure="" ; rvm_ruby_make="" ; rvm_ruby_make_install=""
;;
ruby)
if [[ -n "${rvm_ruby_patch_level}" ]]
then
rvm_ruby_package_file="${rvm_ruby_interpreter}-${rvm_ruby_version}-${rvm_ruby_patch_level}"
rvm_ruby_package_name="${rvm_ruby_interpreter}-${rvm_ruby_version}-${rvm_ruby_patch_level}"
else
rvm_ruby_package_file="${rvm_ruby_interpreter}-${rvm_ruby_version}"
rvm_ruby_package_name="${rvm_ruby_interpreter}-${rvm_ruby_version}"
fi
if [[ -z "${rvm_ruby_version:-""}" ]] && (( ${rvm_head_flag:=0} == 0 ))
then
rvm_error "Ruby version was not specified!"
else
rvm_ruby_repo_url="${rvm_ruby_repo_url:-"$(__rvm_db "ruby_repo_url")"}"
if (( ${rvm_head_flag:=0} == 0 ))
then
case "${rvm_ruby_version}" in
(1.8.4)
rvm_archive_extension="tar.gz"
;;
(*)
rvm_archive_extension="tar.bz2"
;;
esac
fi
fi
;;
ext)
if [[ -z "${rvm_ruby_name:-${detected_rvm_ruby_name:-}}" ]]
then
rvm_error "External ruby name was not specified!"
fi
;;
current)
ruby_binary="$(builtin command -v ruby)"
if (( $? == 0)) && match "$ruby_binary" "*rvm*"
then
rvm_ruby_string="$(dirname "$ruby_binary" | xargs dirname | xargs basename)"
else
rvm_ruby_interpreter="system"
fi
;;
default|system|user)
# no-op?
;;
*)
if [[ -n "${MY_RUBY_HOME:-""}" ]]
then
rvm_ruby_string=$(basename $MY_RUBY_HOME)
__rvm_select
else
if [[ -z "${rvm_ruby_string:-""}" ]]
then
rvm_error "Ruby implementation '$rvm_ruby_interpreter' is not known."
return 1
fi
fi
esac
if [[ -n "$rvm_ruby_version" ]]
then
case "$rvm_ruby_version" in
(+([[:digit:]]).+([[:digit:]]).+([[:digit:]]))
rvm_ruby_release_version="${rvm_ruby_version/.*/}"
rvm_ruby_major_version=${rvm_ruby_version%.*} ; rvm_ruby_major_version=${rvm_ruby_major_version#*.}
rvm_ruby_minor_version="${rvm_ruby_version//*.}"
;;
(+([[:digit:]]).+([[:digit:]]))
rvm_ruby_release_version="${rvm_ruby_version/.*/}"
rvm_ruby_major_version="${rvm_ruby_version#*.}"
rvm_ruby_minor_version=""
;;
esac
fi
if [[ "${rvm_ruby_interpreter}" == ext ]]
then
rvm_ruby_home="$rvm_externals_path/$rvm_ruby_string"
rvm_ruby_irbrc="$rvm_ruby_home/.irbrc"
rvm_ruby_binary="$( readlink $rvm_ruby_home/bin/ruby )"
else
rvm_ruby_package_name="${rvm_ruby_package_name:-${rvm_ruby_string//-n*}}"
rvm_ruby_home="$rvm_rubies_path/$rvm_ruby_string"
rvm_ruby_irbrc="$rvm_ruby_home/.irbrc"
rvm_ruby_binary="$rvm_ruby_home/bin/ruby"
fi
# TODO is this right place to do this ?
if [[ "maglev" == "$rvm_ruby_interpreter" ]]
then
export MAGLEV_HOME="$rvm_ruby_home"
export GEMSTONE_GLOBAL_DIR=$MAGLEV_HOME
fi
if [[ "system" != "$rvm_ruby_interpreter" ]]
then
__rvm_gemset_select
case $? in
1|3|4)
return 1
;;
esac
fi
rvm_ruby_selected_flag=1
if [[ -d "${rvm_log_path}/$rvm_ruby_string" ]]
then
\mkdir -p "${rvm_log_path}/$rvm_ruby_string"
fi
rvm_ruby_interpreter="${rvm_ruby_interpreter:-system}"
}
__rvm_use_system() {
unset GEM_HOME GEM_PATH MY_RUBY_HOME RUBY_VERSION IRBRC
new_path="$(__rvm_remove_rvm_from_path ; printf "%b" "$PATH"):${rvm_bin_path}"
if [[ -s "$rvm_path/config/system" ]]
then
if GREP_OPTIONS="" \grep "MY_RUBY_HOME='$rvm_rubies_path" "$rvm_path/config/system" > /dev/null
then
# 'system' should *not* point to an rvm ruby.
if [[ -f "$rvm_path/config/system" ]]
then
\rm -f "$rvm_path/config/system"
fi
else
source "$rvm_path/config/system"
fi
fi
if (( ${rvm_default_flag:=0} == 1 ))
then
"$rvm_scripts_path/alias" delete default &> /dev/null
\find "${rvm_bin_path}" -maxdepth 0 -name 'default_*' -delete
\rm -f "$rvm_path/config/default"
\rm -f "$rvm_environments_path/default"
__rvm_rm_rf "$rvm_wrappers_path/default"
fi
# Check binaries, remove under the condition they're symlinks.
if (( ${rvm_user_install_flag:=0} == 0 ))
then
for binary in ruby gem irb ri rdoc rake erb testrb
do
full_binary_path="${rvm_bin_path}/$binary"
if [[ -L "$full_binary_path" ]]
then
\rm -f "$full_binary_path"
fi
done
fi
if (( ${rvm_verbose_flag:=0} == 1 ))
then
rvm_log "Now using system ruby."
fi
__rvm_remove_rvm_from_path
new_path="$PATH:${rvm_bin_path}"
export rvm_ruby_string="system"
}
__rvm_use()
{
typeset new_path binary full_binary_path rvm_ruby_gem_home
__rvm_select "$@" || return $?
if [[ "system" == ${rvm_ruby_interpreter:="system"} ]]
then
__rvm_use_system
else
if [[ ! -d "$rvm_ruby_home" ]]
then
if [[ ${rvm_install_on_use_flag:-0} -eq 1 ]]
then
rvm_warn "$rvm_ruby_string is not installed."
"$rvm_scripts_path/manage" "install" "$rvm_ruby_string"
else
rvm_error "$rvm_ruby_string is not installed."
rvm_log "To install do: 'rvm install $rvm_ruby_string'"
return 1
fi
fi
if [[ ! -d "$rvm_ruby_gem_home" || -n "${rvm_expected_gemset_name}" ]]
then
if (( ${rvm_gemset_create_on_use_flag:=0} == 1 || ${rvm_create_flag:=0} == 1 ))
then
rvm_warn "gemset $rvm_gemset_name is not existing, creating."
"$rvm_scripts_path/gemsets" create "$rvm_gemset_name"
else
rvm_error "Gemset '${rvm_expected_gemset_name}' does not exist, 'rvm gemset create ${rvm_expected_gemset_name}'
first, or append '--create'."
return 2
fi
fi
export GEM_HOME GEM_PATH MY_RUBY_HOME RUBY_VERSION IRBRC
GEM_HOME="$rvm_ruby_gem_home"
GEM_PATH="$rvm_ruby_gem_path"
MY_RUBY_HOME="$rvm_ruby_home"
RUBY_VERSION="$rvm_ruby_string"
IRBRC="$rvm_ruby_irbrc"
unset BUNDLE_PATH # Ensure that BUNDLE_PATH is not set!
# Handle MagLev pre-installed gems
if [[ "maglev" == "$rvm_ruby_interpreter" ]]
then
GEM_PATH="$GEM_PATH:$MAGLEV_HOME/lib/maglev/gems/1.8/"
fi
[[ -n "${IRBRC:-}" ]] || unset IRBRC
# Ensure the environment file for the selected ruby exists.
__rvm_ensure_has_environment_files
if (( ${rvm_verbose_flag:=0} == 1 ))
then
rvm_log "Using ${GEM_HOME/${rvm_gemset_separator:-'@'}/ with gemset }"
fi
if [[ "$GEM_HOME" != "$rvm_ruby_global_gems_path" ]]
then
new_path="$GEM_HOME/bin:$rvm_ruby_global_gems_path/bin:$MY_RUBY_HOME/bin:${rvm_bin_path}:$(__rvm_remove_rvm_from_path
;printf "%b" "$PATH")"
else
new_path="$GEM_HOME/bin:$MY_RUBY_HOME/bin:${rvm_bin_path}:$(__rvm_remove_rvm_from_path ;printf "%b" "$PATH")"
fi
fi
[[ -z "${rvm_ruby_string:-}" ]] || export rvm_ruby_string
[[ -z "${rvm_gemset_name:-}" ]] || export rvm_gemset_name
if [[ -n "$new_path" ]]
then
export PATH="$new_path"
unset new_path
builtin hash -r
fi
if [[ "$rvm_ruby_string" != "system" ]]
then
case "${rvm_rvmrc_flag:-0}" in
(rvmrc|versions_conf|ruby_version)
__rvm_set_${rvm_rvmrc_flag}
;;
esac
typeset environment_id
environment_id="$(__rvm_env_string)"
if (( ${rvm_default_flag:=0} == 1 )) &&
[[ "default" != "${rvm_ruby_interpreter:-}" ]] &&
[[ "system" != "${rvm_ruby_interpreter:-}" ]]
then
# Switch the default alias to the new environment id
"$rvm_scripts_path/alias" delete default &> /dev/null
"$rvm_scripts_path/alias" create default "$environment_id" >& /dev/null
fi
rvm_default_flag=0
if [[ -n "${rvm_wrapper_name:-}" ]]
then
"$rvm_scripts_path/wrapper" "$environment_id" "$rvm_wrapper_name" > /dev/null 2>&1
rvm_wrapper_name=""
fi
if [[ -n "${rvm_ruby_alias:-}" ]]
then
rvm_log "Attempting to alias $environment_id to $rvm_ruby_alias"
"$rvm_scripts_path/alias" delete "$rvm_ruby_alias" > /dev/null 2>&1
rvm_alias_expanded=1 "$rvm_scripts_path/alias" create "$rvm_ruby_alias" "$environment_id" > /dev/null 2>&1
ruby_alias="" ; rvm_ruby_alias=""
fi
if [[ "maglev" == "${rvm_ruby_interpreter:-""}" ]]
then
export MAGLEV_HOME="$rvm_ruby_home"
export GEMSTONE_GLOBAL_DIR=$MAGLEV_HOME
if [[ -x "$MAGLEV_HOME/gemstone/bin/gslist" ]]
then
"$MAGLEV_HOME/gemstone/bin/gslist" -clv > /dev/null 2>&1 ; result=$?
if (( result == 1 ))
then
"$rvm_ruby_home/bin/maglev" start
fi
fi
fi
else
if (( ${rvm_default_flag:=0} == 1 ))
then
if ! builtin command -v __rvm_reset >> /dev/null 2>&1
then
source "$rvm_scripts_path/functions/reset"
__rvm_reset
fi
fi
fi
rvm_hook="after_use"
source "$rvm_scripts_path/hook"
return 0
}
__rvm_ruby_string()
{
# rvm_ruby_string may designate any of the following items:
# * rvm_gemset_name
# * rvm_ruby_interpreter
# * rvm_ruby_version
# * rvm_ruby_patch_level
# * rvm_ruby_revision
# * rvm_ruby_tag
typeset ruby_string gemset_name expanded_alias_name repo_url branch_name ruby_name
__rvm_default_flags
rvm_expanding_aliases=
true \
"${rvm_ruby_version:=}" "${rvm_gemset_name:=}" "${rvm_ruby_interpreter:=}"\
"${rvm_ruby_version:=}" "${rvm_ruby_tag:=}" "${rvm_ruby_patch_level:=}"\
"${rvm_ruby_revision:=}" ${rvm_gemset_separator:="@"} "${rvm_ruby_string:=}"\
${rvm_expanding_aliases:=0} ${rvm_head_flag:=0}
if echo "$rvm_ruby_string" | GREP_OPTIONS="" \grep "${rvm_gemset_separator}" >/dev/null 2>&1
then
rvm_gemset_name="${rvm_ruby_string/*${rvm_gemset_separator}/}"
rvm_ruby_string="${rvm_ruby_string/${rvm_gemset_separator}*/}"
fi
# Alias'd rubies
if (( rvm_expanding_aliases == 0 )) &&
[[ -n "${rvm_ruby_string}" && "$rvm_ruby_string" != "system" ]]
then
if expanded_alias_name="$("$rvm_scripts_path/alias" show "$rvm_ruby_string" 2>/dev/null)" \
&& [[ -n "$expanded_alias_name" ]]
then
rvm_ruby_string="$expanded_alias_name"
elif [[ "$rvm_ruby_string" == default ]]
then
# Default is not a known value. Instead, we need to therefore set it to system.
rvm_ruby_string="system"
fi
fi
if echo "$rvm_ruby_string" | GREP_OPTIONS="" \grep "${rvm_gemset_separator}" >/dev/null 2>&1 ; then
rvm_gemset_name="${rvm_ruby_string/*${rvm_gemset_separator}/}"
rvm_ruby_string="${rvm_ruby_string/${rvm_gemset_separator}*/}"
fi
# Stash the ruby string.
ruby_string="${rvm_ruby_string:-}"
gemset_name="${rvm_gemset_name:-}"
repo_url="${rvm_ruby_repo_url:-}"
branch_name="${rvm_ruby_repo_branch:-}"
ruby_name="${rvm_ruby_name:-}"
__rvm_unset_ruby_variables
rvm_ruby_repo_url="${repo_url:-}"
rvm_ruby_repo_branch="${branch_name:-}"
rvm_ruby_name="$ruby_name"
if [[ -n "$gemset_name" ]]
then
rvm_gemset_name="$gemset_name"
rvm_sticky_flag=1 # <- not sold on this.
fi
strings=($(echo ${ruby_string//-/ }))
if (( ${#strings[@]} == 0 ))
then
if echo "${GEM_HOME:-}" | GREP_OPTIONS="" \grep "${rvm_path}" >/dev/null 2>&1
then
# Current Ruby
strings="${GEM_HOME##*\/}"
strings="${strings/%${rvm_gemset_separator:-"@"}*}"
rvm_ruby_string="$strings"
strings=( $(echo ${rvm_ruby_string//-/ }) )
else
strings=(system)
rvm_ruby_string="system"
fi
fi
for string in ${strings[@]}
do
case "$string" in
(head)
rvm_ruby_patch_level=""
rvm_ruby_revision=""
rvm_ruby_tag=""
export rvm_head_flag=1
;;
(system)
rvm_ruby_interpreter="system"
rvm_ruby_patch_level=""
rvm_ruby_tag=""
rvm_ruby_revision=""
rvm_ruby_version=""
rvm_gemset_name=""
rvm_head_flag=0
return 0
;;
(ext|external)
rvm_ruby_interpreter="ext"
rvm_ruby_patch_level=""
rvm_ruby_tag=""
rvm_ruby_revision=""
rvm_ruby_version=""
rvm_head_flag=0
unset strings[__array_start]
strings=( ${strings[@]} )
strings="${strings[*]}"
rvm_ruby_name="${strings// /-}"
break
;;
(nightly)
rvm_ruby_version="nightly"
rvm_nightly_flag=1
break
;;
(preview*)
rvm_ruby_patch_level="$string"
;;
(rc[[:digit:]]*)
rvm_ruby_patch_level="$string"
;;
([[:digit:]].[[:digit:]]*)
#TODO: use normal code for rbx!
if [[ "${rvm_ruby_interpreter}" == "rbx" ]]
then
if [[ -z "${rvm_ruby_version}" ]]
then
rvm_ruby_version="${string}"
elif [[ -z "${rvm_ruby_patch_level}" ]]
then
rvm_ruby_patch_level="${string}"
else
rvm_error "Unknown ruby interpreter string component: '$string'."
return 1
fi
else
case "$string" in
(0.+([[:digit:]])|0.+([[:digit:]]).+([[:digit:]])|1.+([[:digit:]]).+([[:digit:]])|2.+([[:digit:]]).+([[:digit:]])|1.+([[:dig
it:]]).+([[:digit:]]).+([[:digit:]])|1.+([[:digit:]]))
rvm_ruby_version="$string"
rvm_ruby_revision=""
rvm_ruby_tag=""
;;
(1.+([[:digit:]]).+([[:digit:]]).+([[:alnum:]]))
case "${rvm_ruby_interpreter:-""}" in
(jruby)
rvm_ruby_version="$string"
;;
(*)
rvm_error "Unknown ruby interpreter version: '$string'."
return 1
;;
esac
;;
(*)
rvm_error "Unknown ruby interpreter version: '$string'."
return 1
;;
esac
fi
;;
(p[[:digit:]]*)
rvm_ruby_patch_level="$string"
;;
([[:digit:]][[:digit:]]*)
case "${rvm_ruby_interpreter:-""}" in
(ree)
rvm_ruby_patch_level="$string"
rvm_ruby_revision=""
;;
(kiji)
rvm_ruby_patch_level="$string"
rvm_ruby_revision=""
;;
(rbx)
rvm_ruby_patch_level="$string"
;;
(maglev)
rvm_ruby_version="$string"
rvm_ruby_revision=""
rvm_ruby_patch_level=""
;;
(*)
rvm_ruby_revision="r$string"
;;
esac
;;
(r[[:digit:]]*)
rvm_ruby_patch_level=""
rvm_ruby_revision="$string"
;;
(s[[:alnum:]]*)
rvm_ruby_revision=""
rvm_ruby_sha="${string#s}"
;;
(tv[[:digit:]]*|t[[:digit:]]*)
rvm_ruby_patch_level="" ; rvm_ruby_revision=""
rvm_ruby_tag="$string"
;;
(m[[:digit:]]*)
rvm_ruby_mode="$string"
;;
(u[[:alnum:]]*)
rvm_ruby_patch_level="" ; rvm_ruby_revision="" ; rvm_ruby_tag="" ; rvm_ruby_patch=""
rvm_ruby_user_tag="$string"
;;
(a[[:digit:]][[:digit:]]*)
rvm_ruby_bits="$string" # Architecture
;;
(b[[:digit:]]*)
rvm_ruby_repo_branch="${string}"
rvm_head_flag=1
;;
(ruby|rbx|jruby|macruby|ree|kiji|rubinius|maglev|ironruby|goruby|tcs)
rvm_ruby_interpreter="$string"
;;
([[:alpha:]]*([[:alnum:]]|_))
rvm_ruby_name="$string"
;;
(*)
rvm_error "Unknown ruby interpreter string component: '$string'."
return 1
;;
esac
done
if [[ -z "${rvm_ruby_interpreter:-""}" ]]
then
# Detect interpreter based on version.
case "$rvm_ruby_version" in
(1.[8-9]*) rvm_ruby_interpreter="ruby"
;;
(0.[5-6]*) rvm_ruby_interpreter="macruby" ;;
(1.[0-4]*) rvm_ruby_interpreter="rbx"
;;
(1.[5-7]*) rvm_ruby_interpreter="jruby"
;;
(2.*)
rvm_error "Version '$rvm_ruby_version' is to confusing to select ruby interpreter."
return 2
;;
esac
fi
# Unspecified version
rvm_ruby_version="${rvm_ruby_version:-}"
if [[ -z "${rvm_ruby_version:-}" && "${rvm_ruby_interpreter}" != "ext" ]] && (( ${rvm_head_flag:=0} == 0 ))
then
rvm_ruby_version="${rvm_ruby_version:-"$(
__rvm_db "${rvm_ruby_interpreter}_version"
)"}"
fi
if [[ -z "${rvm_ruby_version:-}" ]]
then
rvm_ruby_string="${rvm_ruby_interpreter}"
else
rvm_ruby_string="${rvm_ruby_interpreter}-${rvm_ruby_version}"
fi
if [[ "${rvm_ruby_interpreter}" == "ext" ]]
then
true # skip checking for external rubies
elif (( ${rvm_head_flag:=0} == 1 ))
then
rvm_ruby_string="${rvm_ruby_string}-head"
elif [[ -n "${rvm_ruby_revision:-}" ]]
then
rvm_ruby_string="${rvm_ruby_string}-${rvm_ruby_revision}"
elif [[ -n "${rvm_ruby_sha:-}" ]]
then
rvm_ruby_string="${rvm_ruby_string}-s${rvm_ruby_sha}"
elif [[ -n "${rvm_ruby_tag:-}" ]]
then
rvm_ruby_string="${rvm_ruby_string}-${rvm_ruby_tag}"
elif [[ -n "${rvm_ruby_patch_level:-}" ]]
then
rvm_ruby_string="${rvm_ruby_string}-${rvm_ruby_patch_level}"
elif [[ -n "${rvm_ruby_user_tag:-}" ]]
then
rvm_ruby_string="${rvm_ruby_string}-${rvm_ruby_user_tag}"
else
patch_level="$(
__rvm_db "${rvm_ruby_interpreter}_${rvm_ruby_version}_patch_level"
)"
if [[ -n "${patch_level:-""}" ]]
then
case "$rvm_ruby_interpreter" in
ree|kiji|rbx)
# REE, Kiji & Rubinius use dates for their patch levels.
rvm_ruby_patch_level="${patch_level}"
;;
*)
# MRI uses -pN+ to specify the patch level.
rvm_ruby_patch_level="p${patch_level}"
;;
esac
fi
if [[ -n "${rvm_ruby_patch_level:-""}" ]]
then
rvm_ruby_patch_level="${rvm_ruby_patch_level/#pp/p}"
rvm_ruby_patch_level="${rvm_ruby_patch_level/#prc/rc}"
rvm_ruby_string="${rvm_ruby_string}-${rvm_ruby_patch_level}"
case "$rvm_ruby_interpreter" in
(ree|kiji|rbx)
rvm_ruby_string="${rvm_ruby_string//-p*/-}"
;;
(*)
rvm_ruby_string="${rvm_ruby_string//-pp/-p}"
rvm_ruby_string="${rvm_ruby_string//-prc/-rc}"
;;
esac
fi
fi
if [[ -n "${rvm_ruby_name:-}" ]]
then
rvm_ruby_string="${rvm_ruby_string}-${rvm_ruby_name}"
# record the name for validation of -n option
detected_rvm_ruby_name="${rvm_ruby_name}"
# clean the name so it is not added again (rbx -n install problem)
rvm_ruby_name=""
else
# record the no name for validation of -n option
detected_rvm_ruby_name=""
fi
}
__rvm_ruby_strings_exist()
{
for rvm_ruby_string in ${@//,/ }
do
rvm_verbose_flag=0 __rvm_use "${rvm_ruby_string}" >/dev/null 2>&1 || return $?
printf "%b" "${rvm_ruby_string}${rvm_gemset_name:+@}${rvm_gemset_name:-}\n"
done
unset rvm_ruby_string
}
1.18.7. get
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
get_usage()
{
cat -v "$rvm_help_path/get"
}
get_via_installer()
{
curl -L get.rvm.io | bash -s -- $@ || return $?
typeset -x rvm_hook
rvm_hook="after_update"
source "$rvm_scripts_path/hook"
return 0
}
case "$1" in
(stable|master|head|branch|latest|latest-*|[0-9]*.[0-9]*.[0-9]*)
get_via_installer $@
;;
(help)
get_usage
true
;;
(*)
get_usage
;;
esac
exit $?
1.18.8. docs
#!/usr/bin/env bash
rvm_base_except="selector"
source "$rvm_scripts_path/base"
rvm_docs_ruby_string="$(__rvm_env_string | awk -F"${rvm_gemset_separator:-"@"}" '{print $1}')"
if [[ "$rvm_docs_ruby_string" == "system" || -z "$rvm_docs_ruby_string" ]]
then
rvm_error "Currently 'rvm docs ...' does not work with non-rvm rubies."
exit 1
fi
if [[ ! -d "${rvm_src_path}/$rvm_docs_ruby_string" ]]
then
rvm_error "'rvm docs ...' requires ruby sources to be available, run \`rvm reinstall $rvm_docs_ruby_string"
exit 2
fi
rvm_docs_type="${rvm_docs_type:-rdoc}"
# Ensure we have the doc directories.
if [[ ! -d "${rvm_docs_path:-"$rvm_path/docs"}" ]]
then
mkdir -p "${rvm_docs_path:-"$rvm_path/docs"}/rdoc" "${rvm_docs_path:-"$rvm_path/docs"}/yard"
fi
usage()
{
printf "%b" "
Usage:
rvm docs {open,generate,generate-ri,generate-rdoc}
"
return 0
}
open_docs()
{
if [[ -s "${rvm_docs_path:-"$rvm_path/docs"}/$rvm_docs_ruby_string/$rvm_docs_type/index.html" ]]
then
if
[[ "${DESKTOP_SESSION}" == "gnome" ]] && builtin command -v gnome-open >/dev/null
then
gnome-open "${rvm_docs_path:-"$rvm_path/docs"}/$rvm_docs_ruby_string/$rvm_docs_type/index.html" &>/dev/null
elif
[[ -n "${XDG_SESSION_COOKIE}" || -n "${XDG_SESSION_ID}" ]] && builtin command -v xdg-open >/dev/null
then
xdg-open "${rvm_docs_path:-"$rvm_path/docs"}/$rvm_docs_ruby_string/$rvm_docs_type/index.html" &>/dev/null
elif
builtin command -v open >/dev/null
then
open "${rvm_docs_path:-"$rvm_path/docs"}/$rvm_docs_ruby_string/$rvm_docs_type/index.html"
else
rvm_error "None of open, xdg-open or gnome-open were found, in order to open the docs one of these two are required.
\n(OR you can let me know how else to open the html in your browser from comand line on your OS :) )"
fi
else
rvm_error "$rvm_docs_type docs are missing, perhaps run 'rvm docs generate' first?"
fi
}
generate_ri()
{
# Generate ri docs
(
builtin cd "${rvm_src_path}/$rvm_docs_ruby_string/"
rvm_log "Generating ri documentation, be aware that this could take a *long* time, and depends heavily on your system
resources..."
rvm_log "( Errors will be logged to ${rvm_log_path}/$rvm_docs_ruby_string/docs.log )"
rdoc -a --ri-site > /dev/null 2>> ${rvm_log_path}/$rvm_docs_ruby_string/docs.log
)
}
generate_rdoc()
{
(
builtin cd "${rvm_src_path}/$rvm_docs_ruby_string/"
__rvm_rm_rf "${rvm_docs_path:-"$rvm_path/docs"}/$rvm_docs_ruby_string/$rvm_docs_type/"
rvm_log "Generating rdoc documentation, be aware that this could take a *long* time, and depends heavily on your system
resources..."
rvm_log "( Errors will be logged to ${rvm_log_path}/$rvm_docs_ruby_string/docs.log )"
if gem list | GREP_OPTIONS="" \grep ^hanna >/dev/null 2>&1
then
hanna -o "${rvm_docs_path:-"$rvm_path/docs"}/$rvm_docs_ruby_string/$rvm_docs_type" --inline-source --line-numbers -fmt=html > /dev/null 2>> "${rvm_log_path}/$rvm_docs_ruby_string/docs.log"
else
rdoc -a -o "${rvm_docs_path:-"$rvm_path/docs"}/$rvm_docs_ruby_string/$rvm_docs_type" > /dev/null 2>>
"${rvm_log_path}/$rvm_docs_ruby_string/docs.log"
fi
)
}
args=($*)
action="${args[0]}"
args=($(echo ${args[@]:1})) # Strip trailing / leading / extra spacing.
case "$action" in
generate)
generate_ri
generate_rdoc
;;
open)
open_docs
generate-ri)
generate_ri
generate-rdoc) generate_rdoc
help)
usage
*)
usage ; exit 1
esac
exit $?
;;
;;
;;
;;
;;
1.18.9. cron
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
# Add rvm variables on the beginning of crontab
__rvm_cron_setup()
{
{
echo "#sm start rvm"
rvm env --cron
echo "#sm end rvm"
__sm.cron.show | __sm.filter.remove.group "^#sm start rvm$" "^#sm end rvm$"
} | crontab }
__rvm_cron_remove()
{
__sm.cron.show | __sm.filter.remove.group "^#sm start rvm$" "^#sm end rvm$" | crontab }
__rvm_cron_command()
{
typeset v schedule
schedule="$1"
shift || {
rvm_error "Schedule not given, example: rvm cron command \"@daily\" rake calculate:stats"
rvm_info "Refer to \`man 5 crontab\` for format of the scheduling definition."
exit 1
}
[[ -n "$1" ]] || {
rvm_error "Command not given, example: rvm cron command \"@daily\" rake calculate:stats"
exit 2
}
{
__sm.cron.show
printf "%b" "${schedule} $(which rvm) in \"$PWD\" do"
for v in "$@"
do printf "%b" " \"$v\""
done
printf "\n"
} | crontab }
__sm.cron.show()
{
EDITOR=cat crontab -e 2>/dev/null
}
__sm.filter.remove.group()
{
awk 'BEGIN{in_group=0} /'"$1"'/ {in_group=1} in_group==0 {print} /'"$2"'/ {in_group=0}'
}
__rvm_cron_help()
{
cat "${rvm_help_path}/cron"
}
action="${1:-}"
shift
case "$action" in
setup|remove|help) __rvm_cron_$action
;;
command)
__rvm_cron_$action "$@" ;;
*)
__rvm_cron_help ; exit 1 ;;
esac
1.18.10. current
#!/usr/bin/env bash
if [[ "$rvm_trace_flag" -eq 2 ]] ; then set -x ; export rvm_trace_flag ; fi
source "$rvm_scripts_path/base"
printf "%b" "$(__rvm_env_string)\n"
exit 0
1.18.11. group
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
source "$rvm_scripts_path/version"
source "$rvm_scripts_path/functions/group"
group_add()
{
for user in "${users[@]}"
do
printf "%b" "Ensuring '$user' is in group '$rvm_group_name'\n"
add_user_to_rvm_group $user
done
}
group_remove()
{
:
}
group_help
args=($*)
action="${users[$__array_start]}"
users[$__array_start]=""
users=(${args[@]})
true "${rvm_group_name:=rvm}"
if (( UID > 0 ))
then
rvm_log "rvm group must be run as root."
exit 1
fi
case "$action" in
add)
group_add
;;
rm|remove)
group_remove
;;
help)
get_help
true
;;
*)
false
;;
esac
exit $?
1.18.12. list
#!/usr/bin/env bash
rvm_base_except="selector"
source "$rvm_scripts_path/base"
usage()
{
printf "%b" "
Usage:
rvm list [action]
Actions:
{help,known,gemsets,default [string],rubies,strings,known_strings,ruby_svn_tags}
"
return 0
}
list_gemsets()
{
typeset all_rubies version versions ruby_version_name current_ruby selected system_ruby system_version string binary
if [[ "${1:-""}" == "strings" ]]
then
list_gemset_strings
return 0
fi
current_ruby="$(__rvm_env_string)"
all_rubies="$(list_strings | sort)"
printf "%b" "\nrvm gemsets\n"
versions=($(
builtin cd "${rvm_gems_path:-"$rvm_path/gems"}/"
find . -maxdepth 1 -mindepth 1 -type d -print 2> /dev/null | \
awk '/[a-z]*-.*/ {print $NF}' | sort
))
for version in "${versions[@]//.\/}"
do
ruby_version_name="$(echo "$version" | awk -F"${rvm_gemset_separator:-"@"}" '{print $1}')"
if [[ "$all_rubies" != *"$ruby_version_name"* ]]
then
continue
fi
if printf "%b" "$version" | GREP_OPTIONS="" \grep '^jruby-' >/dev/null 2>&1
then
string="[ $("$rvm_rubies_path/$ruby_version_name/bin/ruby" -v | awk '{print $NF}' | sed -e 's/\[//' -e 's/\]//') ]"
elif [[ -n "$(echo
then
string="[ x86_64
else
string="[ $(file
/ppc/ {print "ppc"}' |
fi
"$version" | awk '/^maglev-|^macruby-/')" ]]
]"
"$rvm_rubies_path/$ruby_version_name/bin/ruby" | awk '/x86.64/ {print "x86_64"} /386/ {print "i386"}
\tr "\n" ' ')]"
printf "%b" "\n"
if [[ "$version" == "$current_ruby" ]]
then
printf "%b" "=> "
else
printf "%b" "
"
fi
if rvm_pretty_print stdout
then
printf "%b" "${rvm_notify_clr:-}$version${rvm_reset_clr:-} $string"
else
printf "%b" "$version $string"
fi
done
if [[ -f "$rvm_path/config/default" && -s "$rvm_path/config/default" ]]
then
version=$(
GREP_OPTIONS="" \grep 'MY_RUBY_HOME' "$rvm_path/config/default" | head -1 | awk -F"'" '{print $2}' | xargs basename -)
if [[ -n "$version" ]]
then
printf "%b" "\nDefault Ruby (for new shells)\n"
string="[ $(file "$rvm_rubies_path/$version/bin/ruby" | awk '/x86.64/ {print "x86_64"} /386/ {print "i386"} /ppc/
{print "ppc"}' | \tr "\n" ' ')]"
if rvm_pretty_print stdout
then
printf "%b" "\n ${rvm_notify_clr:-}$version${rvm_reset_clr:-} $string\n"
else
printf "%b" "\n $version $string\n"
fi
fi
fi
printf "%b" "\n\n"
return 0
}
list_default()
{
typeset version string
if [[ "${args[0]:-""}" == "string" ]]
then
"$rvm_scripts_path/alias" show default 2>/dev/null | \
awk -F"${rvm_gemset_separator:-"@"}" '{print $1}' | \
xargs basename -else
if [[ -L "$rvm_rubies_path/default" ]]
then
version=$(
"$rvm_scripts_path/alias" show default 2>/dev/null | \
awk -F"${rvm_gemset_separator:-"@"}" '{print $1}' | \
xargs basename -)
if [[ -n "$version" ]]
then
printf "%b" "\nDefault Ruby (for new shells)\n"
string="[ $(file "$rvm_rubies_path/$version/bin/ruby" | awk '/x86.64/ {print "x86_64"} /386/ {print "i386"} /ppc/
{print "ppc"}' | \tr "\n" ' ')]"
if rvm_pretty_print stdout
then
printf "%b" "\n
${rvm_notify_clr:-}$version${rvm_reset_clr:-} $string\n"
else
printf "%b" "\n
$version $string\n"
fi
fi
fi
fi
printf "%b" "\n"
return 0
}
list_ruby_svn_tags()
{
typeset prefix tag
while read -r tag
do
prefix="$(
echo ${tag/\//} | \
sed 's#^v1_##' | \
awk -F'_' '{print "(ruby-)1."$1"."$2}' | \
sed 's#p$##'
)"
echo "${prefix}-t${tag/\//}"
done < <(svn list http://svn.ruby-lang.org/repos/ruby/tags/ | \
awk '/^v1_[8|9]/')
return 0
}
# Query for valid rvm ruby strings
# This is meant to be used with scripting.
list_strings()
{
(
builtin cd "$rvm_rubies_path"
find . -maxdepth 1 -mindepth 1 -type d | sed -e 's#./##g'
)
return $?
}
# This is meant to be used with scripting.
list_gemset_strings()
{
typeset all_rubies ruby_name gemset gemsets
all_rubies="$(list_strings | sort)"
gemsets=($(
builtin cd "${rvm_gems_path:-"$rvm_path/gems"}"
find . -maxdepth 1 -mindepth 1 -type d 2>/dev/null | \
xargs -n1 basename -- | \
GREP_OPTIONS="" \grep -v '^\(@\|doc$\|cache$\|system$\)' | sort
))
for gemset in "${gemsets[@]//.\/}"
do
ruby_name="${gemset//${rvm_gemset_separator:-"@"}*}"
if [[ "$all_rubies" != *"$ruby_name"* ]]
then
continue
fi
echo "$gemset"
done
return 0
}
# This is meant to be used with scripting.
list_known_strings()
{
sed -e 's/#.*$//g' -e 's#\[##g' -e 's#\]##g' < "$rvm_path/config/known" | \
sort -r | uniq
return $?
}
list_known()
{
if [[ "${1:-""}" == "strings" ]]
then
list_known_strings
return 0
fi
if [[ -t 0 ]]
then
__rvm_pager_or_cat_v "$rvm_path/config/known"
else
cat "$rvm_path/config/known"
fi
return $?
}
list_rubies_strings()
{
(
builtin cd "$rvm_rubies_path"
find -maxdepth 0 -type d | tail -n+2 | xargs -n1 basename -- |
)
__rvm_strip
return $?
}
list_rubies()
{
typeset current_ruby rubies version selected system_ruby system_version \
default_ruby string binary
if [[ "${1:-""}" == "strings" ]]
then
list_rubies_strings
return 0
fi
current_ruby="$( __rvm_env_string )"
current_ruby="${current_ruby%${rvm_gemset_separator:-"@"}*}"
default_ruby="$( "$rvm_scripts_path/alias" show default 2>/dev/null )"
default_ruby="${default_ruby%${rvm_gemset_separator:-"@"}*}"
printf "%b" "\nrvm rubies\n\n"
rubies=($(
builtin cd "$rvm_rubies_path/"
find . -maxdepth 1 -mindepth 1 -type d 2> /dev/null | sort
))
for version in "${rubies[@]//.\/}"
do
if [[ ! -x "$rvm_rubies_path/$version/bin/ruby" ]]
then
continue
fi
if [[ "$version" = "$current_ruby" && "$version" = "$default_ruby" ]]
then
printf "%b" "=* "
elif [[ "$version" = "$current_ruby" ]]
then
printf "%b" "=> "
elif [[ "$version" = "$default_ruby" ]]
then
printf "%b" " * "
else
printf "%b" "
"
fi
if [[ ! -z "$(echo "$version" | awk '/^maglev-|^macruby-/')" ]] ; then
string="[ x86_64 ]"
else
string="[ $(. $rvm_rubies_path/$version/config ; echo $target_cpu) ]"
fi
if rvm_pretty_print stdout
then
printf "%b" "${rvm_notify_clr:-}$version${rvm_reset_clr:-} $string"
else
printf "%b" "$version $string"
fi
printf "%b" "\n"
done
if (( ${#rubies[@]} == 0 ))
then
printf "%b" "
# No rvm rubies installed yet. Try 'rvm help install'.
"
else
if [[ -z "${default_ruby}" ]]
then
printf "%b" "
# Default ruby not set. Try 'rvm alias create default <ruby>'.
"
fi
printf "%b" "
# => - current
# =* - current && default
# * - default
"
fi
printf "%b" "\n"
return 0
}
# List all rvm installed rubies, default ruby and system ruby.
# Display the rubies, indicate their architecture and indicate which is currently used.
# This is not meant to be used with scripting. This is for interactive mode usage only.
args=($*)
action="${args[0]:-""}"
args=${args[@]:1} # Strip trailing / leading / extra spacing.
if [[ -z "$action" ]]
then
list_rubies
exit 0
fi
case "$action" in
known)
list_known
known_strings) list_known_strings
gemsets)
list_gemsets "$args"
default)
list_default
rubies)
list_rubies "$args"
strings)
list_strings
ruby_svn_tags) list_ruby_svn_tags
help)
usage
*)
usage ; exit 1
esac
exit $?
;;
;;
;;
;;
;;
;;
;;
;;
;;
1.18.13. install
#!/usr/bin/env bash
export PS4 PATH
PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
\${LINENO} > "
set -o errtrace
if [[ "$*" =~ --trace ]] || (( ${rvm_trace_flag:-0} > 0 ))
then # Tracing, if asked for.
set -o xtrace
export rvm_trace_flag=1
fi
#Handle Solaris Hosts
if [[ "$(uname -s)" == "SunOS" ]]
then
PATH="/usr/gnu/bin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin:$PATH"
elif [[ "$(uname)" == "OpenBSD" ]]
then
# don't touch PATH,
true
else
PATH="/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin:/usr/local/sbin:$PATH"
fi
if [[ -n "${rvm_user_path_prefix:-}" ]]
then
PATH="${rvm_user_path_prefix}:$PATH"
fi
shopt -s extglob
source "$PWD/scripts/functions/installer"
# source "$PWD/scripts/rvm"
#
# RVM Installer
#
install_setup
true ${DESTDIR:=}
# Parse RVM Installer CLI arguments.
while (( $# > 0 ))
do
token="$1"
shift
case "$token" in
(--auto)
rvm_auto_flag=1
;;
(--without-gems=*)
export rvm_without_gems="${token#--without-gems=}"
;;
(--path)
rvm_path="$1"
shift
;;
(--version)
rvm_path="${PWD%%+(\/)}"
__rvm_version
unset rvm_path
exit
;;
(--debug)
export rvm_debug_flag=1
set -o verbose
;;
(--trace)
set -o xtrace
export rvm_trace_flag=1
echo "$@"
env | GREP_OPTIONS="" \grep '^rvm_'
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
;;
(--help)
install_usage
exit 0
;;
(*)
echo "Unrecognized option: $token"
install_usage
exit 1
;;
esac
done
if [[ -n "${DESTDIR}" ]]
then
rvm_prefix="${DESTDIR}"
fi
\${LINENO} > "
determine_install_path
determine_install_or_upgrade
if [[ -z "${rvm_path:-}" ]]
then
echo "ERROR: rvm_path is empty, halting installation."
exit 1
fi
export rvm_prefix rvm_path rvm_debug_flag rvm_trace_flag
create_install_paths
print_install_header
configure_installation
cleanse_old_entities
install_rvm_files
install_rvm_hooks
ensure_scripts_are_executable
setup_configuration_files
install_binscripts
install_gemsets
install_patchsets
cleanse_old_environments
migrate_old_gemsets
migrate_defaults
correct_binary_permissions
install_man_pages
root_canal
setup_rvmrc
setup_user_profile
record_ruby_configs
update_gemsets_install_rvm
cleanup_tmp_files
display_notes
display_thank_you
record_installation_time
1.18.14. env
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
environment_file_path="$rvm_environments_path/$(__rvm_env_string)"
# Echo the path or environment file.
if
[[ "$rvm_path_flag" == "1" || "$*" =~ "--path" ]]
then
echo "$environment_file_path"
elif
[[ "$rvm_cron_flag" == "1" || "$*" =~ "--cron" ]]
then
cat "$environment_file_path" |
GREP_OPTIONS="" \grep -Eo "[^ ]+=[^;]+" |
sed -e 's/\$PATH/'"${PATH//\//\/}"'/' -e 's/\${PATH}/'"${PATH//\//\/}"'/'
else
cat "$environment_file_path"
fi
1.18.15. match
#!/usr/bin/env bash
[[ -n "$1" && -n "$2" && -n "$(echo "$1" |
awk "/${2//\//\/}/")" ]] || exit 1
1.18.16. rvm-install
#!/usr/bin/env bash
export PS4 PATH
PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
\${LINENO} > "
set -o errtrace
if [[ "$*" =~ --trace ]] || (( ${rvm_trace_flag:-0} > 0 ))
then # Tracing, if asked for.
set -o xtrace
export rvm_trace_flag=1
fi
#Handle Solaris Hosts
if [[ "$(uname -s)" == "SunOS" ]]
then
PATH="/usr/gnu/bin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin:$PATH"
else
PATH="/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin:/usr/local/sbin:$PATH"
fi
if [[ -n "${rvm_user_path_prefix:-}" ]]
then
PATH="${rvm_user_path_prefix}:$PATH"
fi
shopt -s extglob
source "$PWD/scripts/functions/installer"
# source "$PWD/scripts/rvm"
#
# RVM Installer
#
install_setup
true ${DESTDIR:=}
# Parse RVM Installer CLI arguments.
while (( $# > 0 ))
do
token="$1"
shift
case "$token" in
(--auto)
rvm_auto_flag=1
;;
(--path)
rvm_path="$1"
shift
;;
(--version)
rvm_path="${PWD%%+(\/)}"
__rvm_version
unset rvm_path
exit
;;
(--debug)
export rvm_debug_flag=1
set -o verbose
;;
(--trace)
set -o xtrace
export rvm_trace_flag=1
echo "$@"
env | GREP_OPTIONS="" \grep '^rvm_'
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
;;
(--help)
install_usage
exit 0
;;
(*)
echo "Unrecognized option: $token"
install_usage
exit 1
;;
esac
done
if [[ -n "${DESTDIR}" ]]
then
rvm_prefix="${DESTDIR}"
fi
determine_install_path
determine_install_or_upgrade
if [[ -z "${rvm_path:-}" ]]
then
echo "ERROR: rvm_path is empty, halting installation."
\${LINENO} > "
exit 1
fi
export rvm_prefix rvm_path rvm_debug_flag rvm_trace_flag
create_install_paths
print_install_header
configure_installation
cleanse_old_entities
install_rvm_files
install_rvm_hooks
ensure_scripts_are_executable
setup_configuration_files
install_binscripts
automatic_profile_setup
install_gemsets
install_patchsets
cleanse_old_environments
migrate_old_gemsets
migrate_defaults
correct_binary_permissions
install_man_pages
root_canal
setup_rvmrc
setup_user_profile
record_ruby_configs
cleanup_tmp_files
display_thank_you
display_notes
display_requirements
1.18.17. hash
#!/usr/bin/env bash
#
#
#
#
#
#
#
#
The idea is that we emulate a hash using two methods
The first method is providing functions by sourcing this file
The second method is where this script is called directly,
we then provide functionality of a file based hash
if [[ "$rvm_trace_flag" -eq 2 ]] ; then set -x ; export rvm_trace_flag ; fi
[[ -z "${ZSH_VERSION:-}" ]] ; array_start=$?
hash()
{
hash_name=$1 ; hash_key=$2 ; hash_value=$3
eval "_hash_${hash_name}_keys=\${_hash_${hash_name}_keys:-()} ; _hash_${hash_name}_values=\${_hash_${hash_name}_values:()}"
if [[ -z "$hash_value" ]] ; then
eval "length=\${#_hash_${hash_name}_keys[@]}"
for (( index=$__array_start ; index < $length; index++ )) ; do
eval "key=\"\${_hash_${hash_name}_keys[$index]}\""
if [[ "$hash_key" == "$key" ]] ; then
eval "echo -n \${_hash_${hash_name}_values[$index]}"
break
fi
done
else
eval "index=\$((\${#_hash_${hash_name}_keys[*]} + $__array_start))"
eval "_hash_${hash_name}_keys[$index]=\"$hash_key\""
eval "_hash_${hash_name}_values[$index]=\"$hash_value\""
fi
}
1.18.18. version
#!/usr/bin/env bash
__rvm_meta()
{
rvm_meta_author="Wayne E. Seguin"
rvm_meta_author_email="[email protected]"
rvm_meta_authors=(
"Wayne E. Seguin <[email protected]>"
"Michal Papis <[email protected]>"
)
rvm_meta_website="https://rvm.io/"
rvm_meta_version="${rvm_version}"
}
__rvm_version()
{
__rvm_meta
typeset IFS release
IFS=':'
rvm_meta_authors="${rvm_meta_authors[*]}"
rvm_meta_authors="${rvm_meta_authors//:/, }"
echo -e "\nrvm ${rvm_meta_version} by ${rvm_meta_authors} [${rvm_meta_website}]\n"
}
1.18.19. pkg
#!/usr/bin/env bash
if (( ${rvm_trace_flag:=0} == 2 ))
then
set -x
export rvm_trace_flag
fi
rvm_base_except="selector"
source
source
source
source
"$rvm_scripts_path/base"
"$rvm_scripts_path/functions/build"
"$rvm_scripts_path/functions/db"
"$rvm_scripts_path/functions/pkg"
__rvm_setup_compile_environment
set +o errexit
# Tools to make managing ruby dependencies inside of rvm easier.
args=($*)
action="${args[0]:-""}"
library="${args[1]:-""}"
args="$(echo ${args[@]:2})"
if [[ -n "$library" ]]
then
case $library in
readline|iconv|curl|openssl|zlib|autoconf|ncurses|pkgconfig|gettext|glib|mono|llvm|libxml2|libxslt|libyaml)
${library}
;;
ree_dependencies)
for i in zlib ncurses readline openssl iconv; do
${i}
reset
done
;;
*)
rvm_error "Package '${library}' is unknown."
;;
esac
exit $?
else
rvm_log "\nUsage:\n 'rvm pkg {install,uninstall}
{readline,iconv,curl,openssl,zlib,autoconf,ncurses,pkgconfig,gettext,glib,mono,llvm,libxml2,libxslt,libyaml}'\n
'ree_dependencies' installs zlib, ncurses, readline, openssl and iconv in this order.\n
still need to add ' --with-readline-dir=\$rvm_usr_path --with-iconv-dir=\$rvm_usr_path --with-zlib-dir=\$rvm_usr_path -with-openssl-dir=\$rvm_usr_path' to 'rvm install ree'\n"
exit 1
fi
1.18.20. md5
#!/usr/bin/env bash
variable_is_nonempty()
{
typeset _variable
_variable="${1:-}"
if [[ -n "${_variable}" ]]
then
eval "[[ -n \"\${${_variable}:-}\" ]]" || return $?
else
fail "Cannot check if variable is nonempty; no variable was given."
fi
}
command_exists()
{
typeset _name
_name="${1:-}"
if variable_is_nonempty _name
then
builtin command -v "${_name}" > /dev/null 2>&1 || return 1
else
fail "Cannot test if command exists; no command name was given."
fi
}
if (( ${rvm_trace_flag:=0} == 2 ))
then
set -x
export rvm_trace_flag
fi
_archive="${1}"
shift || fail "archive name not given in first param"
md5="${1}"
shift || fail "md5 value not given in second param"
# Swiped from BDSM
if command_exists md5
then
archive_md5=$(md5 -q "${_archive}")
elif command_exists md5sum
then
archive_md5="$(md5sum "${_archive}")"
archive_md5="${archive_md5%% *}"
else
for _path in /usr/gnu/bin /sbin /bin /usr/bin /usr/sbin
do
if [[ -x "${_path}/md5" ]]
then
archive_md5=$(${_path}/md5 -q "${_archive}")
elif [[ -x "${_path}/md5sum" ]]
then
archive_md5="$(${_path}/md5sum "${_archive}")"
archive_md5="${archive_md5%% *}"
fi
done
fi
[[ "${archive_md5}" == "${md5}" ]] || exit $?
1.18.21. rvm
#!/usr/bin/env bash
# rvm : Ruby enVironment Manager
# https://rvm.io
# https://github.com/wayneeseguin/rvm
# Do not allow sourcing RVM in `sh` - it's not supported
# return 0 to exit from sourcing this script without breaking sh
[[ ":$SHELLOPTS:" =~ ":posix:" ]] && return 0 || true
# TODO: Alter the variable names to make sense
\export HOME rvm_prefix rvm_user_install_flag rvm_path
HOME="${HOME%%+(\/)}" # Remove trailing slashes if they exist on HOME
: rvm_stored_umask:${rvm_stored_umask:=$(umask)}
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
for rvmrc in "${rvm_rvmrc_files[@]}"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "
Error:
$rvmrc is for rvm settings only.
rvm CLI may NOT be called from within $rvmrc.
Skipping the loading of $rvmrc"
return 1
else
source "$rvmrc"
fi
fi
done
unset rvm_rvmrc_files
fi
# detect rvm_path if not set
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 ))
then
if (( ${rvm_user_install_flag:-0} == 0 ))
then
rvm_user_install_flag=0
rvm_prefix="/usr/local"
rvm_path="${rvm_prefix}/rvm"
else
rvm_user_install_flag=1
rvm_prefix="$HOME"
rvm_path="${rvm_prefix}/.rvm"
fi
else
if [[ -d "$HOME/.rvm" && -s "$HOME/.rvm/scripts/rvm" ]]
then
rvm_user_install_flag=1
rvm_prefix="$HOME"
rvm_path="${rvm_prefix}/.rvm"
else
rvm_user_install_flag=0
rvm_prefix="/usr/local"
rvm_path="${rvm_prefix}/rvm"
fi
fi
else
# remove trailing slashes, btw. %%/ <- does not work as expected
rvm_path="${rvm_path%%+(\/)}"
fi
# guess rvm_prefix if not set
if [[ -z "${rvm_prefix}" ]]
then
rvm_prefix=$( dirname $rvm_path )
fi
# guess rvm_user_install_flag if not set
if [[ -z "${rvm_user_install_flag}" ]]
then
if [[ "${rvm_prefix}" == "${HOME}" ]]
then
rvm_user_install_flag=1
else
rvm_user_install_flag=0
fi
fi
export rvm_loaded_flag
if [[ -n "${BASH_VERSION:-}" || -n "${ZSH_VERSION:-}" ]] &&
typeset -f rvm >/dev/null 2>&1
then
rvm_loaded_flag=1
else
rvm_loaded_flag=0
fi
if (( ${rvm_loaded_flag:=0} == 0 )) || (( ${rvm_reload_flag:=0} == 1 ))
then
if [[ -n "${rvm_path}" && -d "$rvm_path" ]]
then
true ${rvm_scripts_path:="$rvm_path/scripts"}
if [[ -f "$rvm_scripts_path/base" ]]
then
source "$rvm_scripts_path/base"
else
printf "%b" "WARNING:
Could not source '$rvm_scripts_path/base' as file does not exist.
RVM will likely not work as expected.\n"
fi
__rvm_ensure_is_a_function
__rvm_setup
export rvm_version
rvm_version="$(cat "$rvm_path/VERSION") ($(cat "$rvm_path/RELEASE" 2>/dev/null))"
alias rvm-restart="rvm_reload_flag=1 source '${rvm_scripts_path:-${rvm_path}/scripts}/rvm'"
if ! builtin command -v ruby >/dev/null 2>&1 ||
builtin command -v ruby | GREP_OPTIONS="" \grep -v "${rvm_path}" >/dev/null ||
builtin command -v ruby | GREP_OPTIONS="" \grep "${rvm_path}/bin/ruby$" >/dev/null
then
if [[ -s "$rvm_environments_path/default" ]]
then
source "$rvm_environments_path/default"
elif [[ -s "$rvm_path/environments/default" ]]
then
source "$rvm_path/environments/default"
fi
fi
# Makes sure rvm_bin_path is in PATH atleast once.
__rvm_conditionally_add_bin_path
if (( ${rvm_reload_flag:=0} == 1 ))
then
[[ "${rvm_auto_reload_flag:-0}" == 2 ]] || printf "%b" 'RVM reloaded!\n'
# make sure we clean env on reload
__rvm_env_loaded=1
unset __rvm_project_rvmrc_lock
fi
rvm_loaded_flag=1
else
printf "%b" "\n\$rvm_path ($rvm_path) does not exist."
fi
unset rvm_prefix_needs_trailing_slash rvm_gems_cache_path \
rvm_gems_path rvm_project_rvmrc_default rvm_gemset_separator rvm_reload_flag
else
source "${rvm_scripts_path:="$rvm_path/scripts"}/initialize"
__rvm_setup
fi
if [[ -t 0 && ${rvm_project_rvmrc:-1} -gt 0 ]] &&
rvm_is_a_shell_function no_warning &&
! __function_on_stack __rvm_project_rvmrc &&
typeset -f __rvm_project_rvmrc >/dev/null 2>&1
then
# Reload the rvmrc, use promptless ensuring shell processes does not
# prompt if .rvmrc trust value is not stored.
rvm_promptless=1 __rvm_project_rvmrc
rvm_hook=after_cd
source "${rvm_scripts_path:-${rvm_path}/scripts}/hook"
fi
__rvm_teardown
1.18.22. aliases
alias
alias
alias
alias
rubydo="rvm ruby"
gemdo="rvm gem"
rakedo="rvm rake"
multiruby="rvm ruby"
1.18.23. default
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
rvm_ruby_gem_home="${rvm_ruby_gem_home:-$GEM_HOME}"
if [[ ! -d "$rvm_ruby_gem_home" ]] && builtin command -v gem > /dev/null 2>&1; then rvm_ruby_gem_home="$(gem env home)" ; fi
usage()
{
printf "%b" "
Usage:
rvm default [ruby] [environment_id]
Action:
{import,export,create,copy,empty,delete,name,dir,list,gemdir,install,pristine,clear,use,update,globalcache}
Description:
Commands for working with and manipulating gemsets within RVM.
Examples:
rvm default
rvm default
rvm default
rvm default
rvm default
rvm default
1.9.2
list 1.9.2
1.9.2 1.9.2-p0
clear 1.9.2
clear
#
#
#
#
#
#
*uses* the default ruby
Sets the 'global' default to 1.9.2
displays the environment_id for the current 1.9.2 default
sets the default for 'rvm 1.9.2' to p0
clears the set default for 1.9.2
removes the current global default
"
}
default_list()
{
:
}
default_clear()
{
:
}
args=($*)
action="${args[0]}"
args=${args[@]:1}
if [[ "list" == "$action" ]] ; then
default_list
elif [[ "clear" == "$action" ]] ; then
default_clear
elif [[ "help" == "$action" ]] ; then
usage ; exit 0
else
usage ; exit 1
fi
exit $?
1.18.24. notes
#!/usr/bin/env bash
if ! typeset -f rvm_pretty_print >/dev/null 2>&1
then source "${rvm_scripts_path:-"$rvm_path/scripts"}/functions/logging"
fi
if [[ "$1" == "initial" ]]
then
notes_type=Upgrade
PAGER=cat
new_notes()
{
typeset file
file="$rvm_path/config/displayed-notes.txt"
rm -f "${file}"
tee "${file}" > /dev/null
}
elif [[ "$1" == "upgrade" ]]
then
notes_type=Upgrade
PAGER=cat
new_notes()
{
typeset file
file="$rvm_path/config/displayed-notes.txt"
touch "${file}"
tee "${file}.new" | (
diff --normal - "${file}" && \
printf " * No new notes to display.\n" >&2 || true
) | sed '/^[^<]/ d ; s/^< //'
mv -f "${file}.new" "${file}"
}
else
notes_type=Installation
new_notes()
{
cat
}
fi
if [[ "$1" == "upgrade" ]]
then
printf "%b" "
$notes_type Notes:
"
fi
# this block groups generated and static notes,
# to add generated msgs put them bellow in code
# for general messages put them in help/upgrade-notes.txt
{
if [[ -z "$1" ]]
then
printf "%b" "
$notes_type Notes:
"
fi
if [[ "$rvm_path" == "/usr/local/rvm" ]] || (( UID == 0 ))
then
printf "%b" "
* Please do NOT forget to add your users to the 'rvm' group.
The installer no longer auto-adds root or users to the rvm group. Admins must do this.
Also, please note that group memberships are ONLY evaluated at login time.
This means that users must log out then back in before group membership takes effect!
"
fi
: \
rvm_scripts_path:${rvm_scripts_path:-$rvm_path/scripts}:
cat "$rvm_path/help/upgrade-notes.txt" | sed \
-e "s/\${SHELL}/${SHELL//\//\/}/g" \
-e "s/\${rvm_scripts_path}/${rvm_scripts_path//\//\/}/g"
printf "\n"
if [[ -f /etc/profile.d/rvm.sh ]] &&
! GREP_OPTIONS="" \grep rvm_stored_umask /etc/profile.d/rvm.sh >/dev/null
then
printf "%b" "
* WARNING: your RVM loading script \`/etc/profile.d/rvm.sh\` is deprecated
and causes you to have \`umask g+w\` set in your shell,
run \`rvm get head --auto\` again to fix your scripts.
"
fi
if [[ "$rvm_path" == "/usr/share/ruby-rvm" ]]
then
printf "%b" "
* WARNING: You are using apt-get broken RVM, you should now:
sudo apt-get --purge remove ruby-rvm
sudo rm -rf /usr/share/ruby-rvm /etc/rvmrc /etc/profile.d/rvm.sh
open new terminal and validate environment is clean from old rvm settings:
env | GREP_OPTIONS="" \grep rvm
install RVM:
curl -L get.rvm.io | bash -s stable
"
fi
if [[ -n "${RUBYOPT:-""}" ]]
then
printf "%b" "
* WARNING: You have RUBYOPT set in your current environment.
This may cause rubies to not work as you expect them to as it is not supported
by all of them If errors show up, please try unsetting RUBYOPT first.
"
fi
if [[ -f ~/.profile ]] && ! [[ "$rvm_path" == "/usr/local/rvm" || $UID == 0 ]]
then
printf "%b" "
* WARNING: You're using ~/.profile, make sure you load it,
add the following line to ~/.bash_profile if it exists
otherwise add it to ~/.bash_login:
source ~/.profile
"
fi
if [[ -n "${ZSH_VERSION:-}" ]] &&
(( 65536 * ${ZSH_VERSION:0:1} + 256 * ${ZSH_VERSION:2:1} + ${ZSH_VERSION:4} != 262924 ))
then
printf "%b" "
* WARNING: ZSH 4.3.12 is recommended, you have $ZSH_VERSION.
"
fi
if [[ -n "${GEM_HOME:-}" ]] && ! [[ "${GEM_HOME}" =~ "$rvm_path/" ]]
then
printf "%b" "
* WARNING: you have GEM_HOME=\"${GEM_HOME}\" this is conflicting with RVM, make sure to:
unset GEM_HOME
"
fi
} | new_notes | eval "${PAGER:-cat}"
printf "%b" \
"
# RVM: Shell scripts enabling management of multiple ruby environments.
# RTFM: https://rvm.io/
# HELP: http://webchat.freenode.net/?channels=rvm (#rvm on irc.freenode.net)
# Cheatsheet: http://cheat.errtheblog.com/s/rvm/
# Screencast: http://screencasts.org/episodes/how-to-use-rvm
"
rvm_log "
# In case of any issues read output of 'rvm requirements' and/or 'rvm notes'
"
1.18.25. migrate
#!/usr/bin/env bash
unset GREP_OPTIONS
source "$rvm_scripts_path/base"
usage()
{
printf "%b" "
Usage:
rvm migrate {source-ruby} {destination-ruby}
Description:
Moves all gemsets from {source-ruby} ruby to {destination-ruby}.
" >&2
}
confirm()
{
typeset confirmation_response
printf "%b" "$1 (Y/n): "
read -r confirmation_response
[[ -z "$confirmation_response" ]] ||
echo "$confirmation_response" | GREP_OPTIONS="" \grep -i '^y' >/dev/null 2>&1
}
die_with_error()
{
rvm_error "$1"
exit "${2:-1}"
}
expand_ruby_name()
{
"$rvm_scripts_path/tools" strings "$1" | awk -F"${rvm_gemset_separator:-"@"}" '{print $1}'
}
migrate_rubies()
{
typeset origin_gemset destination_gemset gemset_name migrate_ruby_name \
migrate_alias_name migrate_new_alias_name binaries origin_wrappers_path \
full_bin_path expanded_symlink linked_binary_name new_wrapper_destination
expanded_source="$(expand_ruby_name "$source_ruby")"
expanded_destination="$(expand_ruby_name "$destination_ruby")"
if [[ -z "$expanded_source" ]]
then
die_with_error "Could not expand source ruby '$source_ruby'"
elif [[ -z "$expanded_destination" ]]
then
die_with_error "Could not expand destination ruby '$destination_ruby'"
elif [[ "$expanded_destination" == "$expanded_source" ]]
then
die_with_error "Source and Destination Ruby are the same ($expanded_destination)"
elif [[ ! -d "$rvm_rubies_path/$expanded_source" ]]
then
die_with_error "Ruby '$expanded_source' is not installed - please install it first."
elif [[ ! -d "$rvm_rubies_path/$expanded_destination" ]]
then
die_with_error "Ruby '$expanded_destination' is not installed - please install it first."
fi
echo "Are you sure you wish to MOVE gems from $expanded_source to $expanded_destination?"
confirm "This will overwrite existing gems in $expanded_destination and remove them from $expanded_source" || return 1
echo "Moving gemsets..."
while read -r origin_gemset
do
[[ "$origin_gemset" == "$expanded_source" || "$origin_gemset" == "${expanded_source}${rvm_gemset_separator:-"@"}"* ]] ||
continue
destination_gemset="$expanded_destination"
case "$origin_gemset" in
*${rvm_gemset_separator:-@}*)
gemset_name="${origin_gemset/*${rvm_gemset_separator:-"@"}/}"
;;
esac
if [[ -n "$gemset_name" ]]
then
destination_gemset="${destination_gemset}${rvm_gemset_separator:-"@"}${gemset_name}"
fi
echo "Moving $origin_gemset to $destination_gemset"
__rvm_rm_rf "${rvm_gems_path:-"$rvm_path/gems"}/$destination_gemset"
result="$?"
[[ $result -gt 0 ]] && die_with_error "Unable to remove gem directory '${rvm_gems_path:"$rvm_path/gems"}/$destination_gemset'" "$result"
mv "${rvm_gems_path:-"$rvm_path/gems"}/$origin_gemset" "${rvm_gems_path:-"$rvm_path/gems"}/$destination_gemset"
result="$?"
[[ $result -gt 0 ]] && die_with_error "Unable to move '${rvm_gems_path:-"$rvm_path/gems"}/$origin_gemset' to
'${rvm_gems_path:-"$rvm_path/gems"}/$destination_gemset'" "$result"
__rvm_run_with_env "gemset.pristine" "$destination_gemset" "rvm gemset pristine" "Making gemset $destination_gemset
pristine."
done < <("$rvm_scripts_path/list" gemsets strings | GREP_OPTIONS="" \grep "^$expanded_source")
if confirm 'Do you wish to move over aliases?'
then
while read -r alias_pair
do
migrate_ruby_name="${alias_pair/*=/}"
migrate_alias_name="${alias_pair/=*/}"
if [[ "$migrate_ruby_name" == "$expanded_source" || \
"$migrate_ruby_name" == "${expanded_source}${rvm_gemset_separator:-"@"}"* ]]
then
migrate_new_alias_name="${migrate_ruby_name/$expanded_source/$expanded_destination}"
echo "Updating alias $migrate_alias_name to point to $migrate_new_alias_name"
"$rvm_scripts_path/alias" delete "$migrate_alias_name" >/dev/null 2>&1
"$rvm_scripts_path/alias" create "$migrate_alias_name" "$migrate_new_alias_name" >/dev/null 2>&1
fi
done < "$rvm_path/config/alias"
fi
if confirm "Do you wish to move over wrappers?"
then
origin_wrappers_path="$rvm_wrappers_path/$expanded_source"
binaries=($(cd "${rvm_bin_path}" ; find . -maxdepth 1 -mindepth 1 -type f))
for binary_name in "${binaries[@]//.\/}"
do
full_bin_path="${rvm_bin_path}/$binary_name"
[[ -L "$full_bin_path" ]] || continue
expanded_symlink="$(readlink "$full_bin_path")"
[[ "$expanded_symlink" == "$origin_wrappers_path/"* ]] || continue
linked_binary_name="$(basename "$expanded_symlink")"
[[ "$binary_name" == "$linked_binary_name-$expanded_source" || "$binary_name" == "$expanded_source" ]] && continue
new_wrapper_destination="${expanded_symlink/$expanded_source/$expanded_destination}"
ln -sf "$new_wrapper_destination" "$full_bin_path"
done
fi
if confirm "Do you also wish to completely remove $expanded_source (inc. archive)?"
then
__rvm_run_with_env "rvm.remove" "$expanded_source" "rvm remove $expanded_source --archive --gems"
fi
echo "Successfully migrated $expanded_source to $expanded_destination"
}
args=($*)
source_ruby="${args[0]}"
destination_ruby="${args[1]}"
args="$(echo ${args[@]:2})" # Strip trailing / leading / extra spacing.
if [[ -z "$source_ruby" || -z "$destination_ruby" ]]; then
usage ; exit 1
fi
source_ruby="$1"; shift
destination_ruby="$1"; shift
migrate_rubies
1.18.26. manage
#!/usr/bin/env bash
sys=$( uname -s )
if [[ "${sys}" == AIX ]]
then
name_opt=-name
else
name_opt=-iname
fi
original_ruby_version=${rvm_ruby_version:-""}
original_ruby_string=${rvm_ruby_string:-""}
source
source
source
source
source
source
source
"$rvm_scripts_path/base"
"$rvm_scripts_path/patches"
"$rvm_scripts_path/functions/build"
"$rvm_scripts_path/functions/pkg"
"$rvm_scripts_path/functions/irbrc"
"$rvm_scripts_path/functions/db"
"$rvm_scripts_path/functions/manage/base"
unset RUBYLIB RUBYOPT # Sanity check.
args=($*)
action="${args[0]:-""}"
rubies_string="${args[1]:-""}"
args="$(echo ${args[@]:2})" # Strip trailing / leading / extra spacing.
binaries=()
__rvm_manage_rubies
exit $?
# located in scripts/functions/manage/base
1.18.27. repair
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
usage()
{
printf "%b" "
Usage:
rvm repair [option]
Options:
wrappers
symlinks
environments
archives
gemsets
all
-
Repair
Repair
Repair
Repair
Repair
Repair
wrappers
symlinks
environments
archives
gemsets
all of the above
"
}
repair_gemsets()
{
typeset directory directories
rvm_log "Removing gemsets missing names or interpreters."
(
builtin cd "${rvm_gems_path:-"rvm_path/gems"}"
directories=(
$( find . -mindepth 1 -maxdepth 1 -type d | GREP_OPTIONS="" \grep '@$' )
$( find . -mindepth 1 -maxdepth 1 -type d | GREP_OPTIONS="" \grep '^./@')
)
for directory in "${directories[@]//.\/}"
do
__rvm_rm_rf "./$directory/"
done
)
rvm_log "Gemsets repaired."
return 0
}
repair_wrappers()
{
typeset wrapper_ruby_name
rvm_log "Regenerating all wrappers..."
while read -r wrapper_ruby_name
do
rvm_log "Regenerating wrappers for $wrapper_ruby_name"
__rvm_run "wrappers.regenerate" "\"$rvm_scripts_path/wrapper\" '$wrapper_ruby_name'"
done < <("$rvm_scripts_path/list" gemsets strings)
rvm_log "Wrappers regenerated"
return 0
}
# Removes stale symlinks in $rvm_bin_path, likely
# related to wrappers.
repair_symlinks()
{
rvm_log "Repairing symlinks..."
(
builtin cd "${rvm_bin_path}"
for executable_name in $(\find \. -type l)
do
if [[ -e "$executable_name" || \
"$(readlink "$executable_name")" != "$rvm_wrappers_path/"* ]]
then
continue
fi
if [[ -f "$executable_name" ]]
then
rvm_log "removing stale symlink from $(basename "$executable_name")"
\rm -f "$executable_name"
fi
done
)
rvm_log "Symlinks repaired"
}
# Regenerates each symlink file.
repair_environments()
{
typeset environment_name environments
rvm_log "Regenerating environments..."
environments=($(builtin cd "$rvm_environments_path" ; find . -maxdepth 1 -mindepth 1 -type f))
for environment_name in "${environments[@]//.\/}"
do
[[ -L "$rvm_environments_path/$environment_name" ]] && continue
rvm_log "Regenerating environment file for '$environment_name'"
[[ -f "$rvm_environments_path/$environment_name" ]] && \rm -f "$rvm_environments_path/$environment_name"
(
source "$rvm_scripts_path/base"
__rvm_become "$environment_name"
__rvm_ensure_has_environment_files
)
done
rvm_log "Environments regenerated"
}
# Removes archives that have incorrect md5 sums.
repair_archives()
{
typeset archive_file archives stored_md5sum
rvm_log "Repairing archives..."
archives=($(builtin cd "${rvm_archives_path}" ; find . -maxdepth 1 -mindepth 1 -type f))
for archive_file in "${archives[@]//.\/}"
do
[[ -f "${rvm_archives_path}/$archive_file" ]] || continue
stored_md5sum="$("$rvm_scripts_path/db" "$rvm_path/config/md5" "$archive_file" | head -n1)"
if [[ -z "$stored_md5sum" ]]
then
stored_md5sum="$("$rvm_scripts_path/db" "$rvm_user_path/md5" "$archive_file" | head -n1)"
fi
if [[ -n "$stored_md5sum" ]]
then
if ! "$rvm_scripts_path/md5" "${rvm_archives_path}/$archive_file" "$stored_md5sum"
then
rvm_log "Removing archive for '$archive_file' - Incorrect md5 checksum."
__rvm_rm_rf "${rvm_archives_path}/$archive_file"
fi
fi
done
rvm_log "Archives repaired"
return 0
}
repair_all()
{
repair_symlinks
repair_archives
repair_environments
repair_wrappers
return 0
}
args=($*)
action="${args[$__array_start]}"
args[$__array_start]=""
args=(${args[@]})
if [[ -z "$action" ]]
then
usage
exit $?
fi
case "$action" in
all)
repair_all
symlinks)
repair_symlinks
gemsets)
repair_gemsets
environments) repair_environments
archives)
repair_archives
wrappers)
repair_wrappers
help)
usage
*)
usage >&2 ; exit 1
esac
exit $?
;;
;;
;;
;;
;;
;;
;;
;;
1.18.28. initialize
#!/usr/bin/env bash
: rvm_trace_flag:${rvm_trace_flag:=0}
if (( rvm_trace_flag > 0 ))
then
set -o xtrace
# set -o errexit
if [[ -z "${ZSH_VERSION:-}" ]]
then
# set -o errtrace
# set -o pipefail
export PS4
PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
\${LINENO} > "
fi
elif [[ ${rvm_debug_flag:-0} > 0 ]]
then
rvm_debug_flag=0
fi
# Set shell options that RVM cannot live without,
# see __rvm_setup and __rvm_teardown for further settings.
if [[ -n "${BASH_VERSION:-}" ]]
then
shopt -s extglob
elif [[ -n "${ZSH_VERSION:-}" ]]
then
setopt extendedglob
setopt kshglob
setopt no_glob_subst
else
printf "%b" "What the heck kind of shell are you running here???\n"
fi
export __rvm_env_loaded
# set env loaded flag if not yet set
: __rvm_env_loaded:${__rvm_env_loaded:=0}:
# increase load count counter
: __rvm_env_loaded:$(( __rvm_env_loaded+=1 )):
# load only if not yet loaded or first time loading
if [[ -z "${rvm_tmp_path:-}" ]] || (( __rvm_env_loaded == 1 ))
then
if typeset -f __rvm_cleanse_variables >/dev/null 2>&1
then
__rvm_cleanse_variables
fi
# Ensure that /etc/rvmrc and $HOME/.rvmrc values take precedence.
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
rvm_stored_umask=$(umask)
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
for rvmrc in "${rvm_rvmrc_files[@]}"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "
Error:
$rvmrc is for rvm settings only.
rvm CLI may NOT be called from within $rvmrc.
Skipping the loading of $rvmrc"
return 1
else
source "$rvmrc"
fi
fi
done
unset rvm_rvmrc_files
fi
export rvm_path
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 )) && [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
elif [[ -d "${HOME}/.rvm" ]]
then rvm_path="${HOME}/.rvm"
elif [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
else echo "Can't find rvm install!" 1>&2 ; exit 1
fi
fi
true ${rvm_scripts_path:="$rvm_path/scripts"}
#
# Setup RVM Environment variables. Each RVM internal path is intended to be
# configurable by the end users for whatever their needs may be.
# They should be set in /etc/rvmrc and then $HOME/.rvmrc
#
if [[ -z "${rvm_user_install_flag:-}" ]]
then
export rvm_user_install_flag rvm_man_path
if (( UID == 0 )) ||
[[ -n "${rvm_prefix:-}" && "${rvm_prefix:-}" != "${HOME}" ]]
then
true "${rvm_man_path:="${rvm_prefix}/share/man"}"
rvm_user_install_flag=0
else
rvm_user_install_flag=1
fi
fi
: \
rvm_bin_path:${rvm_bin_path:="$rvm_path/bin"} \
rvm_man_path:${rvm_man_path:="$rvm_path/man"} \
rvm_archives_path:${rvm_archives_path:="$rvm_path/archives"} \
rvm_docs_path:${rvm_docs_path:="$rvm_path/docs"} \
rvm_environments_path:${rvm_environments_path:="$rvm_path/environments"} \
rvm_examples_path:${rvm_examples_path:="$rvm_path/examples"} \
rvm_gems_path:${rvm_gems_path:="$rvm_path/gems"} \
rvm_gemsets_path:${rvm_gemsets_path:="$rvm_path/gemsets"} \
rvm_help_path:${rvm_help_path:="$rvm_path/help"} \
rvm_hooks_path:${rvm_hooks_path:="$rvm_path/hooks"} \
rvm_lib_path:${rvm_lib_path:="$rvm_path/lib"} \
rvm_log_path:${rvm_log_path:="$rvm_path/log"} \
rvm_patches_path:${rvm_patches_path:="$rvm_path/patches"} \
rvm_repos_path:${rvm_repos_path:="$rvm_path/repos"} \
rvm_rubies_path:${rvm_rubies_path:="$rvm_path/rubies"} \
rvm_externals_path:${rvm_externals_path:="$rvm_path/externals"} \
rvm_rubygems_path:${rvm_rubygems_path:="$rvm_path/rubygems"} \
rvm_src_path:${rvm_src_path:="$rvm_path/src"} \
rvm_tmp_path:${rvm_tmp_path:="$rvm_path/tmp"} \
rvm_user_path:${rvm_user_path:="$rvm_path/user"} \
rvm_usr_path:${rvm_usr_path:="$rvm_path/usr"} \
rvm_wrappers_path:${rvm_wrappers_path:="$rvm_path/wrappers"} \
rvm_verbose_flag:${rvm_verbose_flag:=0} \
rvm_debug_flag:${rvm_debug_flag:=0} \
rvm_gems_cache_path:${rvm_gems_cache_path:=${rvm_gems_path:-"$rvm_path/gems"}/cache}
export rvm_action rvm_alias_expanded rvm_archive_extension rvm_archives_path rvm_bin_flag rvm_bin_path rvm_configure_flags
rvm_debug_flag rvm_default_flag rvm_delete_flag rvm_docs_path rvm_docs_type rvm_dump_environment_flag rvm_environments_path
rvm_error_message rvm_examples_path rvm_expanding_aliases rvm_file_name rvm_gemdir_flag rvm_gems_cache_path rvm_gems_path
rvm_gemset_name rvm_gemset_separator rvm_gemsets_path rvm_gemstone_package_file rvm_gemstone_url rvm_head_flag rvm_help_path
rvm_hook rvm_hooks_path rvm_install_args rvm_install_on_use_flag rvm_lib_path rvm_llvm_flag rvm_loaded_flag rvm_log_path
rvm_make_flags rvm_niceness rvm_nightly_flag rvm_only_path_flag rvm_parse_break rvm_patch_names rvm_patch_original_pwd
rvm_patches_path rvm_path rvm_pretty_print_flag rvm_proxy rvm_quiet_flag rvm_ree_options rvm_reload_flag rvm_remove_flag
rvm_repos_path rvm_rubies_path rvm_ruby_alias rvm_ruby_aliases rvm_ruby_args rvm_ruby_binary rvm_ruby_bits
rvm_ruby_configure rvm_ruby_file rvm_ruby_gem_home rvm_ruby_gem_path rvm_ruby_global_gems_path rvm_ruby_home
rvm_ruby_interpreter rvm_ruby_irbrc rvm_ruby_load_path rvm_ruby_major_version rvm_ruby_make rvm_ruby_make_install
rvm_ruby_minor_version rvm_ruby_mode rvm_ruby_name rvm_ruby_package_file rvm_ruby_package_name rvm_ruby_patch
rvm_ruby_patch_level rvm_ruby_release_version rvm_ruby_repo_url rvm_ruby_require rvm_ruby_revision rvm_ruby_selected_flag
rvm_ruby_sha rvm_ruby_string rvm_ruby_strings rvm_ruby_tag rvm_ruby_url rvm_ruby_user_tag rvm_ruby_version rvm_script_name
rvm_scripts_path rvm_sdk rvm_user_install_flag rvm_silent_flag rvm_src_path rvm_sticky_flag rvm_system_flag rvm_tmp_path
rvm_token rvm_trace_flag rvm_use_flag rvm_user_flag rvm_user_path rvm_usr_path rvm_verbose_flag rvm_wrapper_name
rvm_wrappers_path rvm_ruby_repo_branch rvm_man_path rvm_architectures
fi # if [[ -z "${rvm_tmp_path:-}" ]] || (( __rvm_env_loaded == 1 ))
1.18.29. info
#!/usr/bin/env bash
if [[ "$rvm_trace_flag" -eq 2 ]] ; then set -x ; export rvm_trace_flag ; fi
source "$rvm_scripts_path/base"
source "$rvm_scripts_path/version"
version_for()
{
typeset binary
binary=${1:-""}
if builtin command -v "$binary" >/dev/null ; then
$binary --version | head -n1
else
echo "not installed"
fi
return 0
}
info_system()
{
rvm_info="
system:
uname:
bash:
zsh:
"
}
\"$(uname -a)\"
\"$(command -v bash) => $(version_for bash)\"
\"$(command -v zsh) => $(version_for zsh)\"
print_part()
{
(( $1 )) || return
typeset ret
ret="$1 $2"
(( $1 == 1 )) || ret="${ret}s"
printf "$ret "
}
info_rvm()
{
typeset installed_at years months days hours minutes seconds part
rvm_info="
rvm:
version:
\"$(__rvm_version | \tr "\n" ' ' | __rvm_strip)\"
"
rvm_info="${rvm_info}
updated:
\""
installed_at="$(cat ${rvm_path}/installed.at)"
if [[ -n "${installed_at:-}" ]] && (( installed_at ))
then
seconds="$(( $(date +%s) - installed_at ))"
if (( seconds ))
then
minutes="$(( seconds / 60 % 60 ))"
hours="$(( seconds / 3600 % 24 ))"
days="$(( seconds / 86400 % 31 ))"
months="$(( seconds / 2678400 % 12 ))"
years="$(( seconds / 31536000 ))"
seconds="$(( seconds % 60 ))"
for part in year month day hour minute second
do eval "rvm_info=\"\${rvm_info}\$(print_part \${${part}s} ${part})\""
done
rvm_info="${rvm_info}ago"
else
rvm_info="${rvm_info}just now"
fi
else
rvm_info="${rvm_info}can not read installation time\n"
fi
rvm_info="${rvm_info}\"\n"
}
info_ruby()
{
[[ "$(__rvm_env_string)" == "system" ]] && return
ruby=$(builtin command -v ruby)
if [[ $? -eq 0 ]] && [[ -x "$ruby" ]] ; then full_version="$($ruby -v)" ; fi
rvm_info="
ruby:
interpreter: \"$(printf "%b" "${full_version}" | awk '{print $1}')\"
version:
\"$(printf "%b" "${full_version}" | awk '{print $2}')\"
date:
\"$(printf "%b" "${full_version}" | sed 's/^.*(\([0-9]\{4\}\(-[0-9][0-9]\)\{2\}\).*$/\1/')\"
platform:
\"$(printf "%b" "${full_version}" | sed 's/^.*\[//' | sed 's/\].*$//')\"
patchlevel:
\"$(printf "%b" "${full_version}" | sed 's/^.*(//' | sed 's/).*$//')\"
full_version: \"${full_version}\"
"
}
info_homes()
{
rvm_info="
homes:
gem:
ruby:
"
}
info_binaries()
{
rvm_info="
binaries:
ruby:
irb:
gem:
rake:
"
}
\"${GEM_HOME:-"not set"}\"
\"${MY_RUBY_HOME:-"not set"}\"
\"$(command
\"$(command
\"$(command
\"$(command
-v
-v
-v
-v
ruby)\"
irb)\"
gem)\"
rake)\"
info_environment()
{
rvm_info="
environment:
PATH:
\"${PATH:-""}\"
GEM_HOME:
\"${GEM_HOME:-""}\"
GEM_PATH:
\"${GEM_PATH:-""}\"
MY_RUBY_HOME: \"${MY_RUBY_HOME:-""}\"
IRBRC:
\"${IRBRC:-""}\"
RUBYOPT:
\"${RUBYOPT:-""}\"
gemset:
\"$(__rvm_current_gemset)\"\n
"
if [[ -n "${MAGLEV_HOME:-""}" ]] ; then
rvm_info="$rvm_info\n MAGLEV_HOME: \"$MAGLEV_HOME\""
fi
rvm_info="$rvm_info\n"
}
info_debug()
{
rvm_info="
$(__rvm_version)
$("$rvm_scripts_path/info" "$rvm_ruby_string" "" )
PATH:\n$(printf "%b" "$PATH" | awk -F":" '{print $1":"$2":"$3":"$4":"$5}' )
uname -a: $(uname -a)
permissions: $(\ls -la "$rvm_path" "$rvm_rubies_path")
"
if [[ "Darwin" == "$(uname)" ]] ; then
rvm_info="$rvm_info
uname -r: $(uname -r)
uname -m: $(uname -m)
sw_vers: $(sw_vers | \tr "\n" ',')
ARCHFLAGS: ${ARCHFLAGS:-""}
LDFLAGS: ${LDFLAGS:-""}
CFLAGS: ${CFLAGS:-""}
/Developer/SDKs/*:$(/usr/bin/basename -a /Developer/SDKs/* | \tr "\n" ',')
"
fi
for file_name in "$HOME/.bashrc" "$HOME/.bash_profile" "$HOME/.zshenv" ; do
if [[ -s "$file_name" ]] ; then
rvm_info="$rvm_info\n$file_name:\n$(GREP_OPTIONS="" \grep 'rvm' "$file_name" 2>/dev/null || true)"
fi
done
if (( ${rvm_user_install_flag:=0} == 0 ))
then
debug_files=("$rvm_path/config/alias" "$rvm_path/config/system" "$rvm_path/config/db" "/etc/rvmrc" "/etc/gemrc")
else
debug_files=("$rvm_path/config/alias" "$rvm_path/config/system" "$rvm_path/config/db" "$HOME/.rvmrc" "$HOME/.gemrc")
fi
for file_name in "${debug_files[@]}" ; do
if [[ -f "$file_name" && -s "$file_name" ]] ; then
rvm_info="$rvm_info\n$file_name \(filtered\):\n$(awk '!/assword|_key/' "$file_name" )\n"
fi
done
rvm_info="$rvm_info\ngem sources:\n$(gem sources | awk '/gems/')\n\n"
}
info_sections()
{
for section in $(printf "%b" "${sections//,/ }") ; do
rvm_info=""
"info_${section}"
printf "%b" "$rvm_info"
done
}
rvm_ruby_gem_home="${rvm_ruby_gem_home:-${GEM_HOME:-""}}"
if [[ ! -d "$rvm_ruby_gem_home" ]] && builtin command -v gem > /dev/null 2>&1; then
rvm_ruby_gem_home="$(gem env home)"
fi
rvm_info=""
args=($*)
ruby_strings="${args[$__array_start]// /}"
args[$__array_start]=""
args=(${args[@]})
sections="${args// /}"
all_sections="system rvm ruby homes binaries environment"
# TODO: Figure out what was the thought here and remove external match script
#
dependency
if "$rvm_scripts_path/match" "$all_sections debug" "${ruby_strings/,*/}" ; then
sections="$ruby_strings"
ruby_strings=""
fi
if [[ -z "${sections// /}" ]] ; then
sections="$all_sections"
fi
rvm_is_a_shell_function || true
if [[ -z "$ruby_strings" ]] ; then
printf "%b" "\n$(__rvm_env_string):\n"
info_sections
else
for ruby_string in $(printf "%b" ${ruby_strings//,/ }) ; do
__rvm_become "$ruby_string"
printf "%b" "\n$(__rvm_env_string):\n"
info_sections
done
fi
exit 0
1.18.30. set
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
__rvm_attempt_single_exec()
{
# Return if we have multiple rubies. or we're not running exec.
if (( ${#rvm_ruby_strings[@]} == 1 ))
then
__rvm_become "$rvm_ruby_strings"
__rvm_load_rvmrc
export rvm_project_rvmrc=0 rvm_ignore_rvmrc=1
exec "${args[@]}"
fi
return 1
}
__rvm_ruby_do()
{
# Return on invalid rubies.
__rvm_become "$current_set_ruby" || return 1
rvm_hook="before_do"
source "$rvm_scripts_path/hook"
if [[ -n "$rvm_json_flag" || -n "$rvm_yaml_flag" || -n "$rvm_summary_flag" ]]
then
if [[ ! -d "./log/$rvm_ruby_string/" ]]
then
mkdir -p "./log/$rvm_ruby_string/"
fi
touch "./log/$rvm_ruby_string/$action.log"
"${args[@]}" >> "./log/$rvm_ruby_string/$action.log" 2>&1
else
if (( ${rvm_verbose_flag:-0} > 0 ))
then
current_env="$(__rvm_env_string)"
if [[ "$current_env" != "$current_set_ruby" ]]
then
current_env="$current_set_ruby ($current_env)"
fi
rvm_log "$current_env: $(ruby -v $rvm_ruby_mode | \tr "\n" ' ')\n"
unset current_env
fi
(
__rvm_load_rvmrc
export rvm_project_rvmrc=0 rvm_ignore_rvmrc=1
"${args[@]}"
)
fi
result=$?
string=$rvm_ruby_string #$(basename $rvm_ruby_gem_home)
if (( result == 0 ))
then
eval "successes=(${successes[*]} $string)"
else
eval "errors=(${errors[*]} $string)"
fi
eval "rubies=(${rubies[*]} $string)"
eval "statuses=(${statuses[*]} $result)"
unset string
rvm_hook="after_do"
source "$rvm_scripts_path/hook"
__rvm_unset_ruby_variables
}
# Output the summary in a human readable format.
__rvm_summary()
{
export successes errors statuses
summary="\nSummary:\n\n"
if [[ ${#successes[*]} -gt 0 ]]
then
if rvm_pretty_print stdout
then
summary="$summary ${rvm_notify_clr:-}${#successes[*]} successful: $(echo "${successes[*]}" | sed 's# #,
#g')${rvm_reset_clr:-}\n"
else
summary="$summary ${#successes[*]} successful: $(echo "${successes[*]}" | sed 's# #, #g')\n"
fi
fi
if [[ ${#errors[*]} -gt 0 ]] ; then
if rvm_pretty_print stdout
then
summary="$summary ${rvm_error_clr:-}${#errors[*]} errors: $(echo "${errors[*]}" | sed 's# #, #g')${rvm_reset_clr:-}\n"
else
summary="$summary ${#errors[*]} errors: $(echo "${errors[*]}" | sed 's# #, #g')\n"
fi
fi
total=${#rubies[*]}
[[ -z "${ZSH_VERSION:-}" ]] ; array_start=$?
printf "%b" "$summary" | tee -a log/summary.log
return ${#errors[*]}
}
# Output the summary in a yaml format.
__rvm_yaml()
{
export successes errors statuses
yaml="totals:\n rubies: ${#rubies[*]}\n
successes: ${#successes[*]}\n
for var in ${successes[*]} ; do yaml="$yaml\n
yaml="$yaml\nerrors:"
for var in ${errors[*]} ; do yaml="$yaml\n
yaml="$yaml\nrubies:"
total=${#rubies[*]}
errors: ${#errors[*]}\nsuccesses:"
- $var" ; done
- $var" ; done
[[ -z "${ZSH_VERSION:-}" ]] ; array_start=$?
for (( index = $array_start ; index < $total + $array_start ; index++ )) ; do
if [[ ${rvm_debug_flag:-0} -gt 0 ]] ; then
rvm_debug "${rubies[$index]}: ${statuses[$index]}"
fi
yaml="$yaml\n \"${rubies[$index]}\": ${statuses[$index]}"
done
unset index array_start
\mkdir -p log
printf "%b" "$yaml" | tee -a log/summary.yaml
return ${#errors[*]}
}
# Output the summary in a json format.
__rvm_json()
{
typeset index array_start
json="{
\"totals\": { \"rubies\": ${#rubies[*]}, \"successes\": ${#successes[*]}, \"errors\": ${#errors[*]} },
\"successful\": [$(echo \"${successes[*]}\" | sed 's# #", "#g' | sed 's#\"\"##')],
\"errors\": [$(echo \"${errors[*]}\" | sed 's# #", "#g' | sed 's#\"\"##')],
\"rubies\": { "
total=${#rubies[*]}
[[ -z "${ZSH_VERSION:-}" ]] ; array_start=$?
for (( index = $array_start ; index < $total + $array_start ; index++ )) ; do
if [[ ${rvm_debug_flag:-0} -gt 0 ]] ; then
rvm_debug "${rubies[$index]}: ${statuses[$index]}"
fi
json="$json\n
{\"${rubies[$index]}\": ${statuses[$index]}}"
if (( $index + 1 < $total + $array_start )) ; then json="$json, " ; fi
done
json="$json\n
}\n}"
if [[ ! -d log ]] ; then
mkdir -p log
fi
printf "%b" "$json" | tee -a log/summary.json
return ${#errors[*]}
}
# Loop over a set or all rvm installed rubies to perform some action.
# Record the results and report based on CLI selections.
rubies=() ; successes=() ; errors=() ; statuses=()
args=( "$@" )
action="${args[$__array_start]}"
unset args[$__array_start]
args=( "${args[@]}" )
if [[ -z "$action" ]]
then
rvm_error "Action must be specified."
exit 1
elif [[ "$action" != "do" ]]
then
rvm_error "Only 'do' action is allowed."
exit 1
fi
if [[ -z "${rvm_ruby_strings}" ]]
then
# TODO: deprecation issued on 2011.10.22, for RVM 1.9.0
rvm_warn "\`rvm do ${args[@]}\` is deprecated, use \`rvm all do ${args[@]}\` or \`rvm 1.9.2 do ${args[@]}\` instead."
fi
previous_rvm_ruby_strings="$rvm_ruby_strings"
rvm_ruby_strings=( $( __rvm_expand_ruby_string "$rvm_ruby_strings" ) ) || {
__rvm_ruby_strings_exist ${previous_rvm_ruby_strings} >/dev/null 2>/dev/null
rvm_error "Ruby ${previous_rvm_ruby_strings} is not installed."
exit 1
}
unset previous_rvm_ruby_strings
__rvm_attempt_single_exec
for current_set_ruby in ${rvm_ruby_strings[@]}
do
__rvm_ruby_do
done
if [[ -n "$rvm_summary_flag" ]] ; then __rvm_summary ; fi
if [[ -n "$rvm_yaml_flag" ]]
; then __rvm_yaml
; fi
if [[ -n "$rvm_json_flag" ]]
; then __rvm_json
; fi
rvm_hook="after_do" ; source "$rvm_scripts_path/hook"
exit ${#errors[*]}
1.18.31. override_gem
#!/usr/bin/env bash
if [[ ${rvm_leave_gem_alone:-0} -eq 0 ]]
then
function gem
{
typeset result
(
typeset rvmrc
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
for rvmrc in "${rvm_rvmrc_files[@]}"
do [[ -s "${rvmrc}" ]] && source "${rvmrc}" || true
done
unset rvm_rvmrc_files
command gem "$@"
) || result=$?
hash -r
return ${result:-0}
}
fi
1.18.32. rubygems
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
source "$rvm_scripts_path/functions/db"
result=0
__rvm_become
rubygems_remove()
{
typeset rubygems_path ruby entry
rvm_log "Removing old Rubygems files..."
if [[ "$rvm_ruby_interpreter" == "rbx" ]]
then
ruby="puts Config::CONFIG['prefix']"
elif [[ "$rvm_ruby_string" =~ ruby-1.9.3.* ]]
then
ruby="puts RbConfig::CONFIG.values_at('sitelibdir','vendorlibdir').detect { |path| File.directory?(File.join(path.to_s,
'rubygems')) }.to_s"
else
ruby="puts Config::CONFIG.values_at('sitelibdir','vendorlibdir').detect { |path| File.directory?(File.join(path.to_s,
'rubygems')) }.to_s"
fi
rubygems_path="$(ruby -rrbconfig -e "$ruby")"
# Remove common files installed by ruby gems.
entries=(
"${rubygems_path}/ubygems.rb"
"${rubygems_path}/gauntlet_rubygems.rb"
"${rubygems_path}/rbconfig/"
)
for entry in "${entries[@]}" "${rubygems_path}/rubygems"*
do
__rvm_rm_rf "$entry"
done
}
can_switch_rubygems()
{
case "$rvm_ruby_string" in
jruby*|maglev*)
return 1
;;
*)
return 0
;;
esac
}
rubygems_version_list()
{
curl -s https://api.github.com/repos/rubygems/rubygems/tags |
sed -n '/"name": / {s/^.*".*": "v\(.*\)".*$/\1/; p;}' |
sort -t. -k 1,1n -k 2,2n -k 3,3n -k 4,4n -k 5,5n
}
rubygems_master_sha()
{
curl -s "https://api.github.com/repos/rubygems/rubygems/commits?page=last&per_page=1" | sed -n '/^
"\(.*\)".*$/\1/;p;}'
}
rubygems_select_version_url()
{
case "$version" in
latest|current)
case "$rvm_ruby_string" in
ruby-1.8*|ree-1.8*)
typeset _rbv
_rbv=${rvm_ruby_version##*.}
if (( _rbv <= 5 ))
then
version=1.3.5
elif (( _rbv == 6 ))
then
version=1.3.7
fi
;;
esac
;;
esac
case "$version" in
latest|current)
version="$(__rvm_db "${rvm_ruby_string//-/_}_rubygems_version")"
version="${version:-"$(__rvm_db "${rvm_ruby_interpreter}_rubygems_version")"}"
version="${version:-"$(__rvm_db "rubygems_version")"}"
;;
"sha":/ {s/^.*".*":
esac
case "$version" in
latest-*)
version="${version#latest-}"
version="$(rubygems_version_list | GREP_OPTIONS="" \grep "^${version}\." | tail -n 1 )"
version="${version}"
;;
esac
case "${version}" in
head|master)
typeset sha
sha="$(rubygems_master_sha)"
rvm_rubygems_version="$version"
rvm_gem_package_name="rubygems-rubygems-${sha:0:7}"
rvm_gem_url="https://github.com/rubygems/rubygems/tarball/${sha}"
;;
*)
rvm_rubygems_version="$version"
rvm_gem_package_name="rubygems-${rvm_rubygems_version}"
rvm_rubygems_url=$(__rvm_db "rubygems_url")
rvm_gem_url="${rvm_rubygems_url}/${rvm_gem_package_name}.tgz"
;;
esac
}
rubygems_setup()
{
__rvm_warn_on_rubyopt
true ${rvm_ruby_selected_flag:=0}
unset RUBYOPT
if (( rvm_ruby_selected_flag == 0 ))
then
__rvm_select
fi
rubygems_select_version_url
# Sanity check... If setup.rb is missing from the rubygems source path,
# something went wrong. Cleanup, aisle 3!
if [[ ! -f "${rvm_src_path}/$rvm_gem_package_name/setup.rb" ]]
then
__rvm_rm_rf "${rvm_src_path}/$rvm_gem_package_name"
fi
if [[ ! -d "${rvm_src_path}/${rvm_gem_package_name}" ]]
then
rvm_log "Retrieving $rvm_gem_package_name"
"$rvm_scripts_path/fetch" "$rvm_gem_url" "${rvm_gem_package_name}.tgz"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source. \nHalting the installation."
return $result
fi
if [[ ! -d "${rvm_src_path}/$rvm_gem_package_name" ]]
then
\mkdir -p "${rvm_src_path}/$rvm_gem_package_name"
fi
__rvm_run "rubygems.extract" \
"gunzip < ${rvm_archives_path}/$rvm_gem_package_name.tgz | $rvm_tar_command xf - -C ${rvm_src_path}" \
"Extracting $rvm_gem_package_name ..."
fi
rubygems_remove # Remove old gems.
builtin cd "${rvm_src_path}/$rvm_gem_package_name"
__rvm_run "rubygems.install" \
"GEM_PATH=\"$GEM_PATH:${GEM_PATH%%@*}@global\" GEM_HOME=\"$GEM_HOME\" \"${rvm_ruby_binary}\"
\"${rvm_src_path}/$rvm_gem_package_name/setup.rb\"" \
"Installing $rvm_gem_package_name for ${rvm_ruby_string} ..."
result=$?
if (( result == 0 ))
then
typeset program_suffix
program_suffix="$(${rvm_ruby_binary} -rrbconfig -e "puts RbConfig::CONFIG['configure_args']")"
case "${program_suffix:-}" in
(*--program-suffix=*)
program_suffix="${program_suffix#*--program-suffix=}"
program_suffix="${program_suffix%%[\' ]*}"
__rvm_run "link.gem" "ln -s \"$rvm_ruby_home/bin/gem${program_suffix}\" \
\"$rvm_ruby_home/bin/gem\"" "$rvm_ruby_string - #linking gem${program_suffix} -> gem "
;;
esac
rvm_log "Installation of rubygems completed successfully."
else
rvm_warn "Installation of rubygems did not complete successfully."
fi
if [[ ! -z "$rvm_ruby_major_version" ]]
then
ruby_lib_gem_path="$rvm_ruby_home/lib/ruby/gems/${rvm_ruby_release_version}.${rvm_ruby_major_version}"
else
ruby_lib_gem_path="$rvm_ruby_home/lib/ruby/gems/$interpreter"
fi
# Add ruby's gem path to ruby's lib direcotry.
\mkdir -p "$(dirname $ruby_lib_gem_path)"
__rvm_rm_rf "$ruby_lib_gem_path"
if [[ -d "$rvm_ruby_gem_home" ]]
then
ln -fs "$rvm_ruby_gem_home" "$ruby_lib_gem_path"
fi
unset ruby_lib_gem_path
}
if ! builtin command -v ruby > /dev/null
then
rvm_error "'ruby' was not found, cannot install rubygems unless ruby is present (Do you have an RVM ruby installed &
selected?)"
exit 1
fi
#
# rvm rubygems X
#
args=($*)
export version
version="${args[0]}"
args="$(echo ${args[@]:1})" # Strip trailing / leading / extra spacing.
if [[ -z "$version" ]]
then
rvm_error "Usage: rvm rubygems [x.y.z|latest-x.y|latest|remove]"
exit 1
fi
if can_switch_rubygems
then
case "$version" in
remove) rubygems_remove
;;
*)
rubygems_setup
;;
esac
else
rvm_error "Rubygems version may only be set for an RVM MRI based Ruby, please select one and rerun."
result=1
fi
exit $result
1.18.33. wrapper
#!/usr/bin/env bash
default_flag="$rvm_default_flag"
# Prevent recursion
unset rvm_default_flag rvm_wrapper_name prefix
source "$rvm_scripts_path/base"
source "$rvm_scripts_path/initialize"
usage()
{
printf "%b" "
Usage:
rvm wrapper ruby_string [wrapper_prefix] [binary[ binary[ ...]]]
Binaries
ruby, gem, rake, irb, rdoc, ri, testrb
Notes
For more information, see 'rvm help wrapper'
Example
# Wrap the spec binary as 'rails3_spec' for 1.9.2@rails3
rvm wrapper 1.9.2@rails3 rails3 spec
# To create a single binary you can do the following,
user$ rvm use --create 1.8.7@ey ; gem install ey
user$ rvm wrapper 1.8.7@ey --no-prefix ey
# So that it is clear I am now in a different env,
user$ rvm 1.9.2
user$ ruby -v
ruby 1.9.2p180 (2011-02-18 revision 30909) [x86_64-darwin10.7.0]
# And we have the desired result,
user$ ey
Usage:
ey [--help] [--version] COMMAND [ARGS]
...
"
}
wrap()
{
if [[ -n "${file_name:-""}" ]]
then
mkdir -p "$(dirname "$file_name")"
rm -f "$file_name"
if (( UID == 0 ))
then # ... this stuff should not be in here...
path="${rvm_path:-"/usr/local/rvm"}"
else
path="${rvm_path:-"$HOME/.rvm"}"
fi
printf "%b" "#!/usr/bin/env bash
if [[ -s \"$path/environments/${environment_identifier}\" ]]
then
source \"$path/environments/${environment_identifier}\"
exec $binary_name \"\$@\"
else
echo \"ERROR: Missing RVM environment file: '$path/environments/${environment_identifier}'\" >&2
exit 1
fi
" > "$file_name"
if [[ -f "$file_name" ]]
then
chmod +x "$file_name"
fi
return 0
else
rvm_error "wrap() : file_name unkown variable for wrap()."
return 1
fi
}
symlink_binary()
{
# Generate the default wrapper with the given binary name.
# We first check if we can wrap the binary and if we were able to,
# we then symlink it into place.
if wrap_binary && [[ -f "$file_name" ]]
then
rm -f "$rvm_bin_path/${prefix}_${binary_name##*\/}"
ln -fs "$file_name" "$rvm_bin_path/${prefix}_${binary_name##*\/}"
fi
}
wrap_binary()
{
# We wrap when the given binary is in the path or override_check is set to one.
if [[ "$override_check" == "1" ]] || builtin command -v $binary_name > /dev/null
then
wrap
else
rvm_error "Binary '$binary_name' not found."
return 1
fi
}
# Empty ruby string: show usage and exit.
if (( $# == 0 ))
then
usage
exit 1
else
ruby_string="$1"
shift
if (( $# > 0 ))
then
prefix="$1"
shift
fi
fi
if [[ -z "$ruby_string" ]]
then
usage
exit 1
fi
binaries=($@)
override_check=0
# Default the list of binaries to those we use regularily.
if [[ ${#binaries[@]} -eq 0 ]]
then
binaries=(ruby gem irb ri rdoc rake erb testrb)
fi
# Use the correct ruby.
__rvm_become "$ruby_string" || {
rvm_error "Could not load ruby $ruby_string."
exit 3
}
__rvm_ensure_has_environment_files
environment_identifier="$(__rvm_env_string)"
# For each binary, we want to generate the wrapper / symlink
# it to the existing wrapper if needed.
for binary_name in "${binaries[@]}"
do
file_name="$rvm_wrappers_path/${environment_identifier}/${binary_name##*\/}"
if (( ${rvm_default_flag:-0} > 0 ))
then
prefix="default"
fi
if [[ ! -d "$rvm_bin_path" ]]
then
mkdir -p "$rvm_bin_path"
fi
if [[ -z "${prefix:-}" ]]
then
override_check=1
wrap_binary
# Symlink it into place.
if [[ -f "$file_name" ]]
then
if [[ "$binary_name" == "ruby" ]]
then
destination="$rvm_bin_path/$environment_identifier"
else
destination="$rvm_bin_path/${binary_name##*\/}-${environment_identifier}"
fi
rm -f "$destination"
ln -sf "$file_name" "$destination"
fi
elif [[ "--no-prefix" == "$prefix" ]]
then
override_check=1
wrap_binary
if [[ -f "$file_name" ]]
then
destination="$rvm_bin_path/${binary_name##*\/}"
if [[ -s "$destination" ]]
then
rm -f "$destination"
fi
ln -sf "$file_name" "$destination"
fi
else
symlink_binary
fi
done
exit $?
1.18.34. fetch
#!/usr/bin/env bash
rvm_base_except="selector"
source "$rvm_scripts_path/base"
result=0
# handled by teardown
__rvm_cleanup_download()
{
[[ -f "$archive" ]] && __rvm_rm_rf "$archive"
}
record_md5()
{
case "$(uname)" in
Darwin|FreeBSD)
archive_md5="$(/sbin/md5 -q "${archive}")"
;;
OpenBSD)
archive_md5="$(/bin/md5 -q "${archive}")"
;;
Linux|*)
archive_md5="$(md5sum "${archive}")"
archive_md5="${archive_md5%% *}"
;;
esac
if [[ -w "$rvm_path/config/md5" ]]
then
"$rvm_scripts_path/db" "$rvm_path/config/md5" "$archive" "$archive_md5"
else
"$rvm_scripts_path/db" "$rvm_user_path/md5" "$archive" "$archive_md5"
fi
}
builtin cd "$rvm_archives_path"
# args=($*) # Reserved for future use
if [[ -z "$1" ]] ; then
rvm_error "BUG: $0 called without an argument :/"
exit 1
fi
url="$1"; download=1 ; package_name="$2"
if ! builtin command -v curl > /dev/null ; then
rvm_error "rvm requires curl. curl was not found in your active path."
exit 1
elif [[ ! -z ${rvm_proxy} ]] ; then
fetch_command="curl -x${rvm_proxy} -f -L --create-dirs -C - " # -s for silent
else
fetch_command="curl -f -L --create-dirs -C - " # -s for silent
fi
if [[ ! -z "$package_name" ]] ; then
fetch_command="${fetch_command} -o ${package_name} "
archive="$package_name"
else
fetch_command="${fetch_command} -O "
archive=$(basename "$url")
fi
[[ ${rvm_debug_flag:-0} -gt 0 ]] && rvm_debug "Fetching $archive"
# Check first if we have the correct archive
archive_md5="$("$rvm_scripts_path/db" "$rvm_path/config/md5" "$archive" | head -n1)"
if [[ -z "$archive_md5" ]]
then
archive_md5="$("$rvm_scripts_path/db" "$rvm_user_path/md5" "$archive" | head -n1)"
fi
if [[ -e "$archive" && ! -z "$archive_md5" ]] ; then
[[ ${rvm_debug_flag:-0} -gt 0 ]] && \
rvm_debug "Found archive and its md5, testing correctness"
if ! "$rvm_scripts_path"/md5 "$rvm_archives_path/${archive}" "$archive_md5" ; then
[[ ${rvm_debug_flag:-0} -gt 0 ]] && \
rvm_debug "Archive md5 did not match, downloading"
download=1
else
[[ ${rvm_debug_flag:-0} -gt 0 ]] && \
rvm_debug "Archive md5 matched, not downloading"
download=0
result=0
fi
else
[[ ${rvm_debug_flag:-0} -gt 0 ]] && \
rvm_debug "No archive or no MD5, downloading"
download=1
fi
# try to convert the http url to a ftp url
ftp_url="$(echo "$url" | sed -e 's/http:/ftp:/')"
if [[ $download -gt 0 ]] ; then
rm -f $archive
eval $fetch_command "$url" ; result=$?
if [[ $result -gt 0 ]] ; then
retry=0
try_ftp=0
if [[ $result -eq 78 ]] ; then
rvm_error "The requested url does not exist: '$url'"
try_ftp=1
elif [[ $result -eq 22 ]] ; then
rvm_error "The requested url does not exist: '$url'"
try_ftp=1
elif [[ $result -eq 18 ]] ; then
rvm_error "Partial file. Only a part of the file was transferred. Removing partial and re-trying."
rm -f "$archive"
retry=1
elif [[ $result -eq 33 ]] ; then
[[ ${rvm_debug_flag:-0} -gt 0 ]] && \
rvm_debug "Server does not support 'range' command, removing '$archive'"
rm -f "$archive"
retry=1
else
rvm_error "There was an error, please check ${rvm_log_path}/$rvm_ruby_string/*.log. Next we'll try to fetch via http."
try_ftp=1
fi
if [[ $retry -eq 1 ]] ; then
eval $fetch_command "$url" ; result=$?
if [[ $result -gt 0 ]] ; then
rvm_error "There was an error, please check ${rvm_log_path}/$rvm_ruby_string/*.log"
else
record_md5
fi
fi
if [[ $try_ftp -eq 1 ]] ; then
rvm_log "Trying ftp:// URL instead."
eval $fetch_command "$ftp_url" ; result=$?
if [[ $result -gt 0 ]] ; then
rvm_error "There was an error, please check ${rvm_log_path}/$rvm_ruby_string/*.log"
else
record_md5
fi
fi
else
record_md5
fi
fi
exit $result
1.18.35. update
#!/usr/bin/env bash
export PS4 PATH
PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
\${LINENO} > "
set -o errtrace
if [[ "$*" =~ --trace ]] || (( ${rvm_trace_flag:-0} > 0 ))
then # Tracing, if asked for.
set -o xtrace
export rvm_trace_flag=1
fi
#Handle Solaris Hosts
if [[ "$(uname -s)" == "SunOS" ]]
then
PATH="/usr/gnu/bin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin:$PATH"
else
PATH="/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/bin:/usr/local/sbin:$PATH"
fi
if [[ -n "${rvm_user_path_prefix:-}" ]]
then
PATH="${rvm_user_path_prefix}:$PATH"
fi
shopt -s extglob
source "$PWD/scripts/functions/installer"
# source "$PWD/scripts/rvm"
#
# RVM Installer
#
install_setup
true ${DESTDIR:=}
# Parse RVM Installer CLI arguments.
while (( $# > 0 ))
do
token="$1"
shift
case "$token" in
(--auto)
rvm_auto_flag=1
;;
(--path)
rvm_path="$1"
shift
;;
(--version)
rvm_path="${PWD%%+(\/)}"
__rvm_version
unset rvm_path
exit
;;
(--debug)
export rvm_debug_flag=1
set -o verbose
;;
(--trace)
set -o xtrace
export rvm_trace_flag=1
echo "$@"
env | GREP_OPTIONS="" \grep '^rvm_'
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
;;
(--help)
install_usage
exit 0
;;
(*)
echo "Unrecognized option: $token"
install_usage
exit 1
;;
esac
done
if [[ -n "${DESTDIR}" ]]
then
rvm_prefix="${DESTDIR}"
fi
determine_install_path
determine_install_or_upgrade
if [[ -z "${rvm_path:-}" ]]
then
echo "ERROR: rvm_path is empty, halting installation."
\${LINENO} > "
exit 1
fi
export rvm_prefix rvm_path rvm_debug_flag rvm_trace_flag
create_install_paths
print_install_header
configure_installation
cleanse_old_entities
install_rvm_files
install_rvm_hooks
ensure_scripts_are_executable
setup_configuration_files
install_binscripts
automatic_profile_setup
install_gemsets
install_patchsets
cleanse_old_environments
migrate_old_gemsets
migrate_defaults
correct_binary_permissions
install_man_pages
root_canal
setup_rvmrc
setup_user_profile
record_ruby_configs
cleanup_tmp_files
display_thank_you
display_notes
display_requirements
1.18.36. maglev
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
true ${rvm_trace_flag:-0}
if (( rvm_trace_flag == 2 ))
then
set -x
export rvm_trace_flag
fi
system="$(uname -s)"
version="${rvm_ruby_string}.${system}"
# Check we're on a suitable 64-bit machine
case "$system" in
Linux)
if [[ "$(uname -sm)" != "Linux x86_64" ]]
then
rvm_error "This script only works on a 64-bit Linux OS."
echo "The result from \"uname -sm\" is \"$(uname -sm)\" not \"Linux x86_64\""
exit 1
fi
;;
Darwin)
system_version="$(sw_vers -productVersion)"
MAJOR="$(echo $system_version | cut -f1 -d.)"
MINOR="$(echo $system_version | cut -f2 -d.)"
CPU_CAPABLE="$(sysctl hw.cpu64bit_capable | cut -f2 -d' ')"
#
# Check the CPU and Mac OS profile.
if [[ $CPU_CAPABLE -ne 1 || $MAJOR -lt 10 || $MINOR -lt 5 ]]
then
rvm_error "This script requires Mac OS 10.5 or later on a 64-bit Intel CPU."
exit 1
fi
;;
SunOS)
if [[ "$(uname -p)" != "i386" || "$(isainfo -b)" != "64" ]]
then
rvm_error "This script only works on a 64-bit Solaris-x86 OS."
exit 1
fi
;;
*)
rvm_error "This script only works on a 64-bit Linux, Mac OS X, or Solaris-x86 machine"
echo "The result from \"uname -sm\" is \"$(uname -sm)\""
exit 1
;;
esac
# We should run this as a normal user, not root.
if (( UID == 0 ))
then
rvm_error "This script should be run as a normal user, not root."
exit 1
fi
# Check that the current directory is writable
if [[ ! -w "." ]]
then
rvm_error "This script requires write permission on your current directory."
\ls -ld $PWD
exit 1
fi
# We're good to go. Let user know.
machine_name="$(uname -n)"
rvm_log "Starting installation of $version on $machine_name"
# Figure out how much total memory is installed
rvm_log "Setting up shared memory"
#
# Ref: http://wiki.finkproject.org/index.php/Shared_Memory_Regions_on_Darwin
# Ref: http://developer.postgresql.org/pgdocs/postgres/kernel-resources.html
# Ref: http://www.idevelopment.info/data/Oracle/DBA_tips/Linux/LINUX_8.shtml
#
case "$system" in
Linux)
# use TotalMem: kB because Ubuntu doesn't have Mem: in Bytes
totalMemKB=$(awk '/MemTotal:/{print($2);}' /proc/meminfo)
totalMem=$(($totalMemKB * 1024))
# Figure out the max shared memory segment size currently allowed
shmmax=$(cat /proc/sys/kernel/shmmax)
# Figure out the max shared memory currently allowed
shmall=$(cat /proc/sys/kernel/shmall)
;;
Darwin)
totalMem="$(sysctl hw.memsize | cut -f2 -d' ')"
# Figure out the max shared memory segment size currently allowed
shmmax="$(sysctl kern.sysv.shmmax | cut -f2 -d' ')"
# Figure out the max shared memory currently allowed
shmall="$(sysctl kern.sysv.shmall | cut -f2 -d' ')"
;;
SunOS)
# TODO: figure memory needs for SunOS
# Investigate project.max-shm-memory
totalMemMB="$(/usr/sbin/prtconf | GREP_OPTIONS="" \grep Memory | cut -f3 -d' ')"
totalMem=$(($totalMemMB * 1048576))
shmmax=$(($totalMem / 4))
shmall=$(($shmmax / 4096))
;;
*)
rvm_error "Can't determine operating system. Check script."
exit 1
;;
esac
totalMemMB=$(($totalMem / 1048576))
shmmaxMB=$(($shmmax / 1048576))
shmallMB=$(($shmall / 256))
# Print
echo "
echo "
echo "
current values
Total memory available is $totalMemMB MB"
Max shared memory segment size is $shmmaxMB MB"
Max shared memory allowed is $shmallMB MB"
# Figure out the max shared memory segment size (shmmax) we want
# Use 75% of available memory but not more than 2GB
shmmaxNew=$(($totalMem * 3/4))
if (( shmmaxNew > 2147483648 ))
then
shmmaxNew=2147483648
fi
shmmaxNewMB=$(($shmmaxNew / 1048576))
# Figure out the max shared memory allowed (shmall) we want
# The Darwin (OSX) default is 4MB, way too small
# The Linux default is 2097152 or 8GB, so we should never need this
# but things will certainly break if it's been reset too small
# so ensure it's at least big enough to hold a fullsize shared memory segment
shmallNew=$(($shmmaxNew / 4096))
if (( shmallNew < shmall ))
then
shmallNew=$shmall
fi
shmallNewMB=$(($shmallNew / 256))
# Increase shmmax if appropriate
if (( shmmaxNew > shmmax ))
then
rvm_log "Increasing max shared memory segment size to $shmmaxNewMB MB"
case "${system}" in
Darwin)
sudo sysctl -w kern.sysv.shmmax=$shmmaxNew
;;
Linux)
sudo bash -c "echo $shmmaxNew > /proc/sys/kernel/shmmax"
;;
SunOS)
echo "[[Warning]] shmmax must be set manually on SunOS"
;;
esac
else
rvm_log "No need to increase max shared memory segment size"
fi
# Increase shmall if appropriate
if (( shmallNew > shmall ))
then
rvm_log "Increasing max shared memory allowed to $shmallNewMB MB"
case "${system}" in
Darwin)
sudo sysctl -w kern.sysv.shmall=$shmallNew
;;
Linux)
sudo bash -c "echo $shmallNew > /proc/sys/kernel/shmall"
;;
SunOS)
echo "[[Warning]]shmall must be set manually on SunOS"
;;
esac
else
rvm_log "No need to increase max shared memory allowed"
fi
# At this point, shared memory settings contain the values we want,
# put them in sysctl.conf so they are preserved.
if [[ ! -f /etc/sysctl.conf ]] || (( $(GREP_OPTIONS="" \grep -sc "kern.*.shm" /etc/sysctl.conf) == 0 ))
then
case "$system" in
Linux)
echo "# kernel.shm* settings added by MagLev installation" > /tmp/sysctl.conf.$$
echo "kernel.shmmax=$(cat /proc/sys/kernel/shmmax)" >> /tmp/sysctl.conf.$$
echo "kernel.shmall=$(cat /proc/sys/kernel/shmall)" >> /tmp/sysctl.conf.$$
;;
Darwin)
# On Mac OS X Leopard, you must have all five settings in sysctl.conf
# before they will take effect.
echo "# kern.sysv.shm* settings added by MagLev installation" > /tmp/sysctl.conf.$$
sysctl kern.sysv.shmmax kern.sysv.shmall kern.sysv.shmmin kern.sysv.shmmni \
kern.sysv.shmseg | \tr ":" "=" | \tr -d " " >> /tmp/sysctl.conf.$$
;;
SunOS)
# Do nothing in SunOS since /etc/sysctl.conf is ignored on Solaris 10.
# Must configure shared memory settings manually.
;;
*)
rvm_error "Can't determine operating system. Check script."
exit 1
;;
esac
# Do nothing on SunOS since /etc/sysctl.conf is ignored on Solaris 10.
if [[ "$system" != "SunOS" ]]
then
rvm_log "Adding the following section to /etc/sysctl.conf"
cat /tmp/sysctl.conf.$$
sudo bash -c "cat /tmp/sysctl.conf.$$ >> /etc/sysctl.conf"
/bin/rm -f /tmp/sysctl.conf.$$
fi
else
rvm_log "The following shared memory settings already exist in /etc/sysctl.conf"
echo "To change them, remove the following lines from /etc/sysctl.conf and rerun this script"
GREP_OPTIONS="" \grep "kern.*.shm" /etc/sysctl.conf
fi
# Now setup for NetLDI in case we ever need it.
rvm_log "Setting up GemStone netldi service port"
if (( $(GREP_OPTIONS="" \grep -sc "^gs64ldi" /etc/services) == 0 ))
then
echo '[[Info]] Adding "gs64ldi 50378/tcp" to /etc/services'
sudo bash -c 'echo "gs64ldi
50378/tcp
# Gemstone netldi" >> /etc/services'
else
rvm_log "GemStone netldi service port is already set in /etc/services"
echo "To change it, remove the following line from /etc/services and rerun this script"
GREP_OPTIONS="" \grep "^gs64ldi" /etc/services
fi
1.18.37. disk-usage
#!/usr/bin/env bash
rvm_base_except="selector"
source "$rvm_scripts_path/base"
usage()
{
printf "%b" \
"Usage: 'rvm disk-usage {all,total,archives,repos,sources,logs,pkg,rubies,gemsets,wrappers,tmp,others}'
Lists the space rvm uses for a given item(s).
"
exit 1
}
disk_usage()
{
typeset path name
name="$1"
path="$2"
shift 2
printf "%${length}s" "${name} Usage: "
if [[ -n "$path" && -d "$path" && "$path" != "/" ]]
then
du -hs "$@" "${path}/" | awk '{print $1}'
else
echo "0B"
fi
return 0
}
all_disk_usage()
{
typeset name
export length=30
for name in archives repos sources logs pkg \
rubies gemsets wrappers temporary others total
do
${name}_disk_usage
done
}
archives_disk_usage()
repos_disk_usage()
sources_disk_usage()
logs_disk_usage()
pkg_disk_usage()
rubies_disk_usage()
gemsets_disk_usage()
wrappers_disk_usage()
temporary_disk_usage()
total_disk_usage()
others_disk_usage()
{
typeset flag filter
typeset -a flags
{
{
{
{
{
{
{
{
{
{
disk_usage
disk_usage
disk_usage
disk_usage
disk_usage
disk_usage
disk_usage
disk_usage
disk_usage
disk_usage
"Downloaded Archives"
"Repositories"
"Extracted Source Code"
"Log Files"
"Packages"
"Rubies"
"Gemsets"
"Wrappers"
"Temporary Files"
"Total Disk"
"archives";
"repos";
"src";
"log";
"usr";
"rubies";
"gems";
"wrappers";
"tmp";
".";
}
}
}
}
}
}
}
}
}
}
if du --exclude=* . 2>/dev/null 1>/dev/null
then flag="--exclude="
else flag="-I "
fi
for filter in archives repos src log usr rubies gems wrappers tmp
do flags+=( ${flag}${filter} )
done
disk_usage "Other Files" "." "${flags[@]}"
}
case "${1:-help}" in
all|total|archives|repos|sources|logs|pkg|rubies|gemsets|wrappers|tmp|others)
(
export length=""
cd $rvm_path
$1_disk_usage
)
;;
help|*)
usage
;;
esac
1.18.38. tools
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
usage()
{
echo "Usage: rvm tools {identifier,path-identifier,strings,user}" 1>&2
exit 1
}
# Return the identifier that's current in use.
tools_identifier()
{
__rvm_env_string
}
tools_path_identifier()
{
if [[ -z "$1" || ! -d "$1" ]]; then
echo "Usage: rvm tools path-identifier 'path-to-check'"
return 1
fi
builtin cd "$1"
__rvm_do_with_env_before
rvm_promptless=1 __rvm_project_rvmrc >/dev/null 2>&1
rvmrc_result="$?"
__rvm_env_string
__rvm_do_with_env_after
exit $rvmrc_result
}
tools_strings()
{
for ruby_name in "$@"; do
__rvm_unset_ruby_variables
rvm_ruby_string="$ruby_name"
if { __rvm_ruby_string && __rvm_select; } >/dev/null 2>&1; then
basename "$rvm_ruby_gem_home"
else
echo ""
fi
done
}
tools_user_usage()
{
typeset msg
for msg in "$@"
do
rvm_error "$msg"
done
rvm_error "Usage: rvm user [gemsets] [rubies] [hooks] [pkgs] [wrappers] [all] [--skel]"
}
tools_user_setup()
{
typeset target eval_target name path
target="$1"
name="rvm_${2}_path"
# detect name in config
if [[ -f "${target}/.rvmrc" ]] && GREP_OPTIONS="" \grep "^export ${name}=" "${target}/.rvmrc" > /dev/null
then
# if defined read path
path="$( GREP_OPTIONS="" \grep "^export ${name}=" "${target}/.rvmrc" | sed "s/^export ${name}=//" )"
else
# if not defined - define it
path="\${HOME}/.rvm/${2}"
echo "export ${name}=\"${path}\"" >> "${target}/.rvmrc"
fi
# subprocess cause we change the HOME
(
# set home to target, so --skel works fine
HOME="${target}"
# resolve the stored path
eval "path=\"${path}\""
# ensure the defined path exists
[[ -d "${path}" ]] || mkdir -p "${path}"
# create empty db files for rvm_user_path
if [[ "$1" == "user" ]]
then
for file in db md5
do
[[ -f "${path}/${file}" ]] || touch "${path}/${file}"
done
fi
)
}
tools_user()
{
typeset item dir target
typeset -a selection
for item in $@
do
case "$item" in
all)
selection+=( gemsets rubies hooks pkgs wrappers userdb ) ;;
rubies) selection+=( rubies ) ;;
gemsets) selection+=( gemsets ) ;;
hooks)
selection+=( hooks
) ;;
pkgs)
selection+=( pkgs
) ;;
userdb) selection+=( userdb ) ;;
--skel) rvm_skel_flag=1
;;
*)
tools_user_usage "Unrecognized option '$item'."
exit 1
;;
esac
done
if (( ${#selection[@]} == 0 ))
then
tools_user_usage
exit 1
fi
if [[ ${rvm_skel_flag:-0} == 1 ]] && (( UID ))
then
tools_user_usage "The --skel flag should be run as root: rvmsudo rvm user $@."
exit 1
fi
[[ ${rvm_skel_flag:-0} == 1 ]] && target=/etc/skel || target="${HOME}"
if [[ ! -w "${target}" ]] || [[ -d "${target}/.rvm" && ! -w "${target}/.rvm" ]]
then
tools_user_usage "Directory '${target}' or '${target}/.rvm' is not writable for current user."
exit 1
fi
if [[ -f "${target}/.rvmrc" && ! -w "${target}/.rvmrc" ]]
then
tools_user_usage "Configuration file '${target}/.rvmrc' is not writable for current user."
exit 1
fi
for item in "${selection[@]}"
do
case "$item" in
rubies)
for dir in archives bin environments gems gems_cache log repos rubies rubygems src tmp wrappers user
do
tools_user_setup "${target}" $dir
done
;;
gemsets)
for dir in environments gems gems_cache wrappers
do
tools_user_setup "${target}" $dir
done
;;
hooks)
tools_user_setup "${target}" hooks
;;
pkgs)
tools_user_setup "${target}" usr
;;
userdb)
tools_user_setup "${target}" user
;;
esac
done
}
tools_mirror()
{
typeset n file warn
warn=0
file="$rvm_user_path/db"
for n in 1.0 1.2 1.3 1.4 1.5 1.6 1.7 1.8 1.9 2.0
do
if GREP_OPTIONS="" \grep "^ruby_${n}_url=" "$file" >/dev/null
then
if (( ${rvm_force_flag:-0} == 1 ))
then
sed -i "s/^ruby_${n}_url=.*$/ruby_${n}_url=http:\/\/www.mirrorservice.org\/sites\/ftp.rubylang.org\/pub\/ruby\/${n}/" "$file"
else
warn=1
fi
else
printf "ruby_${n}_url=http://www.mirrorservice.org/sites/ftp.ruby-lang.org/pub/ruby/${n}
" >> "$file"
fi
done
if (( warn == 1 ))
then
rvm_warn "Some settings already exist, use 'rvm --force tools mirror' to overwrite."
fi
}
tools_rvm_env()
{
typeset script
rvm_log "# use shebang: #!/usr/bin/$1-rvm-env 1.9.3"
for script in $@
do
if builtin command -v ${script} >/dev/null
then
sudo ln -nfs $rvm_bin_path/rvm-shell /usr/bin/${script}-rvm-env &&
rvm_log "Created link '/usr/bin/${script}-rvm-env'." ||
rvm_error "Cannot create link '/usr/bin/${script}-rvm-env'."
else
rvm_error "There is no command/script '${script}' in system."
fi
done
}
args=($*)
action="${args[0]}"
args="$(echo ${args[@]:1})" # Strip trailing / leading / extra spacing.
[[ -z "$action" ]] && usage
case "$action" in
identifier)
path-identifier)
strings)
mirror)
user)
rvm-env)
*)
esac
exit $?
tools_identifier ;;
tools_path_identifier "$args" ;;
tools_strings "$args" ;;
tools_mirror ;;
tools_user "$args" ;;
tools_rvm_env $args ;;
usage ;;
1.18.39. irbrc
#
#
#
#
#
This loads some niceties for irb, courtesy of rvm.
It also loads your custom ~/.irbrc if it exists.
If you want to customize the irbrc for ONLY this version of
ruby then edit this file. It will only be deleted if you do
an "rvm install" over this ruby version.
if ENV["rvm_path"].nil?
require File.join(ENV["HOME"], "irbrc")
else
require File.join(ENV["rvm_path"], "scripts", "irbrc")
end
1.18.40. alias
#!/usr/bin/env bash
unset rvm_default_flag rvm_wrapper_name
source "$rvm_scripts_path/base"
usage() {
printf "%b" "
Usage:
rvm alias [action] [arguments]
Examples:
rvm
rvm
rvm
rvm
alias
alias
alias
alias
create [alias_name] [ruby]
delete [alias_name]
show [alias_name]
list
"
}
alias_conflicts_with_ruby() {
# If default exists, we should return true.
[[ "$1" == "default" && ! -L "$rvm_rubies_path/default" ]] && return 1
# Open for suggestions to a better way of doing this...
alias_check_result="$(
\. "$rvm_scripts_path/initialize"
\. "$rvm_scripts_path/selector"
\. "$rvm_scripts_path/selector_gemsets"
export rvm_ruby_string=\"$1\"
__rvm_ruby_string > /dev/null 2>&1
echo "$?"
)"
if [[ "0" == "$alias_check_result" ]]; then
rvm_error "You have attempted to create an alias called '$1', which is recognized as a rvm ruby."
return 0
fi
return 1
unset alias_check_result
}
alias_show() {
typeset expanded_alias_name
if [[ -z "$alias_name" ]]
then
rvm_log "usage: 'rvm alias show [alias_name]'"
result=1
return
fi
[[ -s "$rvm_path/config/alias" ]] || return 0
expanded_alias_name="$("$rvm_scripts_path"/db "$rvm_path/config/alias" "$alias_name")"
if [[ -z "$expanded_alias_name" ]]; then
rvm_error "Unknown alias name: '$alias_name'"
result=1
else
result=0
if [[ -n "$gemset_name" ]] ; then
printf "%b" "${expanded_alias_name}${rvm_gemset_separator:-"@"}${gemset_name}\n"
else
printf "%b" "${expanded_alias_name}\n"
fi
fi
}
alias_after_delete_default()
{
rvm_log "Deleting default links/files"
for _path in $rvm_bin_path/default_* "$rvm_environments_path/default" "$rvm_wrappers_path/default"
do
[[ -f "$_path" ]] && rm -rf ${_path}
done
for wrapper in "$rvm_path"/wrappers/default/*
do
wrapper="${wrapper##*\/}"
if [[ -L "$rvm_bin_path/${wrapper}" ]]
then
rm -f "$rvm_bin_path/${wrapper}"
fi
rm -f "$rvm_bin_path/${wrapper}"
# If the RVM bin path is different from rvm_path/bin, ensure they are
# in sync.
if [[ "${rvm_bin_path}" != "${rvm_path}/bin" ]]
then
rm -f "${rvm_path}/bin/${wrapper}"
fi
done
}
alias_delete() {
rvm_log "Deleting alias: $alias_name"
for link in "$rvm_rubies_path/$alias_name" ; do
if [[ -L "$link" ]] ; then rm -f $link ; fi
done
[[ -s "$rvm_path/config/alias" ]] || return 0
"$rvm_scripts_path"/db "$rvm_path/config/alias" "$alias_name" "delete"
if [[ "default" == "$alias_name" ]] ; then
alias_after_delete_default
fi
}
alias_after_create_default()
{
rvm_log "Creating default links/files"
environment_id="${final_environment_identifier}"
if (( ${rvm_user_install_flag:=0} == 0 ))
then
# Sets up the default wrappers.
"$rvm_scripts_path/wrapper" "$rvm_ruby_string" --no-prefix
else
"$rvm_scripts_path/wrapper" "$rvm_ruby_string" "default"
fi
RUBY_VERSION="$("$rvm_ruby_home/bin/ruby" -v | \sed 's#^\(.*\) (.*$#\1#')"
export GEM_HOME GEM_PATH MY_RUBY_HOME RUBY_VERSION
for _path in "$rvm_environments_path" "$rvm_wrappers_path"
do
# Remove old default if it exists.
[[ -L "$_path/default" ]] && rm -f "$_path/default"
# Symlink n the new default
\ln -fs "$_path/$environment_id" "$_path/default"
done
# Copy wrapper scripts for the newly set default to the RVM bin path.
for wrapper in "$rvm_path"/wrappers/default/*
do
[[ -r "${wrapper}" ]] || continue
if [[ -L "$rvm_bin_path/${wrapper##*\/}" ]]
then
rm -f "$rvm_bin_path/${wrapper##*\/}"
fi
cp -f "$wrapper" "$rvm_bin_path/${wrapper##*\/}"
# If the RVM bin path is different from rvm_path/bin, ensure they are
# in sync.
if [[ "${rvm_bin_path}" != "${rvm_path}/bin" ]]
then
cp -f "${wrapper}" "${rvm_path}/bin/"
fi
done
}
alias_create()
{
alias_name="${alias_name:-""}"
rvm_ruby_string="$rvm_environment_identifier"
rvm_expanding_aliases=1
__rvm_become
unset rvm_expanding_aliases
if [[ "default" != "$alias_name" ]] && alias_conflicts_with_ruby "$alias_name"
then
# Force it to an empty alias name to trigger the usage.
alias_name=""
fi
if [[ -z "${rvm_environment_identifier:-""}" || -z "$alias_name" ]]
then
rvm_error "usage: 'rvm alias [alias_name] [ruby_string]'"
return 1
else
if [[ -z "$rvm_ruby_string" ]]
then
rvm_error "Unknown ruby string '$rvm_ruby_string' specified"
return 1
fi
if [[ "default" == "$alias_name" ]]
then rvm_alias=""
fi
if [[ -z "$rvm_alias" ]]
then
final_environment_identifier="${rvm_ruby_string:-$(__rvm_env_string)}"
rvm_log "Creating alias $alias_name for $final_environment_identifier."
ln -fs "$rvm_rubies_path/$rvm_ruby_string" "$rvm_rubies_path/$alias_name"
rvm_log "Recording alias $alias_name for $final_environment_identifier."
"$rvm_scripts_path"/db "$rvm_path/config/alias" "$alias_name" "$final_environment_identifier"
[[ "default" != "$alias_name" ]] || alias_after_create_default
else
if [[ -d "$rvm_rubies_path/$alias_name" ]]
then rvm_error "$rvm_rubies_path/$alias_name is taken and is *not* able to be an alias name."
else rvm_error "$rvm_rubies_path/$alias_name is already aliased."
fi
return 1
fi
fi
}
alias_list() {
typeset item items
items=($(cd "$rvm_rubies_path" ; find . -maxdepth 1 -mindepth 1 -type l | sed -e 's#./##'))
for item in "${items[@]}"
do
echo "$(basename "$item") => $("$rvm_scripts_path"/db "$rvm_path/config/alias" "$(basename "$item")")"
done
}
alias_search_by_target() {
typeset item items target search
search="${alias_name}@${gemset_name}"
items=($(cd "$rvm_rubies_path" ; find . -maxdepth 1 -mindepth 1 -type l | sed -e 's#./##'))
for item in "${items[@]}"
do
target=$("$rvm_scripts_path"/db "$rvm_path/config/alias" "$(basename "$item")")
if [[ "${search}" == "${target}" ]]
then
echo "$(basename "$item")"
fi
done
}
args=($*)
action="${args[0]:-""}"
alias_name="${args[1]:-""}"
rvm_environment_identifier="${args[2]:-""}"
args="$(echo ${args[@]:3})" # Strip trailing / leading / extra spacing.
result=0
if [[ ! -f "$rvm_path/config/alias" ]] ; then touch "$rvm_path/config/alias" ; fi
if printf "%b" "$alias_name" | GREP_OPTIONS="" \grep "${rvm_gemset_separator:-"@"}" >/dev/null 2>&1 ; then
gemset_name="${alias_name/*${rvm_gemset_separator:-"@"}/}"
alias_name="${alias_name/${rvm_gemset_separator:-"@"}*/}"
else
gemset_name=""
fi
if [[ -n "$alias_name" ]] ; then
rvm_alias="$("$rvm_scripts_path/db" "$rvm_path/config/alias" "$alias_name")"
fi
case "$action" in
delete|create|list|show|search_by_target)
alias_${action}
;;
help|usage)
usage
;;
*)
usage
exit 1
;;
esac
exit $?
1.18.41. irbrc.rb
# This is the common irbrc file used by all rvm ruby installations.
# This file will be overriden every time you update rvm.
# Turn on completion.
begin
require "readline"
require "irb/completion" rescue nil
# Turn on history saving.
# require "irb/ext/save-history"
# IRB.conf[:HISTORY_FILE] = File.join(ENV["HOME"], ".irb-history")
# Use an alternate way to on history saving until save-history is fixed.
#
#
bug:
http://redmine.ruby-lang.org/issues/show/1556
#
patch: http://pastie.org/513500
#
# This technique was adopted from /etc/irbrc on OS X.
histfile = File.expand_path(".irb-history", ENV["HOME"])
if File.exists?(histfile)
lines = IO.readlines(histfile).collect { |line| line.chomp }
Readline::HISTORY.push(*lines)
end
Kernel::at_exit do
maxhistsize = 100
histfile = File::expand_path(".irb-history", ENV["HOME"])
lines = Readline::HISTORY.to_a.reverse.uniq.reverse
lines = lines[-maxhistsize, maxhistsize] if lines.compact.length > maxhistsize
File::open(histfile, "w+") { |io| io.puts lines.join("\n") }
end
rescue LoadError
puts "Readline was unable to be required, if you need completion or history install readline then reinstall the ruby.\nYou
may follow 'rvm notes' for dependencies and/or read the docs page https://rvm.io/packages/readline/ . Be sure you 'rvm
remove X ; rvm install X' to re-compile your ruby with readline support after obtaining the readline libraries."
end
# Calculate the ruby string.
rvm_ruby_string = ENV["rvm_ruby_string"] ||
ENV['GEM_HOME'].nil? ? `ruby -v | awk '{printf $1"-"$2}'` : ENV['GEM_HOME'].split(/\//).last.split(/@/).first
# cut ruby- ... everyone knows it's ruby
rvm_ruby_string = $1 if rvm_ruby_string =~ /^ruby-(.*)/
# Set up the prompt to be RVM specific.
@prompt = {
:PROMPT_I => "#{rvm_ruby_string} :%03n > ", # default prompt
:PROMPT_S => "#{rvm_ruby_string} :%03n%l> ", # known continuation
:PROMPT_C => "#{rvm_ruby_string} :%03n > ",
:PROMPT_N => "#{rvm_ruby_string} :%03n?> ", # unknown continuation
:RETURN => " => %s \n",
:AUTO_INDENT => true
}
IRB.conf[:PROMPT] ||= {}
IRB.conf[:PROMPT][:RVM] = @prompt
IRB.conf[:PROMPT_MODE] = :RVM if IRB.conf[:PROMPT_MODE] == :DEFAULT
# Load the user's irbrc file, if possible.
# Report any errors that occur.
begin
load File.join(ENV["HOME"], ".irbrc") if File.exists?("#{ENV["HOME"]}/.irbrc")
rescue LoadError => load_error
puts load_error
rescue => exception
puts "Error : 'load #{ENV["HOME"]}/.irbrc' : #{exception.message}"
end
1.18.42. upgrade
#!/usr/bin/env bash
unset GREP_OPTIONS
source "$rvm_scripts_path/base"
usage()
{
printf "%b" "
Usage:
rvm upgrade [source ruby] [destination ruby]
Description:
Upgrades the specified (already installed) source ruby given to the
given destination ruby version. Will migrate gemsets, wrappers, aliases
and environment files.
To upgrade rvm itself you want 'rvm get'.
Examples:
$ rvm upgrade 1.9.2-p136 1.9.2-p180
$ rvm upgrade ree-2011.01 ree-2011-02
"
}
confirm()
{
typeset confirmation_response
printf "%b" "$1 (Y/n): "
read -r confirmation_response
if [[ -n "$confirmation_response" ]]
then
echo $confirmation_response | GREP_OPTIONS="" \grep -i '^y\|^Y' >/dev/null 2>&1
fi
}
die_with_error()
{
rvm_error "$1"
exit "${2:-1}"
}
expand_ruby_name()
{
"$rvm_scripts_path/tools" strings "$1" \
| awk -F"${rvm_gemset_separator:-"@"}" '{print $1}'
}
existing_ruby_patch()
{
if "$rvm_scripts_path/list" strings | GREP_OPTIONS="" \grep "^$1$" >/dev/null
then
echo "$1"
else
(
rvm_ruby_string="$1"
__rvm_ruby_string
if "$rvm_scripts_path/list" strings | GREP_OPTIONS="" \grep "^${rvm_ruby_interpreter}-${rvm_ruby_version}-" >/dev/null
then
"$rvm_scripts_path/list" strings | GREP_OPTIONS="" \grep "^${rvm_ruby_interpreter}-${rvm_ruby_version}-" | sort |
tail -n 1
else
"$rvm_scripts_path/list" strings | GREP_OPTIONS="" \grep "^${rvm_ruby_interpreter}-" | sort | tail -n 1
fi
)
fi
}
highest_ruby_patch()
{
typeset patch_level _version
(
rvm_ruby_string=$1
__rvm_ruby_string
patch_level="$(
__rvm_db "${rvm_ruby_interpreter}_${rvm_ruby_version}_patch_level"
)"
_version="$(
__rvm_db "${rvm_ruby_interpreter}_version"
)"
if [[ -n "${patch_level:-""}" ]]
then
case "$rvm_ruby_interpreter" in
ree|kiji|rbx)
# REE, Kiji & Rubinius use dates for their patch levels.
rvm_ruby_patch_level="${patch_level}"
;;
*)
# MRI uses -pN+ to specify the patch level.
rvm_ruby_patch_level="p${patch_level}"
;;
esac
echo ${rvm_ruby_interpreter}-${rvm_ruby_version}-${rvm_ruby_patch_level}
elif [[ -n "${_version:-""}" ]]
then
echo ${rvm_ruby_interpreter}-${_version}
else
echo ${rvm_ruby_interpreter}
fi
)
}
upgrade_ruby()
{
[[ -n "$expanded_source"
]] || die_with_error "The source ruby was not a valid ruby string."
[[ -n "$expanded_destination" ]] || die_with_error "The destination ruby was not a valid ruby string."
if ! confirm \
"Are you sure you wish to upgrade from $expanded_source to $expanded_destination?"
then
die_with_error "Cancelling upgrade."
fi
if [[ ! -d "$rvm_rubies_path/$expanded_destination" ]]
then
rvm_log "Installing new ruby $expanded_destination"
if "${rvm_bin_path}/rvm" install "$expanded_destination"
then
true
else
die_with_error "Unable to install ruby $expanded_destination. Please install it manually to continue." $?
fi
fi
rvm_log "Migrating gems from $expanded_source to $expanded_destination"
"$rvm_scripts_path/migrate" "$expanded_source" "$expanded_destination" || die_with_error "Error migrating gems." "$result"
rvm_log "Upgrade complete!"
}
args=($*)
source_ruby="${args[$__array_start]:-}"
args[$__array_start]=""
args=(${args[@]})
destination_ruby="${args[$__array_start]:-}"
args[$__array_start]=""
args=(${args[@]})
expanded_source="$(existing_ruby_patch "$source_ruby")"
if [[ -n "$source_ruby" && -z "$destination_ruby" ]]
then
highest_source="$(highest_ruby_patch "$(expand_ruby_name "$source_ruby")")"
if [[ "${expanded_source}" != "${highest_source}" ]]
then
destination_ruby="$(expand_ruby_name "$highest_source")"
fi
fi
if [[ -z "$source_ruby" || -z "$destination_ruby" ]]
then
usage >&2
exit 1
elif [[ "help" == "$source_ruby" ]]
then
usage
else
expanded_destination="$(expand_ruby_name "$destination_ruby")"
upgrade_ruby
fi
1.18.43. requirements
#!/usr/bin/env bash
( # wrap color reseting
if ! typeset -f rvm_pretty_print >/dev/null 2>&1
then source "${rvm_scripts_path:-"$rvm_path/scripts"}/functions/logging"
fi
rvm_pretty_print stdout || unset rvm_error_clr rvm_warn_clr rvm_debug_clr rvm_notify_clr rvm_reset_clr
system="$(uname)"
if [[ "Linux" == "$system" ]] || [[ "$(uname|tr a-z A-Z)" =~ *BSD* ]]
then
for file in /etc/*-release
do
release="( $(cat $file) )"
break
done
printf "%b" "
Requirements for ${system} $release
"
rvm_apt_binary="$(builtin command -v apt-get)"
rvm_emerge_binary="$(builtin command -v emerge)"
rvm_pacman_binary="$(builtin command -v pacman)"
rvm_yum_binary="$(builtin command -v yum)"
rvm_zypper_binary="$(builtin command -v zypper)"
rvm_free_ram_mb="$(free -m | awk '{if (NR==3) print $4}')"
printf "%b" "
NOTE: 'ruby' represents Matz's Ruby Interpreter (MRI) (1.8.X, 1.9.X)
This is the *original* / standard Ruby Language Interpreter
'ree' represents Ruby Enterprise Edition
'rbx' represents Rubinius
bash >= 4.1 required
curl is required
git is required (>= 1.7 for ruby-head)
patch is required (for 1.8 rubies and some ruby-head's).
To install rbx and/or Ruby 1.9 head (MRI) (eg. 1.9.2-head),
then you must install and use rvm 1.8.7 first.
"
if [[ ! -z "$rvm_apt_binary" ]]
then
printf "%b" "
Additional Dependencies:
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby: ${rvm_apt_binary} install build-essential openssl libreadline6 libreadline6-dev curl git-core zlib1g zlib1g-dev
libssl-dev libyaml-dev libsqlite3-dev sqlite3 libxml2-dev libxslt-dev autoconf libc6-dev ncurses-dev automake libtool bison
subversion
# For JRuby, install the following:
jruby: ${rvm_apt_binary} install curl g++ openjdk-6-jre-headless
jruby-head: ${rvm_apt_binary} install ant openjdk-6-jdk
# For IronRuby, install the following:
ironruby: ${rvm_apt_binary} install curl mono-2.0-devel
"
elif [[ ! -z "$rvm_emerge_binary" ]]
then
printf "%b" "
Additional Dependencies:
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby|ruby-head: emerge libiconv readline zlib openssl curl git libyaml sqlite libxslt libtool gcc autoconf automake bison
m4
# For JRuby, install the following:
jruby: emerge dev-java/sun-jdk dev-java/sun-jre-bin
# For IronRuby, install the following:
ironruby: emerge dev-lang/mono
"
elif [[ ! -z "$rvm_pacman_binary" ]]
then
printf "%b" "
Additional Dependencies:
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby: pacman -Sy --noconfirm gcc patch curl zlib readline libxml2 libxslt git autoconf automake diffutils make libtool
bison subversion
# For JRuby, install the following:
jruby: pacman -Sy --noconfirm jdk jre curl
jruby-head: pacman -Sy apache-ant
# For IronRuby, install the following:
ironruby: pacman -Sy --noconfirm mono
"
elif [[ ! -z "$rvm_yum_binary" ]]
then
printf "%b" "
Additional Dependencies:
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby: yum install -y gcc-c++ patch readline readline-devel zlib zlib-devel libyaml-devel libffi-devel openssl-devel make
bzip2 autoconf automake libtool bison iconv-devel ## NOTE: For centos >= 5.4 iconv-devel is provided by glibc
# For JRuby, install the following:
jruby: yum install -y java
"
elif [[ ! -z "$rvm_zypper_binary" ]]
then
printf "%b" "
Additional Dependencies:
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby: sudo zypper install -y patterns-openSUSE-devel_basis gcc-c++ bzip2 readline-devel zlib-devel
libxml2-devel libxslt-devel libyaml-devel libopenssl-devel libffi45-devel
libtool bison
# For JRuby, install the following:
jruby: sudo zypper install -y java-1_6_0-sun # Non-Oss repository required
"
else
printf "%b" "
Additional Dependencies:
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following with development headers:
ruby: # gcc-c++ patch readline zlib libyaml iconv libxml2 libxslt libtool bison
# For JRuby, install the following:
jruby: # The SUN java runtime environment and development kit.
# For IronRuby, install the following:
ironruby: #The Mono Runtime and Development Platform (version 2.6 or greater is recommended).
"
fi
elif [[ "SunOS" == "$system" ]]
then
version="$(uname -v)"
if [[ "11.0" == "$version" ]]
then
# looks like Solaris 11
printf "%b" "
RVM requirements for Solaris 11:
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby: pkg install text/gnu-patch developer/gcc-45 developer/library/lint system/header \\
system/library/math/header-math file/gnu-coreutils
# For JRuby, install the following:
jruby: # The Oracle java runtime environment and development kit.
"
elif [[ "$version" =~ ^oi ]]
then
# looks like OpenIndiana
printf "%b" "
RVM requirements for OpenIndiana
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby: pkg install text/gnu-patch runtime/gcc developer/library/lint system/header \\
system/library/math/header-math file/gnu-coreutils
# For JRuby, install the following:
jruby: # The Oracle java runtime environment and development kit.
"
else
printf "%b" "
RVM requirements for unrecognised Solaris system.
# For Ruby / Ruby HEAD (MRI, Rubinius, & REE), install the following:
ruby: you will need to install: gcc, gnu-patch, lint library, system header, system
math header and gnu-coreutils.
Check you package publisher(s) for installing these.
# For JRuby, install the following:
jruby: # The Oracle java runtime environment and development kit.
"
fi
elif [[ "$MACHTYPE" == *darwin* ]]
then
if ! typeset -f __rvm_detect_xcode_version > /dev/null 2>&1
then source $rvm_path/scripts/functions/utility
fi
release="$( sw_vers -productName )"
version="$( sw_vers -productVersion )"
xcode_version="$( __rvm_detect_xcode_version )"
: ${xcode_version:=0}
printf "%b" "
Notes for ${release} ${version}"
if __rvm_version_compare $xcode_version -eq 0
then
printf "%b" ", No Xcode.
"
else
printf "%b" ", Xcode $xcode_version.
"
fi
if __rvm_version_compare $xcode_version -ge 4.2
then
printf "%b" "
For MacRuby: Install LLVM first.
"
fi
printf "%b" "
For JRuby: Install the JDK. See http://developer.apple.com/java/download/ # Current Java version \"1.6.0_26\"
For IronRuby: Install Mono >= 2.6
For Ruby 1.9.3: Install libksba # If using Homebrew, 'brew install libksba'
To use an RVM installed Ruby as default, instead of the system ruby:
rvm install 1.8.7 # installs patch 357: closest supported version
rvm system ; rvm gemset export system.gems ; rvm 1.8.7 ; rvm gemset import system.gems # migrate your gems
rvm alias create default 1.8.7
And reopen your terminal windows.
"
if __rvm_version_compare $xcode_version -gt 0 && __rvm_version_compare $xcode_version -lt 4.1
then
printf "%b" "
** Please note that Xcode 3.x will *not* work on OS X Lion. For notes about Xcode 4.1 and later, see below:
"
fi
printf "%b" "
${rvm_error_clr:-}Xcode and gcc${rvm_reset_clr:-}:
Right now Ruby requires gcc to compile, but Xcode 4.2 and later no longer ship with gcc. Instead they ship with llvm-gcc (to
which gcc is a symlink) and clang, neither of which are supported for building Ruby. Xcode 4.1 was the last version to ship
gcc, which was /usr/bin/gcc-4.2.
${rvm_notify_clr:-}Xcode 4.1${rvm_reset_clr:-} and earlier:
- Ruby will build fine.
${rvm_error_clr:-}Xcode 4.2${rvm_reset_clr:-} and later (including Command Line Tools for Xcode):
- If you have gcc-4.2 (and friends) from an earlier Xcode version, Ruby will build fine.
- If you don't have gcc-4.2, you have two options to get it:
* Install apple-gcc42 from Homebrew
* Install osx-gcc-installer
${rvm_notify_clr:-}Homebrew${rvm_reset_clr:-}:
If you are using Homebrew, you can install the apple-gcc42 package from homebrew/dupes:
brew tap homebrew/dupes
brew install apple-gcc42
This can live side by side with an existing Xcode 4.2+ install or Command Line Tools for Xcode.
${rvm_notify_clr:-}osx-gcc-installer${rvm_reset_clr:-}:
If you don't use Homebrew, you can download and install osx-gcc-installer: https://github.com/kennethreitz/osx-gccinstaller.
${rvm_error_clr:-}Warning${rvm_reset_clr:-}: Installing osx-gcc-installer on top of a recent Xcode is known to cause
problems, so you must uninstall Xcode before installing osx-gcc-installer. Afterwards you may install Xcode 4.2+ or Command
Line Tools for Xcode if you desire.
** NOTE: Currently, Node.js is having issues building with osx-gcc-installer. The only fix is to install Xcode over osxgcc-installer.
"
if (( UID == 0 )) || [[ "$rvm_path" == "/usr/local/rvm" ]]
then
printf "%b" "
${rvm_notify_clr:-}RVM Group Membership Management${rvm_reset_clr:-} - With Multi-User installations, the RVM installer
automatically
creates an 'rvm' group which, as the RVM documentation explains, administrators must add the users they wish
to let use the RVM installation to. The call is made in the installer as:
${rvm_notify_clr:-}sudo dscl . -create /Groups/\$rvm_group_name gid \$gid${rvm_reset_clr:-}
wherein RVM creates the gid by checking for the last assigned gid and adding 1. To physicially add a user to
the group, administrators must use:
${rvm_notify_clr:-}sudo dscl localhost -append /Local/Default/Groups/rvm GroupMembership \$user_name${rvm_notify_clr:-}
To check on group membership to the RVM group, administrators would execute the following:
${rvm_notify_clr:-}rvmsudo dscl localhost -read /Local/Default/Groups/rvm${rvm_reset_clr:-}
Pay attention to the GroupMembership and PrimaryGroupID lines. This tells you who is in it, and the GID for the RVM group.
Afterwards, should administrators wish to remove users from the group, they would execute:
${rvm_notify_clr:-}sudo dscl localhost -delete /Local/Default/Groups/rvm GroupMembership \$user_name${rvm_reset_clr:-}
${rvm_notify_clr:-}sudo dsmemberutil flushcache${rvm_reset_clr:-}
This will keep the 'rvm' group, but remove the listed user from it. They can directly delete the rvm group with:
${rvm_notify_clr:-}sudo dscl . -delete /Groups/rvm && sudo dsmemberutil flushcache${rvm_reset_clr:-}
without previously deleting users from the group, as well. This will completely remove the 'rvm' group from the system.
Please note, the call to 'dsmemberutil flushcache' is required on both removal of the user from the group, and/or
removal of the group directly because that membership is still cached locally until either reboot or sync with
Directory Services. Allowing the group membership to stay in the user's 'groups' output does not mean the user is
automatically re-added to the 'rvm' group should the group be subsequently be re-added. This means the user(s) end up
erroneously showing they are part of the 'rvm' group even though they actually are not, if the call to 'dsmemberutil'
is not made. By this we mean the 'groups' command will still show them a part of the 'rvm' group, even if the user
logs out and then back in, due to caching. This applies to Tiger, Leopard, Snow Leopard, and Lion. Previous versions of
the OS such as Cheetah/Puma, and Jaguar used 'nicl', a.k.a NetInfo, and not 'dscl'.
"
fi
fi
printf "%b" "\n"
) # Finish color resetting block
1.18.44. completion
#!/usr/bin/env bash
# bash completion for Ruby Version Manager (RVM)
__rvm_comp()
{
typeset cur
cur="${COMP_WORDS[COMP_CWORD]}"
COMPREPLY=($(compgen -W "$1" -- "$cur"))
return 0
}
__rvm_subcommand()
{
typeset word subcommand c
c=1
while [[ $c -lt $COMP_CWORD ]] ; do
word="${COMP_WORDS[c]}"
for subcommand in $1; do
if [[ "$subcommand" == "$word" ]]; then
echo "$subcommand"
return
fi
done
c=$((++c))
done
}
__rvm_rubies ()
{
echo "$(rvm list strings) default system"
}
__rvm_gemsets ()
{
echo "$(rvm gemset list | GREP_OPTIONS="" \grep -v gemset 2>/dev/null)"
}
__rvm_help_pages ()
{
ls "$rvm_help_path"
}
__rvm_known ()
{
# Strips comments and expands known patterns into each variation
rvm list known | sed -e 's/#.*$//;' \
-e '/^$/d;' \
-e 's/^\[\(.*-\)\]\(.*\)\[\(-.*\)\]$/\1\2\3 \1\2 \2\3 \2/;' \
-e 's/^\[\(.*-\)\]\(.*\)$/\1\2 \2/;' \
-e 's/^\(.*\)\[\(-.*\)\]\[\(-.*\)\]$/\1\2\3 \1\2 \1/;' \
-e 's/^\(.*\)\[\(-.*\)\]$/\1\2 \1/ ' # | \tr ' ' "\n" | sort
}
_rvm_commands ()
{
typeset cur
cur=${COMP_WORDS[COMP_CWORD]}
COMMANDS='\
version use reload implode update reset info debug\
install uninstall reinstall remove\
ruby gem rake tests specs monitor gemset\
gemdir srcdir fetch list package notes snapshot\
help'
case "${cur}" in
-*)
_rvm_opts ;;
*)
__rvm_comp "$COMMANDS $(__rvm_rubies)" ;;
esac
}
_rvm_opts ()
{
RVM_OPTS='\
-h\
--help\
-v\
--version\
-l --level\
--bin\
--gems\
--archive\
--patch
-S\
-e\
-G\
-C\
--configure\
--nice\
--ree-options\
--head\
--rubygems\
--default\
--debug\
--trace\
--force\
--summary\
--latest\
--docs\
--reconfigure
--create'
__rvm_comp "$RVM_OPTS"
}
_rvm_use ()
{
typeset _command
_command="${COMP_WORDS[COMP_CWORD-2]}"
case "${_command}" in
gemset) __rvm_comp "$(__rvm_gemsets)" ;;
*)
__rvm_comp "$(__rvm_rubies)" ;;
esac
}
_rvm_gemset ()
{
typeset subcommand subcommands
subcommands="use create"
subcommand="$(__rvm_subcommand "$subcommands")"
if [[ -z "$subcommand" ]]; then
__rvm_comp "$subcommands"
return
fi
}
_rvm_help ()
{
__rvm_comp "$(__rvm_help_pages)"
}
_rvm_install ()
{
__rvm_comp "$(__rvm_known)"
}
_rvm ()
{
typeset prev
prev=${COMP_WORDS[COMP_CWORD-1]}
case "${prev}" in
use)
_rvm_use ;;
gemset)
_rvm_gemset ;;
help)
_rvm_help ;;
install) _rvm_install ;;
*)
_rvm_commands ;;
esac
return 0
}
complete -o default -o nospace -F _rvm rvm
1.18.45. selector_gemsets
#!/usr/bin/env bash
__rvm_gemset_handle_default()
{
rvm_gemset_name="@${rvm_gemset_name:-}@"
rvm_gemset_name="${rvm_gemset_name/@default@/@@}"
rvm_gemset_name="${rvm_gemset_name#@}"
rvm_gemset_name="${rvm_gemset_name%@}"
}
__rvm_gemset_select_cli_validation()
{
typeset orig_gemset
if ! builtin command -v gem > /dev/null
then
rvm_log "'gem' command not found, cannot select a gemset."
return 0
fi
orig_gemset="${rvm_gemset_name:-}"
__rvm_gemset_handle_default
# No longer defaulting to 'sticky' gem sets.
# Set 'rvm_sticky_flag=1' in ~/.rvmrc to enable.
if [[ -z "${rvm_gemset_name:-}" && "$orig_gemset" != "default" && ${rvm_sticky_flag:-0} -eq 1 ]]
then
if [[ -n "${rvm_ruby_gem_home:-}" ]]
then
rvm_gemset_name="$rvm_ruby_gem_home"
elif [[ -n "${GEM_HOME:-}" ]]
then
rvm_gemset_name="$GEM_HOME"
fi
rvm_gemset_name="${rvm_gemset_name##*/}"
rvm_gemset_name="${rvm_gemset_name#*${rvm_gemset_separator:-"@"}}"
fi
if [[ -z "${rvm_ruby_string:-}" && -n "${GEM_HOME:-}" && -n "${GEM_HOME%@*}" ]]
then
rvm_ruby_string="${GEM_HOME%@*}"
rvm_ruby_string="${rvm_ruby_string##*/}"
fi
if [[ -z "${rvm_ruby_string:-}" ]]
then
rvm_error "Gemsets can not be used with non rvm controlled rubies (currently)."
return 3
fi
}
__rvm_gemset_select_only()
{
rvm_ruby_gem_home="${rvm_gems_path:-"$rvm_path/gems"}/$rvm_ruby_string"
: rvm_ignore_gemsets_flag:${rvm_ignore_gemsets_flag:=0}:
if (( rvm_ignore_gemsets_flag ))
then
rvm_ruby_global_gems_path="${rvm_ruby_gem_home}"
rvm_ruby_gem_path="${rvm_ruby_gem_home}"
rvm_gemset_name=""
else
rvm_ruby_global_gems_path="${rvm_ruby_gem_home}${rvm_gemset_separator:-"@"}global"
__rvm_gemset_handle_default
[[ -z "$rvm_gemset_name" ]] ||
rvm_ruby_gem_home="${rvm_ruby_gem_home}${rvm_gemset_separator:-"@"}${rvm_gemset_name}"
if [[ "$rvm_gemset_name" == "global" ]]
then
rvm_ruby_gem_path="${rvm_ruby_gem_home}"
else
rvm_ruby_gem_path="${rvm_ruby_gem_home}:${rvm_ruby_global_gems_path}"
fi
fi
if [[ -n "${rvm_gemset_name}" ]]
then
rvm_env_string="${rvm_ruby_string}@${rvm_gemset_name}"
else
rvm_env_string=${rvm_ruby_string}
fi
}
__rvm_gemset_select_validation()
{
# If the gemset does not exist, then notify the user as such and abort the action.
if [[ ! -d "${rvm_ruby_gem_home}" ]]
then
if (( ${rvm_gemset_create_on_use_flag:=0} == 0 && ${rvm_create_flag:=0} == 0 && ${rvm_delete_flag:=0} == 0 ))
then
rvm_expected_gemset_name="${rvm_gemset_name}"
rvm_gemset_name=""
__rvm_gemset_select_only
return 2
fi
elif (( ${rvm_delete_flag:=0} == 1 ))
then
return 4
fi
}
__rvm_gemset_select_ensure()
{
\mkdir -p "$rvm_ruby_gem_home"
if __rvm_using_gemset_globalcache && [[ ! -L "$rvm_ruby_gem_home/cache" ]]
then
: rvm_gems_cache_path:${rvm_gems_cache_path:=${rvm_gems_path:-"$rvm_path/gems"}/cache}
\mv "$rvm_ruby_gem_home/cache/"*.gem "$rvm_gems_cache_path/" 2>/dev/null
__rvm_rm_rf "$rvm_ruby_gem_home/cache"
\ln -fs "$rvm_gems_cache_path" "$rvm_ruby_gem_home/cache"
fi
}
# Select a gemset based on CLI set options and environment.
__rvm_gemset_select_cli()
{
__rvm_gemset_select_cli_validation &&
__rvm_gemset_select
}
__rvm_gemset_select()
{
__rvm_gemset_select_only &&
__rvm_gemset_select_validation &&
__rvm_gemset_select_ensure
}
# Use a gemset specified by 'rvm_ruby_gem_home'
__rvm_gemset_use()
{
if __rvm_gemset_select_cli
then
rvm_log "Using $rvm_ruby_string with gemset ${rvm_gemset_name:-default}"
__rvm_use # Now ensure the selection takes effect for the environment.
else
if [[ ! -d "$rvm_ruby_gem_home" || -n "${rvm_expected_gemset_name}" ]]
then
if (( ${rvm_gemset_create_on_use_flag:=0} == 1 || ${rvm_create_flag:=0} == 1 ))
then
rvm_warn "gemset $rvm_gemset_name is not existing, creating."
"$rvm_scripts_path/gemsets" create "$rvm_gemset_name"
else
rvm_error "Gemset '${rvm_expected_gemset_name}' does not exist, 'rvm gemset create ${rvm_expected_gemset_name}'
first, or append '--create'."
return 2
fi
else
rvm_error "Gemset was not given.\n Usage:\n
rvm gemset use <gemsetname>\n"
return 1
fi
fi
}
__rvm_gemset_clear()
{
export rvm_gemset_name
rvm_gemset_name=""
__rvm_use # Now ensure the selection takes effect for the environment.
}
1.18.46. cd
#!/usr/bin/env bash
# Source a .rvmrc file in a directory after changing to it, if it exists. To
# disable this feature, set rvm_project_rvmrc=0 in /etc/rvmrc or $HOME/.rvmrc
if (( ${rvm_project_rvmrc:-1} > 0 ))
then
__rvm_setup_cd()
{
# try to use smartcd function, fallback to builtin
typeset __cd_prefix __command
if typeset -f smartcd >/dev/null 2>/dev/null
then __cd_prefix="smartcd"
else __cd_prefix="builtin"
fi
__rvm_after_cd()
{
typeset rvm_hook
rvm_hook="after_cd"
if [[ -n "${rvm_scripts_path:-}" || -n "${rvm_path:-}" ]]
then source "${rvm_scripts_path:-$rvm_path/scripts}/hook"
fi
}
__rvm_setup_cd_function()
{
typeset __cd_prefix __command
__cd_prefix=$1
__command=$2
eval "
${__command}(){
if ${__cd_prefix} ${__command} \"\$@\"
then
[[ -n \"\${rvm_current_rvmrc:-""}\" && \"\$*\" == \".\" ]] && rvm_current_rvmrc=\"\" || true
__rvm_do_with_env_before
__rvm_project_rvmrc
__rvm_after_cd
__rvm_do_with_env_after
return 0
else
return \$?
fi
}"
}
if [[ -n "${ZSH_VERSION:-}" ]]
then
autoload is-at-least
if is-at-least 4.3.4 >/dev/null 2>&1; then
# On zsh, use chpwd_functions
export -a chpwd_functions
chpwd_functions=( "${chpwd_functions[@]}" __rvm_do_with_env_before __rvm_project_rvmrc __rvm_after_cd
__rvm_do_with_env_after )
else
for __command in cd popd pushd
do __rvm_setup_cd_function "${__cd_prefix}" "${__command}"
done
fi
else
for __command in cd popd pushd
do __rvm_setup_cd_function "${__cd_prefix}" "${__command}"
done
fi
}
__rvm_setup_cd
# This functionality is opt-in by setting rvm_cd_complete_flag=1 in ~/.rvmrc
# Generic bash cd completion seems to work great for most, so this is only
# for those that have some issues with that.
if (( ${rvm_cd_complete_flag:-0} == 1 ))
then
# If $CDPATH is set, bash should tab-complete based on directories in those paths,
# but with the cd function above, the built-in tab-complete ignores $CDPATH. This
# function returns that functionality.
_rvm_cd_complete ()
{
typeset directory current matches item index sep
sep="${IFS}"
export IFS
IFS=$'\n'
COMPREPLY=()
current="${COMP_WORDS[COMP_CWORD]}"
if [[ -n "$CDPATH" && ${current:0:1} != "/" ]] ; then
index=0
# The change to IFS above means that the \tr below should replace ':'
# with a newline rather than a space. A space would be ignored, breaking
# TAB completion based on CDPATH again
for directory in $(printf "%b" "$CDPATH" | \tr -s ':' '\n') ; do
for item in $( compgen -d "$directory/$current" ) ; do
COMPREPLY[index++]=${item#$directory/}
done
done
else
COMPREPLY=( $(compgen -d ${current}) )
fi
IFS="${sep}";
}
complete -o bashdefault -o default -o filenames -o dirnames -o nospace -F _rvm_cd_complete cd
fi
fi
1.18.47. help
#!/usr/bin/env bash
rvm_base_except="selector"
source "$rvm_scripts_path/base"
args=($*)
_command="${args[$__array_start]}"
args[$__array_start]=""
args=(${args[@]})
action="${args[$array_start]}"
args[$__array_start]=""
args=(${args[@]})
if [[ -n "$_command" && -s "${rvm_help_path}/${_command}" ]] ; then
if [[ -n "$action" && -s "${rvm_help_path}/${_command}/${action}" ]] ; then
__rvm_pager_or_cat_v "${rvm_help_path}/${_command}/${action}"
else
__rvm_pager_or_cat_v "${rvm_help_path}/${_command}"
fi
else
__rvm_pager_or_cat_v "${rvm_path:-$HOME/.rvm}/README" | sed '1,2d'
rvm_log "
Commands available with 'rvm help':
$(builtin cd "${rvm_help_path}" ; find . -maxdepth 1 -mindepth 1 -type f -print | \tr "\n" ' ' | sed -e 's#./##g')
"
fi
rvm_log "
For additional information please visit RVM's documentation website:
https://rvm.io/
If you still cannot find what an answer to your question, find me 'wayneeseguin' in #rvm on irc.freenode.net:
http://webchat.freenode.net/?channels=rvm
"
exit $?
1.18.48. db
#!/usr/bin/env bash
usage()
{
printf "%b" "
Usage:
db database_file {{key}} {{value}} # set
db database_file {{key}}
# get
db database_file {{key}} unset
# unset
" >&2
}
if [[ -f "$1" ]]
then
database_file="$1"
shift
if [[ ! -f "$database_file" ]]
then
directory=$(dirname "$database_file")
[[ -d "$directory" ]] || mkdir -p "$directory"
touch "$database_file"
fi
else
printf "%b" "\n\nDatabase file $1 does not exist.\n\n" >&2
exit 1
fi
key="$1"
shift
if [[ -z "$key" ]]
then
usage
exit 1
else
if (( ${escape_flag:-0} ))
then
escaped_key="$(\printf "%b" "$key" | \sed -e 's#\\#\\#g' -e 's#/#\\/#g' -e 's#\.#\.#g')"
else
escaped_key="$key"
fi
value="$*"
if [[ "unset" == "$value" || "delete" == "$value" ]]
then
\sed -e "s#^$escaped_key=.*\$##" -e '/^$/d' "$database_file" \
> "$database_file.new"
mv "$database_file.new" "$database_file"
else
if [[ -z "$value" ]]
then # get
[[ -s "${database_file}" ]] || exit 0 # File is empty, nothing to get.
\awk -F= '/^'"$escaped_key"'=/' "$database_file" \
| \sed -e "s#^$escaped_key=##" -e '/^$/d'
else # set
\sed -e "s#^$escaped_key=.*\$##" -e '/^$/d' "$database_file" > "$database_file.new"
mv "$database_file.new" "$database_file"
if [[ -z "$(awk -F= "/^'"$escaped_key"'=/{print $2}" "$database_file")" ]]
then # append
echo "$escaped_key=$value" >> "$database_file"
else # overwrite
\sed -i.tmp "s#^$escaped_key=.*\$#$escaped_key=$value#" "$database_file" > "$database_file.new"
mv "$database_file.new" "$database_file"
fi
fi
fi
fi
1.18.49. array
#!/usr/bin/env bash
if [[ -n "${ZSH_VERSION:-}" ]]
then
__array_start=1
else
__array_start=0
fi
# Usage: contains "a_string" "${an_array[@]}"
array_contains()
{
typeset pattern index
typeset -a list
pattern="$1"
shift
list=("$@")
for index in "${!list[@]}"
do
[[ ${list[index]} = $pattern ]] && { echo $index ; return 0 ; }
done
echo -1
return 1
}
array_length()
{
array=$1
eval "length=\${#${array}[*]}"
echo $length
return $length
}
array_push()
{
array=$1
item=$2
# TODO: allow loop over more arguments.
eval "index=\$((\${#${array}[*]} + $__array_start))"
eval "${array}[${index}]=${item}"
}
1.18.50. cleanup
#!/usr/bin/env bash
rvm_base_except="selector"
source "$rvm_scripts_path/base"
usage()
{
printf "%b" "
Usage:
rvm cleanup {all,archives,repos,sources,logs}
Description:
Cleans up the directory tree for the specified item.
"
return 0
}
cleanup()
{
typeset cleanup_type current_path entry
for cleanup_type in $@
do
current_path="${rvm_path}/${cleanup_type}"
if [[ -n "$current_path" && -d "$current_path" && "$current_path" != "/" ]]
then
rvm_log "Cleaning up rvm directory '$current_path'"
for entry in "$current_path"/*
do
case $entry in
(*\*) continue ;; # skip empty dirs
esac
chmod -R u+w "$entry"
__rvm_rm_rf "$entry"
done
fi
done
return 0
}
case "$1" in
all)
cleanup archives repos src log tmp ;;
archives) cleanup archives ;;
repos)
cleanup repos ;;
sources) cleanup src ;;
logs)
cleanup log ;;
tmp)
cleanup tmp ;;
help)
usage ;;
*)
usage ; exit 1;;
esac
exit $?
1.18.51. patches
#!/usr/bin/env bash
# General tools for manipulating patches
# and dealing with patches.
# Returns the path used to look for a patch given a specific name.
__rvm_patch_lookup_path()
{
echo "/"
[[ -n "${rvm_patch_original_pwd:-""}" ]] && echo "$rvm_patch_original_pwd/"
echo "$PWD/"
__rvm_ruby_string_paths_under "$rvm_patches_path" | sed 's/$/\//' | sort -r
return $?
}
__rvm_expand_patch_name()
{
typeset name expanded_patch_name
name="${1:-""}"
[[ -z "$name" ]] && return 0
expanded_patch_name="$(rvm_ruby_string="${rvm_ruby_string}" "$rvm_scripts_path/patchsets" show "$name")"
if
[[ "$?" == "0" ]]
then
echo "${expanded_patch_name}"
elif
[[ "$name" != "default" ]]
then
echo "$name"
fi
return 0
}
# Return the full patch for a given patch.
__rvm_lookup_full_patch_path()
{
typeset extension patch_path directory directories
# Absolute path, pwd and then finally the rvm patches path.
directories=($(__rvm_patch_lookup_path))
for directory in "${directories[@]}" ; do
for extension in {"",.patch,.diff}; do
patch_path="${directory}${1}${extension}"
# -s reports directories too - so additional check -f needed
if [[ -s "$patch_path" && -f "$patch_path" ]]; then
echo "$patch_path"
return 0
fi
done
done
return 0
}
1.18.52. snapshot
#!/usr/bin/env bash
sys=$( uname -s )
if [[ "${sys}" == AIX ]] ; then
name_opt=-name
else
name_opt=-iname
fi
unset GREP_COLOR
unset GREP_OPTIONS
source "$rvm_scripts_path/base"
__error_on_result()
{
if [[ "$1" -gt 0 ]]; then
rvm_error "$2 - Aborting now."
return 0
else
return 1
fi
}
snapshot_save()
{
typeset snapshot_temp_path snapshot_ruby_name_file \
snapshot_alias_name_file snapshot_installable_file \
snapshot_primary_ruby snapshot_ruby_order destination_path
if [[ -z "$1" ]]
then
printf "%b" "
Usage:
rvm snapshot save name
Description:
Saves a snapshot describing the rvm installation
to <name>.tar.gz in the current working directory.\
" >&2
return 1
fi
# Create the temporary directory.
snapshot_temp_path="${rvm_tmp_path}/$$-snapshot"
__rvm_rm_rf "$snapshot_temp_path"
mkdir -p "$snapshot_temp_path"
rvm_log "Backing up a list of aliases"
cp "$rvm_path/config/alias" "$snapshot_temp_path/"
rvm_log "Backing up your user preferences"
cp "$rvm_user_path/db" "$snapshot_temp_path/"
rvm_log "Backing up your installed packages"
sed -e 's/-//' -e 's/^lib//' < "$rvm_path/config/pkg" | awk -F= '{print $1}' | sort | uniq > "$snapshot_temp_path/pkg"
rvm_log "Backing up all of your gemsets"
mkdir -p "$snapshot_temp_path/gems"
(
builtin cd "$snapshot_temp_path/gems"
for snapshot_gemset in $("$rvm_scripts_path/list" gemsets strings) ; do
__rvm_become "$snapshot_gemset" ; result="$?"
__error_on_result "$result" "Error becoming ruby $snapshot_gemset" && return "$result"
"$rvm_scripts_path/gemsets" export "${snapshot_gemset}.gems" >/dev/null ; result="$?"
__error_on_result "$result" "Error exporting gemset contents for $snapshot_gemset" && return "$result"
mkdir -p "./$snapshot_gemset/"
[[ -d "$GEM_HOME/cache/" ]] && \cp -R "$GEM_HOME/cache/" "./$snapshot_gemset/"
done
)
rvm_log "Backing up all of your installed rubies"
printf "%b" "#!/usr/bin/env bash\n\nset -e\n\n" > "$snapshot_temp_path/install-rubies.sh"
echo "source \"\$rvm_scripts_path/rvm\" || true" >> "$snapshot_temp_path/install-rubies.sh"
snapshot_ruby_name_file="${rvm_tmp_path}/$$-rubies"
snapshot_alias_name_file="${rvm_tmp_path}/$$-aliases"
snapshot_installable_file="${rvm_tmp_path}/$$-installable"
"$rvm_scripts_path/alias" list | awk -F ' => ' '{print $1}' | sort | uniq 2>/dev/null > "$snapshot_alias_name_file"
"$rvm_scripts_path/list" strings | \tr ' ' '\n' | sort | uniq > "$snapshot_ruby_name_file"
comm -2 -3 "$snapshot_ruby_name_file" "$snapshot_alias_name_file" > "$snapshot_installable_file"
__rvm_rm_rf "$snapshot_ruby_name_file"
__rvm_rm_rf "$snapshot_alias_name_file"
snapshot_primary_ruby="$(GREP_OPTIONS="" \grep '^\(ree\|ruby-1.8.7\)' < "$snapshot_installable_file" | \grep -v '-head$' |
sort -r | head -n1)"
snapshot_ruby_order="$snapshot_primary_ruby $(GREP_OPTIONS="" \grep -v "$snapshot_primary_ruby" <
"$snapshot_installable_file")"
for snapshot_ruby_name in $snapshot_ruby_order
do
snapshot_install_command="$(__rvm_recorded_install_command "$snapshot_ruby_name")"
if [[ -n "$snapshot_install_command" ]]
then
echo "rvm install $snapshot_install_command" | sed "s#$rvm_path#'\\\"\$rvm_path\\\"'#" >>
"$snapshot_temp_path/install-rubies.sh"
else
__rvm_become "$snapshot_ruby_name"
ruby "$rvm_path/lib/rvm/install_command_dumper.rb" >> "$snapshot_temp_path/install-rubies.sh"
fi
unset snapshot_install_command
done
unset snapshot_ruby_name snapshot_primary_ruby
__rvm_rm_rf "$snapshot_installable_file"
rvm_log "Compressing snapshotting"
destination_path="$PWD"
(
builtin cd "$snapshot_temp_path"
__rvm_rm_rf "$destination_path/$1.tar.gz"
$rvm_tar_command czf "$destination_path/$1.tar.gz" .
result="$?"
__error_on_result "$result" "Error creating archive $destination_path/$1.tar.gz" && return "$result"
)
rvm_log "Cleaning up"
__rvm_rm_rf "$snapshot_temp_path"
rvm_log "Snapshot complete"
}
snapshot_load()
{
typeset package_info snapshot_archive snapshot_temp_path \
alias_name alias_ruby
export rvm_create_flag
if [[ -z "$1" ]]
then
echo "Usage: rvm snapshot load name" >&2
echo "Loads a snapshot from <name>.tar.gz in the current directory." >&2
return 1
fi
snapshot_archive="$PWD/$(echo "$1" | sed 's/.tar.gz$//').tar.gz"
if ! [[ -s "$snapshot_archive" ]]
then
echo "The provides snapshot '$(basename "$snapshot_archive")' doesn't exist." >&2
return 1
fi
snapshot_temp_path="${rvm_tmp_path}/$$-snapshot"
__rvm_rm_rf "$snapshot_temp_path"
\mkdir -p "$snapshot_temp_path"
rvm_log "Extracting snapshot"
(
builtin cd "$snapshot_temp_path"
$rvm_tar_command xzf "$snapshot_archive"
result="$?"
__error_on_result "$result" "Error extracting the archive '$snapshot_archive'" && return "$result"
)
rvm_log "Restoring user settings"
\cp -f "$snapshot_temp_path/db" "$rvm_user_path/db"
rvm_log "Installing rvm-managed packages"
for snapshot_package in $(cat "$snapshot_temp_path/pkg")
do
"$rvm_scripts_path/package" install "$snapshot_package"
result="$?"
__error_on_result "$result" "Error installing package '$snapshot_package'" && return "$result"
done
unset snapshot_package
rvm_log "Installing rubies"
chmod +x "$snapshot_temp_path/install-rubies.sh"
sed -i'' '1 s/#!\/usr\/bin\/env bash -e/#!\/usr\/bin\/env bash\n\nset -e/' "$snapshot_temp_path/install-rubies.sh"
"$snapshot_temp_path/install-rubies.sh"
result="$?"
__error_on_result "$result" "Error importing rubies." && return "$result"
rvm_create_flag=1
rvm_log "Setting up gemsets"
(
builtin cd "$snapshot_temp_path/gems"
gems=($(find . -mindepth 0 -maxdepth 0 -type f "${name_opt}" '*.gems' | sed 's/.gems$//'))
for snapshot_gemset in "${gems[@]//.\/}"
do
__rvm_become "$snapshot_gemset"
result="$?"
__error_on_result "$result" \
"Error becoming '$snapshot_gemset'" && return "$result"
mkdir -p "$GEM_HOME/cache/"
cp -Rf "$snapshot_gemset/" "$GEM_HOME/cache/"
result="$?"
__error_on_result "$result" \
"Error copying across cache for $snapshot_gemset" && return "$result"
"$rvm_scripts_path/gemsets" import "$snapshot_gemset" >/dev/null 2>&1
result="$?"
__error_on_result "$result" \
"Error importing gemset for $snapshot_gemset" && return "$result"
done
)
rvm_log "Restoring aliases"
while read -r package_info
do
# Note: this assumes an '=' int the input...
alias_name="${package_info/=*}"
alias_ruby="${package_info/*=}"
"$rvm_scripts_path/alias" create "$alias_name" "$alias_ruby"
if [[ "$alias_name" == "default" ]]
then
(source "$rvm_scripts_path/rvm" && rvm use "$alias_ruby" --default) >/dev/null 2>&1
result="$?"
__error_on_result "$result" "Error setting default to $alias_ruby" && return "$result"
fi
done < "$snapshot_temp_path/alias"
rvm_log "Cleaning up load process"
__rvm_rm_rf "$snapshot_temp_path"
rvm_log "Loaded snapshot from $(basename "$snapshot_archive")"
}
snapshot_usage()
{
echo "Usage: rvm snapshot {save,load} file" >&2
return 1
}
args=($*)
action="${args[0]}"
args="$(echo ${args[@]:1})" # Strip trailing / leading / extra spacing.
case "$action" in
save) snapshot_save "$args" ;;
load) snapshot_load "$args" ;;
*)
snapshot_usage ;;
esac
exit $?
1.18.53. cli
#!/usr/bin/env bash
__rvm_usage() {
__rvm_pager_or_cat_v "${rvm_path:-$HOME/.rvm}/README"
}
__rvm_run_script()
{
"$rvm_scripts_path/${1:-"$rvm_action"}" "${rvm_ruby_args[@]}"
}
__rvm_parse_args()
{
typeset _string
export rvm_ruby_string
rvm_action="${rvm_action:-""}"
rvm_parse_break=0
if [[ " $* " =~ " --trace " ]]
then
echo "$@"
__rvm_version
fi
while [[ -n "$next_token" ]]
do
rvm_token="$next_token"
if (( $# > 0 ))
then
next_token="$1"
shift
else
next_token=""
fi
case "$rvm_token" in
[[:alnum:]]*|@*) # Commands, Rubies and Gemsets
case "$rvm_token" in
use)
rvm_action="$rvm_token"
rvm_verbose_flag=1
if [[ "ruby" == "$next_token" ]]
then
if (( $# > 0 ))
then
next_token="$1"
shift
else
next_token=""
fi
fi
;;
install|uninstall|reinstall|try_install)
export ${rvm_token}_flag=1
rvm_action=$rvm_token
_string="$*"
if [[ "${_string} " =~ "-- " ]]
then
export rvm_install_args="${_string//*-- /}"
fi
;;
gemset)
rvm_action=$rvm_token
rvm_ruby_gem_home="${GEM_HOME:-""}"
if [[ "$next_token" == "--create" ]]
then
rvm_create_flag=1
next_token="${1:-}"
(( $# == 0 )) || shift
elif [[ " $* " =~ " --create " ]]
then rvm_create_flag=1
fi
if [[ -z "$next_token" ]]
then
rvm_ruby_args=("help")
elif [[ "clear" == "$next_token" ]]
then
__rvm_gemset_clear
rvm_ruby_args=("clear")
elif [[ "use" == "$next_token" ]]
then
rvm_use_flag=1
rvm_ruby_args=("$next_token" "$@")
rvm_gemset_name="$next_token"
if (( $# > 0 ))
then
next_token="$1"
shift
else
next_token=""
fi
if [[ -n "$next_token" ]] ; then rvm_gemset_name="$next_token" ; else rvm_gemset_name="" ; fi
if [[ -z "${rvm_gemset_name:-}" ]]
then
rvm_error "Gemset was not given.\n
return 1
fi
Usage:\n
rvm gemset use <gemsetname>\n"
case "$rvm_gemset_name" in
*${rvm_gemset_separator:-"@"}*)
rvm_ruby_string="${rvm_gemset_name%%${rvm_gemset_separator:-"@"}*}"
rvm_gemset_name="${rvm_gemset_name##*${rvm_gemset_separator:-"@"}}"
if [[ "${rvm_ruby_string:-""}" != "${rvm_gemset_name:-""}" ]] ; then
rvm_ruby_string="$rvm_ruby_string${rvm_gemset_separator:-"@"}$rvm_gemset_name"
fi
rvm_ruby_gem_home="$rvm_ruby_gem_home${rvm_gemset_separator:-"@"}$rvm_gemset_name"
;;
esac
elif [[ "delete" == "$next_token" ]]
then
rvm_delete_flag=1
rvm_ruby_args=("$next_token" "$@")
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
rvm_gemset_name="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
case "$rvm_gemset_name" in
*${rvm_gemset_separator:-"@"}*)
rvm_ruby_string="${rvm_gemset_name%%${rvm_gemset_separator:-"@"}*}"
rvm_gemset_name="${rvm_gemset_name##*${rvm_gemset_separator:-"@"}}"
if [[ "$rvm_ruby_string" != "$rvm_gemset_name" ]] ; then
rvm_ruby_string="$rvm_ruby_string${rvm_gemset_separator:-"@"}$rvm_gemset_name"
fi
rvm_ruby_gem_home="$rvm_ruby_gem_home${rvm_gemset_separator:-"@"}$rvm_gemset_name"
;;
esac
else
if [[ "${rvm_ruby_string:-""}" != "${rvm_gemset_name:-""}" ]] ; then __rvm_ruby_string ;
rvm_ruby_args=("$next_token" "$@")
fi
: rvm_ruby_args:${rvm_ruby_args[*]}:
rvm_parse_break=1
;;
gemdir|gempath|gemhome)
rvm_ruby_args=("$rvm_token")
rvm_action="gemset"
rvm_gemdir_flag=1
if [[ "system" == "$next_token" ]]
then
rvm_system_flag=1
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
if [[ "user" == "$next_token" ]]
then
rvm_user_flag=1
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
;;
pkg)
rvm_action="$rvm_token"
if [[ "$next_token" == "--only-path" ]]
then
shift
rvm_only_path_flag=1
fi
rvm_ruby_args=("$next_token" "$@")
rvm_parse_break=1
;;
fi
system|default)
rvm_action=${rvm_action:-use}
rvm_ruby_interpreter="$rvm_token"
rvm_ruby_string="$rvm_token"
rvm_ruby_strings="$rvm_token"
;;
do|exec|gem|rake|ruby)
if [[ "$rvm_token" == "ruby" ]] && [[ "$rvm_action" == "install" || "$rvm_action" == "use" ]]
then
rvm_ruby_string=ruby
rvm_ruby_strings=ruby
continue
fi
if [[ -z "$next_token" ]]
then
rvm_action="error"
rvm_error_message="'rvm $rvm_token' must be followed by arguments."
break
fi
rvm_action="do"
rvm_parse_break=1
case "$rvm_token" in
do|exec)
# deprecation for exec removed after discsussion with Wayne
rvm_ruby_args=("$next_token" "$@")
;;
*)
# TODO: deprecation issued on 2011.10.11, for RVM 1.9.0
rvm_warn "Please note that \`rvm $rvm_token ...\` is only an alias to \`rvm do $rvm_token ...\`,\n"\
"it might work different as in earlier versions of RVM and will be shortly removed!\n"\
"Also note that you do not have to prefix every command with \`rvm\`, they should just work by itself."
rvm_ruby_args=("$rvm_token" "$next_token" "$@")
;;
esac
;;
fetch|version|srcdir|reset|debug|reload|update|monitor|notes|implode|seppuku|question|answer|env|unexport|requirements|autom
ount)
rvm_action=$rvm_token
;;
mount)
rvm_action=$rvm_token
while [[ -n "${next_token:-}" ]] && [[ -x "${next_token:-}" || -d "${next_token:-}" ]]
do
rvm_ruby_args=("$next_token" "${rvm_ruby_args[@]}")
if (( $# > 0 ))
then
next_token="$1"
shift
else
next_token=""
fi
done
;;
rm|remove)
rvm_action="remove"
rvm_remove_flag=1
;;
# Can likely remove this due to the *) case
default)
# No-op
;;
inspect|ls|list|info|strings|get|current)
if [[ "ls" == "$rvm_action" ]]; then rvm_action="list" ; fi
rvm_action="$rvm_token"
rvm_ruby_args=("$next_token" "$@" )
rvm_parse_break=1
;;
docs|alias|rubygems|cleanup|tools|disk-usage|snapshot|repair|migrate|upgrade|cron)
rvm_action="$rvm_token"
rvm_ruby_args=("$next_token" "$@")
rvm_parse_break=1
;;
user)
rvm_action="tools"
rvm_ruby_args=("$rvm_token" "$next_token" "$@")
rvm_parse_break=1
;;
load-rvmrc)
rvm_action="rvmrc"
rvm_ruby_args=("load" "$next_token" "$@")
rvm_parse_break=1
;;
rvmrc)
rvm_action="rvmrc"
rvm_ruby_args=("$next_token" "$@")
rvm_parse_break=1
;;
benchmark|bench)
rvm_action="benchmark"
;;
specs|tests)
rvm_action="rake"
rvm_ruby_args=("${rvm_token/%ss/s}")
;;
export)
if [[ ! -z "$next_token" ]] ; then
rvm_export_args="$next_token$@"
rvm_action="export"
rvm_parse_break=1
else
rvm_action="error"
rvm_error_message="rvm export must be followed by a NAME=VALUE argument"
fi
;;
group)
rvm_action="group"
rvm_ruby_args=("$next_token" "$@")
rvm_parse_break=1
;;
alt*)
rvm_action="help"
rvm_ruby_args=("alt.md")
rvm_parse_break=1
;;
help|usage)
rvm_action="help"
rvm_ruby_args=("$next_token" "$@")
rvm_parse_break=1
;;
wrapper)
rvm_action="wrapper"
rvm_ruby_string="$next_token" ;
rvm_wrapper_name="$1"
(( $# == 0 )) || shift
rvm_ruby_args=("$@") # list of binaries, or empty
rvm_parse_break=1
;;
rtfm|RTFM)
rvm_action="rtfm"
rvm_parse_break=1
;;
reboot|damnit|wtf|argh|BOOM|boom|wth)
$rvm_action="reboot"
;;
*)
if [[ "$rvm_token" == "in" ]]
then
rvm_token="${next_token}"
next_token="${1:-}"
(( $# == 0 )) || shift
if __rvm_project_dir_check "$rvm_token"
then
export rvm_in_flag="$rvm_token"
__rvm_rvmrc_tools try_to_read_ruby $rvm_token
else
export "rvm_in_flag"=1
fi
elif [[ -n "$rvm_token" ]]
then
# TODO: Middle should be convertable to a case statement for further
#
efficiency only have to deal with the first and last parts.
if [[ "gemset" == "$rvm_action" ]]
then
case "$rvm_token" in
*${rvm_gemset_separator:-"@"}*)
rvm_gemset_name="${rvm_token/*${rvm_gemset_separator:-"@"}/}"
rvm_ruby_string="${rvm_token/${rvm_gemset_separator:-"@"}*/}"
;;
*.gems)
rvm_file_name="${rvm_token/.gems/}.gems" # Account for possible .gems.gems
;;
*)
rvm_gemset_name="${rvm_token/.gems/}"
rvm_file_name="$rvm_gemset_name.gems"
;;
esac
else
case "$rvm_token" in
*,*)
rvm_ruby_strings="$rvm_token"
if [[ -z "${rvm_action:-""}" ]]
then
rvm_action="ruby" # Not sure if we really want to do this but we'll try it out.
fi
;;
${rvm_gemset_separator:-"@"}*)
rvm_action="${rvm_action:-use}"
rvm_gemset_name="${rvm_token/*${rvm_gemset_separator:-"@"}/}"
rvm_ruby_string="${rvm_ruby_string:-""}"
rvm_ruby_strings="${rvm_ruby_string}${rvm_gemset_separator:-"@"}${rvm_gemset_name}"
;;
*${rvm_gemset_separator:-"@"}*)
rvm_action="${rvm_action:-use}"
gemset_name="${rvm_token/*${rvm_gemset_separator:-"@"}/}"
rvm_ruby_string="$rvm_token"
rvm_ruby_strings="$rvm_token"
;;
*+*)
rvm_action="${rvm_action:-use}"
rvm_ruby_alias="${rvm_token/*+/}"
rvm_ruby_string="${rvm_token/+*/}"
rvm_ruby_strings="$rvm_ruby_string"
;;
*-*)
rvm_action="${rvm_action:-use}"
rvm_ruby_string="$rvm_token"
rvm_ruby_strings="$rvm_token"
;;
+([[:digit:]]).+([[:digit:]])*)
rvm_action="${rvm_action:-use}"
rvm_ruby_string="$rvm_token"
rvm_ruby_strings="$rvm_token"
;;
jruby*|ree*|kiji*|macruby*|rbx*|rubinius*|goruby|ironruby*|default*|maglev*|tcs*|all)
rvm_action="${rvm_action:-use}"
if [[ "rubinius" == "$rvm_token" ]] ; then rvm_token="rbx"; fi
rvm_ruby_interpreter="$rvm_token"
rvm_ruby_string="$rvm_token"
rvm_ruby_strings="$rvm_token"
if match "$next_token" "[0-9].[0-9]*" ; then
rvm_ruby_version=$next_token
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
;;
*.rb) # we have a specified ruby script
rvm_ruby_args=("$rvm_token")
rvm_ruby_file="$rvm_token"
if [[ -z "${rvm_action:-""}" || "$rvm_action" == "use" ]]; then
rvm_action="ruby"
fi
;;
*)
if [[ -L "$rvm_rubies_path/$rvm_token" ]] ; then # Alias
rvm_ruby_string=$rvm_token
rvm_ruby_strings="$rvm_token"
rvm_action="${rvm_action:-use}"
elif __rvm_project_dir_check "$rvm_token"
then
__rvm_rvmrc_tools try_to_read_ruby $rvm_token
else
rvm_action="error"
rvm_error_message="Unrecognized command line argument: '$rvm_token'"
fi
;;
esac
fi
else
rvm_action="error"
rvm_error_message="Unrecognized command line argument(s): '$rvm_token $@'"
fi
if [[ "error" == "${rvm_action:-""}" ]] ; then break ; fi
;;
esac
;;
-*) # Flags
case "$rvm_token" in
-S)
rvm_action="ruby"
rvm_ruby_args=("$rvm_token" "$next_token" "$@")
rvm_parse_break=1
;;
-e)
rvm_action="ruby"
IFS="\n"
rvm_ruby_args=("$rvm_token" "'$next_token $@'")
IFS=" "
rvm_parse_break=1
;;
-v|--version)
if [[ -z "$next_token" ]] ; then
rvm_action="version"
else
rvm_ruby_version="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
;;
-n|--name)
rvm_ruby_name="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--branch)
rvm_ruby_repo_branch="$next_token"
next_token="${1:-""}"
shift
;;
--sha)
rvm_ruby_sha="$next_token"
next_token="${1:-""}"
shift
;;
--repository|--repo|--url)
rvm_ruby_repo_url="$next_token"
next_token="${1:-""}"
shift
;;
--ree-options)
if [[ -n "$next_token" ]] ; then
export rvm_ree_options="${next_token//,/ }"
next_token=""
if [[ $# -gt 0 ]] ; then
next_token="$1" ; shift
fi
else
rvm_action="error"
rvm_error_message="--ree-options *must* be followed by... well... options."
fi
;;
--patches|--patch)
rvm_patch_names="$next_token ${rvm_patch_names:-""}"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
rvm_patch_original_pwd="$PWD"
;;
--arch|--archflags)
rvm_architectures="${rvm_architectures:-},${next_token#-arch }" ;
rvm_architectures="${rvm_architectures##,}" ;
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--with-arch=*)
rvm_architectures="${rvm_architectures:-},${rvm_token#--with-arch=}" ;
rvm_architectures="${rvm_architectures##,}" ;
;;
--32)
rvm_architectures="${rvm_architectures:-},i386" ;
rvm_architectures="${rvm_architectures##,}" ;
;;
--64)
rvm_architectures="${rvm_architectures:-},x86_64" ;
rvm_architectures="${rvm_architectures##,}" ;
;;
--universal)
rvm_architectures="${rvm_architectures:-},i386,x86_64" ;
rvm_architectures="${rvm_architectures##,}" ;
;;
--head)
rvm_head_flag=1
;;
--static)
rvm_static_flag=1
;;
--bin)
if [[ "update" == "${rvm_action:-""}" ]] ; then
rvm_bin_flag=1
else
rvm_bin_path="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
;;
-r|--require)
if [[ -z "$next_token" ]] ; then
rvm_action="error"
rvm_error_message="-r|--require *must* be followed by a library name."
else
rvm_ruby_require="$rvm_ruby_require -r$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
;;
--rdoc|--yard)
rvm_docs_type="$rvm_token"
rvm_docs_type
;;
-f|--file)
rvm_action="ruby"
rvm_ruby_file="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--passenger)
rvm_log "NOTE: If you are using Passenger 3 you no longer need the passenger_ruby,\nuse the wrapper script for
your ruby instead (see 'rvm wrapper')"
rvm_wrapper_name="${rvm_token/--/}"
;;
--editor)
rvm_wrapper_name="${rvm_token/--/}"
;;
--alias)
if [[ -n "$next_token" ]]; then
rvm_ruby_aliases="$(echo "${rvm_ruby_aliases//,/ } ${1//,/ }" | __rvm_strip)"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
;;
--symlink)
rvm_warn "--symlink has been removed, please see 'rvm wrapper'."
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
-h|--help)
rvm_action=help
;;
--make)
rvm_ruby_make="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--make-install)
rvm_ruby_make_install="$next_token" ; shift
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--nice)
rvm_niceness="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
-l|--level)
rvm_ruby_patch_level="p$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--sdk)
rvm_sdk="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--autoconf-flags)
rvm_autoconf_flags="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--proxy)
rvm_proxy="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
-q|--quiet)
rvm_quiet_flag=1
;;
-s|--silent)
rvm_silent_flag=1
;;
--disable-llvm|--disable-jit)
rvm_llvm_flag=0
;;
--enable-llvm|--enable-jit)
rvm_llvm_flag=1
;;
--install)
rvm_install_on_use_flag=1
;;
--color=*)
rvm_pretty_print_flag=${rvm_token#--color=}
;;
--pretty)
rvm_pretty_print_flag=auto
;;
--1.8|--1.9)
rvm_token=${rvm_token#--}
rvm_token=${rvm_token//\./}
export "rvm_${rvm_token}_flag"=1
;;
--rvmrc|--versions-conf|--ruby-version)
rvm_token=${rvm_token#--}
rvm_token=${rvm_token//-/_}
export rvm_rvmrc_flag="${rvm_token}"
;;
--self|--gem|--rubygems|--reconfigure|--default|--force|--export|--summary|--latest|--yaml|--json|--archive|-shebang|--env|--path|--cron|--tail|--delete|--verbose|--import|--sticky|--create|--gems|--docs|--skip-autoreconf|--18|--19|-force-autoconf|--auto|--autoinstall-bundler|--ignore-gemsets|--skip-gemsets)
rvm_token=${rvm_token#--}
rvm_token=${rvm_token//-/_}
export "rvm_${rvm_token}_flag"=1
;;
--dump-environment)
export rvm_dump_environment_flag="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
--clang)
rvm_configure_flags="${rvm_configure_flags:-""} --with-gcc=clang"
;;
-M|--make)
if [[ ! -z "$next_token" ]] ; then
rvm_make_flags="$rvm_make_flags ${next_token//,/ }"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
else
rvm_action="error"
rvm_error_message="--make *must* be followed by make flags."
fi
;;
-j)
if [[ ! -z "$next_token" ]] ; then
rvm_make_flags="$rvm_make_flags -j$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
else
rvm_action="error"
rvm_error_message="-j *must* be followed by an integer (normally the # of CPU's in your machine)."
fi
;;
--with-rubies)
rvm_ruby_strings="$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
;;
-C|--configure)
if [[ ! -z "$next_token" ]] ; then
rvm_configure_flags="${next_token//,--/ --}"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
else
rvm_action="error"
rvm_error_message="--configure *must* be followed by configure flags."
fi
;;
--with-*|--without-*|--enable-*|--disable-*)
rvm_configure_flags="${rvm_configure_flags:-""} $rvm_token"
;;
-I|--include)
if [[ -z "$next_token" ]] ; then
rvm_action="error"
rvm_error_message="-I|--include *must* be followed by a path."
else
rvm_ruby_load_path="$rvm_ruby_load_path:$next_token"
if [[ $# -gt 0 ]] ; then next_token="$1" ; shift ; else next_token="" ; fi
fi
;;
--debug)
export rvm_debug_flag=1
set -o verbose
;;
--trace|--debug)
typeset option
[[ -n "${ZSH_VERSION:-""}" ]] || set -o errtrace
# errexit pipefail
if [[ "$rvm_token" == "--trace" ]]
then
export rvm_trace_flag=1
set -o xtrace
[[ -n "${ZSH_VERSION:-""}" ]] ||
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
fi
;;
--)
if [[ "${rvm_action}" == *install ]]
then rvm_configure_flags="${rvm_configure_flags:-""} $next_token
else rvm_ruby_args=("$next_token" "$@")
fi
rvm_parse_break=1
;;
$*"
*)
rvm_action="error"
rvm_error_message="Unrecognized command line flag: '$rvm_token'"
esac
;;
*)
if __rvm_project_dir_check "$rvm_token"
then
__rvm_rvmrc_tools try_to_read_ruby "$rvm_token"
else # People who are smoking crack.
rvm_action="error"
rvm_error_message="Unrecognized command line argument(s): '$rvm_token $@'"
fi
;;
esac
if [[ -z "${rvm_action:-""}" && -n "${rvm_ruby_string:-""}" ]]
; then rvm_action="use" ; fi
if [[ ${rvm_parse_break:-0} -eq 1 || -n "${rvm_error_message:-""}" ]] ; then break ; fi
done
# Empty args list.
while [[ $# -gt 0 ]] ; do shift ; done
if [[ -n "${rvm_error_message:-""}" ]] ; then
rvm_error "$rvm_error_message ( see: 'rvm usage' )"
return 1
fi
}
rvm()
{
typeset result current_result
export -a rvm_ruby_args >/dev/null 2>/dev/null
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
: rvm_stored_umask:${rvm_stored_umask:=$(umask)}
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
\${LINENO} > "
for rvmrc in "${rvm_rvmrc_files[@]}"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "
Error:
$rvmrc is for rvm settings only.
rvm CLI may NOT be called from within $rvmrc.
Skipping the loading of $rvmrc"
return 1
else
source "$rvmrc"
fi
fi
done
unset rvm_rvmrc_files
fi
disk_version="$(cat "$rvm_path/VERSION") ($(cat "$rvm_path/RELEASE" 2>/dev/null))"
if [[ -s "$rvm_path/VERSION" &&
"${rvm_version:-}" != "${disk_version:-}" &&
"reload" != "${1:-}" ]]
then
if [[ ${rvm_auto_reload_flag:-0} -gt 0 ]]
then
__rvm_project_rvmrc_lock=0
rvm_reload_flag=1
source "${rvm_scripts_path:-${rvm_path}/scripts}/rvm"
else
printf "%b" "
A RVM version ${disk_version} is installed yet ${rvm_version} is loaded.
Please do one of the following:
* 'rvm reload'
* open a new shell
* 'echo rvm_auto_reload_flag=1 >> ~/.rvmrc' # for auto reload with msg.
* 'echo rvm_auto_reload_flag=2 >> ~/.rvmrc' # for silent auto reload.
"
return 1
fi
fi
__rvm_initialize
__rvm_setup
next_token="$1"
[[ $# -eq 0 ]] || shift
__rvm_parse_args "$@"
result=$?
rvm_action="${rvm_action:-usage}"
[[ $result -gt 0 ]] ||
case "$rvm_action" in
use)
if rvm_is_a_shell_function
then __rvm_use
fi
;;
srcdir)
__rvm_source_dir
;;
strings)
__rvm_strings
;;
version)
__rvm_version
;;
ls|list)
"$rvm_scripts_path/list" "${rvm_ruby_args[@]}"
;;
# TODO: Make debug run in the current environment, issues with not exported vars.
debug)
rvm_is_not_a_shell_function="${rvm_is_not_a_shell_function}" "$rvm_scripts_path/info" '' debug
;;
usage)
__rvm_usage
;;
benchmark)
source "$rvm_scripts_path/functions/benchmark"
__rvm_benchmark
;;
inspect)
__rvm_inspect
;;
update)
printf "%b" "ERROR: rvm update has been removed. See 'rvm get' and rvm 'rubygems' CLI API instead\n"
;;
reset)
source "$rvm_scripts_path/functions/reset"
__rvm_reset
;;
reboot)
source "$rvm_scripts_path/functions/cleanup"
__rvm_reboot
;;
implode|seppuku)
source "$rvm_scripts_path/functions/implode"
__rvm_implode
;;
get)
next_token="${1:-}"
(( $# > 0 )) && shift
[[ "$next_token" == "${rvm_action}" ]] && shift
tmpdir="${TMPDIR:-/tmp}"
\cp -f "$rvm_scripts_path/get" "$tmpdir/$$"
if bash "$tmpdir/$$" "${rvm_ruby_args[@]}"
then
rvm_reload_flag=1
else
rvm_error "Could not update RVM, get some help at #rvm IRC channel at freenode servers."
fi
\rm -f $tmpdir/$$
;;
help|rtfm|env|current|list|monitor|notes|package|extract|pkg|requirements)
if (( $# > 0 ))
then
next_token="$1"
shift
else
next_token=""
fi
if [[ "$next_token" == "${rvm_action}" ]]
then
shift
fi
"$rvm_scripts_path/${rvm_action}" "${rvm_ruby_args[@]}"
;;
info)
rvm_is_not_a_shell_function="${rvm_is_not_a_shell_function}" "$rvm_scripts_path/${rvm_action}" "${rvm_ruby_args[@]}"
;;
cleanup|tools|snapshot|disk-usage|repair|alias|docs|rubygems|migrate|upgrade|cron)
__rvm_run_script "$rvm_action" "${rvm_ruby_args[@]}"
;;
wrapper)
"$rvm_scripts_path/wrapper" "$rvm_ruby_string" "$rvm_wrapper_name" "${rvm_ruby_args[@]}"
result=$?
unset rvm_wrapper_name
;;
do)
old_rvm_ruby_string=${rvm_ruby_string:-}
unset rvm_ruby_string
export rvm_ruby_strings
(
if [[ -n "${rvm_in_flag}" && -d "${rvm_in_flag}" ]]
then builtin cd "${rvm_in_flag}"
fi
"$rvm_scripts_path/set" "$rvm_action" "${rvm_ruby_args[@]}"
)
result=$?
# Restore the state pre-sets.
[[ -n "$old_rvm_ruby_string" ]] && rvm_ruby_string=$old_rvm_ruby_string
unset old_rvm_ruby_string
;;
rvmrc)
__rvm_rvmrc_tools "${rvm_ruby_args[@]}"
;;
gemset)
if [[ ${rvm_use_flag:-0} -eq 1 ]]
then
__rvm_gemset_use
else
export rvm_ruby_strings
"$rvm_scripts_path/gemsets" "${rvm_ruby_args[@]}" ; result=$?
rvm_ruby_strings=""
# Clear the gemset.
if [[ ${rvm_delete_flag:-0} -eq 1 ]] ; then
gem_prefix="$(echo "${GEM_HOME:-""}" | \sed 's/'${rvm_gemset_separator:-"@"}'.*$//')"
if [[ "${GEM_HOME:-""}" == "${gem_prefix}${rvm_gemset_separator:-"@"}${rvm_gemset_name}" ]] ; then
rvm_ruby_gem_home="$gem_prefix"
GEM_HOME="$rvm_ruby_gem_home"
GEM_PATH="$rvm_ruby_gem_home:$rvm_ruby_gem_home${rvm_gemset_separator:-"@"}global"
export rvm_ruby_gem_home GEM_HOME GEM_PATH
fi
unset gem_prefix
fi
fi
;;
reload)
rvm_reload_flag=1
;;
tests|specs)
rvm_action="rake" ; __rvm_do
;;
remove)
export rvm_path
if [[ -n "${rvm_ruby_strings}" ]]
then
"$rvm_scripts_path"/manage "$rvm_action" "${rvm_ruby_strings//*-- }"
else
"$rvm_scripts_path"/manage "$rvm_action"
fi
rvm_ruby_string=default
__rvm_use
;;
fetch|uninstall|reinstall)
export rvm_path
if [[ -n "${rvm_ruby_strings}" ]]
then
"$rvm_scripts_path"/manage "$rvm_action" "${rvm_ruby_strings//*-- }"
else
"$rvm_scripts_path"/manage "$rvm_action"
fi
;;
try_install|install)
export rvm_path
if [[ -n "${rvm_ruby_strings}" ]]
then
typeset save_ruby
selected_ruby="$( __rvm_select && echo $rvm_env_string )"
if [[ -z "${selected_ruby}" ]]
then
rvm_error "Could not detect ruby version/name for installation, please be more specific."
false #report error
elif (( ${rvm_force_flag:-0} == 0 )) && "$rvm_scripts_path"/list strings | GREP_OPTIONS="" \grep
"^${selected_ruby}$" > /dev/null
then
rvm_log "Already installed ${selected_ruby}.
To reinstall use:
rvm reinstall ${rvm_ruby_strings}
"
else
if [[ $(ls -1 $rvm_rubies_path/*/bin/ruby 2>/dev/null | wc -l) -eq 0 ]] &&
[[ ${rvm_is_not_a_shell_function:-0} -eq 0 ]]
then
{
echo "Ruby (and needed base gems) for your selection will be installed shortly."
echo "Before it happens, please read and execute the instructions below."
echo "Please use a separate terminal to execute any additional commands."
"$rvm_scripts_path"/requirements
echo "Press 'q' to continue."
} | less
fi
"$rvm_scripts_path"/manage install "${rvm_ruby_strings}"
fi
else
rvm_error "Can not use or install 'all' rubies."
false #report error
fi
;;
mount|automount)
"${rvm_scripts_path}/external" "$rvm_action" "${rvm_ruby_args[@]}"
;;
export)
__rvm_export "$rvm_export_args"
;;
unexport)
__rvm_unset_exports
;;
error)
false
;;
answer)
source "$rvm_scripts_path/functions/fun"
__rvm_Answer_to_the_Ultimate_Question_of_Life_the_Universe_and_Everything ; result=42
;;
question)
source "$rvm_scripts_path/functions/fun"
__rvm_ultimate_question ; result=42
;;
*)
if [[ -n "${rvm_action:-""}" ]] ; then
rvm_error "unknown action '$rvm_action'"
else
__rvm_usage
fi
false # result
esac
current_result=$?
# Use the result of first found error
(( result > 0 )) || result=${current_result}
[[ $result -gt 0 ]] ||
case "$rvm_action" in
reinstall|try_install|install)
if [[ $(ls -1 $rvm_rubies_path/*/bin/ruby 2>/dev/null | wc -l) -eq 1 ]] &&
[[ ! -f "${rvm_environments_path}/default" ]]
then
if rvm_is_a_shell_function
then rvm_default_flag=1 __rvm_use
fi
fi
;;
esac
current_result=$?
# Use the result of first found error
(( result > 0 )) || result=${current_result}
if [[ ${rvm_reload_flag:-0} -eq 1 ]]
then
__rvm_project_rvmrc_lock=0
source "$rvm_scripts_path/rvm"
fi
typeset __local_rvm_trace_flag
__local_rvm_trace_flag=${rvm_trace_flag:-0}
__rvm_teardown
if (( __local_rvm_trace_flag > 0 ))
then
set +o verbose
set +o xtrace
[[ -n "${ZSH_VERSION:-""}" ]] || set +o errtrace
fi
return ${result:-0}
}
1.18.54. patchsets
#!/usr/bin/env bash
rvm_base_except="selector"
source "$rvm_scripts_path/base"
source "$rvm_scripts_path/patches"
lookup_patchset()
{
typeset paths lookup_path
if [[ -z "$1" ]]
then
echo "Usage: rvm patchset show name"
return 1
fi
paths=($(__rvm_ruby_string_paths_under "$rvm_path/patchsets" | sort -r))
for lookup_path in "${paths[@]}"
do
if [[ -s "$lookup_path/$1" ]]
then
cat "$lookup_path/$1"
return 0
fi
done
return 1
}
# Return the full patch for a given patch.
__rvm_lookup_full_patch_path()
{
typeset directory directories extension patch_path
directories=($(__rvm_patch_lookup_path))
# Absolute path, pwd and then finally the rvm patches path.
for directory in "${directories[@]}" ; do
for extension in {"",.patch,.diff}; do
patch_path="${directory}${1}${extension}"
if [[ -s "$patch_path" ]]; then
echo "$patch_path"
return
fi
done
done
return 1
}
usage()
{
printf "%b" "
Usage:
rvm patchset {show,lookup} [patchset]
Description:
Tools for manipulating patchsets.
"
return 1
}
args=($*)
action="${args[0]}"
patchset="${args[1]}"
args="$(echo ${args[@]:2})" # Strip trailing / leading / extra spacing.
case "$action" in
show|lookup) lookup_patchset "$patchset" ;;
*) usage ;;
esac
exit $?
1.18.55. base
#!/usr/bin/env bash
# Base is a collection of general files + commonly included setup functions.
: rvm_trace_flag:${rvm_trace_flag:=0}
if (( rvm_trace_flag > 0 ))
then
set -o xtrace
# set -o errexit
if [[ -z "${ZSH_VERSION:-}" ]]
then
# set -o errtrace
# set -o pipefail
export PS4
PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
\${LINENO} > "
fi
elif [[ ${rvm_debug_flag:-0} > 0 ]]
then
rvm_debug_flag=0
fi
export __array_start rvm_path >/dev/null
#
# Setup environment parameters.
#
if [[ -n "${ZSH_VERSION:-}" ]]
then
__array_start=1
else
__array_start=0
fi
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
: rvm_stored_umask:${rvm_stored_umask:=$(umask)}
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
for rvmrc in "${rvm_rvmrc_files[@]}"
do
if [[ -f "$rvmrc" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$rvmrc" >/dev/null 2>&1
then
printf "%b" "
Error:
$rvmrc is for rvm settings only.
rvm CLI may NOT be called from within $rvmrc.
Skipping the loading of $rvmrc"
return 1
else
source "$rvmrc"
fi
fi
done
unset rvm_rvmrc_files
fi
export rvm_path
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 )) && [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
elif [[ -d "${HOME}/.rvm" ]]
then rvm_path="${HOME}/.rvm"
elif [[ -d "/usr/local/rvm" ]]
then rvm_path="/usr/local/rvm"
else echo "Can't find rvm install!" 1>&2 ; exit 1
fi
fi
true ${rvm_scripts_path:="$rvm_path/scripts"}
# Initialize all main RVM variables.
source "$rvm_scripts_path/initialize"
# Load the general scripts.
# Use rvm_base_except="selector", for example, to override the loading.
case " ${rvm_base_except:-} " in
(*[[:space:]]selector[[:space:]]*)
true # do not load.
;;
(*)
source "$rvm_scripts_path/selector"
source "$rvm_scripts_path/selector_gemsets"
;;
esac
typeset -a scripts
scripts=(
logging utility init cleanup env rvmrc install environment gemset db bundler
)
for entry in ${scripts[@]} ; do
source "$rvm_scripts_path/functions/$entry"
done
unset scripts entry rvm_base_except
1.18.56. gemsets
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
source "$rvm_scripts_path/functions/build" # For gems with C extensions.
rvm_ruby_gem_home="${rvm_ruby_gem_home:-$GEM_HOME}"
if [[ ! -d "$rvm_ruby_gem_home" ]] && builtin command -v gem > /dev/null 2>&1
then
rvm_ruby_gem_home="$(gem env home)"
fi
usage()
{
cat -v "${rvm_help_path}/gemset"
}
gemset_list_all()
{
for rvm_ruby_string in $( rvm_project_rvmrc=0 rvm list strings )
do
(__rvm_use ; gemset_list)
done
unset rvm_ruby_string
}
gemset_list_strings()
{
typeset gem_string
for rvm_ruby_string in $( rvm_project_rvmrc=0 rvm list strings )
do
for gem_string in "${rvm_gems_path:-${rvm_path}/gems}/${rvm_ruby_string}${rvm_gemset_separator:-@}"*
do
printf "%b" "${gem_string##*/}\n"
done
done
unset rvm_ruby_string
}
gemset_update()
{
if [[ -z "$rvm_ruby_strings" ]]
then
rvm_log "Running gem update for all rubies and gemsets."
rvm_ruby_strings="$(
builtin cd "${rvm_gems_path:-"$rvm_path/gems"}" ;
find . -maxdepth 1 -mindepth 1 -type d -print 2>/dev/null \
| GREP_OPTIONS="" \grep -v '^\(doc\|cache\|@\|system\)' | \tr '\n' ','
)"
rvm_ruby_strings="${rvm_ruby_strings/%,}"
rvm_ruby_strings="${rvm_ruby_strings//.\/}"
else
rvm_log "Running gem update for the specified rubies."
fi
export rvm_ruby_strings
"$rvm_scripts_path/set" "gem" "update"
return $?
}
gemset_globalcache()
{
typeset gc_status globalcache_enabled directories directory_name \
full_directory_path directory_name
if [[ "$1" == "enabled" ]]
then
if __rvm_using_gemset_globalcache
then
gc_status="Enabled"
globalcache_enabled=0
else
gc_status="Disabled"
globalcache_enabled=1
fi
rvm_log "Gemset global cache is currently: $gc_status"
return $globalcache_enabled
elif [[ "$1" == "disable" ]]
then
rvm_log "Removing the global cache (note: this will empty the caches)"
directories=($(
builtin cd "${rvm_gems_path:-"$rvm_path/gems"}" ;
find . -maxdepth 1 -mindepth 1 -type d -print)
)
for directory_name in "${directories[@]//.\/}"
do
current_cache_path="${rvm_gems_path:-"$rvm_path/gems"}/$directory_name/cache"
if [[ -L "$current_cache_path" \
&& "$(readlink "$current_cache_path")" == "$rvm_gems_cache_path" ]]
then
rvm_log "Reverting the gem cache for $directory_name to an empty directory."
rm -f "$current_cache_path" 2>/dev/null
mkdir -p "$current_cache_path" 2>/dev/null
fi
done
"$rvm_scripts_path/db" "$rvm_user_path/db" "use_gemset_globalcache" "delete"
elif [[ "$1" == "enable" ]]
then
rvm_log "Enabling global cache for gems."
mkdir -p "$rvm_gems_cache_path"
directories=($(
builtin cd "${rvm_gems_path:-"$rvm_path/gems"}" ;
find . -maxdepth 1 -mindepth 1 -type d -print)
)
for directory_name in "${directories[@]//.\/}"
do
current_cache_path="${rvm_gems_path:-"$rvm_path/gems"}/$directory_name/cache"
if [[ -d "$current_cache_path" && ! -L "$current_cache_path" ]]
then
rvm_log "Moving the gem cache for $directory_name to the global cache."
mv "$current_cache_path/"*.gem "$rvm_gems_cache_path/" 2>/dev/null
case "${current_cache_path%\/}" in
*cache)
__rvm_rm_rf "$current_cache_path"
ln -fs "$rvm_gems_cache_path" "$current_cache_path"
;;
esac
fi
done
"$rvm_scripts_path/db" "$rvm_user_path/db" "use_gemset_globalcache" "true"
else
printf "%b" "
Usage:
rvm gemset globalcache {enable,disable,enabled}
Enable / Disable / Status the use of a global gem cachedir.
"
return 1
fi
}
gemset_name()
{
echo "${rvm_ruby_gem_home##*${rvm_gemset_separator:-"@"}}"
return $?
}
gemset_dir()
{
echo "$rvm_ruby_gem_home"
return $?
}
gemset_create()
{
typeset gem_home gemset gemsets prefix
if [[ -n "$rvm_ruby_string" ]]
then
__rvm_select
fi
prefix=$(echo $rvm_ruby_gem_home | sed 's/'${rvm_gemset_separator:-"@"}'.*$//')
gemsets=(${args[@]})
for gemset in "${gemsets[@]}"
do
if [[ "$(__rvm_env_string)" == "system" ]]
then
rvm_error "Can not create gemset before using a ruby. Try 'rvm use <some ruby>'."
return 1
fi
if [[ "$gemset" == *"${rvm_gemset_separator:-"@"}"* ]]
then
rvm_error "Can not create gemset '$gemset', it contains a \"${rvm_gemset_separator:-"@"}\"."
return 2
fi
if [[ -z "$gemset" || "$gemset" == *"${rvm_gemset_separator:-"@"}" ]]
then
rvm_error "Can not create gemset '$gemset', Missing name. "
return 3
fi
gem_home="${prefix}${rvm_gemset_separator:-"@"}${gemset}"
[[ -d "$gem_home/bin" ]] || mkdir -p "$gem_home/bin"
: rvm_gems_cache_path:${rvm_gems_cache_path:=${rvm_gems_path:-"$rvm_path/gems"}/cache}
# When the globalcache is enabled, we need to ensure we setup the cache directory correctly.
if __rvm_using_gemset_globalcache
then
if [[ -d "$gem_home/cache" && ! -L "$gem_home/cache" ]]
then
mv "$gem_home/cache"/*.gem "$rvm_gems_cache_path/" 2>/dev/null
__rvm_rm_rf "$gem_home/cache"
fi
ln -fs "$rvm_gems_cache_path" "$gem_home/cache"
fi
if ! ( rvm_ruby_string="$(__rvm_env_string)${rvm_gemset_separator:-"@"}${gemset}" __rvm_use )
then
rvm_error "Can not create environment file for '$gemset', Could not use ruby. "
return 4
fi
rvm_log "'$gemset' gemset created ($gem_home)."
done
return 0
}
__gemset_list_single()
{
typeset gemset current_gemset
gemset="$1"
current_gemset="$2"
gemset="${gemset##*${rvm_gemset_separator:-@}}"
[[ -n "${gemset}" ]] || gemset="(default)"
[[ -n "${current_gemset}" ]] || current_gemset="(default)"
if [[ "${gemset}" == "${current_gemset}" ]]
then
if [[ "${args[0]:-""}" != "strings" ]]
then
echo "=> ${gemset}"
else
echo "${gemset} (current)"
fi
else
if [[ "${args[0]:-""}" != "strings" ]]
then
echo "
${gemset}"
else
echo "$gemset"
fi
fi
}
gemset_list()
{
if [[ ${rvm_ruby_selected_flag:-0} -eq 0 ]]
then
__rvm_select
fi
[[ -d "${rvm_gems_path:-"$rvm_path/gems"}" ]] || {
rvm_error "${rvm_gems_path:-"$rvm_path/gems"} does not exist!"
return 1
}
[[ -n "${rvm_ruby_string:-""}" ]] || {
rvm_error "\$rvm_ruby_string is not set!"
return 1
}
typeset current_gemset IFS
current_gemset=$(__rvm_current_gemset)
IFS=""
[[ "${args[0]:-""}" == "strings" ]] ||
rvm_log "\ngemsets for $rvm_ruby_string (found in ${rvm_gems_path:-"$rvm_path/gems"}/$rvm_ruby_string)"
for gemset in ${rvm_gems_path:-${rvm_path}/gems}/${rvm_ruby_string}${rvm_gemset_separator:-@}*
do
__gemset_list_single "${gemset}" "${current_gemset}"
done
[[ "${args[0]:-""}" == "strings" ]] || printf "%b" "\n"
return 0
}
gemset_after_delete_cleanup()
{
typeset rvm_gemset_name ruby_at_gemset gemdir
rvm_gemset_name=$1
ruby_at_gemset=$2
gemdir=$3
if [[ -L "$gemdir/cache" ]]
then
rm -f "$gemdir/cache"
fi
(
for item in $( $rvm_scripts_path/alias search_by_target ${ruby_at_gemset} )
do
$rvm_scripts_path/alias delete ${item}
done
find "${rvm_bin_path:=$rvm_path/bin}" \( -name \*${ruby_at_gemset} -or -lname \*${ruby_at_gemset}/\* \) -delete
)
rm -rf "${rvm_wrappers_path:="$rvm_path/wrappers"}/${ruby_at_gemset}"
}
gemset_delete()
{
gemsets=(${args[@]})
if (( ${rvm_ruby_selected_flag:-0} == 0))
then
__rvm_select
fi
if [[ -n "${gemsets[$__array_start]}" ]]
then
rvm_gemset_name="${gemsets[$__array_start]}"
fi
if [[ -n "$rvm_gemset_name" ]]
then
ruby_at_gemset="$rvm_ruby_string${rvm_gemset_separator:-"@"}$rvm_gemset_name"
gemdir="${rvm_gems_path:-"$rvm_path/gems"}/${ruby_at_gemset}"
if [[ -d "$gemdir" && "$gemdir" != '/' && ${rvm_force_flag:-0} -gt 0 ]]
then
__rvm_rm_rf "$gemdir"
gemset_after_delete_cleanup $rvm_gemset_name $ruby_at_gemset $gemdir
elif [[ -d "$gemdir" ]]
then
rvm_warn "Are you SURE you wish to remove the entire gemset directory '$rvm_gemset_name' ($gemdir)?"
printf "%b" "(anything other than 'yes' will cancel) > "
read response
if [[ "yes" == "$response" ]]
then
__rvm_rm_rf "$gemdir"
gemset_after_delete_cleanup $rvm_gemset_name $ruby_at_gemset $gemdir
else
rvm_log "Not doing anything, phew... close call that one eh?"
return 2
fi
else
rvm_log "$gemdir did not previously exist. Ignoring."
fi
else
rvm_error "A gemset name must be specified in order to delete a gemset."
return 1
fi
return 0
}
gemset_empty()
{
typeset gemdir entry
gemsets=(${args[@]})
if [[ -z "${rvm_ruby_gem_home:-""}" ]]
then
__rvm_select
fi
if [[ -n "${gemsets[$__array_start]}" ]]
then
rvm_gemset_name="${gemsets[$__array_start]}"
rvm_gemset_name="${rvm_gemset_name#default}"
ruby_at_gemset="$rvm_ruby_string${rvm_gemset_name:+${rvm_gemset_separator:-"@"}}${rvm_gemset_name}"
gemdir="${rvm_gems_path:-"$rvm_path/gems"}/${ruby_at_gemset}"
else
gemdir="${rvm_ruby_gem_home}"
fi
if [[ ${rvm_force_flag:-0} -gt 0 ]]
then
for entry in "$gemdir"/bin/* "$gemdir"/doc/* "$gemdir"/gems/* "$gemdir"/specifications/*
do
__rvm_rm_rf "$entry"
done
elif [[ -d "$gemdir" ]]
then
rvm_warn "Are you SURE you wish to remove the installed gems for gemset '$(basename "$gemdir")' ($gemdir)?"
echo -n "(anything other than 'yes' will cancel) > "
read response
if [[ "yes" == "$response" ]]
then
for entry in "$gemdir"/bin/* "$gemdir"/doc/* "$gemdir"/gems/* "$gemdir"/specifications/* ; do
__rvm_rm_rf "$entry"
done
else
rvm_log "Not doing anything, phew... close call that one eh?"
fi
else
rvm_log "$gemdir did not previously exist. Ignoring."
fi
return 0
}
# Migrate gemsets from ruby X to ruby Y
gemset_copy()
{
typeset source_ruby destination_ruby source_path destination_path
# Clear the current environment so that it does not influence this operation.
unset rvm_gemset_name rvm_ruby_gem_home GEM_HOME GEM_PATH
source_ruby="${args[$__array_start]:-""}"
args[$__array_start]="" ; args=(${args[@]})
destination_ruby="${args[$__array_start]:-""}"
args[$__array_start]="" ; args=(${args[@]})
if [[ -z "$destination_ruby" || -z "$source_ruby" ]]
then
rvm_error "Source and destination must be specified: 'rvm gemset copy X Y'"
return 1
fi
# Verify the destination gemset exists before attempting to use it.
(
rvm_ruby_string="$destination_ruby"
export rvm_create_flag=1
{ __rvm_ruby_string && __rvm_gemset_select; } 2> /dev/null
)
result=$?
if [[ $result -ne 0 ]]
then
rvm_error "Destination gemset '$destination_ruby' does not yet exist."
return 1
fi
# TODO: Account for more possibilities:
#
rvm gemset copy 1.9.2 @gemsetb
#
rvm gemset copy @gemseta @gemsetb
#
rvm gemset copy gemseta gemsetb
#
rvm gemset copy gemseta 1.8.7@gemsetb
#
#
#
#
From 1.9.2 default to current ruby, 1.9.2 exists.
Current ruby, gemseta exists.
Currenty Ruby, gemseta exists.
Currenty Ruby@gemseta, current ruby@gemseta exists.
source_path=$(
rvm_ruby_string="$source_ruby"
{ __rvm_ruby_string && __rvm_gemset_select; } > /dev/null 2>&1
echo $rvm_ruby_gem_home
)
destination_path=$(
rvm_ruby_string="$destination_ruby"
{ __rvm_ruby_string && __rvm_gemset_select; }
echo $rvm_ruby_gem_home
)
> /dev/null 2>&1
if [[ -z "$source_path" || ! -d "$source_path" ]]
then
rvm_error "Unable to expand '$source_ruby' or directory does not exist."
return 1
fi
if [[ -z "$destination_path" ]]
then
rvm_error "Unable to expand '$destination_ruby'."
return 1
fi
if [[ -d "$source_path" ]]
then
rvm_log "Copying gemset from $source_ruby to $destination_ruby"
for dir in bin doc gems specifications cache bundle
do
mkdir -p "$destination_path/$dir"
if [[ -d "$source_path/$dir" ]]
then
cp -Rf "$source_path/$dir" "$destination_path/"
elif [[ -L "$source_path/$dir" ]]
then
cp "$source_path/$dir" "$destination_path/$dir"
fi
done
rvm_log "Making gemset for $destination_ruby pristine."
__rvm_run_with_env "gemset.pristine" "$destination_ruby" "rvm gemset pristine"
else
rvm_error "Gems directory does not exist for $source_path ($source_path)"
return 1
fi
}
# Migrate gemsets from ruby X to ruby Y
gemset_rename()
{
typeset source_name destination_name source_path destination_path
source_name="${args[$__array_start]:-""}"
args[$__array_start]="" ; args=(${args[@]})
destination_name="${args[$__array_start]:-""}"
args[$__array_start]="" ; args=(${args[@]})
if [[ -z "$destination_name" || -z "$source_name" ]]
then
rvm_error "Source and destination gemsets must be specified: 'rvm gemset rename X Y'"
return 1
fi
source_path="$(rvm_silence_logging=1 rvm_gemset_name=${source_name} __rvm_use "${rvm_ruby_string}@${source_name}" ; gem
env gemdir)"
if [[ -z "$source_path" || ! -d "$source_path" ]]
then
rvm_error "gemset '$source_name' does not exist."
return 1
fi
destination_path=${source_path/%$source_name/$destination_name}
if [[ -d "$source_path" ]]
then
if [[ ! -d "$destination_path" ]]
then
mv "$source_path" "$destination_path"
else
rvm_error "Gemset $destination_name already exists!"
return 1
fi
else
rvm_error "Gems directory does not exist for $source_path ($source_path)"
return 1
fi
}
gemset_unpack()
{
typeset gems name directory version
_platforms
directory="${args[$__array_start]}"
if [[ -z "$directory" ]]
then
directory="vendor/gems"
fi
if [[ -n "$rvm_ruby_gem_home" ]]
then
export GEM_HOME="$rvm_ruby_gem_home"
export GEM_PATH="$rvm_ruby_gem_home:$rvm_ruby_global_gems_path"
fi
rvm_log "Unpacking current environments gemset to ${directory}\n"
unset -f gem
while read gem_name version _platforms
do
( command gem unpack "$gem_name" -v"$version" --target "$directory" )&
done < <( GEM_PATH="$GEM_HOME" __rvm_list_gems )
wait
rvm_log "Unpacking into ${directory} complete\n"
return 0
}
gemset_export()
{
typeset gem_name version versions _platforms
rvm_file_name="${rvm_file_name:-${gems_args// }}"
if [[ -n "$rvm_ruby_gem_home" ]]
then
export GEM_HOME="$rvm_ruby_gem_home"
export GEM_PATH="$rvm_ruby_gem_home:$rvm_ruby_global_gems_path"
fi
if [[ -n "$rvm_file_name" ]]
then
[[ "${rvm_file_name}" =~ Gemfile ]] || rvm_file_name="${rvm_file_name%.gems}.gems"
else
if [[ -n "$rvm_gemset_name" ]]
then
rvm_file_name="$rvm_gemset_name.gems"
else
rvm_file_name="default.gems"
fi
fi
rvm_log "Exporting current environments gemset to $rvm_file_name"
if [[ -f "$rvm_file_name" ]]
then
rm -f "$rvm_file_name"
fi
if [[ "${rvm_file_name}" =~ Gemfile ]]
then
printf "%b" "source :rubygems
#ruby=${GEM_HOME##*/}
"
else
printf "%b" "# $rvm_file_name generated gem export file. \
Note that any env variable settings will be missing. \
Append these after using a ';' field separator
"
fi > "$rvm_file_name"
if (( ${rvm_latest_flag:-0} == 0 ))
then
while read gem_name version _platforms
do
if [[ "${rvm_file_name}" =~ Gemfile ]]
then
echo "gem '$gem_name', '$version'"
else
echo "$gem_name -v$version"
fi
done < <( GEM_PATH="$GEM_HOME" __rvm_list_gems )
else
while read gem_name versions
do
if [[ "${rvm_file_name}" =~ Gemfile ]]
then
echo "gem '$gem_name'"
else
echo "$gem_name"
fi
done < <( GEM_PATH="$GEM_HOME" gem list )
fi >> "$rvm_file_name"
return 0
}
gemset_import()
{
unset -f gem
if [[ -n "${rvm_ruby_gem_home:-""}" ]]
then
export GEM_HOME="$rvm_ruby_gem_home"
export GEM_PATH="$rvm_ruby_gem_home"
else
rvm_ruby_gem_home=${GEM_HOME:-$(gem env gemdir)}
fi
#rvm_gemset_name="${gems_args//.gem*/}"
#rvm_gemset_name="${gems_args// /}"
rvm_file_name="${gems_args// /}"
# TODO: this could likely be better with find
if [[ -s "${rvm_file_name%.gems*}.gems" ]]
then
rvm_file_name="${rvm_file_name%.gems*}.gems"
elif [[ -s "${rvm_gemset_name}.gems" ]]
then
rvm_file_name="${rvm_gemset_name}.gems"
elif [[ -s "default.gems" ]]
then
rvm_file_name="default.gems"
elif [[ -s "system.gems" ]]
then
rvm_file_name="system.gems"
elif [[ -s ".gems" ]]
then
rvm_file_name=".gems"
else
rvm_error "No *.gems file found."
return 1
fi
if [[ ! -d "$rvm_ruby_gem_home/specifications/" ]]
then
mkdir -p "$rvm_ruby_gem_home/specifications/"
fi
if [[ ! -d "$rvm_gems_cache_path" ]]
then
mkdir -p "$rvm_gems_cache_path" # Ensure the base cache dir is initialized.
fi
if [[ -s "$rvm_file_name" ]]
then
printf "%b" "\nInstalling gems listed in $rvm_file_name file...\n\n"
rvm_ruby_gem_list=$(
builtin cd "$rvm_ruby_gem_home/specifications/" ;
find . -maxdepth 1 -mindepth 1 -type f -print 2> /dev/null | \
sed -e 's#.gems.*$##' -e 's#^./##g' 2> /dev/null
)
# rvm_ruby_gem_list="${rvm_ruby_gem_list//.\/}"
# Read the file into an array by changing the IFS temporarily.
typeset oldifs
oldifs="${IFS}"
# Yes, that's a newline....edit with care.
IFS="
"
typeset -a lines
lines=( $(cat "${rvm_file_name}") )
IFS="${oldifs}"
# Parse the lines, throwing out comments and empty lines.
for line in "${lines[@]}"
do
if [[ "${line}" != '#'* && -n "${line// /}" ]]
then
gems_args="$line"
gem_install
fi
done
printf "%b" "\nProcessing of $rvm_file_name is complete.\n\n"
else
rvm_error "${rvm_file_name} does not exist to import from."
fi
}
__rvm_parse_gems_args()
{
gem="${gems_args/;*}"
gem_prefix=""
if echo "$gems_args" | GREP_OPTIONS="" \grep ';' >/dev/null 2>&1
then
gem_prefix="${gems_args/*;}"
fi
if match "$gem" "*.gem$"
then
gem_name="$(basename "${gem/.gem/}" | awk -F'-' '{$NF=NULL;print}')"
gem_version="$(basename "${gem/.gem/}" | awk -F'-' '{print $NF}' )"
gem_postfix="$(basename "${gem/*.gem/}")"
else
gem_name="${gem/ */}"
case "$gem" in
*--version*)
gem_version=$(
echo "$gem" | sed -e 's#.*--version[=]*[ ]*##' | awk '{print $1}'
)
gem_postfix="$(
echo "$gem" |
sed -e "s#${gem_name/ /}##" -e "s#--version[=]*[ ]*${gem_version/ /}##"
)"
;;
*-v*)
gem_version=$(
echo "$gem" | sed -e 's#.*-v[=]*[ ]*##' | awk '{print $1}'
)
gem_postfix="$(
echo "$gem" |
sed -e "s#${gem_name/ /}##" -e "s#-v[=]*[ ]*${gem_version/ /}##"
)" #"
;;
*)
unset gem_version # no version
;;
esac
fi
if [[ -s "$gem" ]] ; then
gem_file_name="$gem"
elif match "$gem" "*.gem"
then
gem_file_name="$gem"
elif [[ -z "${gem_version/ /}" ]]
then
gem_file_name="${gem_name/ /}*.gem"
else # version
gem_file_name="${gem_name/ /}-${gem_version/ /}.gem"
fi
}
# Install a gem
gem_install()
{
typeset gem gem_prefix gem_name gem_version gem_file_name gem_postfix cache_file gem_file_name gem_string gem_action
_command
result=0
# First we parse the gem args to pick apart the pieces.
__rvm_parse_gems_args
# Now we determine if a .gem cache file is already installed
if (( ${rvm_force_flag:-0} == 0 )) &&
[[ -f "${rvm_ruby_gem_home}/specifications/$(basename "$gem_file_name")spec" ]]
then
gem=""
rvm_log "$gem_name $gem_version is already installed."
else
if [[ -s "$gem" ]]
then
cache_file="$gem"
elif [[ -s "$(__rvm_current_gemcache_dir)/${gem_file_name}" ]]
then
cache_file="$(__rvm_current_gemcache_dir)/${gem_file_name}"
else
true ${cache_file:=$( find "$(__rvm_current_gemcache_dir)/${gem_file_name}" -maxdepth 1 -mindepth 1 -type f -print 2>
/dev/null | sort | head -n1)}
cache_file="${cache_file/.\/}"
fi
if [[ ! -s "$cache_file" ]]
then
if [[ -s "$gem_file_name" ]]
then
gem="$gem_file_name"
elif [[ -z "${gem_version// /}" ]]
then
gem="${gem_name// /}"
else
gem="${gem_name// /} -v $gem_version"
fi
else # cached
gem_file_name="$(basename "$cache_file")"
gem_string="$(echo "$gem_file_name" | sed 's#\.gem$##')"
if (( ${rvm_force_flag:-0} == 0 )) &&
[[ -s "${rvm_ruby_gem_home}/specifications/$(basename $gem_file_name)spec" ]]
then
unset gem # already installed, not forcing reinstall.
rvm_log "$gem_name $gem_version exists, skipping (--force to re-install)"
else
if [[ -s "$(__rvm_current_gemcache_dir)/$(basename $gem_file_name)" ]]
then
mkdir -p "${rvm_tmp_path}/$$/"
mv "$(__rvm_current_gemcache_dir)/$gem_file_name" "${rvm_tmp_path}/$$/$gem_file_name"
gem="${rvm_tmp_path}/$$/$gem_file_name -f -l"
else
gem="$cache_file"
fi
fi
fi
fi
# If $gem is still set, go forward with the install.
if [[ -n "$gem" ]]
then
# TODO: Set vars if fourth field is non-empty (means that there are conditional statements to execute in the gem install
line.
if [[ -n "$rvm_ruby_gem_home" &&
"$rvm_ruby_gem_home" != "${rvm_gems_path:-"$rvm_path/gems"}" ]]
then
_command="GEM_HOME='$rvm_ruby_gem_home' GEM_PATH='$rvm_ruby_gem_home' $gem_prefix gem install --remote $gems_args
$rvm_gem_options $gem_postfix $vars"
else
_command="$gem_prefix gem install --ignore-dependencies --remote $gems_args $rvm_gem_options -q $gem $gem_postfix
$vars"
fi
unset -f gem
__rvm_run "gem.install" "$_command" "installing ${gem_name} ${gem_version}..."
result=$?
if (( result == 0 ))
then
rvm_log "$gem_name $gem_version installed."
else
rvm_log "$gem_name $gem_version failed to install ( output logged to: $rvm_log_path/$rvm_ruby_string/gem.install.log
)"
fi
fi
return $result
}
# Output the user's current gem directory.
gemset_info()
{
if (( ${rvm_user_flag:-0} == 1 ))
then
(__rvm_use system ; gem env | GREP_OPTIONS="" \grep "\- $HOME" | awk '{print $NF}')
elif [[ ${rvm_system_flag:-0} == 1 ]]
then
(__rvm_use system ; gem env $action system)
# elif [[ -n "${rvm_ruby_string:-""}${rvm_gemset_name:+${rvm_gemset_separator:-"@"}}${rvm_gemset_name:-}" ]]
# then
#
(__rvm_use "${rvm_ruby_string:-""}${rvm_gemset_name:+${rvm_gemset_separator:-"@"}}${rvm_gemset_name:-}" ; gem env
$action)
# elif [[ -n "${GEM_HOME:-""}" ]]
# then
#
echo "$GEM_HOME"
else
gem env $action
fi
return $?
}
gemset_prune()
{
typeset temporary_cache_path live_cache_path gemset_name version versions \
cached_gem_name cached_file_path
temporary_cache_path="$GEM_HOME/temporary-cache"
live_cache_path="$GEM_HOME/cache"
mkdir -p "$temporary_cache_path"
rvm_log "Moving active gems into temporary cache..."
while read gem_name version _platforms
do
cached_gem_name="${gem_name}-${version}.gem"
cached_file_path="${live_cache_path}/${cached_gem_name}"
if [[ -f "$cached_file_path" ]]; then
mv "$cached_file_path" "${temporary_cache_path}/${cached_gem_name}"
fi
done < <( GEM_PATH="$GEM_HOME" __rvm_list_gems )
rvm_log "Removing live cache and restoring temporary cache..."
# Switch the cache back.
__rvm_rm_rf "$live_cache_path"
mv "$temporary_cache_path" "$live_cache_path"
return 0
}
gemset_pristine()
{
if ( unset -f gem ; builtin command -v gem > /dev/null )
then
typeset _gem _version _platforms
typeset -a _failed
rvm_log "Restoring gems to pristine condition..."
while read _gem _version _platforms
do
printf "%b" "${_gem}-${_version} "
if ! gem pristine ${_gem} --version ${_version} >/dev/null
then _failed+=( "${_gem} --version ${_version}" )
fi
done < <( GEM_PATH="$GEM_HOME" __rvm_list_gems )
if (( ${#_failed[@]} > 0 ))
then
rvm_error "\n'gem pristine ${_failed[*]}' failed, you need to fix this gems manually."
return 1
else
rvm_log "\nfinished."
return 0
fi
else
rvm_error "'gem' command not found in PATH."
return 1
fi
}
# Transform the list of gems one version per line
__rvm_list_gems()
{
gem list |
sed '/\*\*\*/ d ; /^$/ d; s/ (/,/; s/, /,/g; s/)//;' |
awk -F ',' '{for(i=2;i<=NF;i++) print $1" "$i }'
}
# Loads the default gemsets for the current interpreter and gemset.
gemset_initial()
{
typeset gemsets gemset path paths
true ${rvm_gemsets_path:="$rvm_path/gemsets"}
rvm_log "Importing initial gemsets for $(__rvm_env_string)."
if [[ ! -d "$rvm_gemsets_path/${rvm_ruby_string//-//}/cache" ]]
then
mkdir -p "$rvm_gemsets_path/${rvm_ruby_string//-//}/cache" 2>/dev/null
fi
paths=($(__rvm_ruby_string_paths_under "$rvm_gemsets_path"))
echo "paths: ${paths[@]}"
for path in "${paths[@]}"
do
if [[ -n "$rvm_gemset_name" ]]
then
if [[ -s "${rvm_gemset_name}.gems" ]]
then
( gems_args="${rvm_gemset_name}.gems" ; gemset_import )
fi
else
if [[ -s "${path}/default.gems" ]]
then
( gems_args="${path}/default.gems" ; gemset_import )
fi
if [[ -s "${path}/global.gems" ]]
then
(
rvm_create_flag=1
rvm_ruby_gem_home="${rvm_ruby_gem_home//@*/}@global"
gems_args="${path}/global.gems"
gemset_import
)
fi
fi
done
rvm_log "Installation of gems for $(__rvm_env_string) is complete."
return 0
}
search()
{
typeset gemspec gemspecs gem_name option environment_id ruby_string \
name gem_version
gem_name="${2:-}"
option="${3:-}"
if [[ -z "${gem_name}" ]]
then
return 0
fi
true "${rvm_gems_path:="$rvm_path/gems"}"
gemspecs=($(
find "${rvm_gems_path}" -mindepth 3 -iname "${gem_name}*.gemspec"
))
-type f
if [[ "${option}" != "strings" ]]
then
printf "%-40s %-20s %-20s\n" "environment_id" "name" "version"
printf "%b" "================================================================================\n"
fi
for gemspec in "${gemspecs[@]}"
do
environment_id="${gemspec//${rvm_gems_path}\/}"
environment_id="${environment_id//\/*}"
ruby_string="${environment_id//@*}"
gemset_name="${environment_id//${ruby_string}}"
name=${gemspec//*\/}
name=${name/%.gemspec}
gem_version=${name//*-}
if [[ "${option}" != "strings" ]]
then
printf "%-40s %-20s %-20s\n" "${environment_id}" "${gem_name}" "${gem_version}"
else
printf "%b" "${environment_id}\n"
fi
done
}
args=($*)
action="${args[$__array_start]}"
args[$__array_start]=""
args=(${args[@]})
gems_args="$(echo ${args[@]})" # Strip trailing / leading / extra spacing.
export rvm_gemset_name="${args[1]:-""}" # For wherever used.
rvm_sticky_flag=1
if [[ "$action" != "globalcache" ]] && ! builtin command -v gem > /dev/null
then
rvm_error "'gem' was not found, cannot perform gem actions (Do you have an RVM ruby selected?)"
exit 1
fi
if [[ -z "$rvm_ruby_string" ]]
then
if echo "${GEM_HOME:-""}" | GREP_OPTIONS="" \grep "${rvm_path}" >/dev/null 2>&1
then
rvm_ruby_string="${GEM_HOME##*/}"
rvm_ruby_string="${rvm_ruby_string%%@*}"
fi
fi
case "$action" in
import|load)
if [[ -z "${rvm_ruby_strings:-""}" ]]
then
gemset_import
else
original_env="$(__rvm_env_string)"
for rvm_ruby_string in $(echo "$rvm_ruby_strings" | \tr "," " ")
do
__rvm_become
gemset_import
done
__rvm_become "$original_env"
unset original_env
fi
;;
export|dump)
gemset_export
;;
create|copy|delete|dir|empty|initial|list|list_all|list_strings|prune|rename|update|unpack)
gemset_$action
;;
name|string)
gemset_name
;;
gemdir|gempath|gemhome|home|path|version)
gemset_info
;;
pristine)
gemset_$action "$@"
;;
install)
gem_$action "$@"
;;
globalcache)
gemset_globalcache "$2"
;;
search)
search "$@"
;;
clear)
rvm_log "gemset cleared."
exit 0
;;
help)
usage
exit 0
;;
*)
usage
exit 1
;;
esac
exit $?
1.18.57. rtfm
#!/usr/bin/env bash
rvm_url="https://rvm.io/"
source "$rvm_path/scripts/functions/logging"
if builtin command -v open >/dev/null ; then
open "$rvm_url"
elif builtin command -v xdg-open >/dev/null ; then
xdg-open "$rvm_url"
else
rvm_log "Please RTFM at the URL $rvm_url"
fi
exit $?
1.18.58. external
#!/usr/bin/env bash
source "$rvm_scripts_path/base"
external_automount()
{
external_mount_uniq $(
__rvm_remove_rvm_from_path
which -a ruby
)
}
external_grep_existing()
{
typeset IFS
typeset -a existing
IFS="|"
existing=( $(
for ext in $rvm_externals_path/*
do
if [[ -L "$ext" ]]
then
readlink "$ext"
fi
done
) )
: existing:${existing[@]}:
if (( ${#existing[@]} > 0 ))
then
GREP_OPTIONS="" \grep -vE "${existing[@]}" else
cat fi
}
external_mount_uniq()
{
typeset ruby_path
typeset -a ruby_paths
ruby_paths=( $(
for ruby_path in "$@"
do
if [[ -d "${ruby_path}" && -x "${ruby_path}/bin/ruby" ]] && "${ruby_path}/bin/ruby" -rrbconfig -e "" >/dev/null 2>&1
then
echo "${ruby_path}"
elif [[ ! -d "${ruby_path}" && -x "${ruby_path}" ]]
then
"${ruby_path}" -rrbconfig -e "puts RbConfig::CONFIG['prefix']" 2>/dev/null
fi
done | sort -u | external_grep_existing
) )
if (( ${#ruby_paths[@]} == 0 ))
then
rvm_error "The given paths '$*' either do not point to a ruby installation or are already mounted."
exit 1
else
for ruby_path in ${ruby_paths[@]}
do
( external_mount "${ruby_path}" ) || exit $?
done
fi
}
external_mount()
{
typeset path ruby_path prefix_path
path="$1"
if [[ ! -d "${path}" && -x "${path}" ]] && "${path}" --version | GREP_OPTIONS="" \grep rub >/dev/null
then
ruby_path="${path}"
prefix_path="$("${path}" -rrbconfig -e "puts RbConfig::CONFIG['prefix']")"
elif [[ -d "${path}" && -x "${path}/bin/ruby" ]] && "${path}/bin/ruby" --version | GREP_OPTIONS="" \grep rub >/dev/null
then
ruby_path="${path}/bin/ruby"
prefix_path="$("${ruby_path}" -rrbconfig -e "puts RbConfig::CONFIG['prefix']")"
if [[ "${path}" != "${prefix_path}" ]]
then
rvm_error "The given path '$path' contains ruby but it has different prefix '$prefix_path'."
exit 2
fi
else
rvm_error "The given path '$path' does not point to a ruby installation."
exit 3
fi
if [[ -z "${rvm_ruby_name:-}" ]]
then
if ! external_select_name "${ruby_path}" "${prefix_path}" ||
[[ -z "${rvm_ruby_name:-}" ]]
then
rvm_error "No name selected for ruby in '$prefix_path'."
exit 4
fi
fi
old_gem_home=$(
unset GEM_HOME
"${prefix_path}/bin/gem" env gemhome
)
rvm_ruby_string="ext-${rvm_ruby_name}"
echo "Mounting '${rvm_ruby_string}' from '${prefix_path}'"
mkdir -p "$rvm_externals_path"
ln -nfs "${prefix_path}" "$rvm_externals_path/$rvm_ruby_string"
mkdir -p "$rvm_rubies_path/$rvm_ruby_string/bin"
ln -nfs "${ruby_path}" "$rvm_rubies_path/$rvm_ruby_string/bin/ruby"
rvm_create_flag=1 __rvm_use
mkdir -p "$rvm_gems_path/$rvm_ruby_string@global"
ln -nfs "${old_gem_home}" "$rvm_gems_path/$rvm_ruby_string"
__rvm_bin_script
# Import the initial gemsets, unless skipped.
if (( ${rvm_skip_gemsets_flag:-0} == 0 ))
then
(
export rvm_gemset_name=global
__rvm_run_with_env "gemsets.initial" "$rvm_ruby_string" \
"'$rvm_scripts_path/gemsets' initial" \
"$rvm_ruby_string - #importing default gemsets ($rvm_gemsets_path/)"
)
else
rvm_log "Skipped importing default gemsets"
fi
"$ruby_path" -rrbconfig \
-e 'File.open("'"$rvm_rubies_path/$rvm_ruby_string/config"'","w") { |file| RbConfig::CONFIG.each_pair{|key,value|
file.write("#{key.gsub(/\.|-/,"_")}=\"#{value.gsub("$","\\$")}\"\n")} }' >/dev/null 2>&1
__rvm_record_install "$rvm_ruby_string"
}
external_select_name()
{
typeset proposed_name ruby_version ruby_path prefix_path
export rvm_ruby_name
ruby_path="$1"
prefix_path="$2"
ruby_version="$( "${ruby_path}" --version)"
if [[ -x "${ruby_path}" ]] &&
proposed_name="$( external_propose_name "$ruby_version" )" &&
[[ -n "${proposed_name:-}" ]]
then
echo "Found '${ruby_version}' in '${prefix_path}'"
printf "\n# Please enter name [${proposed_name}]: "
read rvm_ruby_name
printf "\n"
: rvm_ruby_name:${rvm_ruby_name:=${proposed_name}}:
else
echo "Name not found for '${ruby_path}' in '${prefix_path}'"
false
fi
}
external_propose_name()
{
typeset parts __tmp1 __tmp2
parts="$( echo "$1" | sed 's/[()]//g; s/\[.*\]//;' )"
case "${parts}" in
(*Ruby[[:space:]]Enterprise[[:space:]]Edition*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${parts##* }"
printf "ree-${__tmp1}-${__tmp2}"
;;
(ruby[[:space:]]*patchlevel[[:space:]]*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${parts##*patchlevel }"
__tmp2="${__tmp2%% *}"
printf "ruby-${__tmp1}-p${__tmp2}"
;;
(ruby[[:space:]][[:digit:]].[[:digit:]].[[:digit:]]p[[:digit:]]*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${__tmp1##+([[:digit:]\.])}"
__tmp1="${__tmp1%${__tmp2}}"
printf "ruby-${__tmp1}-${__tmp2}"
;;
(ruby[[:space:]]*revision[[:space:]]*|ruby[[:space:]]*trunk[[:space:]]*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${parts##*trunk }"
__tmp2="${__tmp2##*revision }"
__tmp2="${__tmp2%% *}"
printf "ruby-${__tmp1}-r${__tmp2}"
;;
(ruby[[:space:]]*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${__tmp1##+([[:digit:]\.])}"
__tmp1="${__tmp1%${__tmp2}}"
printf "ruby-${__tmp1}-${__tmp2}"
;;
(jruby[[:space:]]*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${parts#* }"
__tmp2="${__tmp2#* }"
__tmp2="${__tmp2%% *}"
__tmp2="${__tmp2#ruby-}"
__tmp2="${__tmp2//-/_}"
printf "jruby-${__tmp1}-default_${__tmp2}"
;;
(maglev[[:space:]]*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${parts#* }"
__tmp2="${__tmp2#* }"
__tmp2="${__tmp2#* }"
__tmp2="${__tmp2%% *}"
printf "maglev-${__tmp1}-default_${__tmp2}"
;;
(rubinius[[:space:]]*)
__tmp1="${parts#* }"
__tmp1="${__tmp1%% *}"
__tmp2="${parts#* }"
__tmp2="${__tmp2#* }"
__tmp2="${__tmp2%% *}"
printf "rbx-${__tmp1}-default_${__tmp2}"
;;
(*)
false
;;
esac
}
args=( "$@" )
action="${args[__array_start]}"
unset args[__array_start]
args=( "${args[@]}" )
case "${action}" in
(automount)
external_$action
;;
(mount|*_name)
external_mount_uniq "${args[@]}"
;;
(*)
echo "Wrong action '$action'"
;;
esac
1.18.59. extras
1.18.59.1. rails
#!/usr/bin/env bash
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
#
Copyright (c) 2011 Wayne E. Seguin <[email protected]>
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
This feature is opt-in, in order to use the functions provided below source
this script in your start up from your profile(s).
For example, if RVM is installed to $HOME/.rvm, you can put this in your
~/.bash_profile:
[[ -s "$HOME/.rvm/scripts/extras/rails" ]] && . "$HOME/.rvm/scripts/extras/rails"
enable_extendglob() {
if [[ -n "${ZSH_VERSION:-}" ]] ; then
setopt extendedglob
else
if [[ -n "${BASH_VERSION:-}" ]] ; then
shopt -s extglob # Extended globs
else
printf "%b" "What the heck kind of shell are you running here???\n"
fi
fi
}
rails_routes()
{
# Usage:
#
#
rails_routes <or list, space separated> [options]
#
#
include string is a valid shell glob: http://mywiki.wooledge.org/glob
#
#
options are among
#
#
* a valid shell glob pattern
#
* -a <and glob>
#
* -o <or glob>
#
* -e <exclude (not) glob>
#
#
Processing occurs as ((or list) AND (and list)) NOT (exclude list)
#
# Examples:
#
#
rails_routes admin
#
/admin/reports/agent/:id(.:format)
{:controller=>"reports", :action=>"agent"}
#
#
rails_routes "P@(OS|U)T"
#
POST
/current(.:format)
{:action=>"create", :controller=>"current"}
#
PUT
/current/:id(.:format)
{:action=>"update", :controller=>"current"}
#
#
or, equivalently, rails_routes POST -o PUT
#
#
List all routes containing admin but not test
#
rails_routes admin -e test
#
#
rails_routes
enable_extendglob
typeset md5_current md5_cached cache_file routes
typeset -a ands ors nots
while [[ $# -gt 0 ]] ; do
token="$1" ; shift
case "$token" in
--trace)
set -o xtrace
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
;;
-a|and)
ands=(${ands[@]} "$1")
shift
;;
\${LINENO} > "
-o|or)
ors=(${ors[@]} "$1")
shift
;;
-e|exclude)
nots=(${exclude[@]} "$1")
shift
;;
*) # Default is or.
ors=(${ors[@]} "$token")
;;
esac
done
[[ -d tmp/rake ]] || mkdir -p "tmp/rake"
cache_file="tmp/rake/routes"
if ! builtin command -v rake >/dev/null 2>&1 ; then
printf "%b" "ERROR: rake not found.\n" >&2
return 1
fi
case $(uname) in
Linux) md5="md5sum" ;;
Darwin) md5="/sbin/md5 -q" ;;
*)
printf "%b" "ERROR: Unknown OS Type.\n" >&2 ;
esac
return 1 ;;
md5_current=$($md5 config/routes.rb)
md5_current=${md5%% *}
if [[ -s "$cache_file" && -s "$cache_file.md5" ]]; then
md5_cached=$(cat -v "${cache_file}.md5")
md5_cached=${md5%% *}
else
md5_cached=""
fi
if [[ -s "$cache_file" && $md5_current == $md5_cached ]]; then
routes=$(cat -v "$cache_file")
else
routes=$(rake routes 2>/dev/null)
if [[ $? -gt 0 ]]; then
printf "%b" "ERROR: There was an error running 'rake routes', does your application load console properly?" >&2
return 1
else
printf "%b" "$md5_current" > "${cache_file}.md5"
printf "%b" "$routes" > "$cache_file"
fi
fi
routes="${routes#\|\(in *\)}"
orig_ifs="$IFS"
condition="${ors[@]}"
condition="*${condition// /*|*}*"
IFS="
"
# ORs
results=()
for route in ${routes} ; do
eval "case '${route}' in (${condition}) results=(\"${results[@]}\" \"${route}\") ;; esac"
done
routes=(${results[@]})
# ANDs
results=()
for condition in "${ands[@]}" ; do
for route in ${routes[@]} ; do
if [[ ${route} == ${condition} ]]; then
results=(${results[@]} ${route})
fi
done
routes=(${results[@]})
results=()
done
# NOTs
results=()
for condition in "${nots[@]}" ; do
for route in ${routes[@]} ; do
if [[ ${route} != *${condition}* ]]; then
results=(${results[@]} ${route})
fi
done
routes=(${results[@]})
results=()
done
for route in ${routes[@]} ; do
printf "%b" "${route}\n"
done
IFS="$orig_ifs"
}
#
# r - Rails scripts helper function.
#
r() {
typeset action args
action="$1" ; shift
args="$@"
enable_extendglob
case "$action" in
c|console)
action=console
;;
d|db)
action=dbconsole
;;
g|generate)
action=generate
;;
d|destroy)
action=destroy
;;
s|server)
action=server
;;
r|routes)
rails_routes $args
return $?
;;
n|new)
rails_version=$(rails -v)
rails_version=${rails_version##* }
rails_version=${rails_version%%.*}
if [[ $rails_version -ge 3 ]]; then
rails new $args
elif [[ $rails_version == 1 || $rails_version == 2 ]] ; then
rails $args
fi
;;
(*(-)@(h|?|help))
action="-h"
;;
(*(-)@(v|V|version))
action="-h"
;;
usage)
printf "%b" "
r - Rails shell convenience function
Usage:
r [action]
Actions:
c
d
c
s
r
-
Start
Start
rails
rails
rails
a Rails Console
a database console
generate
server
routes <include filter glob> [-e <exclude filter glob>]
\n"
;;
esac
if [[ -s ./script/rails ]] ; then
ruby ./script/rails $action $args
elif [[ -s ./script/$action ]] ; then
ruby ./script/$action $args
else
printf "%b" "ERROR: rails $action not found!!!"
fi
return 0
}
1.18.60. zsh
1.18.60.1. Completion
1.18.60.1.1. _rvm
#compdef rvm
typeset curcontext state line cmds ret
curcontext="$curcontext"
ret=1
_arguments -C \
'(- 1 *)'{-v,--version}'[display version information]' \
'(-l|--level)'{-l,--level}'+[patch level to use with rvm use / install]:number' \
'(--bin)--bin[path for binaries to be placed (~/.rvm/bin/)]:path:_files' \
'(--source)--source[src directory to use (~/.rvm/src/)]:path:_files' \
'(--archives)--archives[directory for downladed files (~/.rvm/archives/)]:path:_files' \
'-S[Specify a script file to attempt to load and run (rubydo)]:file:_files' \
'-e[Execute code from the command line]:code' \
'(-G)-G[root gem path to use]:path:_files' \
'(--gems)--gems[Used to set the gems_flag, use with remove to remove gems]' \
'(--archive)--archive[Used to set the archive_flag, use with remove to remove archive]' \
'(--patch)--patch[With MRI Rubies you may specify one or more full paths to patches]' \
'(-C|--configure)'{-C,--configure}'=[custom configure options]' \
'(--nice)--nice[process niceness (for slow computers, default 0)]:number' \
'(--ree)--ree-options[Options passed directly to ree ./installer on the command line]:options' \
'(--head)--head[with update, updates rvm to git head version]' \
'(--rubygems)--rubygems[with update, updates rubygems for selected ruby]' \
'(--default)--default[with ruby select, sets a default ruby for new shells]' \
'(--debug)--debug[Toggle debug mode on for very verbose output]' \
'(--trace)--trace[Toggle trace mode on to see EVERYTHING rvm is doing]' \
'(--force)--force[Force install, even given ruby is already install]' \
'(--summary)--summary[Used with rubydo to print out a summary of the commands run]' \
'(--latest)--latest[with gemset --dump skips version strings for latest gem]' \
'(--gems)--gems[with uninstall/remove removes gems with the interpreter]' \
'(--docs)--docs[with install, attempt to generate ri after installation]' \
'(--reconfigure)--reconfigure[Force ./configure on install even if Makefile already exists]' \
'1: :->cmds' \
'*: :->args' && ret=0
case $state in
cmds)
cmds=( ${(f)"$(_call_program commands rvm help 2> /dev/null | sed -e '/^== Action/,/^== Implementation/!d; / :: /!d;
s/^[ *]*\([^ ]*\) *:: *\(.*\)/\1:\2/')"} )
cmds+=( $(rvm list strings) )
_describe -t commands 'rvm command' cmds && ret=0
;;
args)
case $line[1] in
(use|uninstall|remove|list)
if (( CURRENT == 3 )); then
# See if weve made it to the @; eg, 1.9.2@
if ! GREP_OPTIONS="" \grep '@' <<< "${line[CURRENT-1]}" >/dev/null ; then
_values -S , 'rubies' \
$(rvm list strings | sed -e 's/ruby-\([^) ]*\)-\([^) ]*\)/ruby-\1-\2 \1-\2 \1/g') \
default system $(rvm alias list | cut -d' ' -f1) && ret=0
else
# Construct a full version string for each of the gemsets.
# Eg, 1.9.2@min 1.9.2@rail3 …
_values -S , 'gemsets' \
$(rvm ${line[CURRENT-1]%%@*} gemset list | awk '/^[ -_[:alnum:]]+$/ {print "'${line[CURRENT-1]%%@*}'@"$1}')
fi
fi
;;
(install|fetch)
_values -S , 'rubies' $(rvm list known_strings) && ret=0
;;
gemset)
if (( CURRENT == 3 )); then
_values 'gemset_commands' $(rvm gemset | sed -e '/create/!d; s/^.*[{]\(.*\)[}].*$/\1/; s/,/ /g')
else
#_values -S , 'gemsets' $(rvm gemset list | GREP_OPTIONS="" \grep -v gemset 2>/dev/null)
_values -S , 'gemsets' $(rvm gemset list | GREP_OPTIONS="" \grep -Ev '(gemset|info)' 2>/dev/null | awk '/^[ _[:alnum:]]+$/ {print '$1'}')
fi
ret=0
;;
package)
if (( CURRENT == 3 )); then
_values 'package_commands' $(rvm package | sed -e '/Usage/!d; s/^.*[{]\(.*\)[}] [{].*$/\1/; s/,/ /g')
else
_values 'packages' $(rvm package | sed -e '/Usage/!d; s/^.*[}] [{]\(.*\)[}].*$/\1/; s/,/ /g')
fi
ret=0
;;
*)
(( ret )) && _message 'no more arguments'
;;
esac
;;
esac
return ret
1.18.61. functions
1.18.61.1. implode
#!/usr/bin/env bash
# Remove binaries.
__rvm_implode_binaries()
{
# Load inside a subshell to avoid polutting the current shells env.
(
source "$rvm_scripts_path/base"
rvm_log "Removing rvm-shipped binaries (rvm-prompt, rvm, rvm-sudo rvm-shell and rvm-auto-ruby)"
for entry in "$rvm_bin_path/"{rvm-prompt,rvm,rvmsudo,rvm-shell,rvm-auto-ruby} ; do
__rvm_rm_rf "$entry"
done
rvm_log "Removing rvm wrappers in $rvm_bin_path"
\find "$rvm_bin_path" -type l | while read symlinked_rvm_file; do
if [[ "$(readlink "$symlinked_rvm_file")" == "$rvm_wrappers_path/"* ]]; then
__rvm_rm_rf "$symlinked_rvm_file"
fi
done
unset symlinked_rvm_file
)
}
# Implode removes the entire rvm installation under $rvm_path, including removing wrappers.
__rvm_implode()
{
while : ; do
rvm_warn "Are you SURE you wish for rvm to implode?\
\nThis will recursively remove $rvm_path and other rvm traces?\
\n(type 'yes' or 'no')> "
read response
if [[ "yes" == "$response" ]] ; then
if [[ "/" == "$rvm_path" ]] ; then
rvm_error "remove '/' ?!... Ni!"
else
if [[ -d "$rvm_path" ]] ; then
__rvm_implode_binaries
rvm_log "Hai! Removing $rvm_path"
for file in /etc/profile.d/rvm.sh $rvm_man_path/man1/rvm.1* $rvm_path/ ; do __rvm_rm_rf $file ; done
echo "$rvm_path has been removed."
if [[ "$rvm_path" == "/usr/local/rvm"* && -f "/usr/local/lib/rvm" ]]; then
rvm_log "Removing the rvm loader at /usr/local/lib/rvm"
fi
printf "%b" "rvm has been fully removed. Note you may need to manually remove /etc/rvmrc and ~/.rvmrc if they
exist still.\n"
else
rvm_log "It appears that $rvm_path is already non existant."
fi
fi
break
elif [[ "no" == "$response" ]] ; then
rvm_log "Psychologist intervened, cancelling implosion, crisis avoided :)"
break
fi
done
return 0
}
1.18.61.2. reset
#!/usr/bin/env bash
# Reset any rvm gathered information about the system and its state.
# rvm will refresh the stored information the next time it is called after reset.
__rvm_reset()
{
typeset flag flags file files config configs variable
__rvm_remove_rvm_from_path ; __rvm_conditionally_add_bin_path
export PATH
builtin hash -r
flags=( default passenger editor )
for flag in "${flags[@]}"; do
\rm -f "${rvm_bin_path}"/${flag}_*
done
for file in system default ; do
if [[ -f "$rvm_path/${file}" ]] ; then
\rm -f "$rvm_path/${file}"
fi
if [[ -f "$rvm_path/config/${file}" ]] ; then
\rm -f "$rvm_path/config/${file}"
fi
if [[ -f "$rvm_environments_path/${file}" ]] ; then
\rm -f "$rvm_environments_path/${file}"
fi
done
# Go back to a clean state.
__rvm_use_system
__rvm_unset_ruby_variables
__rvm_unset_exports
configs=(system_ruby system_gem_path system_user_gem_path)
for system_config in "${configs[@]}" ; do
"$rvm_scripts_path/db" "$rvm_user_path/db" "$system_config" "delete"
done
files=(ruby gem rake irb $(cd "${rvm_bin_path}" ; \
find . -mindepth 1 -maxdepth 1 -iname 'default*' -type f \
| \sed -e 's#./##g'))
for file in "${files[@]}"; do
if [[ -f "${rvm_bin_path}/$file" ]] ; then
\rm -f "${rvm_bin_path}/$file"
fi
done
return 0
}
1.18.61.3. utility
#!/usr/bin/env bash
if [[ -z "${rvm_tar_command:-}" ]]
then
# check for the right tar to use
if builtin command -v gtar >/dev/null
then rvm_tar_command=gtar
else rvm_tar_command=tar
fi
fi
if [[ ! " ${rvm_tar_options:-} " =~ " --no-same-owner " ]] && \
$rvm_tar_command --help | GREP_OPTIONS="" \grep -- --no-same-owner >/dev/null
then
rvm_tar_options="${rvm_tar_options:-} --no-same-owner"
rvm_tar_options="${rvm_tar_options## }"
fi
#
# Functions RVM is built on
#
# match <value> <string|glob>
match()
{
case "$1" in
$2) return 0 ;;
*) return 1 ;;
esac
}
printenv_null()
{
if printenv --null >/dev/null 2>/dev/null
then
printenv --null
else
# this messes with escape sequences but allows new lines in variables
printenv | sed '/=/ { s/=.*$//; p; }; d;' | while read name
do
zero="\0"
eval "eval \"printf '%b' '$name=\$$name$zero'\""
done
fi
}
is_a_function() {
typeset -f $1 >/dev/null 2>&1 || return $?
}
#
# RVM specific functions.
#
__rvm_warn_on_rubyopt()
{
if [[ -n "${RUBYOPT:-""}" ]]; then
rvm_warn \
"Please note: You have the RUBYOPT environment variable set and this \
may interfere with normal rvm operations. We sugges unsetting it."
return 1
else
return 0
fi
}
__rvm_strings()
{
typeset strings ruby_strings
ruby_strings=($(echo ${rvm_ruby_args:-$rvm_ruby_string}))
for rvm_ruby_string in "${ruby_strings[@]}" ; do
strings="$strings $(__rvm_select ; echo $rvm_ruby_string)"
done
echo $strings
return 0
}
# Return a list of directories under a given base path.
# Derived from rvm_ruby_string.
__rvm_ruby_string_paths_under()
{
typeset path part parts
path="${1%/}" # Strip off any trailing slash
parts=(${rvm_ruby_string//-/ }) # Strip white space.
echo "$path"
for part in "${parts[@]}"
do
path="$path/$part"
echo "$path"
done
return 0
}
# Run a specified command and log it.
__rvm_run()
{
typeset name log temp_log_path _command message
true ${rvm_debug_flag:=0} ${rvm_niceness:=0}
name="${1:-}"
_command="${2:-}"
message="${3:-}"
if [[ -n "$message" ]]
then
rvm_log "$message"
fi
if (( rvm_debug_flag > 0 ))
then
rvm_debug "Executing: $_command"
fi
if [[ -n "${rvm_ruby_string:-}" ]]
then
temp_log_path="${rvm_log_path}/$rvm_ruby_string"
else
temp_log_path="${rvm_log_path}"
fi
log="$temp_log_path/$name.log"
if [[ ! -d "${log%\/*}" ]]
then
\mkdir -p "${log%\/*}"
fi
if [[ ! -f "$log" ]]
then
\touch "$log" # for zsh :(
fi
# TODO: Allow an 'append_flag' setting?
printf "%b" "[$(date +'%Y-%m-%d %H:%M:%S')] $_command\n" > "$log"
if (( rvm_niceness > 0 ))
then
_command="nice -n $rvm_niceness $_command"
fi
eval "$_command" >> "$log" 2>&1
result=$?
if (( result > 0 ))
then
rvm_error "Error running '$_command', please read $log"
fi
return ${result}
}
# Output the current ruby's rvm source path.
__rvm_source_dir()
{
if [[ ${rvm_ruby_selected_flag:-0} -eq 0 ]]
then __rvm_select
fi
if [[ -z "$rvm_ruby_src_path" ]]
then
rvm_error "No source directory exists for the default implementation."
else
echo "$rvm_ruby_src_path"
fi
return 0
}
# Output an inspection of selected 'binary' scripts, based on CLI selection.
__rvm_inspect()
{
for binary in $rvm_ruby_args
do
actual_file="$(unset -f gem ; builtin command -v gem )"
rvm_log "$actual_file:"
if [[ ${rvm_shebang_flag:-0} -eq 1 ]]
then
\head -n 1
< "$actual_file"
fi
if [[ ${rvm_env_flag:-0} -eq 1 ]]
then
\awk '/ENV/' < "$actual_file"
fi
if [[ ${rvm_path_flag:-0} -eq 1 ]]
then
\awk '/PATH/' < "$actual_file"
fi
if [[ ${rvm_head_flag:-0} -eq 1 ]]
then
\head -n 5
< "$actual_file"
fi
if [[ ${rvm_tail_flag:-0} -eq 1 ]]
then
\tail -n 5
< "$actual_file"
fi
if [[ ${rvm_all_flag:-0} -eq 1 ]]
then
\cat $actual_file
fi
done
return 0
}
# Strip whitespace and normalize it all.
__rvm_strip()
{
\sed -e 's/^[[:space:]]*//' -e 's/[[:space:]]*$//' -e 's/[[:space:]]\{1,\}/ /g'
return $?
}
__rvm_remove_from_path()
{
export PATH
PATH=":$PATH:"
PATH="${PATH//:$1:/:}"
PATH="${PATH//::/:}"
PATH="${PATH%:}"
PATH="${PATH#:}"
}
__rvm_add_to_path()
{
export PATH
if (( $# != 2 )) || [[ -z "$2" ]]
then
rvm_error "__rvm_add_to_path requires two parameters"
return 1
fi
__rvm_remove_from_path "$2"
case "$1" in
prepend) PATH="$2:$PATH" ;;
append) PATH="$PATH:$2" ;;
#*) anything else will just remove it from PATH - not adding back
esac
if [[ -n "${rvm_user_path_prefix:-}" ]]
then
__rvm_remove_from_path "${rvm_user_path_prefix}"
PATH="${rvm_user_path_prefix}:$PATH"
fi
builtin hash -r
}
is_parent_of()
{
typeset name pid ppid pname
name=$1
pid=$2
while [[ -n "$pid" && "$pid" != "0" ]]
do
read ppid pname < <(ps -p $pid -o ppid= -o comm=)
if [[ -n "$ppid" && -n "$pname" ]]
then
if [[ "$pname" == "$name" ]]
then
echo $pid
return 0
else
pid=$ppid
fi
else
break
fi
done
return 1
}
rvm_is_a_shell_function()
{
if (( ${rvm_is_not_a_shell_function:-0} > 0 )) && [[ "${1:-}" != "no_warning" ]]
then
if rvm_pretty_print stderr
then
printf "%b" "\n${rvm_notify_clr:-}RVM is not a function, selecting rubies with '${rvm_error_clr:-}rvm use
...${rvm_notify_clr:-}' will not work.${rvm_reset_clr:-}\n" >&2
else
printf "%b" "\nRVM is not a function, selecting rubies with 'rvm use ...' will not work.\n" >&2
fi
if is_parent_of gnome-terminal $$ >/dev/null
then
rvm_log "Please visit https://rvm.io/integration/gnome-terminal/ for a solution.\n" >&2
else
rvm_log "You need to change your terminal settings to allow shell login.
Please visit https://rvm.io/workflow/screen/ for example.\n" >&2
fi
fi
return ${rvm_is_not_a_shell_function:-0}
}
__rvm_detect_xcode_version()
{
typeset version_file
for version_file in \
/Applications/Xcode.app/Contents/version.plist \
/Developer/Applications/Xcode.app/Contents/version.plist
do
if [[ -f $version_file ]]
then
if [[ -x /usr/libexec/PlistBuddy ]]
then
/usr/libexec/PlistBuddy -c "Print CFBundleShortVersionString" $version_file
else
sed -n '/<key>CFBundleShortVersionString<\/key>/{n; s/^.*>\(.*\)<.*$/\1/; p;}' < $version_file
fi
return 0
fi
done
if builtin command -v xcodebuild >/dev/null
then
xcodebuild -version | sed -n '/Xcode/ {s/Xcode //; p;}'
fi
}
__rvm_detect_xcode_version_is()
{
[[ "$(__rvm_detect_xcode_version)" == "$1" ]] || return 1
}
__rvm_version_compare()
{
typeset v1d v2d dots counter IFS
typeset -a transformer
counter=1
IFS="+" # to put + in transformer ;)
v1d=$( printf -- $1 | GREP_OPTIONS="" \grep -o '\.' | wc -l )
v2d=$( printf -- $3 | GREP_OPTIONS="" \grep -o '\.' | wc -l )
if [[ $v1d -ge $v2d ]]
then dots=$v1d
else dots=$v2d
fi
while (( dots >= 0 ))
do transformer+=( "$(( 256 ** dots-- ))*\$$((counter++))" )
done
eval "$(
printf
printf
printf
printf
printf
)"
'[[ ';
$1 | \awk -F. "{ printf ${transformer[*]} }";
-- " $2 ";
$3 | \awk -F. "{ printf ${transformer[*]} }";
' ]]'
}
__function_on_stack()
{
typeset fun
for fun in "$@"
do
if [[ " ${FUNCNAME[*]} " =~ " $fun " ]]
then return 0
fi
done
return $#
}
__rvm_pager_or_cat_v()
{
eval "${PAGER:-cat -v} '$1'"
}
1.18.61.4. init
#!/usr/bin/env bash
__rvm_load_rvmrc()
{
typeset _file
typeset -a rvm_rvmrc_files
if (( ${rvm_ignore_rvmrc:=0} == 1 ))
then
return 0
fi
: rvm_stored_umask:${rvm_stored_umask:=$(umask)}
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
for _file in "${rvm_rvmrc_files[@]}"
do
if [[ -s "$_file" ]]
then
if GREP_OPTIONS="" \grep '^\s*rvm .*$' "$_file" >/dev/null 2>&1
then
rvm_error "
$_file is for rvm settings only.
rvm CLI may NOT be called from within $_file.
Skipping the loading of $_file
"
return 1
else
source "$_file"
fi
fi
done
return 0
}
# Initialize rvm, ensuring that the path and directories are as expected.
__rvm_initialize()
{
export rvm_ruby_load_path rvm_ruby_require
rvm_ruby_load_path="."
rvm_ruby_require=""
true ${rvm_scripts_path:="$rvm_path/scripts"}
source "$rvm_scripts_path/base"
__rvm_clean_path
__rvm_conditionally_add_bin_path
export PATH
if [[ ! -d "${rvm_tmp_path:-/tmp}" ]]
then
command mkdir -p "${rvm_tmp_path}"
fi
return 0
}
1.18.61.5. bundler
#!/usr/bin/env bash
1.18.61.6. group
#!/usr/bin/env bash
add_user_to_rvm_group()
{
echo "Adding user '$user' to the RVM group '${rvm_group_name}'"
case "$(uname)" in
"OpenBSD")
usermod -G "$rvm_group_name" "$user"
;;
"FreeBSD")
pw usermod "$user" -G "$rvm_group_name"
;;
"Linux")
if [[ -f "/etc/SuSE-release" ]] ; then
groupmod -A "$user" "$rvm_group_name"
else
/usr/sbin/usermod -a -G "$rvm_group_name" "$user"
fi
;;
"Darwin")
dscl . -append "/Groups/$rvm_group_name" GroupMembership "$user"
;;
"SunOS")
groups="$(id -G "$user") \"$rvm_group_name\""
usermod -G "${groups// /, }" "$user"
;;
esac
return 0
}
# TODO: Remove this... it is now replaced with rvm group cli api.
setup_rvm_group_users()
{
case "$(uname)" in
"Darwin")
usernames=$(dscl . -search /Users PrimaryGroupID 20 | GREP_OPTIONS="" \grep PrimaryGroupID | cut -f 1)
;;
*)
usernames=($(GREP_OPTIONS="" \grep -xF -f <(cat /etc/passwd | cut -d: -f1) <(find /home -mindepth 1 -maxdepth 1 -type
d | cut -d '/' -f 3)))
;;
esac
for user in ${usernames[@]}
do
if ! groups "$user" | GREP_OPTIONS="" \grep 'rvm' >/dev/null 2>&1
then
printf "%b" "Ensuring '$user' is in group '$rvm_group_name'\n"
add_user_to_rvm_group $user
fi
done
}
1.18.61.7. state
#!/usr/bin/env bash
# Save or restore the rvm's state. This is a toggle action.
# Meant for use before and after an operation that might reset
# the currently selected ruby.
# TODO: Determine if we should a) yank this out or b) actually use it :)
__rvm_state()
{
if [[ -z "$rvm_state" ]] ; then
rvm_state="$(__rvm_env_string)"
rvm_state="${rvm_state:-"system"}"
if [[ -n "$1" ]]; then
rvm_ruby_string="$1"
__rvm_select
__rvm_use
fi
else
rvm_ruby_string="$rvm_state"
__rvm_select
__rvm_use
unset rvm_state
fi
return 0
}
1.18.61.8. install
#!/usr/bin/env bash
__rvm_record_install()
{
typeset recorded_ruby_name rvm_install_record_file rvm_install_command
[[ -z "$1" ]] && return
recorded_ruby_name="$("$rvm_scripts_path/tools" strings "$1")"
rvm_install_record_file="$rvm_user_path/installs"
rvm_install_command=$(printf "%b" "$recorded_ruby_name $rvm_install_args\n")
[[ ! -f "$rvm_install_record_file" ]] && \touch "$rvm_install_record_file"
\rm -f "$rvm_install_record_file.tmp"
GREP_OPTIONS="" \grep -v "^$recorded_ruby_name " < "$rvm_install_record_file" \
> "$rvm_install_record_file.tmp"
echo "$rvm_install_command" >> "$rvm_install_record_file.tmp"
\rm -f "$rvm_install_record_file"
\mv "$rvm_install_record_file.tmp" "$rvm_install_record_file"
return 0
}
__rvm_remove_install_record()
{
typeset recorded_ruby_name rvm_install_record_file
recorded_ruby_name="$("$rvm_scripts_path/tools" strings "$1")"
rvm_install_record_file="$rvm_user_path/installs"
if [[ -s "$rvm_install_record_file" ]]; then
\mv "$rvm_install_record_file" "$rvm_install_record_file.tmp"
GREP_OPTIONS="" \grep -v "^$recorded_ruby_name " < "$rvm_install_record_file.tmp" \
> "$rvm_install_record_file"
\rm -f "$rvm_install_record_file.tmp"
fi
return 0
}
__rvm_recorded_install_command()
{
typeset recorded_ruby_name recorded_ruby_match
recorded_ruby_name="$("$rvm_scripts_path/tools" strings "$1" \
| awk -F"${rvm_gemset_separator:-"@"}" '{print $1}')"
[[ -z "$recorded_ruby_name" ]] && return 1
recorded_ruby_match="^$recorded_ruby_name "
if [[ -s "$rvm_user_path/installs" ]] \
&& GREP_OPTIONS="" \grep "$recorded_ruby_match" "$rvm_user_path/installs" >/dev/null 2>&1 ; then
GREP_OPTIONS="" \grep "$recorded_ruby_match" < "$rvm_user_path/installs" | head -n1
else
return 1
fi
return $?
}
1.18.61.9. env
#!/usr/bin/env bash
#
# Environment manipulation functions.
#
__rvm_default_flags()
{
true ${rvm_head_flag:=0} ${rvm_delete_flag:=0}
}
__rvm_nuke_rvm_variables()
{
unset rvm_head_flag $(env | awk -F= '/^rvm_/{print $1" "}')
}
# Unset ruby-specific variables
__rvm_unset_ruby_variables()
{
# unset rvm_ruby_flag $(env | awk -F= '/^rvm_ruby_/{printf $1" "}')
unset rvm_env_string rvm_ruby_string rvm_ruby_strings rvm_ruby_binary rvm_ruby_gem_home rvm_ruby_gem_path rvm_ruby_home
rvm_ruby_interpreter rvm_ruby_irbrc rvm_ruby_log_path rvm_ruby_major_version rvm_ruby_minor_version rvm_ruby_package_name
rvm_ruby_patch_level rvm_ruby_release_version rvm_ruby_repo_url rvm_ruby_repo_branch rvm_ruby_revision
rvm_ruby_selected_flag rvm_ruby_tag rvm_ruby_version rvm_ruby_load_path rvm_ruby_require rvm_head_flag rvm_ruby_package_file
rvm_ruby_configure rvm_ruby_name rvm_ruby_url rvm_ruby_global_gems_path rvm_ruby_args rvm_ruby_name rvm_llvm_flag
__rvm_load_rvmrc # restore important variables
}
# TODO: Should be able to...
#
Unset both rvm variables as well as ruby-specific variables
# Preserve gemset if 'rvm_sticky' is set
# (persist gemset unless clear is explicitely called).
__rvm_cleanse_variables()
{
__rvm_unset_ruby_variables
if [[ ${rvm_sticky_flag:-0} -eq 1 ]] ; then
export rvm_gemset_name
else
unset rvm_gemset_name
fi
unset rvm_env_string rvm_ruby_string rvm_action rvm_irbrc_file rvm_command rvm_error_message rvm_force_flag rvm_all_flag
rvm_reconfigure_flag rvm_make_flags rvm_bin_flag rvm_import_flag rvm_export_flag rvm_self_flag rvm_gem_flag
rvm_rubygems_flag rvm_debug_flag rvm_delete_flag rvm_summary_flag rvm_test_flag _rvm_spec_flag rvm_json_flag rvm_yaml_flag
rvm_shebang_flag rvm_env_flag rvm_tail_flag rvm_use_flag rvm_dir_flag rvm_list_flag rvm_empty_flag rvm_file_name
rvm_benchmark_flag rvm_clear_flag rvm_name_flag rvm_verbose_flag rvm_user_flag rvm_system_flag rvm_configure_flags
rvm_uninstall_flag rvm_install_flag rvm_llvm_flag rvm_ruby_bits rvm_sticky_flag rvm_rvmrc_flag rvm_gems_flag
rvm_only_path_flag rvm_docs_flag rvm_ruby_aliases rvm_patch_names rvm_install_args rvm_dump_environment_flag rvm_ruby_alias
rvm_static_flag rvm_archive_extension rvm_hook rvm_ruby_name
# rvm_gemsets_path rvm_user_path rvm_wrappers_path rvm_patches_path rvm_docs_path rvm_examples_path rvm_rubies_path
rvm_usr_path rvm_src_path rvm_tmp_path rvm_lib_path rvm_repos_path rvm_log_path rvm_help_path rvm_environments_path
rvm_archives_path
__rvm_load_rvmrc # restore important variables
}
# Add bin path if not present
__rvm_conditionally_add_bin_path()
{
if printf "%b" "${PATH//:/ }" | GREP_OPTIONS="" \grep -vF "${rvm_bin_path}" >/dev/null 2>&1
then
case "${rvm_ruby_string:-"system"}" in
system)
PATH="$PATH:${rvm_bin_path}"
;;
*)
PATH="${rvm_bin_path}:$PATH"
;;
esac
builtin hash -r
fi
return 0
}
__rvm_load_environment()
{
typeset string
string="$1"
if [[ -f "$rvm_environments_path/$string" ]]; then
# Restore the path to it's state minus rvm
__rvm_remove_rvm_from_path
# source the environment file
\. "$rvm_environments_path/$string"
if [[ -s "${rvm_path:-$HOME/.rvm}/hooks/after_use" ]]
then
\. "${rvm_path:-$HOME/.rvm}/hooks/after_use"
fi
# clear the PATH cache
builtin hash -r
elif [[ -n "$string" ]] ; then
rvm "$string"
else
: # TODO: This should have some error handling in the context.
fi
return 0
}
__rvm_export()
{
# extract the variable name from the first arg.
typeset name
name=${1%%=*}
# store the current value, to be restored later.
builtin export rvm_old_$name=${!name}
# pass-through the return value of the builtin.
export "$@"
return $?
}
__rvm_unset_exports()
{
typeset wrap_name name value
while IFS== read -d "" wrap_name value
do
case "$wrap_name" in
rvm_old_*)
name=${wrap_name#rvm_old_}
if [[ -n "${value:-}" ]]
then export $name="${value}"
else unset $name
fi
unset $wrap_name
;;
esac
done < <(printenv_null)
}
# Clean all *duplicate* items out of the path. (keep first occurrence of each)
__rvm_clean_path()
{
PATH="$(printf "%b" "$PATH" \
| awk -v RS=: -v ORS=: '!($0 in a){a[$0];print}')"
PATH="${PATH/%:/}" # Strip trailing : if it exists
export PATH
builtin hash -r
}
# Clean all rvm items out of the current working path.
__rvm_remove_rvm_from_path()
{
PATH="$(printf "%b" "$PATH" \
| awk -v RS=: -v ORS=: "/${rvm_path//\//\/}/ {next} {print}")"
PATH="${PATH/%:/}" # Strip trailing : if it exists
export PATH
builtin hash -r
}
1.18.61.10. pkg
#!/usr/bin/env bash
install_package()
{
__rvm_db "${package}_url" "package_url"
(
builtin cd "$rvm_src_path"
rvm_log "Fetching $package-$version.$archive_format to $rvm_archives_path"
case "$archive_format" in
tar.gz|tgz)
"$rvm_scripts_path/fetch" \
"$package_url/$package-$version.$archive_format" \
|| (result=$? && return $result)
__rvm_run "$package/extract" \
"$rvm_tar_command xmzf $rvm_archives_path/$package-$version.$archive_format -C $rvm_src_path ${rvm_tar_options:-}"
\
"Extracting $package-$version.$archive_format to $rvm_src_path"
;;
tar.bz2)
"$rvm_scripts_path/fetch" \
"$package_url/$package-$version.$archive_format" \
|| (result=$? && return $result)
__rvm_run "$package/extract" \
"$rvm_tar_command xmjf $rvm_archives_path/$package-$version.$archive_format -C $rvm_src_path ${rvm_tar_options:-}
"\
"Extracting $package-$version.$archive_format to $rvm_src_path"
;;
zip)
"$rvm_scripts_path/fetch" \
"$package_url/$package-$version.$archive_format" \
|| (result=$? && return $result)
__rvm_run "$package/extract" \
"unzip -q -o $rvm_archives_path/$package-$version.$archive_format -d $rvm_src_path/$package-$version" \
"Extracting $package-$version.$archive_format to $rvm_src_path"
;;
*)
printf "%b" "\nUnrecognized archive format '$archive_format'" ; return 1
esac
builtin cd "$rvm_src_path/$package-$version"
__rvm_add_to_path append /usr/bin
if [[ ! -z "$patches" ]] ; then
for patch in $(echo $patches | \tr ',' ' ') ; do
__rvm_run "$package/patch" "patch -p0 -f < $patch" "Applying patch '$patch'..."
if [[ $? -gt 0 ]] ; then
rvm_error "Patch $patch did not apply cleanly... back to the patching board :(" ; exit 1
fi
done
fi
if [[ "${rvm_skip_autoreconf_flag:-0}" == 0 ]] &&
which autoreconf >/dev/null 2>&1 &&
which libtoolize >/dev/null 2>&1 &&
[[ -f configure.ac || -f configure.in ]]
then
if [[ -z "${rvm_autoconf_flags:-}" ]]
then
if uname -s | GREP_OPTIONS="" \grep -iE 'cygwin|mingw' >/dev/null
then # no symlinks on windows :(
rvm_autoconf_flags="-ivf"
else
rvm_autoconf_flags="-is --force"
fi
fi
__rvm_run "$package/autoreconf" "autoreconf ${rvm_autoconf_flags}" \
"Prepare $package in $rvm_src_path/$package-$version."
fi
__rvm_run "$package/configure" \
"${configure:-"${rvm_configure_env:-""} ./configure --prefix=\"${prefix_path:-"$rvm_usr_path"}\""}
${rvm_configure_flags:-""} $configure_flags" \
"Configuring $package in $rvm_src_path/$package-$version."
unset configure_flags
if [[ "$action" == "uninstall" ]]
then
__rvm_run "$package/make.uninstall" \
"make uninstall" \
"Uninstalling $package from $rvm_usr_path" && \
builtin cd "$rvm_src_path" && \
__rvm_run "$package/rm_src.uninstall" \
"rm -rf $rvm_src_path/$package-$version" \
"Removing ${package}-${version} from $rvm_src_path" && \
touch "$rvm_path/config/packages"
"$rvm_scripts_path/db" \
"$rvm_path/config/packages" "${package}" delete
else
__rvm_run "$package/make" \
"make $rvm_make_flags" \
"Compiling $package in $rvm_src_path/$package-$version." && \
__rvm_run "$package/make.install" \
"make install" \
"Installing $package to $rvm_usr_path" && \
touch "$rvm_path/config/packages"
"$rvm_scripts_path/db" \
"$rvm_path/config/packages" "${package}" "${version}"
fi
)
}
readline()
{
package="readline" ; archive_format="tar.gz"
configure="env CFLAGS=-I${rvm_usr_path}/include LDFLAGS=-L${rvm_usr_path}/lib ./configure --prefix=${rvm_usr_path} -disable-dependency-tracking --disable-static --enable-shared"
version="5.2"
patches="$rvm_patches_path/$package-$version/shobj-conf.patch"
install_package
version="6.2"
patches="$rvm_patches_path/$package-$version/patch-shobj-conf.diff"
install_package
}
iconv()
{
package="libiconv" ; version=1.13.1 ; archive_format="tar.gz"
install_package
}
curl()
{
package="curl" ; version=7.19.7 ; archive_format="tar.gz"
install_package
}
openssl()
{
package="openssl" ; archive_format="tar.gz"
__rvm_db "${package}_version" "version"
if [[ "Darwin" == "$(uname)" ]] ; then
if [[ -n "$rvm_architectures" ]]; then
if match "$rvm_architectures" "64"; then
hw_cpu64bit=1
fi
if match "$rvm_architectures" "ppc"; then
hw_machine="Power Macintosh"
fi
else
hw_machine=$(sysctl hw.machine | awk -F: '{print $2}' | sed 's/^ //')
hw_cpu64bit=$(sysctl hw.cpu64bit_capable | awk '{print $2}')
fi
if [[ "Power Macintosh" == "$hw_machine" ]] ; then
if [[ $hw_cpu64bit == 1 ]]; then
openssl_os="darwin64-ppc-cc"
else
openssl_os="darwin-ppc-cc"
fi
else
if [[ $hw_cpu64bit == 1 ]]; then
openssl_os="darwin64-x86_64-cc"
else
openssl_os="darwin-i386-cc"
fi
fi
configure_command="./Configure"
# Anyone know WTF happened to these patches???
#patches="$rvm_patches_path/$package/Makefile.org.patch,$rvm_patches_path/$package/crypto-Makefile.patch"
# Don't use -j option for make OpenSSL
[[ -z "$rvm_make_flags" ]] ||
rvm_make_flags=$(echo "$rvm_make_flags" | sed -e "s/-j[[:space:]]*[[:digit:]]*//")
else
configure_command="./config"
fi
configure="$configure_command $openssl_os -I$rvm_usr_path/include -L$rvm_usr_path/lib --prefix=$rvm_usr_path zlib no-asm
no-krb5 shared"
install_package
}
zlib()
{
package="zlib" ; version="1.2.7" ; archive_format="tar.gz"
install_package
}
autoconf()
{
package="autoconf" ; version="2.65" ; archive_format="tar.gz"
prefix_path="$rvm_usr_path"
install_package
}
ncurses()
{
package="ncurses" ; version="5.7" ; archive_format="tar.gz"
configure_flags="--with-shared --disable-rpath --without-debug --without-ada --enable-safe-sprintf --enable-sigwinch -without-progs"
install_package
}
pkgconfig()
{
package="pkg-config" ; version="0.23" archive_format="tar.gz"
install_package
}
gettext()
{
package="gettext" ; version="0.17" ; archive_format="tar.gz"
install_package
}
libxml2()
{
package="libxml2" ; version="2.7.3" ; archive_format="tar.gz"
if [[ "Darwin" == "$(uname)" ]] ; then
configure="./configure --prefix=$rvm_usr_path --build=i686-apple-darwin$(uname -r) --host=i686-apple-darwin$(uname -r)"
fi
install_package
unset prefix_path
}
libxslt()
{
package="libxslt" ; version="1.1.26" ; archive_format="tar.gz"
install_package
unset prefix_path
}
libyaml()
{
package="yaml" ; version="0.1.4" ; archive_format="tar.gz"
if [[ "Darwin" == "$(uname)" ]]
then
unset rvm_configure_env
fi
install_package
}
libyaml_installed()
{
typeset path
path="${prefix_path:-${rvm_usr_path:-${rvm_path}/usr}}"
if [[ "Darwin" == "$(uname)" ]]
then
extension="dylib"
else
extension="so"
fi
[[ -f "${path}/include/yaml.h" ]] && \find "${path}" -name "libyaml.${extension}" | GREP_OPTIONS="" \grep '.*' >/dev/null
}
glib()
{
pkgconfig
gettext
package="glib" ; version="2.23.1" ; archive_format="tar.gz"
configure="CC=\"cc -L$rvm_usr_path/lib -I$rvm_usr_path/include\" PKG_CONFIG=\"$rvm_usr_path/bin/pkg-config\" ./configure -prefix=\"$rvm_usr_path\""
install_package
}
mono()
{
glib
__rvm_mono_env
package="mono" ; version="2.6.1" ; archive_format="tar.bz2"
install_package
}
llvm()
{
package="llvm"
version="89156"
(
builtin cd $rvm_src_path
if [[ ! -d "$rvm_src_path/llvm/.svn" ]] ; then
__rvm_db "${package}_url" "package_url"
__rvm_rm_rf "$rvm_src_path/llvm"
svn co -r "$version" "$package_url" llvm
builtin cd "$rvm_src_path/llvm"
./configure --enable-bindings=none
UNIVERSAL=1 UNIVERSAL_ARCH="i386 x86_64" ENABLE_OPTIMIZED=1 make -j2
sudo env UNIVERSAL=1 UNIVERSAL_ARCH="i386 x86_64" ENABLE_OPTIMIZED=1 make install
fi
)
}
reset()
{
unset package version archive_format patches prefix_path configure configure_flags
}
1.18.61.11. rvmrc
#!/usr/bin/env bash
export escape_flag _first _second
escape_flag=1
_first=${__array_start}
_second=$[__array_start + 1]
__rvm_md5_for()
{
if builtin command -v md5 > /dev/null; then
echo "$1" | md5
elif builtin command -v md5sum > /dev/null ; then
echo "$1" | md5sum | awk '{print $1}'
else
rvm_error "Neither md5 nor md5sum were found in the PATH"
return 1
fi
return 0
}
__rvm_sha256_for()
{
if builtin command -v sha256sum > /dev/null ; then
echo "$1" | sha256sum | awk '{print $1}'
elif builtin command -v sha256 > /dev/null ; then
echo "$1" | sha256 | awk '{print $1}'
elif builtin command -v shasum > /dev/null ; then
echo "$1" | shasum -a256 | awk '{print $1}'
else
rvm_error "Neither sha256sum nor shasum found in the PATH"
return 1
fi
return 0
}
__rvm_md5_for_contents()
{
if builtin command -v md5 > /dev/null
then
echo "$1" | cat - "$1" | md5
elif builtin command -v md5sum > /dev/null
then
echo "$1" | cat - "$1" | md5sum | awk '{print $1}'
else
rvm_error "Neither md5 nor md5sum were found in the PATH"
return 1
fi
return 0
}
__rvm_sha256_for_contents()
{
if builtin command -v sha256sum > /dev/null ; then
echo "$1" | cat - "$1" | sha256sum | awk '{print $1}'
elif builtin command -v sha256 > /dev/null ; then
echo "$1" | cat - "$1" | sha256 | awk '{print $1}'
elif builtin command -v shasum > /dev/null ; then
echo "$1" | cat - "$1" | shasum -a256 | awk '{print $1}'
else
rvm_error "Neither sha256sum nor shasum found in the PATH"
return 1
fi
return 0
}
__rvm_rvmrc_key()
{
printf "%b" "$1" | \tr '[#/.=]' _
return $?
}
__rvm_reset_rvmrc_trust()
{
if [[ "$1" == all ]]
then
echo "" > "$rvm_user_path/rvmrcs"
else
"$rvm_scripts_path/db" "$rvm_user_path/rvmrcs" \
"$(__rvm_rvmrc_key "$1")" "delete" >/dev/null 2>&1
fi
}
__rvm_trust_rvmrc()
{
__rvm_reset_rvmrc_trust "$1"
"$rvm_scripts_path/db" "$rvm_user_path/rvmrcs" \
"$(__rvm_rvmrc_key "$1")" "1;$(__rvm_md5_for_contents "$1")$(__rvm_sha256_for_contents "$1")" >/dev/null 2>&1
return $?
}
__rvm_untrust_rvmrc()
{
__rvm_reset_rvmrc_trust "$1"
"${rvm_scripts_path:-"$rvm_path/scripts"}/db" "$rvm_user_path/rvmrcs" \
"$(__rvm_rvmrc_key "$1")" "0;$(__rvm_md5_for_contents "$1")$(__rvm_sha256_for_contents "$1")" >/dev/null 2>&1
}
__rvm_rvmrc_stored_trust()
{
"${rvm_scripts_path:-"$rvm_path/scripts"}/db" "$rvm_user_path/rvmrcs" \
"$(__rvm_rvmrc_key "$1")"
return $?
}
__rvm_rvmrc_tools()
{
export escape_flag
typeset rvmrc_action rvmrc_path saveIFS trust rvmrc_ruby
escape_flag=1
rvmrc_action="$1"
(( $# )) && shift || true
if [[ "${rvmrc_action}" == "create" ]]
then
rvmrc_ruby="${1:-${MY_RUBY_HOME##*/}}"
rvmrc_path="$(builtin cd "$PWD" >/dev/null 2>&1; pwd)"
elif [[ "${1:-}" == "all" ]]
then
rvmrc_path="all"
else
rvmrc_path="$(builtin cd "${1:-$PWD}" >/dev/null 2>&1; pwd)"
fi
(( $# )) && shift || true
if (( $# ))
then rvmrc_path="${rvmrc_path}/$1"
elif [[ -s "${rvmrc_path}/.rvmrc" ]]
then rvmrc_path="${rvmrc_path}/.rvmrc"
elif [[ -s "${rvmrc_path}/.versions.conf" ]]
then rvmrc_path="${rvmrc_path}/.versions.conf"
elif [[ -f "${rvmrc_path}/.ruby-version" ]]
then rvmrc_path="${rvmrc_path}/.ruby-version"
elif [[ -f "${rvmrc_path}/.rbfu-version" ]]
then rvmrc_path="${rvmrc_path}/.rbfu-version"
elif [[ -f "${rvmrc_path}/.rbenv-version" ]]
then rvmrc_path="${rvmrc_path}/.rbenv-version"
elif [[ -f "${rvmrc_path}/Gemfile" ]]
then rvmrc_path="${rvmrc_path}/Gemfile"
elif [[ "${rvmrc_path}" == "all" ]]
then rvmrc_path="all"
else rvmrc_path="${rvmrc_path}/.rvmrc"
fi
case "$rvmrc_action" in
create)
(
rvm_ruby_string="${rvmrc_ruby}"
rvm_create_flag=1 __rvm_use
case "${rvmrc_path}" in
(*/.rvmrc|*/--rvmrc)
__rvm_set_rvmrc
;;
(*/.ruby-version|*/--ruby-version)
__rvm_set_ruby_version
;;
(*/.versions.conf|*/--versions-conf)
__rvm_set_versions_conf
;;
(*)
rvm_error "Unrecognized project file format."
return 1
;;
esac
)
;;
reset)
__rvm_reset_rvmrc_trust "$rvmrc_path"
echo "Reset trust for $rvmrc_path"
;;
trust)
__rvm_trust_rvmrc "$rvmrc_path"
echo "Marked $rvmrc_path as trusted"
;;
untrust)
__rvm_untrust_rvmrc "$rvmrc_path"
echo "Marked $rvmrc_path as untrusted"
;;
trusted)
if [[ -f "$rvmrc_path" ]]
then
saveIFS=$IFS
IFS=$';'
trust=($(__rvm_rvmrc_stored_trust "$rvmrc_path"))
IFS=$saveIFS
if [[ "${trust[${_second}]:-'#'}" != "$(__rvm_md5_for_contents "$rvmrc_path")$(__rvm_sha256_for_contents
"$rvmrc_path")" ]]
then
echo "The rvmrc at '$rvmrc_path' contains unreviewed changes."
elif [[ "${trust[${_first}]}" == '1' ]]
then
echo "The rvmrc at '$rvmrc_path' is currently trusted."
elif [[ "${trust[${_first}]}" == '0' ]]
then
echo "The rvmrc at '$rvmrc_path' is currently untrusted."
else
echo "The trustiworthiness of '$rvmrc_path' is currently unknown."
fi
else
echo "There is no $rvmrc_path"
fi
;;
is_trusted)
if [[ -f "$rvmrc_path" ]]
then
saveIFS=$IFS
IFS=$';'
trust=($(__rvm_rvmrc_stored_trust "$rvmrc_path"))
IFS=$saveIFS
if [[ "${trust[${_second}]:-'#'}" != "$(__rvm_md5_for_contents "$rvmrc_path")$(__rvm_sha256_for_contents
"$rvmrc_path")" ]]
then
return 1
elif [[ "${trust[${_first}]}" == '1' ]]
then
return 0
else
return 1
fi
else
return 1
fi
;;
load)
rvm_rvmrc_cwd="" rvm_trust_rvmrcs_flag=1 \
__rvm_project_rvmrc "$(dirname "$rvmrc_path")" "$(basename "$rvmrc_path")"
;;
try_to_read_ruby)
case "$rvmrc_path" in
(*/.rvmrc)
if ! __rvm_rvmrc_tools is_trusted "$(dirname "$rvmrc_path")" "$(basename "$rvmrc_path")"
then
# subprocess to not mess with current process variables
( rvm_promptless=1 __rvm_project_rvmrc "$(dirname "$rvmrc_path")" "$(basename "$rvmrc_path")" >/dev/null 2>&1 )
fi
if __rvm_rvmrc_tools is_trusted "$(dirname "$rvmrc_path")" "$(basename "$rvmrc_path")"
then
rvm_action="${rvm_action:-use}"
rvm_ruby_string="$(
rvm_rvmrc_cwd=""
rvm_trust_rvmrcs_flag=1
__rvm_project_rvmrc "$(dirname "$rvmrc_path")" "$(basename "$rvmrc_path")" >/dev/null 2>&1
__rvm_env_string
)"
rvm_ruby_strings="$rvm_ruby_string"
else
rvm_action="error"
rvm_error_message="The give path does not contain '$(basename "$rvmrc_path")' (or it is not trusted): '$(dirname
"$rvmrc_path")' rest of params: '$@'"
fi
;;
(*)
rvm_action="${rvm_action:-use}"
rvm_ruby_string="$(
rvm_rvmrc_cwd=""
rvm_trust_rvmrcs_flag=1
__rvm_project_rvmrc "$(dirname "$rvmrc_path")" "$(basename "$rvmrc_path")" >/dev/null 2>&1
__rvm_env_string
)"
rvm_ruby_strings="$rvm_ruby_string"
;;
esac
;;
*)
echo "Usage: rvm rvmrc {trust,untrust,trusted,load,reset,is_trusted,try_to_read_ruby,create}"
return 1
;;
esac
unset escape_flag
return $?
}
__rvm_check_rvmrc_trustworthiness()
{
typeset saveIFS trust result
# Trust when they have the flag... of doom!
if [[ -n "$1" && ${rvm_trust_rvmrcs_flag:-0} == 0 ]]
then
saveIFS="$IFS"
IFS=$';'
trust=( $( __rvm_rvmrc_stored_trust "$1" ) )
IFS="$saveIFS"
if [[ "${trust[${_second}]:-'#'}" != "$(__rvm_md5_for_contents "$1")$(__rvm_sha256_for_contents "$1")" ]]
then
__rvm_ask_to_trust "$1"
else
[[ "${trust[${_first}]}" == '1' ]]
fi
fi
result=$?
unset escape_flag
return $result
}
__rvm_display_rvmrc()
{
typeset _rvmrc_base _read_char_flag
_rvmrc_base="$(basename "${_rvmrc}")"
[[ -n "${ZSH_VERSION:-}" ]] && _read_char_flag=k || _read_char_flag=n
printf "
====================================================================================
= %-80s =
= After reading the file, you will be prompted again for 'yes or no' to set
=
= the trust level for this particular version of the file.
=
=
=
= %-80s =
= changes, and may change the trust setting manually at any time.
=
====================================================================================
(( press a key to review the ${_rvmrc_base} file ))
" \
"The contents of the ${_rvmrc_base} file will now be displayed." \
"Note: You will be re-prompted each time the ${_rvmrc_base} file's contents change"
builtin read -${_read_char_flag} 1 -s -r anykey
printf "%b" "${rvm_warn_clr}"
command cat -v "${_rvmrc}"
printf "%b" "${rvm_reset_clr}"
printf "
====================================================================================
= %-80s =
====================================================================================
= %-80s =
= %-80s =
= Note that if the contents of the file change, you will be re-prompted to
=
= review the file and adjust its trust settings. You may also change the
=
= trust settings manually at any time with the 'rvm rvmrc' command.
=
====================================================================================
" \
"Viewing of ${_rvmrc} complete." \
"Trusting an ${_rvmrc_base} file means that whenever you cd into this directory," \
"RVM will run this ${_rvmrc_base} shell script."
}
__rvm_ask_to_trust()
{
typeset trusted value anykey _rvmrc
_rvmrc="${1}"
if [[ ! -t 0 ]] || (( ${rvm_promptless:=0} == 1 )) || [[ -n "$MC_SID" ]]
then
return 2
fi
printf "====================================================================================
= NOTICE
=
====================================================================================
= %-80s =
= This is a shell script and therefore may contain any shell commands.
=
=
=
= Examine the contents of this file carefully to be sure the contents are
=
= safe before trusting it! ( Choose v[iew] below to view the contents )
=
====================================================================================
" \
"RVM has encountered a new or modified $(basename "${_rvmrc}") file in the current directory"
trusted=0
while (( ! trusted ))
do
printf "Do you wish to trust this $(basename "${_rvmrc}") file? (%b)\n" "${_rvmrc}"
printf "%b" 'y[es], n[o], v[iew], c[ancel]> '
builtin read response
value="$(echo -n "${response}" | \tr '[[:upper:]]' '[[:lower:]]' | __rvm_strip)"
case "${value:-n}" in
v|view)
__rvm_display_rvmrc
;;
y|yes)
trusted=1
;;
n|no)
break
;;
c|cancel)
return 1
;;
esac
done
if (( trusted ))
then
__rvm_trust_rvmrc "$1"
return 0
else
__rvm_untrust_rvmrc "$1"
return 1
fi
}
# Checks the rvmrc for the given directory. Note that if
# argument is passed, it will be used instead of pwd.
__rvm_project_rvmrc()
{
export __rvm_project_rvmrc_lock
: __rvm_project_rvmrc_lock:${__rvm_project_rvmrc_lock:=0}
: __rvm_project_rvmrc_lock:$((__rvm_project_rvmrc_lock+=1))
if (( __rvm_project_rvmrc_lock > 1 ))
then return 0 # no nesting
fi
typeset working_dir requested_file found_file rvm_trustworthiness_result
# Get the first argument or the pwd.
working_dir="${1:-"$PWD"}"
requested_file="${2:-}"
while :
do
if [[ -z "$working_dir" || "$HOME" == "$working_dir" || "${rvm_prefix:-}" == "$working_dir"
then
if [[ -n "${rvm_current_rvmrc:-""}" ]]
then
__rvm_remove_rvm_from_path ; __rvm_conditionally_add_bin_path
if (( ${rvm_project_rvmrc_default:-0} == 1 ))
then
__rvm_load_environment "default"
elif [[ -n "${rvm_previous_environment:-""}" ]]
then
__rvm_load_environment "$rvm_previous_environment"
fi
unset rvm_current_rvmrc rvm_previous_environment
fi
break
else
if [[ -n "${requested_file}" && -f "$working_dir/${requested_file}" ]]
then found_file="$working_dir/${requested_file}"
elif [[ -f "$working_dir/.rvmrc" ]]
then found_file="$working_dir/.rvmrc"
elif [[ -f "$working_dir/.versions.conf" ]]
then found_file="$working_dir/.versions.conf"
elif [[ -f "$working_dir/.ruby-version" ]]
then found_file="$working_dir/.ruby-version"
elif [[ -f "$working_dir/.rbfu-version" ]]
then found_file="$working_dir/.rbfu-version"
elif [[ -f "$working_dir/.rbenv-version" ]]
then found_file="$working_dir/.rbenv-version"
elif [[ -f "$working_dir/Gemfile" ]]
|| "/" == "$working_dir" ]]
then found_file="$working_dir/Gemfile"
fi
if [[ -n "${found_file}" ]]
then
if [[ "${rvm_current_rvmrc:-""}" != "${found_file}" ]]
then
if __rvm_conditionally_do_with_env __rvm_load_project_config "${found_file}"
then true
else
rvm_trustworthiness_result=$?
unset __rvm_project_rvmrc_lock
return "$rvm_trustworthiness_result"
fi
fi
break
else
working_dir="$(dirname "$working_dir")"
fi
fi
done
unset __rvm_project_rvmrc_lock
return $?
}
__rvm_load_project_config()
{
typeset __gemfile
: rvm_autoinstall_bundler_flag:${rvm_autoinstall_bundler_flag:=0}
case "$1" in
(*/.rvmrc)
if __rvm_check_rvmrc_trustworthiness "$1"
then
__rvm_remove_rvm_from_path ; __rvm_conditionally_add_bin_path
rvm_previous_environment="$(__rvm_env_string)"
rvm_current_rvmrc="$1"
__rvm_ensure_is_a_function
source "$1"
else return $?
fi
;;
(*/.versions.conf)
typeset _gem _gem_names _bundle_install
__rvm_ensure_is_a_function
rvm_previous_environment="$(__rvm_env_string)"
rvm_current_rvmrc="$1"
rvm_ruby_string="$(sed -n '/^ruby=/ {s/ruby=//;p;}' < "$1")"
[[ -n "${rvm_ruby_string}" ]] || return 2
rvm_gemset_name="$(sed -n '/^ruby-gemset=/ {s/ruby-gemset=//;p;}' < "$1")"
rvm_create_flag=1 __rvm_use
|| return 3
# TODO: read env.* # how to sanitize ?
_gem_names="$(sed -n '/^ruby-gem-install=/ {s/ruby-gem-install=//;p;}' < "$1")"
for _gem in ${_gem_names//,/ }
do
# TODO: add support for versions
if ! gem list | GREP_OPTIONS="" \grep "^${_gem} " > /dev/null
then gem install "${_gem}"
fi
done
_bundle_install="$(sed -n '/^ruby-bundle-install=/ {s/ruby-bundle-install=//;p;}' < "$1")"
if [[ -n "${_bundle_install}" ]] || [[ "${rvm_autoinstall_bundler_flag:-0}" == 1 ]]
then
if [[ "${_bundle_install}" == true ]] # prevent file named true for Gemfile
then __gemfile="$(dirname $1)/Gemfile"
elif [[ -f "${_bundle_install}" ]]
then __gemfile="${_bundle_install}"
elif [[ "${rvm_autoinstall_bundler_flag:-0}" == 1 ]]
then __gemfile="$(dirname $1)/Gemfile"
fi
fi
;;
(*/Gemfile)
__rvm_ensure_is_a_function
rvm_previous_environment="$(__rvm_env_string)"
rvm_current_rvmrc="$1"
rvm_ruby_string="$(sed -n '/^#ruby=/ {s/#ruby=//;p;}' < "$1")"
[[ -n "${rvm_ruby_string}" ]] || {
rvm_ruby_string="$(sed -n "/^\s*ruby/ {s/^\s*ruby//; s/[ ()'\"]//g; p;}" < "$1")"
[[ -n "${rvm_ruby_string}" ]] || return 2
}
rvm_gemset_name="$(sed -n '/^#ruby-gemset=/ {s/#ruby-gemset=//;p;}' < "$1")"
rvm_create_flag=1 __rvm_use
|| return 3
# TODO: read #env.* # how to sanitize ?
if [[ "${rvm_autoinstall_bundler_flag:-0}" == "1" ]]
then
__gemfile="$1"
gem list | GREP_OPTIONS="" \grep "^bundler " > /dev/null ||
gem install bundler
fi
;;
(*/.ruby-version|*/.rbfu-version|*/.rbenv-version)
__rvm_ensure_is_a_function
rvm_previous_environment="$(__rvm_env_string)"
rvm_current_rvmrc="$1"
rvm_ruby_string="$(cat "$1")"
[[ -n "${rvm_ruby_string}" ]] || return 2
if [[ -f "$(dirname $1)/.ruby-gemset" ]]
then
rvm_gemset_name="$(cat "$(dirname $1)/.ruby-gemset")"
fi
rvm_create_flag=1 __rvm_use
|| return 3
# "$(dirname $1)/.rbenv-vars" ... can we support those without licensing ?
if [[ "${rvm_autoinstall_bundler_flag:-0}" == 1 && -f "$(dirname $1)/Gemfile" ]]
then
if ! gem list | GREP_OPTIONS="" \grep "^bundler " > /dev/null
then
gem install "bundler"
fi
__gemfile="$(dirname $1)/Gemfile"
fi
;;
(*)
rvm_error "Unsupported file format for '$1'"
return 1
;;
esac
if [[ -n "${__gemfile:-}" && -f "${__gemfile:-}" ]]
then bundle install --gemfile="${__gemfile}" | GREP_OPTIONS="" \grep -vE '^Using|Your bundle is complete'
fi
}
__rvm_project_rvmrc_with_env()
{
__rvm_do_with_env __rvm_project_rvmrc "$@"
}
__rvm_set_versions_conf()
{
typeset gemset identifier
if [[ -s .versions.conf ]]
then
mv .versions.conf .versions.conf.$(date +%m.%d.%Y-%H:%M:%S)
rvm_warn ".version.conf is not empty, moving aside to preserve."
fi
identifier=$(__rvm_env_string)
gemset=${identifier#*@}
identifier=${identifier%@*}
printf "%b" "ruby=$identifier
" >> .versions.conf
if [[ -n "$gemset" && "$gemset" != "$identifier" ]]
then
printf "%b" "ruby-gemset=$gemset
" >> .versions.conf
else
printf "%b" "#ruby-gemset=my-projectit
" >> .versions.conf
fi
printf "%b" "#ruby-gem-install=bundler rake
#ruby-bundle-install=true
" >> .versions.conf
}
__rvm_set_ruby_version()
{
if [[ -s .ruby-version ]]
then
mv .ruby-version .ruby-version.$(date +%m.%d.%Y-%H:%M:%S)
rvm_warn ".ruby-version is not empty, moving aside to preserve."
fi
echo "$(__rvm_env_string)" >> .ruby-version
}
__rvm_set_rvmrc()
{
typeset flags identifier short_identifier gem_file
true ${rvm_verbose_flag:=0}
if [[ "$HOME" != "$PWD" && "${rvm_prefix:-}" != "$PWD" ]]
then
if (( rvm_verbose_flag ))
then
flags="use "
fi
if [[ -s .rvmrc ]]
then
mv .rvmrc .rvmrc.$(date +%m.%d.%Y-%H:%M:%S)
rvm_warn ".rvmrc is not empty, moving aside to preserve."
fi
identifier=$(__rvm_env_string)
short_identifier="${identifier#ruby-}"
short_identifier="${short_identifier%%-*}"
printf "%b" "#!/usr/bin/env bash
# This is an RVM Project .rvmrc file, used to automatically load the ruby
# development environment upon cd'ing into the directory
# First we specify our desired <ruby>[@<gemset>], the @gemset name is optional,
# Only full ruby name is supported here, for short names use:
#
echo \"rvm use ${short_identifier}\" > .rvmrc
environment_id=\"$identifier\"
# Uncomment the following lines if you want to verify rvm version per project
# rvmrc_rvm_version=\"${rvm_version}\" # 1.10.1 seams as a safe start
# eval \"\$(echo \${rvm_version}.\${rvmrc_rvm_version} | awk -F. '{print \"[[ \"\$1*65536+\$2*256+\$3\" -ge
\"\$4*65536+\$5*256+\$6\" ]]\"}' )\" || {
#
echo \"This .rvmrc file requires at least RVM \${rvmrc_rvm_version}, aborting loading.\"
#
return 1
# }
" >> .rvmrc
if [[ "$identifier" =~ jruby* ]]
then
printf "%b" "
# Uncomment following line if you want options to be set only for given project.
# PROJECT_JRUBY_OPTS=( --1.9 )
# The variable PROJECT_JRUBY_OPTS requires the following to be run in shell:
#
chmod +x \${rvm_path}/hooks/after_use_jruby_opts
" >> .rvmrc
fi
printf "%b" "
# First we attempt to load the desired environment directly from the environment
# file. This is very fast and efficient compared to running through the entire
# CLI and selector. If you want feedback on which environment was used then
# insert the word 'use' after --create as this triggers verbose mode.
if [[ -d \"\${rvm_path:-\$HOME/.rvm}/environments\"
&& -s \"\${rvm_path:-\$HOME/.rvm}/environments/\$environment_id\" ]]
then
\\. \"\${rvm_path:-\$HOME/.rvm}/environments/\$environment_id\"
[[ -s \"\${rvm_path:-\$HOME/.rvm}/hooks/after_use\" ]] &&
\\. \"\${rvm_path:-\$HOME/.rvm}/hooks/after_use\" || true
" >> .rvmrc
if [[ " $flags " =~ " use " ]]
then
printf "%b" " if [[ \$- == *i* ]] # check for interactive shells
then echo \"Using: \$(tput setaf 2)\$GEM_HOME\$(tput sgr0)\" # show the user the ruby and gemset they are using in green
else echo \"Using: \$GEM_HOME\" # don't use colors in non-interactive shells
fi
" >> .rvmrc
fi
printf "%b" "else
# If the environment file has not yet been created, use the RVM CLI to select.
rvm --create $flags \"\$environment_id\" || {
echo \"Failed to create RVM environment '\${environment_id}'.\"
return 1
}
fi
" >> .rvmrc
for gem_file in *.gems
do
case "$gem_file" in
(\*.gems) continue ;;
esac
printf "%b" "
# If you use an RVM gemset file to install a list of gems (*.gems), you can have
# it be automatically loaded. Uncomment the following and adjust the filename if
# necessary.
#
# filename=\".gems\"
# if [[ -s \"\$filename\" ]]
# then
#
rvm gemset import \"\$filename\" | GREP_OPTIONS="" \grep -v already | grep -v listed | grep -v complete | sed '/^$/d'
# fi
" >> .rvmrc
done
if [[ -s Gemfile ]]
then
printf "%b" "
# If you use bundler, this might be useful to you:
# if [[ -s Gemfile ]] && {
#
! builtin command -v bundle >/dev/null ||
#
#
#
#
#
#
#
#
#
#
"
builtin command -v bundle | GREP_OPTIONS="" \grep \$rvm_path/bin/bundle >/dev/null
}
then
printf \"%b\" \"The rubygem 'bundler' is not installed. Installing it now.\\\\n\"
gem install bundler
fi
if [[ -s Gemfile ]] && builtin command -v bundle >/dev/null
then
bundle install | GREP_OPTIONS="" \grep -vE '^Using|Your bundle is complete'
fi
>> .rvmrc
fi
else
rvm_error ".rvmrc cannot be set in your home directory.\
\nThe home .rvmrc is for global rvm settings only."
fi
}
__rvm_project_dir_check()
{
[[ -n "${1:-}" && -d "$1" ]] && {
[[ -f "$1/.rvmrc"
&& -s "$1/.rvmrc"
]] ||
[[ -f "$1/.versions.conf" && -s "$1/.versions.conf" ]] ||
[[ -f "$1/.ruby-version" && -s "$1/.ruby-version" ]] ||
[[ -f "$1/.rbfu-version" && -s "$1/.rbfu-version" ]] ||
[[ -f "$1/.rbenv-version" && -s "$1/.rbenv-version" ]] ||
{
[[ -f "$1/Gemfile" && -s "$1/Gemfile" ]] && {
GREP_OPTIONS="" \grep "^#ruby=" "$1/Gemfile" >/dev/null ||
GREP_OPTIONS="" \grep "^\s*ruby" "$1/Gemfile" >/dev/null
}
}
}
}
1.18.61.12. logging
#!/usr/bin/env bash
# Logging functions
# check if user wants colors and if output goes to terminal
# rvm_pretty_print_flag:
# - 0|no
- disabled always
# - 1|auto - automatic depending if the output goes to terminal (default)
# - 2|force - forced always
# to select which terminal output should be checked use first param:
# - stdout - for stdout (default)
# - stderr - for stderr
# - number - for the given terminal fd
# - else
- for both stdout and stderr
rvm_pretty_print()
{
case "${rvm_pretty_print_flag:=auto}" in
(0|no)
return 1
;;
(1|auto)
case "${TERM:-dumb}" in
(dumb|unknown) return 1 ;;
esac
case "$1" in
(stdout)
[[ -t 1
]] || return 1 ;;
(stderr)
[[ -t 2
]] || return 1 ;;
([[:digit:]]) [[ -t $1
]] || return 1 ;;
(any)
[[ -t 1 || -t 2 ]] || return 1 ;;
(*)
[[ -t 1 && -t 2 ]] || return 1 ;;
esac
return 0
;;
(2|force)
return 0
;;
esac
}
case "${TERM:-dumb}" in
(dumb|unknown)
rvm_error_clr=""
rvm_warn_clr=""
rvm_debug_clr=""
rvm_notify_clr=""
rvm_reset_clr=""
;;
(*)
rvm_error_clr="$( "${rvm_scripts_path:-${rvm_pat}/scripts}/color"
rvm_warn_clr="$(
"${rvm_scripts_path:-${rvm_pat}/scripts}/color"
rvm_debug_clr="$( "${rvm_scripts_path:-${rvm_pat}/scripts}/color"
rvm_notify_clr="$( "${rvm_scripts_path:-${rvm_pat}/scripts}/color"
rvm_reset_clr="$( "${rvm_scripts_path:-${rvm_pat}/scripts}/color"
;;
esac
rvm_error()
{
if rvm_pretty_print stderr
then printf "%b" "${rvm_error_clr:-}$*${rvm_reset_clr:-}\n"
else printf "%b" "$*\n"
fi >&2
}
rvm_warn()
{
if rvm_pretty_print stdout
then printf "%b" "${rvm_warn_clr:-}$*${rvm_reset_clr:-}\n"
else printf "%b" "$*\n"
fi
}
rvm_debug()
{
if rvm_pretty_print stdout
then printf "%b" "${rvm_debug_clr:-}$*${rvm_reset_clr:-}\n"
else printf "%b" "$*\n"
fi
}
rvm_log()
{
if rvm_pretty_print stdout
then printf "%b" "${rvm_notify_clr:-}$*${rvm_reset_clr:-}\n"
else printf "%b" "$*\n"
fi
}
"${rvm_error_color:-red}"
"${rvm_warn_color:-yellow}"
"${rvm_debug_color:-magenta}"
"${rvm_notify_color:-green}"
"${rvm_reset_color:-reset}"
)"
)"
)"
)"
)"
1.18.61.13. benchmark
#!/usr/bin/env bash
# Wrap the specified ruby code file in a Benchmark.bmbm block and execute it.
__rvm_benchmark()
{
typeset old_rvm_ruby_string
code="require \"benchmark\" \n \
Benchmark.bmbm do |benchmark| \n \
benchmark.report(\"${rvm_ruby_file}\") do \n"
printf "%b" "\n$code" > "${rvm_tmp_path}/$$.rb"
unset code
cat $rvm_ruby_file >> "${rvm_tmp_path}/$$.rb"
printf "%b" "\n end \nend\n" >> "${rvm_tmp_path}/$$.rb"
rvm_ruby_args="${rvm_tmp_path}/$$.rb"
rvm_benchmark_flag=1
rvm_action="ruby"
if [[ ${rvm_debug_flag:0} -gt 0 ]] ; then
printf "%b" "\n${rvm_tmp_path}/$$.rb:\n\
$(cat ${rvm_tmp_path}/$$.rb)"
fi
# Override ruby string stuff, pass through.
old_rvm_ruby_string=$rvm_ruby_string
# TODO: We can likely do this in a subshell in order to
#
preserve the original environment?
unset rvm_ruby_string
export rvm_ruby_strings
"$rvm_scripts_path/set" "$rvm_action" $rvm_ruby_args ; result=$?
# Restore the state pre-sets.
[[ -n "$old_rvm_ruby_string" ]] && rvm_ruby_string=$old_rvm_ruby_string
return ${result:-0}
}
1.18.61.14. developer
#!/usr/bin/env bash
#
# Switch between RVM installs.
# Given a topic context name like "testing", looks for a directory named ".rvm.testing"
# (installing a new copy of RVM in it if it doesn't already exist), then symlinks
# .rvm to it.
#
# rvmselect testing
rvmselect()
{
if [[ -z "${1:-}" ]]
then
echo "No topic context name specified (example: work )"
return 0
fi
typeset name
name=$1
true ${rvm_path:=$HOME/.rvm}
if [[ ! -L "$rvm_path" && -d "$rvm_path" ]]
then
printf "%b" "ERROR: $rvm_path is a directory, rename it to .<somename> first."
fi
if [[ ! -d "${rvm_path}.${name}" ]]
then
curl -L get.rvm.io | bash
mv "${rvm_path}" "${rvm_path}.${name}"
fi
rm -f "${rvm_path}"
ln -fs "${rvm_path}.${name}" "${rvm_path}"
ls -al "$(basename "${rvm_path}")" | GREP_OPTIONS="" \grep "$rvm_path" | awk '/rvm/{print "=> "$NF}'
return $?
}
1.18.61.15. build
#!/usr/bin/env bash
# show the user selected compiler or return 1
__rvm_selected_compiler()
{
if [[ " ${rvm_configure_flags:-}" =~ " --with-gcc=" ]]
then
typeset __compiler
__compiler="${rvm_configure_flags}"
__compiler="${__compiler#*--with-gcc=}"
__compiler="${__compiler% *}"
echo "${__compiler}"
elif [[ -n "${CC:-}" ]]
then
echo "${CC}"
else
return 1
fi
}
__rvm_found_compiler()
{
__rvm_selected_compiler || which gcc 2>/dev/null
}
__rvm_compiler_is_llvm()
{
typeset compiler
if compiler=$(__rvm_found_compiler)
then
$compiler --version | GREP_OPTIONS="" \grep -i llvm >/dev/null
else
return 1
fi
}
__rvm_compiler_is_gcc47()
{
typeset compiler
if compiler=$(__rvm_found_compiler)
then
[[ "$($compiler -dumpversion)" =~ "4.7" ]]
else
return 1
fi
}
__rvm_setup_compile_environment()
{
__rvm_setup_compile_environment_osx_gcc
__rvm_setup_compile_environment_osx_architectures
__rvm_setup_compile_environment_gcc47
}
__rvm_setup_compile_environment_osx_gcc()
{
if [[ "Darwin" == "$(uname)" ]] && ! __rvm_selected_compiler > /dev/null
then
export CC
# override CC if gcc-4.2 available (OSX)
if [[ -x /usr/bin/gcc-4.2 ]]
then
CC=/usr/bin/gcc-4.2
elif which gcc-4.2 > /dev/null
then
CC=gcc-4.2
fi
fi
if [[ "${rvm_patch_names:-}" =~ *debug* ]]
then rvm_force_autoconf_flag=1
fi
}
__rvm_setup_compile_environment_osx_architectures()
{
[[ -n "${rvm_architectures:-}" ]] || return 0
if [[ "${rvm_ruby_version}" =~ 1.9.* ]]
then
# Ruby 1.9.x supports the easy way
rvm_configure_flags="${rvm_configure_flags:-} --with-arch=${rvm_architectures}"
else
export -a rvm_configure_env
typeset architectures architecture
for architecture in ${rvm_architectures//,/ }
do architectures="${architectures} -arch ${architecture}"
done
rvm_configure_env+=(
"MACOSX_DEPLOYMENT_TARGET=$(sw_vers -productVersion | awk -F'.' '{print $1"."$2}')"
)
rvm_configure_env+=("CFLAGS='${architectures} -g -Os -pipe -no-cpp-precomp'")
rvm_configure_env+=("CCFLAGS='${architectures} -g -Os -pipe'")
rvm_configure_env+=("CXXFLAGS='${architectures} -g -Os -pipe'")
rvm_configure_env+=("LDFLAGS='${architectures} -bind_at_load'")
rvm_configure_env+=(
"LDSHARED='cc ${architectures} -dynamiclib -undefined suppress -flat_namespace'"
)
rvm_configure_env="${rvm_configure_env[*]}"
if ! [[ "${rvm_patch_names:-}" =~ *osx-arch-fix* ]]
then rvm_patch_names="osx-arch-fix ${rvm_patch_names:-}"
fi
fi
}
__rvm_setup_compile_environment_gcc47()
{
__rvm_compiler_is_gcc47 || return 0
[[ "${rvm_ruby_version}" =~ 1.8.* ]] || return 0
typeset gcc47flags
gcc47flags="-O2 -fno-tree-dce -fno-optimize-sibling-calls"
if [[ "${rvm_configure_env}" =~ "CCFLAGS=" ]]
then
rvm_configure_env="${rvm_configure_env/CCFLAGS='/CCFLAGS='${gcc47flags} }"
else
rvm_configure_env="CCFLAGS='${gcc47flags}' ${rvm_configure_env}"
fi
}
__rvm_check_for_compiler()
{
if __rvm_selected_compiler > /dev/null &&
! builtin command -v $(__rvm_selected_compiler) >/dev/null
then
rvm_error "You requested building with '$(__rvm_selected_compiler)' but it is not in your path."
return 1
fi
}
# Checks for bison, returns zero iff it is found
__rvm_check_for_bison()
{
true ${rvm_head_flag:=0}
if (( rvm_head_flag > 0 ))
then
if ! builtin command -v bison > /dev/null
then
rvm_error "\nbison is not available in your path. \nPlease ensure bison is installed before compiling from head.\n"
return 1
fi
fi
}
__rvm_mono_env()
{
DYLD_LIBRARY_PATH="${rvm_usr_path}/lib:$DYLD_LIBRARY_PATH"
C_INCLUDE_PATH="${rvm_usr_path}/include:$C_INCLUDE_PATH"
ACLOCAL_PATH="${rvm_usr_path}/share/aclocal"
ACLOCAL_FLAGS="-I $ACLOCAL_PATH"
PKG_CONFIG_PATH="${rvm_usr_path}/lib/pkgconfig:$PKG_CONFIG_PATH"
export
DYLD_LIBRARY_PATH C_INCLUDE_PATH ACLOCAL_PATH ACLOCAL_FLAGS PKG_CONFIG_PATH
__rvm_add_to_path prepend "${rvm_usr_path}/bin"
builtin hash -r
return 0
}
# Returns all mri compatible (partly) ruby for use
# with things like rbx etc which require a ruby be installed.
__rvm_mri_rubies()
{
typeset versions _ruby
versions="${1:-"1.8.|ree|1.9."}"
for _ruby in $( find $rvm_rubies_path/ -maxdepth 1 -mindepth 1 -type d -not -type l )
do
printf "%b" "${_ruby##*/}\n"
done | GREP_OPTIONS="" \grep -E "$versions"
}
# Returns the first mri compatible (partly) ruby for use
# with things like rbx etc which require a ruby be installed.
__rvm_mri_ruby()
{
typeset versions
versions="${1:-"1.8.|ree|1.9."}"
_mri_rubies=( $( __rvm_mri_rubies "$versions" ) )
_current_ruby=$(__rvm_env_string)
if [[ " ${_mri_rubies[*]} " =~ " ${_current_ruby} " ]]
then
printf "%b" "${_current_ruby}\n"
else
for _ruby in ${_mri_rubies[@]}
do
printf "%b" "${_ruby}\n"
done | sort | head -n 1
fi
return 0
}
__rvm_ensure_has_mri_ruby()
{
typeset versions
versions="${1:-"1.8.|ree|1.9."}"
if [[ -z "$(__rvm_mri_ruby $versions)" ]]
then
typeset compat_result
compat_result=0
if ! ( "$rvm_bin_path"/rvm install 1.8.7 )
then
rvm_error "
To proceed rvm requires a 1.8-compatible ruby is installed.
We attempted to install 1.8.7 automatically but it failed.
Please install it manually (or a compatible alternative) to proceed.
"
compat_result=1
fi
return $compat_result
fi
return 0
}
1.18.61.16. irbrc
#!/usr/bin/env bash
# Create the irbrc for the currently selected ruby installation.
__rvm_irbrc()
{
if [[ -d "$rvm_ruby_home" && ! -s "$rvm_ruby_irbrc" ]] ; then
\cp "$rvm_scripts_path/irbrc" "$rvm_ruby_irbrc"
fi
return $?
}
1.18.61.17. db
#!/usr/bin/env bash
# Query the rvm key-value database for a specific key
# Allow overrides from user specifications in $rvm_user_path/db
__rvm_db()
{
typeset value key variable
key=${1:-""}
key=${key#go} # Support for goruby - remove the go
variable=${2:-""}
if [[ -f "$rvm_user_path/db" ]] ; then
value="$("$rvm_scripts_path/db" "$rvm_user_path/db" "$key")"
fi
if [[ -z "$value" ]] ; then
value="$("$rvm_scripts_path/db" "$rvm_path/config/db" "$key")"
fi
if [[ -n "$value" ]] ; then
if [[ -z "$variable" ]] ; then
echo $value
else
eval "$variable='$value'"
fi
fi
return 0
}
1.18.61.18. environment
#!/usr/bin/env bash
__rvm_env_string()
{
typeset _path _string
_path="${GEM_HOME:-""}"
_string="${_path//*gems\//}"
_string="${_string//\/*/}"
printf "%b" "${_string:-system}"
}
__rvm_expand_ruby_string()
{
typeset string current_ruby
string="$1"
case "${string:-all}" in
all)
"$rvm_scripts_path/list" strings | \tr ' ' "\n"
;;
all-gemsets)
"$rvm_scripts_path/list" gemsets strings
;;
default-with-rvmrc|rvmrc)
"$rvm_scripts_path/tools" path-identifier "$PWD"
;;
all-rubies|rubies)
"$rvm_scripts_path/list" rubies strings
;;
current-ruby|gemsets)
current_ruby="$(__rvm_env_string)"
current_ruby="${current_ruby%@*}"
rvm_silence_logging=1 "$rvm_scripts_path/gemsets" list strings \
| \sed "s/ (default)//; s/^/$current_ruby${rvm_gemset_separator:-@}/ ; s/@default// ;"
;;
current)
__rvm_env_string
;;
aliases)
awk -F= '{print $string}' < "$rvm_path/config/alias"
;;
*)
__rvm_ruby_strings_exist $( echo "$string" | \tr "," "\n" | __rvm_strip )
;;
esac
}
__rvm_become()
{
# set rvm_rvmrc_flag=0 to not create .rvmrc in random places of code
typeset string rvm_rvmrc_flag
string="$1"
rvm_rvmrc_flag=0
[[ -n "$string" ]] && {
rvm_ruby_string="$string"
rvm_gemset_name=""
}
__rvm_use >/dev/null || return $?
rvm_ruby_string="${rvm_ruby_string}${rvm_gemset_name:+${rvm_gemset_separator:-'@'}}${rvm_gemset_name:-}"
return 0
}
__rvm_ensure_has_environment_files()
{
typeset environment_id file_name directory identifier variable value variables
environment_id="$(__rvm_env_string)"
file_name="${rvm_environments_path}/$environment_id"
if [[ ! -d "$rvm_environments_path" ]]
then
\mkdir -p "$rvm_environments_path"
fi
if [[ ! -s "$file_name" ]] || ! GREP_OPTIONS="" \grep 'rvm_env_string=' "$file_name" >/dev/null
then
rm -f "$file_name"
printf "%b" \
"export PATH ;
PATH=\"${rvm_ruby_gem_home}/bin:${rvm_ruby_global_gems_path}/bin:${rvm_ruby_home}/bin:${rvm_bin_path}:\$PATH\"\n" \
> "$file_name"
for variable in rvm_env_string rvm_path rvm_ruby_string rvm_gemset_name \
RUBY_VERSION GEM_HOME GEM_PATH MY_RUBY_HOME IRBRC MAGLEV_HOME RBXOPT
do
eval "export $variable"
eval "value=\${${variable}:-""}"
if [[ -n "$value" ]]
then
printf "export %b ; %b='%b'\n" "${variable}" "${variable}" "${value}" >> "$file_name"
else
printf "unset %b\n" "${variable}" >> "$file_name"
fi
done
fi
# Next, ensure we have default wrapper files. Also, prevent it from recursing.
if (( ${rvm_create_default_wrappers:=0} == 1 )) ||
[[ ! -f "$rvm_wrappers_path/$environment_id/ruby" ]]
then
# We need to generate wrappers for both the default gemset and the global gemset.
for identifier in "$environment_id" "${environment_id//@*/}@global"
do
rvm_create_default_wrappers=1
directory="$rvm_wrappers_path/$identifier"
if [[ ! -L "$directory" && ! -d "$directory" ]]; then
\mkdir -p "$directory"
"$rvm_scripts_path/wrapper" "$identifier" &> /dev/null
fi
done
rvm_create_default_wrappers=0
fi
return 0
}
# Loop over the currently installed rubies and refresh their binscripts.
__rvm_bin_scripts()
{
for rvm_ruby_binary in "$rvm_rubies_path"/*/bin/ruby
do
if [[ -x "$rvm_ruby_binary" ]]
then
rvm_ruby_string=$(
dirname "$rvm_ruby_binary" | xargs dirname | xargs basename
)
__rvm_select
__rvm_bin_script
fi
done
return 0
}
# Write the bin/ wrapper script for currently selected ruby.
# TODO: Adjust binscript to be able to handle all rubies,
#
not just the standard interpreteres.
__rvm_bin_script()
{
"$rvm_scripts_path/wrapper" "$rvm_ruby_string"
}
# Runs a command in a given env.
__rvm_run_with_env()
{
typeset name environment _command message log path
name="${1:-""}"
environment="${2:-""}"
_command="${3:-""}"
message="${4:-""}"
[[ -n "$environment" ]] || environment="$(__rvm_env_string)"
if [[ -n "$message" ]] ; then rvm_log "$message" ; fi
if (( ${rvm_debug_flag:=0} == 1 ))
then
rvm_debug "Executing: $_command in environment $environment"
fi
path="${rvm_log_path}/$rvm_ruby_string"
log="$path/$name.log"
if [[ ! -d "$path" ]]
then
command mkdir -p "$path"
fi
if [[ ! -f "$log" ]]
then
command touch "$log" # for zsh :(
fi
printf "%b"
"[$(date +'%Y-%m-%d %H:%M:%S')] $_command # under $environment\n" >> "${log}"
if (( ${rvm_niceness:=0} > 0 ))
then
_command="nice -n $rvm_niceness $_command"
fi
(
rvm_ruby_string="$environment"
__rvm_use
eval "$_command" >> "${log}" 2>&1
)
result=$?
if (( result > 0 ))
then
rvm_error "Error running '$command' under $env_name,\nplease read $log"
fi
return ${result:-0}
}
# Set shell options that RVM needs temporarily, these are reverted by __rvm_teardown.
# see the top of ./scripts/initialize for settings that are needed all the time.
# Setup must be always called after initialize, otherwise it does nothing ... except exporting.
__rvm_setup()
{
# NOTE: the same set is located below - maker kjfdngkjd
export rvm_head_flag rvm_ruby_selected_flag rvm_user_install_flag rvm_path_flag rvm_cron_flag rvm_static_flag
rvm_default_flag rvm_loaded_flag rvm_llvm_flag rvm_skip_autoreconf_flag rvm_18_flag rvm_19_flag rvm_force_autoconf_flag
rvm_autoconf_flags rvm_dump_environment_flag rvm_verbose_flag rvm_debug_flag rvm_trace_flag rvm_pretty_print_flag
rvm_create_flag rvm_remove_flag rvm_gemdir_flag rvm_reload_flag rvm_auto_reload_flag rvm_ignore_gemsets_flag
rvm_skip_gemsets_flag rvm_install_on_use_flag
export rvm_gems_cache_path rvm_gems_path rvm_man_path rvm_ruby_gem_path rvm_ruby_log_path rvm_ruby_load_path
rvm_gems_cache_path rvm_archives_path rvm_docs_path rvm_environments_path rvm_examples_path rvm_gems_path rvm_gemsets_path
rvm_help_path rvm_hooks_path rvm_lib_path rvm_log_path rvm_patches_path rvm_repos_path rvm_rubies_path rvm_scripts_path
rvm_src_path rvm_tmp_path rvm_user_path rvm_usr_path rvm_wrappers_path rvm_externals_path
export rvm_ruby_strings rvm_ruby_binary rvm_ruby_gem_home rvm_ruby_home rvm_ruby_interpreter rvm_ruby_irbrc
rvm_ruby_major_version rvm_ruby_minor_version rvm_ruby_package_name rvm_ruby_patch_level rvm_ruby_release_version
rvm_ruby_repo_url rvm_ruby_repo_branch rvm_ruby_revision rvm_ruby_tag rvm_ruby_sha rvm_ruby_version rvm_ruby_require
rvm_ruby_package_file rvm_ruby_name rvm_ruby_name rvm_ruby_args rvm_ruby_user_tag rvm_ruby_patch detected_rvm_ruby_name
export __rvm_env_loaded next_token rvm_error_message rvm_gemset_name rvm_parse_break rvm_token rvm_action rvm_export_args
rvm_gemset_separator rvm_expanding_aliases rvm_architectures rvm_patch_names rvm_tar_command rvm_tar_options rvm_ree_options
rvm_patch_original_pwd rvm_project_rvmrc rvm_archive_extension rvm_autoinstall_bundler_flag rvm_codesign_identity
rvm_expected_gemset_name rvm_without_gems
# Setup only on first load.
if (( __rvm_env_loaded != 1 ))
then return 0
fi
if [[ -n "${BASH_VERSION:-}" ]] && ! __function_on_stack cd pushd popd
then
trap 'status=$? ; __rvm_teardown_final ; set +x ; return $status' 0 1 2 3 15
fi
if [[ -n "${ZSH_VERSION:-}" ]]
then
export rvm_zsh_clobber rvm_zsh_nomatch
# Set clobber for zsh users, for compatibility with bash's append operator ( >> file ) behavior
if setopt | GREP_OPTIONS="" \grep -s '^noclobber$' >/dev/null 2>&1
then rvm_zsh_clobber=0
else rvm_zsh_clobber=1
fi
setopt clobber
# Set no_nomatch so globs that don't match any files don't print out a warning
if setopt | GREP_OPTIONS="" \grep -s '^nonomatch$' >/dev/null 2>&1
then rvm_zsh_nomatch=0
else rvm_zsh_nomatch=1
fi
setopt no_nomatch
fi
}
__rvm_teardown()
{
if builtin command -v __rvm_cleanup_tmp >/dev/null 2>&1
then
__rvm_cleanup_tmp
fi
export __rvm_env_loaded
# if __rvm_env_loaded is not set - detect it via rvm_tmp_path
: __rvm_env_loaded:${__rvm_env_loaded:=${rvm_tmp_path:+1}}:
: __rvm_env_loaded:${__rvm_env_loaded:=0}:
# decrease load count counter
: __rvm_env_loaded:$(( __rvm_env_loaded-=1 )):
#skip teardown when already done or when not yet finished
if [[ -z "${rvm_tmp_path:-}" ]] || (( __rvm_env_loaded > 0 ))
then
return 0
fi
if [[ -n "${BASH_VERSION:-}" ]]
then
trap - 0 1 2 3 15 # Clear all traps, we do not want to go into an loop.
fi
if [[ -n "${ZSH_VERSION:-""}" ]]
then
# If rvm_zsh_clobber is 0 then "setopt" contained "noclobber" before rvm performed "setopt clobber".
(( rvm_zsh_clobber == 0 )) && setopt noclobber
# If rvm_zsh_nomatch is 0 then "setopt" contained "nonomatch" before rvm performed "setopt nonomatch".
(( rvm_zsh_nomatch == 0 )) || setopt nomatch
unset rvm_zsh_clobber rvm_zsh_nomatch
fi
if [[ -n "${rvm_stored_umask:-}" ]]
then
umask ${rvm_stored_umask}
fi
# TODO: create a cleanse array for this instead of the current hard coded
# method. The array will be appended to whenever variables are used that
# should be cleaned up when the current RVM commadn is done.
# Cleanse and purge! (may be some redundancy here)
#
# NOTE: Removing rvm_bin_path here causes system wide installations to generate
# a corrupt PATH, breaking the RVM installation.
#
# NOTE: the same set is located above - maker kjfdngkjd
unset rvm_head_flag rvm_ruby_selected_flag rvm_user_install_flag rvm_path_flag rvm_cron_flag rvm_static_flag
rvm_default_flag rvm_loaded_flag rvm_llvm_flag rvm_skip_autoreconf_flag rvm_18_flag rvm_19_flag rvm_force_autoconf_flag
rvm_autoconf_flags rvm_dump_environment_flag rvm_verbose_flag rvm_debug_flag rvm_trace_flag rvm_pretty_print_flag
rvm_create_flag rvm_remove_flag rvm_gemdir_flag rvm_reload_flag rvm_auto_reload_flag rvm_ignore_gemsets_flag
rvm_skip_gemsets_flag rvm_install_on_use_flag
unset rvm_gems_cache_path rvm_gems_path rvm_man_path rvm_ruby_gem_path rvm_ruby_log_path rvm_ruby_load_path
rvm_gems_cache_path rvm_archives_path rvm_docs_path rvm_environments_path rvm_examples_path rvm_gems_path rvm_gemsets_path
rvm_help_path rvm_hooks_path rvm_lib_path rvm_log_path rvm_patches_path rvm_repos_path rvm_rubies_path rvm_scripts_path
rvm_src_path rvm_tmp_path rvm_user_path rvm_usr_path rvm_wrappers_path rvm_externals_path
unset rvm_ruby_strings rvm_ruby_binary rvm_ruby_gem_home rvm_ruby_home rvm_ruby_interpreter rvm_ruby_irbrc
rvm_ruby_major_version rvm_ruby_minor_version rvm_ruby_package_name rvm_ruby_patch_level rvm_ruby_release_version
rvm_ruby_repo_url rvm_ruby_repo_branch rvm_ruby_revision rvm_ruby_tag rvm_ruby_sha rvm_ruby_version rvm_ruby_require
rvm_ruby_package_file rvm_ruby_name rvm_ruby_name rvm_ruby_args rvm_ruby_user_tag rvm_ruby_patch detected_rvm_ruby_name
unset __rvm_env_loaded next_token rvm_error_message rvm_gemset_name rvm_parse_break rvm_token rvm_action rvm_export_args
rvm_gemset_separator rvm_expanding_aliases rvm_architectures rvm_patch_names rvm_tar_command rvm_tar_options rvm_ree_options
rvm_patch_original_pwd rvm_project_rvmrc rvm_archive_extension rvm_autoinstall_bundler_flag rvm_codesign_identity
rvm_expected_gemset_name rvm_without_gems
if builtin command -v __rvm_cleanup_download >/dev/null 2>&1
then
__rvm_cleanup_download
fi
return 0
}
__rvm_teardown_final()
{
__rvm_env_loaded=1
unset __rvm_project_rvmrc_lock
__rvm_teardown
}
__rvm_do_with_env_before()
{
if [[ -n "${rvm_scripts_path:-}" || -n "${rvm_path:-}" ]]
then
# Load env - setup all required variables, __rvm_teardown is called on the end
source "${rvm_scripts_path:-"$rvm_path/scripts"}/initialize"
__rvm_setup
fi
}
__rvm_do_with_env_after()
{
__rvm_teardown
}
__rvm_do_with_env()
{
typeset result
__rvm_do_with_env_before
"$@"
result=$?
__rvm_do_with_env_after
return ${result:-0}
}
__rvm_conditionally_do_with_env()
{
if (( __rvm_env_loaded > 0 ))
then
"$@"
else
__rvm_do_with_env "$@"
fi
}
__rvm_ensure_is_a_function()
{
if [[ ${rvm_reload_flag:=0} == 1 ]] || ! is_a_function rvm
then
for script in version selector selector_gemsets cd cli override_gem
do
if [[ -f "$rvm_scripts_path/$script" ]]
then
source "$rvm_scripts_path/$script"
else
printf "%b" \
"WARNING:
Could not source '$rvm_scripts_path/$script' as file does not exist.
RVM will likely not work as expected.\n"
fi
done
fi
}
1.18.61.19. cleanup
#!/usr/bin/env bash
#
# rm -rf with *some* safeguards in place.
#
__rvm_rm_rf()
{
typeset result target
result=1
target="${1%%+(/|.)}"
#NOTE: RVM Requires extended globbing shell feature turned on.
if [[ -n "${ZSH_VERSION:-}" ]]
then
setopt extendedglob
else
if [[ -n "${BASH_VERSION:-}" ]]
then
shopt -s extglob # Extended globs
else
printf "%b" "What the heck kind of shell are you running here???\n"
fi
fi
case "${target}" in
(*(/|.)@(|/Applications|/Developer|/Guides|/Information|/Library|/Network|/System|/User|/Users|/Volumes|/backups|/bdsm|/bin|
/boot|/cores|/data|/dev|/etc|/home|/lib|/lib64|/mach_kernel|/media|/misc|/mnt|/net|/opt|/private|/proc|/root|/sbin|/selinux|
/srv|/sys|/tmp|/usr|/var))
false
;;
(*)
if [[ -n "${target}" ]]
then
if [[ -d "${target}" ]]
then # Directory
\rm -rf "${target}"
result=0
elif [[ -f "${target}" || -L "${target}" ]]
then # File / Symbolic Link
\rm -f "${target}"
result=0
else
result=0 # already gone!?
fi
fi
;;
esac
return $result
}
__rvm_reboot()
{
rvm_warn "Do you wish to reboot rvm?\n('yes', or 'no')> "
typeset response
response="no"
read response
if [[ "yes" == "$response" ]]
then
builtin cd $rvm_path
command -v __rvm_reset >> /dev/null 2>&1 || \
source "$rvm_scripts_path/functions/reset"
__rvm_reset
mv "$rvm_archives_path" "$HOME/.archives"
if [[ "/" == "$rvm_path" ]]
then
rvm_error "remove '/' ?!... NO!"
else
if [[ -d "$rvm_path" ]]
then __rvm_rm_rf "$rvm_path"
fi
fi
gem install rvm $rvm_gem_options
"$rvm_scripts_path/get" latest
source "$rvm_scripts_path/rvm"
else
rvm_log "Carry on then..."
fi
return 0
}
# Cleans up temp folders for a given prefix ($1),
# or the current process id.
__rvm_cleanup_tmp()
{
if [[ -d "${rvm_tmp_path}/" ]]
then
case "${rvm_tmp_path%\/}" in
*tmp)
__rvm_rm_rf "${rvm_tmp_path}/${1:-$$}*"
;;
esac
fi
return 0
}
1.18.61.20. installer
#!/usr/bin/env bash
#Handle Solaris Hosts
if [[ "$(uname -s)" == "SunOS" ]]
then
export PATH
PATH="/usr/gnu/bin:$PATH"
fi
if [[ -n "${rvm_user_path_prefix:-}" ]]
then
PATH="${rvm_user_path_prefix}:$PATH"
fi
install_setup()
{
set -o errtrace
export HOME="${HOME%%+(\/)}" # Remove trailing slashes if they exist on HOME
case "$MACHTYPE" in
*aix*) name_opt=-name ;;
*)
name_opt=-iname ;;
esac
if (( ${rvm_ignore_rvmrc:=0} == 0 ))
then
: rvm_stored_umask:${rvm_stored_umask:=$(umask)}
rvm_rvmrc_files=("/etc/rvmrc" "$HOME/.rvmrc")
if [[ -n "${rvm_prefix:-}" ]] && ! [[ "$HOME/.rvmrc" -ef "${rvm_prefix}/.rvmrc" ]]
then rvm_rvmrc_files+=( "${rvm_prefix}/.rvmrc" )
fi
for file in "${rvm_rvmrc_files[@]}"
do
if [[ -s "$file" ]]
then
. $file
fi
done
unset rvm_rvmrc_files
fi
export PS4 PATH
PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
if [[ -n "${rvm_user_path_prefix:-}" ]]
then
PATH="${rvm_user_path_prefix}:$PATH"
fi
# TODO: Figure out a much better name for 'rvm_user_install_flag'
# mpapis: self contained was a quite good name
if (( UID == 0 )) ||
[[ -n "${rvm_prefix:-}" && "${rvm_prefix:-}" != "${HOME}" ]]
then
true "${rvm_user_install_flag:=0}"
else
true "${rvm_user_install_flag:=1}"
fi
export rvm_user_install_flag
unset rvm_auto_flag
}
install_usage()
{
printf "%b" "
Usage:
${0} [options]
options:
--auto
: Automatically update shell profile files.
--path
: Installation directory (rvm_path).
--help
: Display help/usage (this) message
--version : display rvm package version
"
}
display_thank_you()
{
printf "%b" "
# ${name:-"${USER:-$(id | sed -e 's/^[^(]*(//' -e 's/).*$//')}"},
\${LINENO} > "
#
#
Thank you for using RVM!
#
I sincerely hope that RVM helps to make your life easier and more enjoyable!!!
#
# ~Wayne
"
}
determine_install_path()
{
export HOME="${HOME%%+(\/)}" # Remove trailing slashes if they exist on HOME
if [[ -z "${rvm_path:-}" ]]
then
if (( UID == 0 ))
then
rvm_path="/usr/local/rvm"
else
rvm_path="${HOME}/.rvm"
fi
fi
export rvm_path
}
determine_install_or_upgrade()
{
export upgrade_flag
if [[ -d "$rvm_path" && -s "${rvm_path}/scripts/rvm" ]]
then upgrade_flag=1
else upgrade_flag=0
fi
}
print_install_header()
{
if [[ ${upgrade_flag:-0} -eq 1 ]]
then
printf "%b" "\nUpgrading the RVM installation in $rvm_path/\n"
else
printf "%b" "\nInstalling RVM to $rvm_path/\n"
fi
}
configure_installation()
{
typeset save_rvm_without_gems
install_source_path="$(dirname "$0" | sed 's#\/scripts$##')"
if [[ -d "$install_source_path/scripts" \
&& -s "$install_source_path/scripts/functions/utility" ]]
then
builtin cd "$install_source_path"
fi
# Save scripts path
scripts_path=${rvm_scripts_path:-""}
rvm_scripts_path="${PWD%%+(\/)}/scripts"
save_rvm_without_gems="${rvm_without_gems:-}"
# Load scripts.
source "$PWD/scripts/initialize"
source "$PWD/scripts/functions/init"
source "$PWD/scripts/version"
__rvm_initialize
# Restore Scripts Path
rvm_scripts_path=${scripts_path:-"$rvm_path/scripts"}
rvm_without_gems="${save_rvm_without_gems:-${rvm_without_gems}}"
item="* "
question="\n<?>"
cwd="${PWD%%+(\/)}"
true "${source_path:=$cwd}"
return 0
}
create_install_paths()
{
install_paths=(
archives src log bin gems man rubies config
user tmp gems environments wrappers
)
for install_path in "${install_paths[@]}"
do
if [[ ! -d "$rvm_path/$install_path" ]]
then
mkdir -p "$rvm_path/$install_path"
fi
done
if [[ "$rvm_bin_path" != "" ]]
then
if [[ ! -d "$rvm_bin_path" ]]
then
mkdir -p "$rvm_bin_path"
fi
fi
return 0
}
cleanse_old_entities()
{
#
# Remove old files that no longer exist.
#
for script in utility array ; do
if [[ -f "$rvm_path/scripts/${script}" ]]
then
rm -f "$rvm_path/scripts/${script}"
fi
done
return 0
}
install_rvm_files()
{
files=(README LICENCE VERSION)
for file in "${files[@]}"
do
cp -f "$source_path/${file}" "$rvm_path/${file}"
done
directories=(config contrib scripts examples lib help patches)
for directory in ${directories[@]}
do
for entry in $(find $directory 2>/dev/null)
do
if [[ -f "$source_path/$entry" ]]
then
# Target is supposed to be a file, remove if it is a directory.
if [[ -d "$rvm_path/$entry" ]]
then
__rvm_rm_rf "$rvm_path/$entry"
fi
cp -f "$source_path/$entry" "$rvm_path/$entry"
elif [[ -d "$source_path/$entry" ]]
then
# Target is supposed to be a directory, remove if it is a file.
if [[ -f "$rvm_path/$entry" ]]
then
rm -f "$rvm_path/$entry"
fi
if [[ ! -d "$rvm_path/$entry" ]]
then
mkdir -p "$rvm_path/$entry"
fi
fi
done
done
return 0
}
install_rvm_hooks()
{
typeset hook_x_flag entry
for entry in $(find hooks 2>/dev/null)
do
if [[ -f "$source_path/$entry" ]]
then
# Target is supposed to be a file, remove if it is a directory.
if [[ -d "$rvm_path/$entry" ]]
then
__rvm_rm_rf "$rvm_path/$entry"
fi
# Source is first level hook (after_use) and target is custom user hook, preserve it
if echo "$entry" | GREP_OPTIONS="" \grep -E '^hooks/[[:alpha:]]+_[[:alpha:]]+$' >/dev/null &&
[[ -f "$rvm_path/$entry" ]] &&
! GREP_OPTIONS="" \grep "$(basename ${entry})_\*" "$rvm_path/$entry" >/dev/null
then
mv -f "$rvm_path/$entry" "$rvm_path/${entry}_custom"
fi
if [[ -x "$rvm_path/$entry" ]]
then hook_x_flag=$?
else hook_x_flag=$?
fi
cp -f "$source_path/$entry" "$rvm_path/$entry"
if (( hook_x_flag == 0 ))
then
[[ -x "$rvm_path/$entry" ]] || chmod +x "$rvm_path/$entry"
fi
elif [[ -d "$source_path/$entry" ]]
then
# Target is supposed to be a directory, remove if it is a file.
if [[ -f "$rvm_path/$entry" ]]
then
rm -f "$rvm_path/$entry"
fi
if [[ ! -d "$rvm_path/$entry" ]]
then
mkdir -p "$rvm_path/$entry"
fi
fi
done
#fix broken copy of after_use to after_use_custom
if [[ -f "$rvm_path/hooks/after_use_custom" ]] &&
GREP_OPTIONS="" \grep "after_use_\*" "$rvm_path/hooks/after_use_custom" >/dev/null
then
rm -f "$rvm_path/hooks/after_use_custom"
fi
return 0
}
setup_configuration_files()
{
pushd "$rvm_path" >/dev/null
if [[ -f config/user ]]
then
mv config/user user/db
fi
if [[ -f config/installs ]]
then
mv config/installs user/installs
fi
if [[ ! -s user/db ]]
then
echo '# User settings, overrides db settings and persists across installs.' \
>> user/db
fi
if [[ -s config/rvmrcs ]]
then
mv config/rvmrcs user/rvmrcs
else
if [[ ! -f user/rvmrcs ]]
then
touch user/rvmrcs
fi
fi
if [[ ! -f user/md5 ]]
then
touch user/md5
fi
# Prune old (keyed-by-hash) trust entries
GREP_OPTIONS="" \grep '^_' user/rvmrcs > user/rvmrcs.new || true
mv user/rvmrcs.new user/rvmrcs
popd >/dev/null
}
ensure_scripts_are_executable()
{
scripts=(monitor match log install db fetch log set package)
for script_name in "${scripts[@]}"
do
if [[ -s "$rvm_scripts_path/$script_name" && ! -x "$rvm_scripts_path/$script_name" ]]
then
chmod +x "$rvm_scripts_path/$script_name"
fi
done
return 0
}
install_binscripts()
{
typeset -a files
typeset system_bin
files=(rvm-prompt rvm-installer rvm rvmsudo rvm-shell rvm-smile rvm-exec rvm-auto-ruby)
[[ -d "${rvm_bin_path}" ]] || mkdir -p "${rvm_bin_path}"
for file in "${files[@]}"
do
# Ensure binscripts are always available in rvm_path/bin first.
[[ -f "${rvm_bin_path}/${file}" ]] && rm -f "${rvm_bin_path}/${file}"
cp -f "${source_path}/binscripts/${file}" "${rvm_bin_path}/${file}"
[[ -x "${rvm_bin_path}/${file}" ]] || chmod +x "${rvm_bin_path}/${file}"
# try to clean old installer files left in usual places added to PATH
for system_bin in ~/bin /usr/local/bin
do
if [[ "${system_bin}" != "${rvm_bin_path}" && -x "${system_bin}/${file}" ]]
then
rm -f "${system_bin}/${file}" 2>/dev/null ||
printf "!!! could not remove ${system_bin}/${file}, remove it manually with:
!!! > sudo rm -f ${system_bin}/${file}
"
fi
done
done
# optional binscripts
for file in rake bundle
do
[[ -f "${rvm_bin_path}/${file}" ]] ||
cp -f "${source_path}/binscripts/${file}" "${rvm_bin_path}/${file}"
done
return 0
}
install_gemsets()
{
typeset gemset_files
if [[ ${rvm_keep_gemset_defaults_flag:-0} == 0 && -d "$rvm_path/gemsets" ]]
then
rm -rf "$rvm_path/gemsets"
fi
if [[ -d gemsets/ ]]
then
[[ -d "$rvm_path/gemsets" ]] || mkdir -p "$rvm_path/gemsets"
gemset_files=($(
find "${PWD%%+(\/)}/gemsets" "${name_opt}" '*.gems' | sed 's/^\.\///'
))
for gemset_file in "${gemset_files[@]}"
do
cwd="${PWD//\//\\/}\/gemsets\/"
destination="$rvm_path/gemsets/${gemset_file/$cwd}"
if [[ ! -s "$destination" ]]
then
destination_path="${destination%/*}"
[[ -d "$destination_path" ]] || mkdir -p "$destination_path"
if
[[ -n "${rvm_without_gems:-}" ]]
then
sed -E '/^('"${rvm_without_gems// /|}"')/ d' < "$gemset_file" > "$destination"
else
cp "$gemset_file" "$destination"
fi
fi
done
fi
if [[ -n "${rvm_without_gems:-}" ]]
then
if GREP_OPTIONS="" \grep "rvm_without_gems=" ~/.rvmrc >/dev/null
then
sed -i 's/^rvm_without_gems=.*$/rvm_without_gems="'"${rvm_without_gems}"'"/' ~/.rvmrc
else
echo "rvm_without_gems=\"${rvm_without_gems}\"" >> ~/.rvmrc
fi
fi
}
update_gemsets_install_rvm()
{
typeset paths path installed found missing
typeset -a missing
if [[ ${rvm_keep_gemset_defaults_flag:-0} == 0 ]] &&
! [[ " ${rvm_without_gems:-} " =~ " rvm " ]]
then
# rvm /gems
paths=($(
find "$rvm_path/gems" -maxdepth 1 "${name_opt}" '*@global' | sed 's/^\.\///'
))
for path in "${paths[@]}"
do
# skip unless this ruby is installed
installed="${path%@global}"
installed="${installed/\/gems\//\/rubies\//}/bin/ruby"
installed=${installed//\\/}
[[ -x "$installed" ]] || continue
# rvm /gems @global /gems
found=($(
find "${path%%+(\/)}/gems" -maxdepth 1 "${name_opt}" 'rvm-*' | sed 's/^\.\///'
))
(( ${#found[@]} > 0 )) || missing+=( "$path" )
done
if (( ${#missing[@]} > 0 ))
then
printf "
Installing rvm gem in ${#missing[@]} gemsets "
for path in "${missing[@]}"
do
rvm "${path##*/}" do gem install rvm | awk '{printf "."}'
done
printf "\n"
fi
fi
}
install_patchsets()
{
if [[ ${rvm_keep_patchsets_flag:-0} == 0 && -d "$rvm_path/patchsets" ]]
then
rm -rf "$rvm_path/patchsets"
fi
if [[ -d patchsets/ ]]
then
[[ -d "$rvm_path/patchsets" ]] || mkdir -p "$rvm_path/patchsets"
patchsets=($(
builtin cd patchsets
find \. -type f "${name_opt}" '*' | sed 's/^\.\///'
))
for patchset_file in "${patchsets[@]}"
do
destination="$rvm_path/patchsets/$patchset_file"
if [[ ! -s "$destination" || "${patchset_file##*/}" == "default" ]]
then
destination_path="${destination%/*}"
[[ -d "$destination_path" ]] || mkdir -p "$destination_path"
[[ -f "$destination"
]] && rm -f "$destination"
cp "patchsets/$patchset_file" "$destination"
fi
done
fi
}
cleanse_old_environments()
{
if [[ -d "$rvm_path/environments" ]]
then
# Remove BUNDLE_PATH from environment files
environments=($(
find "$rvm_path/environments/" -maxdepth 1 -mindepth 1 -type f
))
if (( ${#environments[@]} > 0 ))
then
for file in "${environments[@]}"
do
if GREP_OPTIONS="" \grep 'BUNDLE_PATH' "$file" > /dev/null 2>&1
then
GREP_OPTIONS="" \grep -v 'BUNDLE_PATH' "$file" > "$file.new"
mv "$file.new" "$file"
fi
done
fi
fi
}
migrate_old_gemsets()
{
for gemset in "$rvm_path"/gems/*\%*
do
new_path=${gemset/\%/${rvm_gemset_separator:-"@"}}
if [[ -d "$gemset" ]] && [[ ! -d "$new_path" ]]
then
printf "%b" "\n
Renaming $(basename "$gemset") to $(basename "$new_path") for new gemset separator."
mv "$gemset" "$new_path"
fi
done
for gemset in "$rvm_path"/gems/*\+*
do
new_path=${gemset/\+/${rvm_gemset_separator:-"@"}}
if [[ -d "$gemset" && ! -d "$new_path" ]]
then
printf "%b" "\n
Renaming $(basename "$gemset") to $(basename "$new_path") for new gemset separator."
mv $gemset $new_path
fi
done
for gemset in "$rvm_path"/gems/*\@
do
new_path=$(echo $gemset | sed -e 's#\@$##')
if [[ -d "$gemset" && ! -d "$new_path" ]]
then
printf "%b" "\n
Fixing: $(basename "$gemset") to $(basename "$new_path") for new gemset separator."
mv "$gemset" "$new_path"
fi
done
}
migrate_defaults()
{
# Move from legacy defaults to the new, alias based system.
if [[ -s "$rvm_path/config/default" ]]
then
original_version="$(basename "$(GREP_OPTIONS="" \grep GEM_HOME "$rvm_path/config/default" \
| awk -F"'" '{print $2}' | sed "s#\%#${rvm_gemset_separator:-"@"}#")")"
if [[ -n "$original_version" ]]
then
"$rvm_scripts_path/alias" create default "$original_version" &> /dev/null
fi
unset original_version
__rvm_rm_rf "$rvm_path/config/default"
fi
}
correct_binary_permissions()
{
typeset -a files
mkdir -p "${rvm_bin_path}"
files=(rvm rvmsudo rvm-shell rvm-auto-ruby)
for file in "${files[@]}"
do
if [[ -s "${rvm_bin_path}/${file}" && ! -x "${rvm_bin_path}/${file}" ]]
then
chmod +x "${rvm_bin_path}/${file}"
fi
done
files=(
manage alias cleanup current db disk-usage docs env
fetch gemsets get hash help hook info install list maglev match md5 migrate
monitor notes override_gem package patchsets repair rtfm rubygems rvm selector
selector_gemsets set snapshot tools upgrade wrapper
)
for file in "${files[@]}"
do
if [[ -s "${rvm_scripts_path}/${file}" && ! -x "${rvm_scripts_path}/${file}" ]]
then
chmod +x "${rvm_scripts_path}/${file}"
fi
done
}
install_man_pages()
{
files=($(
builtin cd "$install_source_path/man"
find . -maxdepth 2 -mindepth 1 -type f -print
))
for file in "${files[@]//.\/}"
do
if [[ ! -d $rvm_man_path/${file%\/*} ]]
then
mkdir -p $rvm_man_path/${file%\/*}
fi
cp -Rf "$install_source_path/man/$file" "$rvm_man_path/$file" || \
printf "%b" "
Please run the installer using rvmsudo to fix file permissions
"
chown :$rvm_group_name "$rvm_man_path/$file"
done
}
cleanup_tmp_files()
{
files=($(
find "$rvm_path/" -mindepth 1 -maxdepth 2 "${name_opt}" '*.swp' -type f
))
if (( ${#files[@]} > 0 ))
then
printf "%b" "\n
Cleanup any .swp files."
for file in "${files[@]}"
do
if [[ -f "$file" ]]
then
rm -f "$file"
fi
done
fi
}
display_notes()
{
true ${upgrade_flag:=0}
typeset itype profile_file
if (( upgrade_flag == 0 ))
then itype=Installation
else itype=Upgrade
fi
if builtin command -v git > /dev/null 2>&1
then name="$(git config user.name 2>/dev/null || echo ${SUDO_USER:-${USERNAME}} )"
fi
[[ -x ./scripts/notes ]] || chmod +x ./scripts/notes
if (( upgrade_flag == 0 ))
then
./scripts/notes initial
else
./scripts/notes upgrade
fi
if (( upgrade_flag == 0 ))
then
profile_file="${user_profile_file:-${etc_profile_file:-$rvm_path/scripts/rvm}}"
printf "%b" "$itype of RVM in $rvm_path/ is almost complete:
"
if (( ${rvm_user_install_flag:=0} == 0 ))
then
printf "%b" "
* First you need to add all users that will be using rvm to '${rvm_group_name}' group,
and logout - login again, anyone using rvm will be operating with \`umask g+w\`.
"
fi
printf "%b" "
* To start using RVM you need to run \`source ${profile_file}\`
in all your open shell windows, in rare cases you need to reopen all shell windows.
"
else
printf "%b" "$itype of RVM in $rvm_path/ is complete.
"
fi
}
#
# root install functions.
#
setup_rvm_path_permissions()
{
chown -R root:"$rvm_group_name" "$rvm_path"
chmod -R g+w "$rvm_path"
if [[ -d "$rvm_path" ]]
then
find "$rvm_path" -type d -print0 | xargs -n1 -0 chmod g+s
fi
return 0
}
setup_rvm_group()
{
typeset __group_params
__group_params=""
if [[ -n "${rvm_group_id}" ]]
then __group_params="${__group_params} -g ${rvm_group_id}"
fi
if [[ -n "$ZSH_VERSION" ]]
then __group_params=( ${=__group_params} )
else __group_params=( ${__group_params} )
fi
if GREP_OPTIONS="" \grep "$rvm_group_name" /etc/group >/dev/null 2>&1
then
echo "
RVM system user group '$rvm_group_name' exists, proceeding with installation."
else
echo "
Creating RVM system user group '$rvm_group_name'"
case "$(uname)" in
"OpenBSD")
groupadd ${__group_params[@]} "$rvm_group_name"
;;
"FreeBSD")
pw groupadd ${__group_params[@]} "$rvm_group_name" -q
;;
"Linux")
if [[ -f "/etc/SuSE-release" ]]
then
groupadd ${__group_params[@]} "$rvm_group_name"
else
groupadd -f ${__group_params[@]} "$rvm_group_name"
fi
;;
"Darwin")
if ! dscl . -read "/Groups/$rvm_group_name" 1>/dev/null 2>&1
then
if [[ -n "${rvm_group_id}" ]]
then
__group_params="${rvm_group_id}"
else
__group_params="501" #only gids > 500 show up in user preferences
#Find an open gid
while true
do
name=$(dscl . search /groups PrimaryGroupID ${__group_params} | cut -f1 -s)
if [[ -z "$name" ]]
then break
fi
__group_params=$(( __group_params + 1 ))
done
fi
# Create the group, isn't OSX "fun"?! :)
# Thanks for the assist frogor of ##osx-server on freenode! Appreciate the assist!
dscl . -create "/Groups/$rvm_group_name" gid "${__group_params}"
fi
;;
"SunOS")
groupadd ${__group_params[@]} "$rvm_group_name"
;;
esac
fi
return 0
}
system_check()
{
typeset os
os=$(uname)
case "$os" in
OpenBSD|Linux|FreeBSD|Darwin|SunOS)
return 0 # Accounted for, continue.
;;
*)
printf "%b" "Installing RVM as root is currently only supported on the following known OS's (uname):\n
FreeBSD, OpenBSD, Darwin and SunOS\nWhereas your OS is reported as '$os'" >&2
return 1
;;
esac
}
setup_etc_profile()
{
export etc_profile_file
if (( ${rvm_etc_profile_flag:-1} == 0 ))
then return 0 ; fi # opt-out
typeset executable add_to_profile_flag zshrc_file
executable=0
add_to_profile_flag=0
etc_profile_file="/etc/profile.d/rvm.sh"
if [[ -d /etc/profile.d ]]
then
executable=1
else
mkdir -p /etc/profile.d
add_to_profile_flag=1
executable=0
fi
if ! [[ -s "${etc_profile_file}" ]] || (( ${rvm_auto_flag:-0} == 1 ))
then
printf "%b" "#
# RVM profile
#
# /etc/profile.d/rvm.sh # sh extension required for loading.
#
if [ -n \"\${BASH_VERSION:-}\" -o -n \"\${ZSH_VERSION:-}\" ] &&
test \"\`ps -p \$\$ -o comm=\`\" != dash &&
test \"\`ps -p \$\$ -o comm=\`\" != sh
then
: rvm_stored_umask:\${rvm_stored_umask:=\$(umask)}
# Load user rvmrc configurations, if exist
for file in \"/etc/rvmrc\" \"\$HOME/.rvmrc\" ; do
[[ -s \"\$file\" ]] && source \$file
done
if [[ -n \"\${rvm_prefix:-}\" ]] && ! [[ \"\$HOME/.rvmrc\" -ef \"\${rvm_prefix}/.rvmrc\" ]] && [[ -s
\"\${rvm_prefix}/.rvmrc\" ]]
then source \"\${rvm_prefix}/.rvmrc\"
fi
# Load RVM if it is installed, try user then root install.
if [[ -s \"\$rvm_path/scripts/rvm\" ]] ; then
source \"\$rvm_path/scripts/rvm\"
elif [[ -s \"\$HOME/.rvm/scripts/rvm\" ]] ; then
Linux,
true \${rvm_path:=\"\$HOME/.rvm\"}
source \"\$HOME/.rvm/scripts/rvm\"
elif [[ -s \"/usr/local/rvm/scripts/rvm\" ]] ; then
true \${rvm_path:=\"/usr/local/rvm\"}
source \"/usr/local/rvm/scripts/rvm\"
fi
#
# Opt-in for custom prompt through by setting:
#
#
rvm_ps1=1
#
# in either /etc/rvmrc or \$HOME/.rvmrc
#
if [[ \${rvm_ps1:-0} -eq 1 ]] ; then
# Source RVM ps1 functions for a great prompt.
if [[ -s \"\$rvm_path/contrib/ps1_functions\" ]] ; then
source \"\$rvm_path/contrib/ps1_functions\"
elif [[ -s \"/usr/local/rvm/contrib/ps1_functions\" ]] ; then
source \"/usr/local/rvm/contrib/ps1_functions\"
fi
if command -v ps1_set >/dev/null 2>&1 ; then
ps1_set
fi
fi
# Add \$rvm_bin_path to \$PATH if necessary
if [[ \"\${rvm_bin_path}\" != \"\${rvm_path}/bin\" ]] ; then
regex=\"^([^:]*:)*\${rvm_bin_path}(:[^:]*)*\$\"
if [[ ! \"\${PATH}\" =~ \$regex ]] ; then
__rvm_add_to_path prepend \"\${rvm_bin_path}\"
fi
fi
fi
" > "${etc_profile_file}"
if (( executable )) && [[ ! -x "${etc_profile_file}" ]]
then
chmod +x "${etc_profile_file}"
fi
if (( add_to_profile_flag )) &&
! GREP_OPTIONS="" \grep "source ${etc_profile_file}" /etc/profile >/dev/null 2>&1
then
printf "%b" "\nsource ${etc_profile_file}\n" >> /etc/profile
fi
for zshrc_file in $(
find /etc/ -name zprofile -type f 2>/dev/null ;
find /etc/ -name zlogin
-type f 2>/dev/null ;
true ) /etc/zprofile
do
if
[[ ! -f "${zshrc_file}" ]]
then
printf "%b" "\nsource ${etc_profile_file}\n" > $zshrc_file
elif
! GREP_OPTIONS="" \grep "source /etc/bash"
"${zshrc_file}" &&
! GREP_OPTIONS="" \grep "source /etc/profile" "${zshrc_file}"
then
printf "%b" "\nsource ${etc_profile_file}\n" >> $zshrc_file
fi
break # process only first file found
done
fi
return 0
}
setup_rvmrc()
{
if (( UID == 0 ))
then
rvmrc_file="/etc/rvmrc"
if ! GREP_OPTIONS="" \grep 'umask g+w' $rvmrc_file >/dev/null 2>&1
then
echo 'umask g+w' >> $rvmrc_file
fi
if [[ -s $rvmrc_file ]]
then
chown $USER:${rvm_group_name:-$USER} $rvmrc_file
fi
else
rvmrc_file="$HOME/.rvmrc"
fi
return 0
}
setup_user_profile()
{
(( UID > 0 )) || return 0
export user_profile_file
export -a user_login_files user_rc_files
typeset -a search_list target_rc target_login found_rc found_login
typeset etc_profile_file profile_file
etc_profile_file="/etc/profile.d/rvm.sh"
search_list=(
~/.profile
~/.bashrc ~/.bash_profile ~/.bash_login
~/.zshenv ~/.zprofile ~/.zshrc ~/.zlogin
)
target_rc=( ~/.bashrc )
[[ -f ~/.zshenv ]] &&
target_rc+=( ~/.zshenv ) || target_rc+=( ~/.zshrc )
[[ -f ~/.bash_profile ]] &&
target_login+=( ~/.bash_profile ) || target_login+=( ~/.bash_login )
[[ -f ~/.zprofile ]] &&
target_login+=( ~/.zprofile ) || target_login+=( ~/.zlogin )
for profile_file in ${search_list[@]}
do
[[ -f $profile_file ]] &&
GREP_OPTIONS="" \grep PATH=.*\$HOME/.rvm/bin $profile_file >/dev/null &&
found_rc+=( $profile_file ) || true
[[ -f $profile_file ]] && { {
GREP_OPTIONS="" \grep \..*scripts/rvm $profile_file >/dev/null &&
found_login+=( $profile_file )
} || {
GREP_OPTIONS="" \grep source.*scripts/rvm $profile_file >/dev/null &&
found_login+=( $profile_file )
} } || true
done
if (( rvm_auto_flag == 1 && ${#found_rc[@]} > 0 ))
then
printf "%b" "
Removing rvm PATH line from ${found_rc[*]}.\n"
for profile_file in ${found_rc[@]}
do
sed -i"" -e '/PATH=.*\$HOME\/.rvm\/bin/ d;' ${profile_file}
# also delete duplicate blank lines
sed -i"" -e '/^\s*$/{ N; /^\n$/ D; };' ${profile_file}
done
found_rc=()
fi
if (( rvm_auto_flag == 1 || ${#found_rc[@]} == 0 ))
then
printf "%b" "
Adding rvm PATH line to ${target_rc[*]}.\n"
for profile_file in ${target_rc[@]}
do
touch $profile_file
printf "%b" "
PATH=\$PATH:\$HOME/.rvm/bin # Add RVM to PATH for scripting
" >> $profile_file
done
user_rc_files=( ${target_rc[@]} )
else
printf "%b" "
RVM PATH line found in ${found_rc[*]}.\n"
user_rc_files=( ${found_rc[@]} )
fi
if (( rvm_auto_flag == 1 && ${#found_login[@]} > 0 ))
then
printf "%b" "
Removing rvm loading line from ${found_login[*]}.\n"
for profile_file in ${found_login[@]}
do
sed -i"" -e '/source.*scripts\/rvm/ d; /\. .*scripts\/rvm/ d;' ${profile_file}
# also delete duplicate blank lines
sed -i"" -e '/^\s*$/{ N; /^\n$/ D; };' ${profile_file}
done
found_rc=()
fi
if (( rvm_auto_flag == 1 || ${#found_login[@]} == 0 ))
then
printf "%b" "
Adding rvm loading line to ${target_login[*]}.\n"
for profile_file in ${target_login[@]}
do
touch $profile_file
printf "%b" "
[[ -s \"\$HOME/.rvm/scripts/rvm\" ]] && source \"\$HOME/.rvm/scripts/rvm\" # Load RVM into a shell session *as a function*
" >> $profile_file
done
user_login_files=( ${target_login[@]} )
else
printf "%b" "
RVM sourcing line found in ${found_login[*]}.\n"
user_login_files=( ${found_login[@]} )
fi
return 0
}
root_canal()
{
true ${rvm_group_name:=rvm}
if (( UID == 0 )) && system_check
then
setup_rvm_group
setup_etc_profile
setup_rvm_path_permissions
fi
return 0
}
record_ruby_configs()
{
source "$PWD/scripts/functions/manage/base"
__rvm_record_ruby_configs
}
record_installation_time()
{
date +%s > $rvm_path/installed.at
if (( UID == 0 )) && system_check
then
# fix the rights explicitly as this is the last action
chmod g+w "$rvm_path/installed.at"
fi
return 0
}
1.18.61.21. fun
#!/usr/bin/env bash
__rvm_Answer_to_the_Ultimate_Question_of_Life_the_Universe_and_Everything()
{
for index in {1..750} ; do sleep 0.25 ; echo -n '.' ; done ; printf "%d" 0x2A
echo
return 0
}
__rvm_ultimate_question()
{
printf "%b" "
I do not know the Ultimate Question,
however I can help you build a more
powerful Ruby which can compute the
Ultimate Question:
$ rvm install rbx
"
return 0
}
1.18.61.22. gemset
#!/usr/bin/env bash
__rvm_current_gemset()
{
# Fetch the current gemset via GEM_HOME
typeset current_gemset
current_gemset="${GEM_HOME:-}"
# We only care about the stuff to the right of the separator.
current_gemset="${current_gemset##*${rvm_gemset_separator:-@}}"
if [[ "${current_gemset}" == "${GEM_HOME:-}" ]] ; then
echo ''
else
echo "${current_gemset}"
fi
}
__rvm_using_gemset_globalcache()
{
"$rvm_scripts_path/db" "$rvm_user_path/db" \
"use_gemset_globalcache" | GREP_OPTIONS="" \grep '^true$' >/dev/null 2>&1
return $?
}
__rvm_current_gemcache_dir()
{
if __rvm_using_gemset_globalcache; then
echo "$rvm_gems_cache_path"
else
echo "${rvm_ruby_gem_home:-"$GEM_HOME"}/cache"
fi
return 0
}
1.18.61.23. hooks
1.18.61.23.1. jruby
#!/usr/bin/env bash
export JRUBY_OPTS
jruby_ngserver_is_running()
{
ps auxww | GREP_OPTIONS="" \grep '[c]om.martiansoftware.nailgun.NGServer' >/dev/null
}
jruby_ngserver_start()
{
if ! jruby_ngserver_is_running
then
(JRUBY_OPTS='' jruby --ng-server 2>&1 1>/dev/null)&
fi
}
jruby_options_trim()
{
JRUBY_OPTS="${JRUBY_OPTS## }"
JRUBY_OPTS="${JRUBY_OPTS%% }"
}
jruby_options_append()
{
for param in "$@"
do
if ! [[ " ${JRUBY_OPTS} " =~ " $param " ]]
then
JRUBY_OPTS="${JRUBY_OPTS} $param"
fi
done
jruby_options_trim
}
jruby_options_remove()
{
JRUBY_OPTS=" ${JRUBY_OPTS} "
for param in "$@"
do
if [[ "${JRUBY_OPTS}" =~ " $param " ]]
then
JRUBY_OPTS="${JRUBY_OPTS// $param / }"
fi
done
jruby_options_trim
}
jruby_clean_project_options()
{
if [[ -n "${PROJECT_JRUBY_OPTS}" ]]
then
unset PROJECT_JRUBY_OPTS
fi
}
1.18.61.24. manage
1.18.61.24.1. goruby
#!/usr/bin/env bash
goruby_install()
{
unset GEM_HOME GEM_PATH MY_RUBY_HOME IRBRC
export PATH
__rvm_remove_rvm_from_path
__rvm_conditionally_add_bin_path
builtin hash -r
rvm_ruby_home="$rvm_rubies_path/$rvm_ruby_interpreter"
__rvm_fetch_from_github "ruby" "trunk"
__rvm_apply_patches ; result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to apply patches to goruby.
exit $result
fi
\nHalting the installation."
#builtin cd "${rvm_src_path}/$rvm_ruby_string/configure"
if [[ ! -s "${rvm_src_path}/$rvm_ruby_string/configure" ]]
then
if builtin command -v autoreconf &> /dev/null
then
__rvm_run "autoreconf" "autoreconf" "Running autoreconf"
else
rvm_error "rvm expects autoreconf to install this ruby interpreter, autoreconf was not found in PATH. \
\nHalting installation."
exit $result
fi
fi
if [[ -s ./Makefile && -z "$rvm_reconfigure_flag" ]]
then
if (( ${rvm_debug_flag:=0} > 0 ))
then
rvm_debug "Skipping configure step, Makefile exists so configure must have already been run."
fi
elif [[ -n "$rvm_ruby_configure" ]]
then
__rvm_run "configure" "$rvm_ruby_configure"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to configure the source.
exit $result
fi
\nHalting the installation."
elif [[ -s ./configure ]]
then
typeset configure_command
configure_command="${rvm_configure_env:-""} ./configure --prefix=$rvm_ruby_home $rvm_configure_flags"
__rvm_run "configure" "$configure_command" \
"Configuring $rvm_ruby_string using $rvm_configure_flags, this may take a while depending on your cpu(s)..."
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to configure the source.
exit $result
fi
\nHalting the installation."
else
rvm_error "Skipping configure step, 'configure' script does not exist, did autoreconf not run successfully?"
fi
rvm_ruby_make=${rvm_ruby_make:-"make"}
__rvm_run "make" "$rvm_ruby_make golf $rvm_make_flags" \
"Compiling $rvm_ruby_string, this may take a while depending on your cpu(s)..."
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to run make.
exit $result
fi
\nHalting the installation."
rvm_ruby_make_install=${rvm_ruby_make_install:-"make install"}
__rvm_run "install" "$rvm_ruby_make_install" "Installing $rvm_ruby_string"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to run make install.
exit $result
fi
rvm_log "Installation of $rvm_ruby_string is complete."
export GEM_HOME="$rvm_ruby_gem_home"
export GEM_PATH="$rvm_ruby_gem_path"
(
rvm_create_flag=1 __rvm_use
"$rvm_scripts_path/rubygems" ${rvm_rubygems_version:-latest}
)
__rvm_bin_script
__rvm_run "chmod.bin" "chmod +x $rvm_ruby_home/bin/*"
__rvm_post_install
rm $rvm_ruby_home/bin/ruby
ln -s $rvm_ruby_home/bin/goruby $rvm_ruby_home/bin/ruby
}
\nHalting the installation."
1.18.61.24.2. ree
#!/usr/bin/env bash
ree_install()
{
if [[ -n "$(echo "$rvm_ruby_version" | awk '/^1\.8/')" ]] && (( rvm_head_flag == 0 ))
then
rvm_log "Installing Ruby Enterprise Edition from source to: $rvm_ruby_home"
builtin cd "${rvm_src_path}"
if [[ -d "${rvm_src_path}/$rvm_ruby_string" &&
-x "${rvm_src_path}/$rvm_ruby_string/installer" ]]
then
rvm_log "It appears that the archive has already been extracted. Skipping extract (use reinstall to do fresh
installation)."
else
rvm_log "$rvm_ruby_string - #fetching ($rvm_ruby_package_file)"
"$rvm_scripts_path/fetch" "$rvm_ruby_url"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source. \nHalting the installation."
return $result
fi
__rvm_rm_rf "${rvm_src_path}/$rvm_ruby_string"
__rvm_run "extract" \
"gunzip < \"${rvm_archives_path}/$rvm_ruby_package_file.$rvm_archive_extension\" | $rvm_tar_command xf - -C
${rvm_src_path} ${rvm_tar_options:-}" \
"$rvm_ruby_string - #extracting $rvm_ruby_package_file to ${rvm_src_path}/$rvm_ruby_string"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to extract the source. Halting the installation."
return $result
fi
mv "${rvm_src_path}/$rvm_ruby_package_file" \
"${rvm_src_path}/$rvm_ruby_string"
fi
builtin cd "${rvm_src_path}/$rvm_ruby_string"
__rvm_setup_compile_environment
# wait, what? v v v TODO: Investigate line smell.
mkdir -p "${rvm_ruby_home}/lib/ruby/gems/1.8/gems"
if [[ -n "$rvm_configure_flags" ]]
then
rvm_configure_flags="${rvm_configure_flags//--/-c --}"
fi
if [[ "Darwin" == "$(uname)" && ("1.8.6" == "$rvm_ruby_version" || "1.8.7" == "$rvm_ruby_version") && !
"$rvm_ree_options" =~ "--no-tcmalloc" ]]
then
rvm_ree_options="${rvm_ree_options} --no-tcmalloc"
fi
__rvm_db "${rvm_ruby_interpreter}_configure_flags" "db_configure_flags"
__rvm_apply_patches "${rvm_src_path}/$rvm_ruby_string/source"
result=$?
if (( result == 0 )) && [[ "$(uname -m)" == "x86_64" ]]
then
(
full_patch_path="$(__rvm_lookup_full_patch_path lib64)"
cd "${rvm_src_path}/$rvm_ruby_string"
__rvm_run "patch.apply.lib64" \
"patch -F 3 -p1 -N -f <\"$full_patch_path\"" \
"Applying patch 'lib64' (located at $full_patch_path)"
)
result=$?
fi
if (( result > 0 ))
then
rvm_error "There has been an error while trying to apply patches to ree. \nHalting the installation."
return $result
fi
: rvm_configure_env:${rvm_configure_env:=""}
__rvm_run "install" \
"${rvm_configure_env/CCFLAGS=/CFLAGS=} ./installer -a $rvm_rubies_path/$rvm_ruby_string \
$rvm_ree_options $db_configure_flags $rvm_configure_flags" "$rvm_ruby_string - #installing"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to run the ree installer. Halting the installation."
return $result
fi
chmod +x "$rvm_ruby_home"/bin/*
(
rvm_create_flag=1 __rvm_use
"$rvm_scripts_path/rubygems" ${rvm_rubygems_version:-latest}
)
__rvm_bin_script
__rvm_post_install
else
__rvm_db "${rvm_ruby_interpreter}_${rvm_ruby_version}_repo_url" "rvm_ruby_url"
if [[ -z "$rvm_ruby_url" ]] ; then
rvm_error "rvm does not know the rvm repo url for '${rvm_ruby_interpreter}_${rvm_ruby_version}'"
result=1
else
rvm_ruby_repo_url="$rvm_ruby_url"
__rvm_setup_compile_environment
__rvm_install_source $*
fi
fi
}
1.18.61.24.3. rubinius
#!/usr/bin/env bash
file_exists_at_url()
{
typeset _url
_url="${1:-}"
if [[ -n "${_url}" ]]
then
( #subshell to be able to temporary disable curl function
unset curl 2>/dev/null
if curl -slk --head ${_url} 2>&1 | \head -n 1 | GREP_OPTIONS="" \grep '200 OK' >/dev/null 2>&1
then
return 0
else
return 1
fi
)
else
rvm_log "Warning: URL was not passed to __rvm_check_for_tarball"
return 1
fi
}
rbx_configure_with_path()
{
typeset name path
name="${1:-}"
path="${2:-}"
[[ -d "${path}" ]] || return 1
[[ -d "${path}/include" ]] || return 2
rvm_configure_args="${rvm_configure_args:-} --with-${name}-dir=${path}"
rvm_configure_flags="${rvm_configure_flags:-} --with-opt-dir=${path}"
return 0
}
rbx_install()
{
typeset rvm_configure_args
rvm_log "$rvm_ruby_string installing #dependencies "
if ! __rvm_ensure_has_mri_ruby
then
rvm_log "No MRI ruby found, cannot build rbx."
return 1
fi
export ruby="$(__rvm_mri_ruby)"
# TODO: use 'rvm gems load' here:
unset CFLAGS LDFLAGS ARCHFLAGS # Important.
unset GEM_HOME GEM_PATH MY_RUBY_HOME IRBRC
__rvm_remove_rvm_from_path
__rvm_conditionally_add_bin_path
export PATH
builtin hash -r
case ${rvm_ruby_string} in
rbx-head*|rbx-2.*)
# #RBX 2.0 should now use libyaml which is for Psych.
if ! libyaml_installed
then libyaml # Installs libyaml
fi
rbx_configure_with_path libyaml "$rvm_path/usr" || {
rvm_error "Could not find 'lib' dir for libyaml, please make sure libyaml is compiled properly."
return 1
}
;;
esac
__rvm_compatibility_flag_configuration --default-version=
if [[ -s "${rvm_archives_path}/${rvm_ruby_package_file}" ]] ||
[[ -n "${rvm_ruby_url:-}" ]] && file_exists_at_url "${rvm_ruby_url}"
then
rvm_head_flag=0
else
rvm_head_flag=1
if [[ "${rvm_ruby_version}" == 'head' ]]
then
true ${rvm_ruby_repo_branch:="master"}
else
true ${rvm_ruby_repo_branch:="${rvm_ruby_version}"}
fi
fi
if (( rvm_head_flag == 0 ))
then
# Install from tarball url.
rvm_log "$rvm_ruby_string #downloading ($rvm_ruby_package_file), this may take a while depending on your connection..."
"$rvm_scripts_path/fetch" "$rvm_ruby_url"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source. Halting the installation."
exit $result
fi
__rvm_run "extract" \
"gunzip < \"${rvm_archives_path}/$(basename ${rvm_ruby_package_file})\" | $rvm_tar_command xf - -C ${rvm_src_path}
${rvm_tar_options:-}" \
"$rvm_ruby_string - #extracting"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to extract the source.
exit $result
fi
\nHalting the installation."
# Remove the left over folder first.
__rvm_rm_rf "${rvm_src_path}/$rvm_ruby_string"
mv "${rvm_src_path}/rubinius-${rvm_ruby_version}" \
"${rvm_src_path}/$rvm_ruby_string"
else
# Install from repository
__rvm_db "rubinius_repo_url" "rvm_ruby_repo_url"
#rvm_ruby_home="$rvm_rubies_path/$rvm_ruby_interpreter-$rvm_ruby_version"
__rvm_fetch_from_github "rbx"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while fetching the rbx git repo.
exit $result
fi
\nHalting the installation."
fi
builtin cd "${rvm_src_path}/$rvm_ruby_string"
chmod +x ./configure
__rvm_apply_patches
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to apply patches to rubinius.
return $result
fi
\nHalting the installation."
__rvm_db "${rvm_ruby_interpreter}_configure_flags" "db_configure_flags"
rvm_configure_flags="${rvm_configure_flags:-"--skip-system"}"
rvm_ruby_configure="$rvm_wrappers_path/$ruby/ruby ${rvm_configure_env:-""} ./configure --prefix=$rvm_ruby_home
$db_configure_flags $rvm_configure_flags ${rvm_install_args:-}"
if (( ${rvm_llvm_flag:=1} == 0 ))
then # Explicitely disabled
rvm_ruby_configure="$rvm_ruby_configure --disable-llvm"
fi
__rvm_run "configure" "$rvm_ruby_configure" "$rvm_ruby_string - #configuring"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while running '$rvm_ruby_configure'.
exit $result
fi
\nHalting the installation."
if [[ -n "${rvm_configure_args:-}" ]]
then
rvm_ruby_make="CONFIGURE_ARGS=${rvm_configure_args## } "
fi
rvm_ruby_make="${rvm_ruby_make:-}$rvm_wrappers_path/$ruby/rake install --trace"
__rvm_run "rake" "$rvm_ruby_make" "$rvm_ruby_string - #compiling"
result=$?
if (( result > 0 )) || ! [[ -d "$rvm_ruby_home" ]] || ! [[ -f "$rvm_ruby_home/bin/rbx" ]]
then
rvm_error "There has been an error while running '$rvm_ruby_make'.\nHalting the installation."
exit $result
fi
unset ruby
# Symlink rubinius wrapper if not available
[[ -f "$rvm_ruby_home/bin/ruby" ]] ||
ln -fs "$rvm_ruby_home/bin/rbx" "$rvm_ruby_home/bin/ruby"
case ${rvm_ruby_string} in
rbx-head*|rbx-2.*)
true
;;
*) # older rbx had issues
# Install IRB Wrapper on Rubinius.
file_name="$rvm_ruby_home/bin/irb"
rm -f "$file_name"
printf "%b" '#!/usr/bin/env bash\n' > "$file_name"
printf "%b" "exec '$rvm_ruby_home/bin/rbx' 'irb' \"\$@\"\n" >> "$file_name"
[[ -x "$file_name" ]] || chmod +x "$file_name"
# Install Gem Wrapper on Rubinius.
file_name="$rvm_ruby_home/bin/gem"
cp -f "$rvm_ruby_home/lib/bin/gem.rb" "$file_name"
__rvm_inject_ruby_shebang "$file_name"
[[ -x "$file_name" ]] || chmod +x "$file_name"
unset file_name
;;
esac
(
rvm_create_flag=1 __rvm_use
)
case ${rvm_ruby_string} in
rbx-head*|rbx-2.*) binaries=()
;;
*)
binaries=(erb ri rdoc) ;;
esac
__rvm_post_install
__rvm_bin_script
}
1.18.61.24.4. ruby
#!/usr/bin/env bash
transform_configure_flags()
{
typeset flag path
typeset -a new_flags
for flag in ${rvm_configure_flags}
do
case "${flag}" in
--with-opt-dir=*)
new_flags+=( "${flag}" )
;;
--with-*-dir=*)
path="${flag#*=}"
flag="${flag%-dir=*}"
new_flags+=( "${flag}" )
if ! [[ " ${new_flags[*]} " =~ " --with-opt-dir=${path} " ]]
then new_flags+=( "--with-opt-dir=${path}" )
fi
;;
*)
new_flags+=( "${flag}" )
;;
esac
done
rvm_configure_flags="${new_flags[*]}"
}
# 1.9.3-p125+
__clang_ready()
{
typeset _patch_level
case ${rvm_ruby_string} in
ruby-1.9.3-head*|ruby-2*)
return 0
;;
ruby-1.9.3*)
_patch_level="${rvm_ruby_patch_level:-p0}"
_patch_level="${_patch_level#p}"
(( _patch_level >= 125 )) && return 0 || true
;;
esac
return 1
}
ruby_install()
{
typeset result temp_flags
__rvm_check_for_bison # && Run like hell...
if __rvm_check_for_bison
then true
else
result=$?
rvm_log "Bison required but not found. Halting."
exit $result
fi
case ${rvm_ruby_string:-""} in
ruby-1.8*|ree*|ruby-1.9*)
true # carry on then, nothing to see here :P
;;
ruby-head|1.9.*-head)
if __rvm_ensure_has_mri_ruby "1.8.|ree"
then true
else return $?
fi
;;
esac
case ${rvm_ruby_string} in
ruby-1.9*)
# Ruby 1.9 should now use libyaml which is for Psych.
if [[ " ${rvm_configure_flags[*]}" =~ " --with-opt-dir=" ]]
then
rvm_warn "Please note that you are using your own '--with-opt-dir=', make sure 'libyaml' is installed and available
for ruby compilation."
else
if ! libyaml_installed
then libyaml # Installs libyaml
fi
rvm_configure_flags="${rvm_configure_flags:-} --with-libyaml-dir=${rvm_path}/usr"
fi
# Ruby 1.9 does not allow --with-<lib>-dir,
# so we transform it to --with-<lib> --with-opt-dir=...
# see https://github.com/wayneeseguin/rvm/issues/674
temp_flags=" ${rvm_configure_flags[*]}"
temp_flags="${temp_flags// --with-opt-dir=/}"
if [[ " ${rvm_configure_flags[*]}" =~ " --with-opt-dir=" && "${temp_flags}" =~ "-dir=" ]]
then
rvm_warn "You are using conflicting '--*-dir=' configure flags."
else
transform_configure_flags
fi
;;
esac
# Temporary solution for this bug http://bugs.ruby-lang.org/issues/5384
case "$(uname -s)" in
SunOS)
case ${rvm_ruby_string} in
ruby-1.9*)
rvm_configure_flags="${rvm_configure_flags:-} ac_cv_func_dl_iterate_phdr=no"
;;
esac
;;
esac
__rvm_setup_compile_environment
# Force using clang when only LLVM available and user did not selected compiler,
# hides the need for `rvm_force_autoconf=1`
# which should be default, but is not by default available on Xcode 4.3.
if [[ "$MACHTYPE" == *darwin* ]] &&
__clang_ready && __rvm_compiler_is_llvm &&
! __rvm_selected_compiler > /dev/null
then
rvm_configure_flags="${rvm_configure_flags:-""} --with-gcc=clang"
fi
if __rvm_compiler_is_llvm
then
if __clang_ready || __rvm_selected_compiler > /dev/null
then
rvm_warn "Building '${rvm_ruby_string}' using clang - but it's not (fully) supported, expect errors."
else
rvm_error "The provided compiler '$(__rvm_found_compiler)' is LLVM based, it is not yet fully supported by ruby and
gems, please read \`rvm requirements\`."
exit 1
fi
fi
( __rvm_install_source $* )
result=$?
if __rvm_compiler_is_llvm
then
rvm_warn "Ruby '${rvm_ruby_string}' was build using clang - but it's not (fully) supported, expect errors."
rvm_warn "Ruby '${rvm_ruby_string}' was built using clang - but it's not (fully) supported, expect errors."
fi
typeset patches_count
patches_count=$(
rvm_ruby_string="${rvm_ruby_string}" "$rvm_scripts_path/patchsets" show default | wc -l
)
# 1.9.3 provides a patch to compile better with LLVM
if [[ ! "${rvm_ruby_string}" =~ "ruby-1.9.3" ]] && (( patches_count > 0 ))
then
rvm_warn "Please be aware that you just installed a ruby that requires ${patches_count} patches just to be compiled on
up to date linux system.
This may have known and unaccounted for security vulnerabilities.
Please consider upgrading to Ruby $(__rvm_db "ruby_version")-$(__rvm_db "ruby_patchlevel") which will have all of the latest
security patches."
fi
return ${result:-0}
}
1.18.61.24.5. macruby
#!/usr/bin/env bash
macruby_install()
{
if [[ "Darwin" != "$(uname)" ]]
then
rvm_error "MacRuby can only be installed on a Darwin OS."
exit 1
fi
if (( rvm_head_flag == 1 ))
then
if (( ${rvm_llvm_flag:=0} == 1 ))
then
"$rvm_scripts_path/package" llvm install
fi
macruby_path="/usr/local/bin"
# TODO: configure & make variables should be set here.
rvm_ruby_configure=" true "
rvm_ruby_make="rake"
rvm_ruby_make_install="$rvm_bin_path/rvmsudo rake install"
__rvm_db "${rvm_ruby_interpreter}_repo_url" "rvm_ruby_url"
rvm_ruby_repo_url=$rvm_ruby_url
__rvm_setup_compile_environment
__rvm_install_source $*
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to install from source. \nHalting the installation."
return $result
fi
elif [[ "nightly" == "$rvm_ruby_version" ]] ; then
__rvm_db "macruby_nightly_version" "macruby_nightly_version"
macruby_path="/Library/Frameworks/MacRuby.framework/Versions/${macruby_nightly_version}/usr/bin"
unset macruby_nightly_version
# TODO: Separated nightly from head.
rvm_log "Retrieving the latest nightly macruby build..."
"$rvm_scripts_path/fetch" "$rvm_ruby_url"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source.
return $result
fi
\nHalting the installation."
mv "${rvm_archives_path}/macruby_nightly-latest.pkg" \
"${rvm_archives_path}/macruby_nightly.pkg"
__rvm_run "macruby/extract" \
"sudo /usr/sbin/installer -pkg '${rvm_archives_path}/macruby_nightly.pkg' -target '/'"
mkdir -p "$rvm_ruby_home/bin"
else
macruby_path="/Library/Frameworks/MacRuby.framework/Versions/${rvm_ruby_version}/usr/bin"
# TODO: Separated nightly from head.
rvm_log "Retrieving MacRuby ${rvm_ruby_version} ..."
"$rvm_scripts_path/fetch" "$rvm_ruby_url"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source. Halting the installation."
return $result
fi
mkdir -p ${rvm_src_path}/$rvm_ruby_string
unzip -o -j "${rvm_archives_path}/$rvm_ruby_package_file" \
"MacRuby ${rvm_ruby_version}/MacRuby ${rvm_ruby_version}.pkg" \
-d "${rvm_src_path}/$rvm_ruby_string"
mv "${rvm_src_path}/$rvm_ruby_string/MacRuby ${rvm_ruby_version}.pkg" \
"${rvm_src_path}/$rvm_ruby_string/$rvm_ruby_string.pkg"
__rvm_run "macruby/extract" \
"sudo /usr/sbin/installer -pkg '${rvm_src_path}/$rvm_ruby_string/$rvm_ruby_string.pkg' -target '/'"
mkdir -p "$rvm_ruby_home/bin"
fi
(
rvm_create_flag=1 __rvm_use
)
binaries=(erb gem irb rake rdoc ri ruby testrb)
for binary_name in ${binaries[@]}; do
# TODO: This should be generated via an external script.
ruby_wrapper=$(cat <<RubyWrapper
#!/usr/bin/env bash
export
export
export
export
GEM_HOME="\${GEM_HOME:-$rvm_ruby_gem_home}"
GEM_PATH="\${GEM_PATH:-$rvm_ruby_gem_path}"
MY_RUBY_HOME="$rvm_ruby_home"
PATH="$rvm_ruby_gem_home/bin:$rvm_ruby_global_gems_path/bin:$rvm_ruby_home/bin:\$PATH"
exec "$macruby_path/mac$binary_name" "\$@"
RubyWrapper
)
file_name="$rvm_ruby_home/bin/$binary_name"
if [[ -f "$file_name" ]]
then
rm -f "$file_name"
fi
echo "$ruby_wrapper" > "$file_name"
if [[ ! -x "$file_name" ]]
then
chmod +x $file_name
fi
if [[ "$binary_name" == "ruby" ]]
then
rm -f "${rvm_bin_path:-"$rvm_path/bin"}/$rvm_ruby_string"
echo "$ruby_wrapper" \
> "${rvm_bin_path:-"$rvm_path/bin"}/$rvm_ruby_string"
fi
done
unset binaries
__rvm_irbrc
}
1.18.61.24.6. maglev
#!/usr/bin/env bash
maglev_install()
{
__rvm_ensure_has_mri_ruby
compatible_ruby="$(__rvm_mri_ruby)"
rvm_log "Running MagLev prereqs checking script."
"$rvm_scripts_path/maglev"
result=$?
if (( result > 0 ))
then
rvm_error "Prerequisite checks have failed. \nHalting the installation."
exit $result
fi
builtin cd "${rvm_src_path}"
system="$(uname -s)"
arch="$(uname -m)"
[ "${system}-${arch}" == "Darwin-x86_64" ] && arch="i386"
if [[ ! -d "${rvm_src_path}/$rvm_ruby_string" ]] || (( ${rvm_head_flag:=0} == 1 ))
then
__rvm_fetch_ruby
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source.
exit $result
fi
\nHalting the installation."
fi
if (( ${rvm_head_flag:=0} == 1 ))
then
builtin cd "${rvm_src_path}/$rvm_ruby_string"
rvm_gemstone_package_file="GemStone-$(GREP_OPTIONS="" \grep ^GEMSTONE version.txt | cut -f2 -d-).${system}-${arch}"
rvm_gemstone_url="$maglev_url/${rvm_gemstone_package_file}.${rvm_archive_extension}"
fi
rvm_log "Downloading the GemStone package, this may take a while depending on your connection..."
"$rvm_scripts_path/fetch" "$rvm_gemstone_url"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the GemStone package.\nHalting the installation."
exit $result
fi
builtin cd "${rvm_src_path}"
if [[ -s "$rvm_ruby_package_file" ]]
then
mv "$rvm_ruby_package_file" "${rvm_src_path}/$rvm_ruby_string"
fi
builtin cd "${rvm_src_path}/$rvm_ruby_string"
if [[ -d
${rvm_src_path}/${rvm_gemstone_package_file} ]]
then
__rvm_run "gemstone.fix_rights" \
"chmod -R u+w ${rvm_src_path}/${rvm_gemstone_package_file}"
else
mkdir -p "${rvm_src_path}/${rvm_gemstone_package_file}"
fi
__rvm_run "gemstone.extract" \
"$rvm_tar_command xzf \"${rvm_archives_path}/${rvm_gemstone_package_file}.${rvm_archive_extension}\" -C ${rvm_src_path}/
${rvm_tar_options:-}"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to extract the GemStone package. \nHalting the installation."
exit $result
fi
ln -fs "${rvm_src_path}/$rvm_gemstone_package_file" "gemstone"
__rvm_rm_rf $rvm_ruby_home
__rvm_run "install" \
"/bin/cp -Rf ${rvm_src_path}/$rvm_ruby_string $rvm_ruby_home" \
"Installing maglev to $rvm_ruby_home"
(
builtin cd "$rvm_ruby_home/bin/"
for binary in maglev-irb maglev-ruby maglev-gem
do
ln -fs "$binary" "${binary#maglev-}"
done
unset binary
)
binaries=(maglev-ruby maglev-irb maglev-gem)
for binary in "${binaries[@]}"
do
__rvm_inject_gem_env "$rvm_ruby_home/bin/$binary"
done
builtin cd "$rvm_ruby_home"
if (( ${rvm_head_flag:=0} == 1 ))
then
git submodule update --init
"$rvm_ruby_home/bin/maglev" force-reload
fi
ln -fs maglev.demo.key-${system}-${arch} etc/maglev.demo.key
rvm_log "Bootstrapping a new image"
"$rvm_wrappers_path/$compatible_ruby/rake" "build:maglev"
if [[ ! -e ${rvm_ruby_home}/etc/conf.d/maglev.conf ]]
then
rvm_log "Creating default 'maglev' repository."
"$rvm_wrappers_path/$compatible_ruby/rake" "stone:create[maglev]" >/dev/null 2>&1
fi
rvm_log "Generating maglev HTML documentation"
"$rvm_wrappers_path/$compatible_ruby/rake" rdoc >/dev/null 2>&1
rvm_log "Generating smalltalk FFI."
"$rvm_wrappers_path/$compatible_ruby/rake" stwrappers >/dev/null 2>&1
# maglev ships with some built in gems, copy them in to place.
if [[ -d "$rvm_ruby_home/lib/maglev/gems/1.8" ]]
then
rvm_log "Copying across included gems"
cp -R "$rvm_ruby_home/lib/maglev/gems/1.8/" "$rvm_ruby_gem_home/"
fi
unset compatible_ruby
# MagLev comes with RubyGems preinstalled -- don't try to install it
# "$rvm_scripts_path/rubygems" latest
__rvm_irbrc
__rvm_bin_script
rvm_create_flag=1 __rvm_use
}
1.18.61.24.7. ironruby
#!/usr/bin/env bash
ironruby_install()
{
if ! builtin command -v mono > /dev/null
then
printf "%b" "mono must be installed and in your path in order to install IronRuby." ; return 1
fi
if (( ${rvm_head_flag:=0} == 1 ))
then
mono_version="$(mono -V | head -n 1 | cut -d ' ' -f5)"
if "$rvm_scripts_path/match" "$mono_version" "([0-9]+)\.([0-9]+)\.?([0-9]+)?"
then
mono_major_ver="$(echo "$mono_version" | cut -d '.' -f1)"
mono_minor_ver="$(echo "$mono_version" | cut -d '.' -f2)"
if [[ $mono_major_ver -lt 2 ]] ||
( [[ $mono_major_ver -eq 2 && $mono_minor_ver -lt 6 ]] )
then
printf "%b" "Mono 2.6 (or greater) must be installed and in your path in order to build IronRuby from the repository."
printf "%b" "Version detected: ${mono_version}"
return 1
fi
else
printf "%b" "Cannot recognize mono version."
return 1
fi
__rvm_ensure_has_mri_ruby
__rvm_fetch_ruby
result=$?
if (( result > 0 ))
then
return $result
fi
builtin cd "${rvm_src_path}/$rvm_ruby_string"
compatible_ruby="$(__rvm_mri_ruby)"
"$rvm_wrappers_path/$compatible_ruby/gem" install pathname2 --no-rdoc --no-ri
# MONO_LIB=/Library/Frameworks/Mono.framework/Versions/current/lib/
rvm_ruby_make="$rvm_wrappers_path/$compatible_ruby/rake MERLIN_ROOT=\"${rvm_src_path}/$rvm_ruby_string/Merlin/Main\"
compile mono=1 configuration=release --trace"
__rvm_run "rake" "$rvm_ruby_make" "Building IronRuby..."
unset compatible_ruby
result=$?
if (( result > 0 ))
then
exit $result
fi
__rvm_rm_rf "$rvm_ruby_home"/*
mkdir -p "$rvm_ruby_home/bin" "$rvm_ruby_home/lib" \
"$rvm_ruby_home/lib/ruby" "$rvm_ruby_home/lib/IronRuby"
cp -r "${rvm_src_path}/$rvm_ruby_string/Merlin/Main/Bin/mono_release"/* "$rvm_ruby_home/bin/"
cp -r "${rvm_src_path}/$rvm_ruby_string/Merlin/Main/Languages/Ruby/Scripts/bin"/* "$rvm_ruby_home/bin/"
cp -r "${rvm_src_path}/$rvm_ruby_string/Merlin/External.LCA_RESTRICTED/Languages/Ruby/redist-libs/ruby"/*
"$rvm_ruby_home/lib/ruby"
cp -r "${rvm_src_path}/$rvm_ruby_string/Merlin/Main/Languages/Ruby/Libs"/* "$rvm_ruby_home/lib/IronRuby"
else
rvm_log "Retrieving IronRuby"
"$rvm_scripts_path/fetch" "$rvm_ruby_url" \
"$rvm_ruby_package_file"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source. \nHalting the installation."
exit $result
fi
mkdir -p "${rvm_src_path}/$rvm_ruby_string" "$rvm_ruby_home"
unzip -o -d "${rvm_src_path}/$rvm_ruby_string" \
"${rvm_archives_path}/${rvm_ruby_package_file}" >> \
"${rvm_log_path}/$rvm_ruby_string/extract.log" 2>&1
result=$?
if (( result > 1 ))
then
rvm_error "There has been an error while trying to extract
$rvm_ruby_package_file.\n${rvm_log_path}/$rvm_ruby_string/extract.log might have more details.\nHalting the installation."
exit $result
fi
for dir in bin lib silverlight
do
cp -Rf "${rvm_src_path}/$rvm_ruby_string/$dir" "$rvm_ruby_home/$dir"
done
fi
binaries=(gem irb rdoc rake ri ruby)
for binary_name in "${binaries[@]}"
do
if [[ -s "$rvm_ruby_home/bin/$binary_name" ]]
then
\tr -d '\r' < "$rvm_ruby_home/bin/$binary_name" > "$rvm_ruby_home/bin/$binary_name.new"
#sed -e '1,1s=.*=#!'"/usr/bin/env ir=" "$rvm_ruby_home/bin/$binary_name" > "$rvm_ruby_home/bin/$binary_name.new"
mv -f "$rvm_ruby_home/bin/$binary_name.new" "$rvm_ruby_home/bin/$binary_name"
chmod +x "$rvm_ruby_home/bin/$binary_name"
fi
done ; unset binaries
sed -e '1,1s=.*=#!'"/usr/bin/env bash=" "$rvm_ruby_home/bin/ir" \
| \tr -d '\r' > "$rvm_ruby_home/bin/ir.new"
mv -f "$rvm_ruby_home/bin/ir.new" "$rvm_ruby_home/bin/ir"
chmod +x "$rvm_ruby_home/bin/ir"
ln -fs "$rvm_ruby_home/bin/ir" "$rvm_ruby_home/bin/ruby"
(
rvm_create_flag=1 __rvm_use
)
builtin hash -r
__rvm_run "gems.install" \
"PATH=\"$rvm_ruby_gem_home/bin:$rvm_ruby_global_gems_path/bin:$rvm_ruby_home/bin:$PATH\" GEM_HOME=\"$rvm_ruby_gem_home\"
GEM_PATH=\"$rvm_ruby_gem_home:$rvm_ruby_global_gems_path\" $rvm_ruby_home/bin/gem install --no-rdoc --no-ri rake
$rvm_gem_options" \
"Installing $rvm_gem_name to $dir"
}
1.18.61.24.8. jruby
#!/usr/bin/env bash
jruby_install()
{
__rvm_compatibility_flag_configuration -Djruby.default.ruby.version=
if ! builtin command -v java > /dev/null
then
printf "%b" "java must be installed and in PATH for JRuby."
return 1
fi
if [[ -n "$JRUBY_HOME" ]]
then
printf "%b" "You have environment variable JRUBY_HOME set, please unset it before installing/using JRuby."
return 2
fi
if [[ "Darwin" == "$(uname)" ]]
then
java_version=$(java -version 2>&1 | awk -F'"' '/ version /{print $2}')
case "$java_version" in
(1.5.*)
printf "%b" "\n\nWARNING: A very outdated JAVA version is being used ($java_version), it is strongly recommended
that you upgrade to the latest version.\n\n"
;;
(1.3.*|1.4.*)
printf "%b" "\n\nERROR: Unsupported JAVA version $java_version. In order to install and use JRuby you must upgrade
to the latest JAVA version.\n\n"
exit 1
;;
esac
fi
builtin cd "${rvm_src_path}"
__rvm_fetch_ruby
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source.
exit $result
fi
\nHalting the installation."
builtin cd "${rvm_src_path}/$rvm_ruby_string"
if [[ -n ${rvm_configure_flags:-} ]] || (( ${rvm_head_flag:=0} ))
then
__rvm_apply_patches
__rvm_run "ant.jar" "ant jar" "$rvm_ruby_string - #ant jar"
if [[ -n ${rvm_configure_flags:-} ]]
then
__rvm_run "ant.jar.flags" "ant jar ${rvm_configure_flags}" "$rvm_ruby_string - #ant jar ${rvm_configure_flags}"
fi
fi
if (( ${rvm_head_flag:=0} ))
then
__rvm_run "ant.cext" "ant cext ${rvm_configure_flags}" "$rvm_ruby_string - #ant cext" || \
rvm_warn "cext is know to fail please report here: https://jira.codehaus.org/browse/JRUBY"
fi
mkdir -p "$rvm_ruby_home/bin/"
case "$rvm_ruby_version" in
1.2*|1.3*)
__rvm_run "nailgun" \
"builtin cd \"${rvm_src_path}/$rvm_ruby_string/tool/nailgun\" && make $rvm_make_flags" \
"Building Nailgun"
;;
*)
__rvm_run "nailgun" \
"builtin cd \"${rvm_src_path}/$rvm_ruby_string/tool/nailgun\" && ${rvm_configure_env:-""} ./configure -prefix=$rvm_ruby_home && make $rvm_make_flags" \
"Building Nailgun"
;;
esac
__rvm_rm_rf "$rvm_ruby_home"
__rvm_run "install" \
"/bin/cp -Rf ${rvm_src_path}/$rvm_ruby_string $rvm_ruby_home" "$rvm_ruby_string - #installing to $rvm_ruby_home"
(
builtin cd "$rvm_ruby_home/bin/"
for binary in jirb jruby jgem ; do
ln -fs "$binary" "${binary#j}"
done
)
# -server is "a lot slower for short-lived scripts like rake tasks, and takes longer to load"
#sed -e 's#^JAVA_VM=-client#JAVA_VM=-server#' $rvm_ruby_home/bin/jruby > $rvm_ruby_home/bin/jruby.new &&
# mv $rvm_ruby_home/bin/jruby.new $rvm_ruby_home/bin/jruby
chmod +x "$rvm_ruby_home/bin/jruby"
binaries=(jrubyc jirb_swing jirb jgem rdoc ri spec autospec testrb ast generate_yaml_index.rb)
for binary in "${binaries[@]}"
do
__rvm_inject_gem_env "$rvm_ruby_home/bin/$binary"
done
__rvm_inject_ruby_shebang "$rvm_ruby_home/bin/rake"
__rvm_irbrc
rvm_create_flag=1 __rvm_use
__rvm_bin_script
__rvm_post_install
# jruby ships with some built in gems, copy them in to place.
if [[ -d "$rvm_ruby_home/lib/ruby/gems/1.8" ]]
then
rvm_log "Copying across included gems"
cp -R "$rvm_ruby_home/lib/ruby/gems/1.8/" "$rvm_ruby_gem_home/"
fi
}
1.18.61.24.9. base
#!/usr/bin/env bash
# Emits a number of patches to STDOUT, each on a new name
# Expands patchsets etc.
__rvm_current_patch_names()
{
# TODO: Lookup default patches on rvm_ruby_string heirarchy.
typeset separator patches level name
separator="%"
patches="${rvm_patch_names:-""} default"
for name in $(echo ${patches//,/ })
do
if [[ "${name//${separator}*/}" == "${name}" ]]
then
level=1
else
level="${name/*${separator}/}"
name="${name//${separator}*/}"
fi
typeset expanded_name
expanded_name="$( __rvm_expand_patch_name "$name" )"
if [[ -n "${name}" && -n "${expanded_name}" ]]
then
echo "${expanded_name}${separator}${level}"
fi
done
return 0
}
__rvm_apply_patches()
{
typeset patches patch_name patch_level_separator patch_fuzziness patch_level source_directory full_patch_path
result=0
patch_level_separator="%"
patch_fuzziness="25" # max fuziness that makes sense is 3 (or there are patches with bigger context ?)
patch_level=1
source_directory="${1:-""}"
if [[ -z "$source_directory" ]]
then
source_directory="${rvm_src_path}/$rvm_ruby_string"
fi
(
builtin cd "$source_directory"
patches=($(__rvm_current_patch_names))
for patch_name in ${patches[*]}
do
# If set, extract the patch level from the patch name.
patch_level=1
if echo "$patch_name" | GREP_OPTIONS="" \grep "$patch_level_separator" >/dev/null 2>&1; then
patch_level=${patch_name//*${patch_level_separator}/}
patch_name="${patch_name//${patch_level_separator}*/}"
fi
full_patch_path="$(__rvm_lookup_full_patch_path "$patch_name")"
# Expand paths, and for those we found we then apply the patches.
if [[ -n "${full_patch_path:-""}" ]]
then
if [[ -f "$full_patch_path" ]]
then
__rvm_run "patch.apply.${patch_name/*\/}" \
"patch -F $patch_fuzziness -p$patch_level -N -f <\"$full_patch_path\"" \
"Applying patch '$patch_name' (located at $full_patch_path)"
if (( $? > 0 ))
then
result=1 # Detect failed patches
fi
fi
else
rvm_warn "Patch '$patch_name' not found."
result=1
fi
done
)
return ${result:-0}
}
__rvm_install_source()
{
true ${rvm_ruby_selected_flag:=0} ${rvm_static_flag:=0}
typeset directory configure_parameters db_configure_flags autoconf_flags
if (( rvm_ruby_selected_flag == 0 ))
then
__rvm_select
fi
rvm_log "Installing Ruby from source to: $rvm_ruby_home, this may take a while depending on your cpu(s)...\n"
builtin cd "${rvm_src_path}"
__rvm_fetch_ruby
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error fetching the ruby interpreter. Halting the installation."
return $result
fi
builtin cd "${rvm_src_path}/$rvm_ruby_string"
result=$?
if (( result > 0 ))
then
rvm_error "Source directory is missing. \nDid the download or extraction fail?
return $result
fi
\nHalting the installation."
if [[ -d "${rvm_path}/usr" ]]
then
__rvm_add_to_path prepend "${rvm_path}/usr/bin"
builtin hash -r
fi
if (( rvm_static_flag == 1 ))
then
if [[ -s "ext/Setup" ]]
then
echo 'option nodynamic' >> ext/Setup
rvm_log "Setting option nodynamic (static)."
else
rvm_log "
You asked for static Ruby compilation however the file ext/Setup
appears to be missing from the source directory
${rvm_src_path}/$rvm_ruby_string
please investigate this, continuing installation regardless.
"
fi
fi
__rvm_apply_patches
result="$?"
if (( result > 0 ))
then
rvm_error "There has been an error applying the specified patches. Halting the installation."
return $result
fi
if [[ -z "${rvm_ruby_configure:-""}" \
&& (! -s "${rvm_src_path}/$rvm_ruby_string/configure" \
|| "${rvm_src_path}/$rvm_ruby_string/configure.in" -nt "${rvm_src_path}/$rvm_ruby_string/configure") ]] ||
(( ${rvm_force_autoconf_flag:-0} == 1 ))
then
if builtin command -v autoreconf > /dev/null
then
if (( ${rvm_force_autoconf_flag:-0} == 1 ))
then
autoconf_flags=" -f"
fi
__rvm_run "autoreconf" "autoreconf${autoconf_flags:-}" "$rvm_ruby_string - #autoreconf${autoconf_flags:-}"
else
rvm_error "rvm requires autoreconf to install the selected ruby interpreter however autoreconf was not found in the
PATH."
exit 1
fi
fi
if [[ -n "${rvm_ruby_configure:-""}" ]]
then
__rvm_run "configure" "$rvm_ruby_configure"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while configuring. Halting the installation."
return $result
fi
elif [[ -s ./configure ]]
then
# REE stores configure flags differently for head vs. the distributed release.
if [[ "ree" != "${rvm_ruby_interpreter:-""}" ]]
then
__rvm_db "${rvm_ruby_interpreter}_configure_flags" "db_configure_flags"
fi
# On 1.9.*-head, we manually set the --with-baseruby option
# to point to an expanded path.
case "${rvm_ruby_string:-""}" in
ruby-head|ruby-1.9.3-head)
typeset compatible_baseruby
compatible_baseruby="$rvm_wrappers_path/$(__rvm_mri_ruby "1.8|ree")/ruby"
if [[ -x "$compatible_baseruby" ]]
then
configure_parameters="--with-baseruby=$compatible_baseruby"
fi
;;
esac
typeset configure_command
configure_command="${rvm_configure_env:-""} ./configure --prefix=$rvm_ruby_home ${db_configure_flags:-""}
${rvm_configure_flags:-""} ${configure_parameters:-""}"
__rvm_run "configure" "$configure_command" "$rvm_ruby_string - #configuring "
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while running configure. Halting the installation."
return $result
fi
else
rvm_error "Skipping configure step, 'configure' does not exist, did autoreconf not run successfully?"
fi
rvm_ruby_make=${rvm_ruby_make:-"make"}
__rvm_run "make" "$rvm_ruby_make ${rvm_make_flags:-""}" "$rvm_ruby_string - #compiling "
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while running make. Halting the installation."
return $result
fi
__rvm_rm_rf "$PWD/.ext/rdoc"
rvm_ruby_make_install=${rvm_ruby_make_install:-"make install"}
__rvm_run "install" "$rvm_ruby_make_install" "$rvm_ruby_string - #installing "
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while running make install. Halting the installation."
return $result
fi
case "${rvm_ruby_string:-""}" in
ruby-1.8.4|ruby-1.8.5-*)
typeset libdir
libdir="$rvm_ruby_home/lib"
if [[ -d "${libdir}64" ]]
then
rm -rf "${libdir}"
ln -s "${libdir}64" "${libdir}"
fi
;;
esac
: rvm_configure_flags:${rvm_configure_flags:=}:
case "${rvm_configure_flags}" in
(*--program-suffix=*)
typeset program_suffix
program_suffix="${rvm_configure_flags#*--program-suffix=}"
program_suffix="${program_suffix%%[\' ]*}"
__rvm_run "link.ruby" "ln -s \"$rvm_ruby_home/bin/ruby${program_suffix}\" \
\"$rvm_ruby_home/bin/ruby\"" "$rvm_ruby_string - #linking ruby${program_suffix} -> ruby "
;;
esac
export GEM_HOME="$rvm_ruby_gem_home"
export GEM_PATH="$rvm_ruby_gem_path"
(
rvm_create_flag=1 __rvm_use
"$rvm_scripts_path/rubygems" ${rvm_rubygems_version:-latest}
)
result=$?
__rvm_bin_script
__rvm_run "chmod.bin" "chmod +x $rvm_ruby_home/bin/*"
__rvm_post_install
result=$?
rvm_log "Install of $rvm_ruby_string - #complete "
return ${result:-0}
}
__rvm_install_ruby()
{
true ${rvm_head_flag:=0} ${rvm_ruby_selected_flag:=0}
typeset binary __rvm_ruby_name
if (( rvm_ruby_selected_flag == 0 ))
then
__rvm_ruby_name="$rvm_ruby_name"
__rvm_select || return $?
if [[ -n "$__rvm_ruby_name" ]]
then
__rvm_select || return $?
if [[ "$__rvm_ruby_name" != "$detected_rvm_ruby_name" ]]
then
rvm_error "
The used ruby name (-n) is not valid, it was matched as:
$( env | GREP_OPTIONS="" \grep "^rvm.*=$__rvm_ruby_name$" || printf "# Was not used at all\n")
for more details on selecting names please visit:
https://rvm.io/rubies/named/
" #" fix escaping
return 1
fi
fi
fi
if [[ -n "${RUBYOPT:-""}" ]]
then ruby_options="$RUBYOPT"
fi
unset RUBYOPT
if __rvm_check_for_compiler
then true # sok
else return $?
fi
case "${rvm_ruby_interpreter}" in
macruby|ree|jruby|maglev|goruby)
source "$rvm_scripts_path/functions/manage/${rvm_ruby_interpreter}"
${rvm_ruby_interpreter}_install
;;
rbx|rubinius)
source "$rvm_scripts_path/functions/manage/rubinius"
rbx_install
;;
ironruby|ir)
source "$rvm_scripts_path/functions/manage/ironruby"
ironruby_install
;;
ruby|kiji|tcs)
source "$rvm_scripts_path/functions/manage/ruby"
ruby_install
;;
default)
rvm_error "a ruby interpreter to install must be specified and not simply 'default'."
;;
*)
rvm_error "Either the ruby interpreter is unknown or there was an error!."
;;
esac
# Record the Ruby's configuration to a file, key=value format.
"$rvm_ruby_home/bin/ruby" -rrbconfig \
-e 'File.open(RbConfig::CONFIG["prefix"] + "/config","w") { |file| RbConfig::CONFIG.each_pair{|key,value|
file.write("#{key.gsub(/\.|-/,"_")}=\"#{value.gsub("$","\\$")}\"\n")} }' >/dev/null 2>&1
rvm_hook="after_install"
source "$rvm_scripts_path/hook"
if [[ -n "$ruby_options" ]]
then
RUBYOPT="$ruby_options"
export RUBYOPT
fi
}
__rvm_fetch_from_git_revision_or_sha()
{
typeset result
if
[[ -n "$rvm_ruby_revision" ]]
then
(
cd "${rvm_repos_path}/${rvm_ruby_interpreter}"
[[ "$rvm_ruby_revision" != "head" ]] || rvm_ruby_revision="master"
git checkout -f "${rvm_ruby_revision}"
)
result=$?
elif
[[ -n "${rvm_ruby_sha:-}" ]]
then
(
cd "${rvm_repos_path}/${rvm_ruby_interpreter}"
git checkout -f "${rvm_ruby_sha}"
)
result=$?
fi
if
(( result > 0 ))
then
rvm_error "There has been an error while trying to checkout the source branch.\nHalting the installation."
return $result
fi
}
__rvm_fetch_from_github()
{
__rvm_rm_rf "${rvm_src_path}/$rvm_ruby_string"
if [[ -d "${rvm_repos_path}/${rvm_ruby_interpreter}/.git" ]]
then
typeset existing_uri
existing_uri="$(
cd "${rvm_repos_path}/${rvm_ruby_interpreter}" >/dev/null
git remote -v 2>/dev/null | awk '/^origin.*fetch/ {print $2}'
)"
if [[ "$rvm_ruby_repo_url" != "$existing_uri" ]]
then
\rm -rf "${rvm_repos_path}/${rvm_ruby_interpreter}"
fi
fi
if [[ ! -d "${rvm_repos_path}/${rvm_ruby_interpreter}/.git" ]]
then
if [[ -d "${rvm_repos_path}/${rvm_ruby_interpreter}" ]]
then
\rm -rf "${rvm_repos_path}/${rvm_ruby_interpreter}"
fi
builtin cd "$rvm_home"
__rvm_run "$1.repo" \
"git clone --depth 1 $rvm_ruby_repo_url ${rvm_repos_path}/${rvm_ruby_interpreter}" \
"Cloning $rvm_ruby_repo_url"
result=$?
if (( result > 0 ))
then
rvm_ruby_repo_http_url="${rvm_ruby_repo_url//git:/http:}"
rvm_log "Could not fetch $rvm_ruby_repo_url - trying $rvm_ruby_repo_http_url"
__rvm_run "$1.repo" "git clone --depth 1 $rvm_ruby_repo_http_url ${rvm_repos_path}/${rvm_ruby_interpreter}" "Cloning
$rvm_ruby_repo_http_url"
fi
else
typeset branch
branch="${rvm_ruby_repo_branch:-"master"}"
builtin cd "${rvm_repos_path}/${rvm_ruby_interpreter}"
__rvm_run "$1.clean" "git checkout -f master ; git reset --hard HEAD ; rm -fr .git/rebase-apply" "Cleaning git repo"
__rvm_run "$1.fetch" "git fetch origin" "Fetching from origin"
fi
(
remote="origin"
cd "${rvm_repos_path}/${rvm_ruby_interpreter}"
if [[ -z "$(git branch | awk "/$rvm_ruby_repo_branch$/")" ]]
then
git checkout -b "$rvm_ruby_repo_branch" \
--track "$remote/$rvm_ruby_repo_branch" 2>/dev/null
elif [[ -z "$(git branch | awk "/\* $rvm_ruby_repo_branch$/")" ]]
then
if ! git checkout $rvm_ruby_repo_branch 2>/dev/null
then
rvm_error "Branch $remote/$rvm_ruby_repo_branch not found."
fi
fi
__rvm_run "$1.pull" "git pull origin $branch" "Pulling from origin $branch"
)
__rvm_fetch_from_git_revision_or_sha || return $?
if [[ -n "${rvm_ruby_string}" ]]
then
__rvm_rm_rf "${rvm_src_path}/$rvm_ruby_string"
fi
__rvm_run "$1.copy" "\\cp -Rf \"${rvm_repos_path}/${rvm_ruby_interpreter}/\" \"${rvm_src_path}/$rvm_ruby_string\""
"Copying from repo to source..."
builtin cd "${rvm_src_path}/$rvm_ruby_string"
return ${result:-0}
}
__rvm_fetch_ruby()
{
if (( ${rvm_ruby_selected_flag:=0} == 0 ))
then
__rvm_select
fi
if (( ${rvm_head_flag:=0} == 0 )) &&
[[ -z "${rvm_ruby_tag:-}" && -z "${rvm_ruby_revision:-}" && -z "${rvm_ruby_sha:-}" ]]
then
rvm_ruby_package_name="${rvm_ruby_package_name:-"$rvm_ruby_string"}"
rvm_ruby_package_file="${rvm_ruby_package_file:-"$rvm_ruby_package_name"}"
case "$rvm_ruby_string" in
(ruby-1.8.4*) rvm_archive_extension="${rvm_archive_extension:-tar.gz}" ;;
(ruby-*)
rvm_archive_extension="${rvm_archive_extension:-tar.bz2}" ;;
(*)
rvm_archive_extension="${rvm_archive_extension:-tar.gz}" ;;
esac
case "$rvm_ruby_interpreter" in
(ruby)
rvm_ruby_url="$(__rvm_db
"${rvm_ruby_interpreter}_${rvm_ruby_release_version}.${rvm_ruby_major_version}_url")/$rvm_ruby_package_file.$rvm_archive_ext
ension"
;;
(ree)
rvm_ruby_url="$(__rvm_db
"${rvm_ruby_interpreter}_${rvm_ruby_version}_url")/${rvm_ruby_package_file}.${rvm_archive_extension}"
;;
(jruby)
rvm_ruby_url="$(__rvm_db
"${rvm_ruby_interpreter}_url")/${rvm_ruby_version}/${rvm_ruby_package_file}.${rvm_archive_extension}"
;;
(maglev)
: # Should already be set from selector
;;
(*)
rvm_ruby_url="$(__rvm_db "${rvm_ruby_interpreter}_url")/${rvm_ruby_package_file}.${rvm_archive_extension}"
;;
esac
rvm_log "$rvm_ruby_string - #downloading ${rvm_ruby_package_file}, this may take a while depending on your
connection..."
"$rvm_scripts_path/fetch" "${rvm_ruby_url}"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the source.
return $result
fi
\nHalting the installation."
# Remove the directory if it is empty
( [[ ! -d "${rvm_src_path}/$rvm_ruby_string" ]] || rmdir "${rvm_src_path}/$rvm_ruby_string" 2>/dev/null ) || true
if [[ ! -d "${rvm_src_path}/$rvm_ruby_string" ]]
then
mkdir -p "${rvm_tmp_path:-/tmp}/rvm_src_$$"
case "$rvm_archive_extension" in
tar.gz|tgz)
__rvm_run "extract" \
"$rvm_tar_command xzf \"${rvm_archives_path}/$rvm_ruby_package_file.$rvm_archive_extension\" -C ${rvm_tmp_path:/tmp}/rvm_src_$$ ${rvm_tar_options:-}" \
"$rvm_ruby_string - #extracting $rvm_ruby_package_file to ${rvm_src_path}/$rvm_ruby_string"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to extract the source.
return $result
fi
;;
zip)
\nHalting the installation."
__rvm_run "extract" \
"unzip -q -o ${rvm_archives_path}/$rvm_ruby_package_file -d ${rvm_tmp_path:-/tmp}/rvm_src_$$" \
"$rvm_ruby_string - #extracting $rvm_ruby_package_file to ${rvm_src_path}/$rvm_ruby_string"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to extract $rvm_ruby_package_file. \nHalting the installation."
return $result
fi
;;
tar.bz2)
__rvm_run "extract" \
"$rvm_tar_command xjf ${rvm_archives_path}/$rvm_ruby_package_file.$rvm_archive_extension -C ${rvm_tmp_path:/tmp}/rvm_src_$$ ${rvm_tar_options:-}" \
"$rvm_ruby_string - #extracting $rvm_ruby_package_file to ${rvm_src_path}/$rvm_ruby_string"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to extract the source.
return $result
fi
;;
\nHalting the installation."
*)
rvm_error "Unknown archive format extension '$rvm_archive_extension'.
return 1
;;
\nHalting the installation."
esac
__rvm_rm_rf "${rvm_src_path}/$rvm_ruby_string"
mv "${rvm_tmp_path:-/tmp}/rvm_src_$$/$(builtin cd ${rvm_tmp_path:-/tmp}/rvm_src_$$ ; \ls )" \
"${rvm_src_path}/$rvm_ruby_string"
__rvm_rm_rf "${rvm_tmp_path:-/tmp}/rvm_src_$$"
if [[ -n "${rvm_ruby_name:-""}" && -d "${rvm_src_path}/$(echo $rvm_ruby_string | sed -e 's/-n.*//')" ]] ; then
mv "${rvm_src_path}/$(echo "$rvm_ruby_string" | sed -e 's/-n.*//')" "${rvm_src_path}/$rvm_ruby_string"
fi
rvm_log "$rvm_ruby_string - #extracted to ${rvm_src_path}/$rvm_ruby_string"
else
rvm_log "$rvm_ruby_string - #extracted to ${rvm_src_path}/$rvm_ruby_string (already extracted)"
fi
return 0
else # -head
mkdir -p "${rvm_repos_path}"
true ${rvm_ruby_url:="$rvm_ruby_repo_url"}
if echo "$rvm_ruby_url" | GREP_OPTIONS="" \grep 'git' >/dev/null 2>&1
then # Using a git url.
case "$rvm_ruby_interpreter" in
ruby)
# Determine Branch
if [[ -z "${rvm_ruby_repo_branch:-}" ]]
then
if [[ -n "${rvm_ruby_major_version:-}" ]]
then
if [[ -n "${rvm_ruby_minor_version:-}" ]]
then
rvm_ruby_repo_branch="ruby_1_${rvm_ruby_major_version}_${rvm_ruby_minor_version}"
else
rvm_ruby_repo_branch="ruby_1_${rvm_ruby_major_version}"
fi
else
rvm_ruby_repo_branch="trunk" # NOTE: Ruby Core team maps 'trunk' as HEAD
fi
fi
;;
ree|jruby|maglev|*)
rvm_ruby_repo_branch="${rvm_ruby_repo_branch:-"master"}"
;;
esac
# Clone if repository does not yet exist locally
if [[ ! -d "${rvm_repos_path}/${rvm_ruby_interpreter}/.git" ]]
then
__rvm_rm_rf "${rvm_repos_path}/${rvm_ruby_interpreter}"
rvm_ruby_repo_http_url="${rvm_ruby_repo_url//git:/https:}"
rvm_log "Cloning from $rvm_ruby_repo_url, this may take a while depending on your connection..."
# do not use '--depth 1' - we need to allow getting different commits
git clone "$rvm_ruby_repo_url" "${rvm_repos_path}/${rvm_ruby_interpreter}"
result=$?
if (( result > 0 ))
then
rvm_log "cloning from $rvm_ruby_repo_url failed, now attempting to clone from $rvm_ruby_repo_http_url, this may
take a while depending on your connection..."
git clone "$rvm_ruby_repo_http_url" \
"${rvm_repos_path}/${rvm_ruby_interpreter}"
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch the repository.
return $result
fi
\nHalting the installation."
fi
else
(
cd "${rvm_repos_path}/${rvm_ruby_interpreter}"
typeset current_url
current_url="$(git remote -v | awk '$1=="origin" && $3=="(fetch)" {print $2}')"
[[ "$current_url" == "$rvm_ruby_repo_url" ]] || git remote set-url origin "$rvm_ruby_repo_url"
)
fi
# Use the selected branch.
(
cd "${rvm_repos_path}/${rvm_ruby_interpreter}"
remote="${remote:-origin}"
branch=$(git symbolic-ref -q HEAD 2>/dev/null)
branch=${branch##refs/heads/}
git reset --hard HEAD # Ensure we are in a good state.
git fetch "${remote}" # Download the latest updates locally.
if [[ "$branch" == "${rvm_ruby_repo_branch}" ]]
then
git pull "${remote}" "${rvm_ruby_repo_branch}"
else
case "$(git branch 2>/dev/null)" in
(*[[:space:]]${rvm_ruby_repo_branch}*)
# Not already on the desired branch, but it does exist locally.
git checkout -f "${rvm_ruby_repo_branch}" # Branch is local, checkout
git pull "$remote" "${rvm_ruby_repo_branch}" # Bring local to latest
;;
(*)
# Desired branch does not exist locally.
if git checkout -f -t "${remote}/${rvm_ruby_repo_branch}"
then
true
else
result=$?
rvm_error "Branch $remote/$rvm_ruby_repo_branch not found."
return $result
fi
;;
esac
fi
if [[ -n "${rvm_ruby_tag:-}" ]]
then git checkout -f -q ${rvm_ruby_tag#t} ; fi
return $?
)
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while checking out branch ${rvm_ruby_repo_branch}.
return $result
fi
\nHalting the installation."
__rvm_fetch_from_git_revision_or_sha || return $?
else
if [[ -n "${rvm_ruby_tag:-""}" ]]
then
# TODO: Check if tag v is valid
true "${rvm_ruby_url:="$rvm_ruby_repo_url/tags/$(echo "$rvm_ruby_tag" | sed 's/^t//')"}"
elif [[ -z "${rvm_ruby_version:-""}" && ${rvm_head_flag:-0} -eq 1 ]]
then
true "${rvm_ruby_url:="$rvm_ruby_repo_url/trunk"}"
elif [[ "${rvm_ruby_major_version:-""}" == "9" ]]
then
if [[ -z "${rvm_ruby_minor_version:-""}" ||
"${rvm_ruby_minor_version:-""}" = 3 ]]
then
true "${rvm_ruby_url:="$rvm_ruby_repo_url/trunk"}"
else
true
"${rvm_ruby_url:="$rvm_ruby_repo_url/branches/ruby_${rvm_ruby_release_version}_${rvm_ruby_major_version}_${rvm_ruby_minor_ve
rsion}"}"
fi
elif [[ -z "${rvm_ruby_minor_version:-""}" ||
"${rvm_ruby_major_version:-""}.${rvm_ruby_minor_version:-""}" = "8.8" ]]
then
true "${rvm_ruby_url:="$rvm_ruby_repo_url/branches/ruby_${rvm_ruby_release_version}_${rvm_ruby_major_version}"}"
else
"${rvm_ruby_url:="$rvm_ruby_repo_url/branches/ruby_${rvm_ruby_release_version}_${rvm_ruby_major_version}_${rvm_ruby_minor_ve
rsion}"}"
fi
rvm_rev=""
if [[ -n "${rvm_ruby_revision:-""}" ]]
then
rvm_rev="-$rvm_ruby_revision"
fi
(
builtin cd "${rvm_repos_path}/${rvm_ruby_interpreter}"
if [[ -d "${rvm_repos_path}/${rvm_ruby_interpreter}/.svn" ]]
then
rvm_log "Updating ruby from $rvm_ruby_url"
__rvm_run "svn.switch" "svn switch $rvm_ruby_url"
__rvm_run "svn.update" "svn update"
if [[ -n "${rvm_rev:-""}" ]]
then
rvm_log "Checking out revision ${rvm_rev/-r/-r } from $rvm_ruby_url"
__rvm_run "svn.checkout" "svn update -q ${rvm_rev/-r/-r }"
fi
else
__rvm_rm_rf "${rvm_repos_path}/${rvm_ruby_interpreter}"
__rvm_run "svn.checkout" \
"svn checkout -q ${rvm_rev/-r/-r } $rvm_ruby_url ${rvm_repos_path}/${rvm_ruby_interpreter}" \
"Downloading source from ${rvm_ruby_url}."
fi
)
result=$?
if (( result > 0 ))
then
rvm_error "There has been an error while trying to fetch / update the source.
return $result
fi
fi
rvm_log "Copying from repo to src path..."
__rvm_rm_rf "${rvm_src_path}/$rvm_ruby_string"
cp -R "${rvm_repos_path}/${rvm_ruby_interpreter}" \
"${rvm_src_path}/$rvm_ruby_string"
fi
return ${result:-0}
}
__rvm_check_default()
{
typeset default_ruby_interpreter current_ruby_interpreter
default_ruby_interpreter="$(rvm alias show default 2>/dev/null \
| awk -F"${rvm_gemset_separator:-"@"}" '{print $1}')"
current_ruby_interpreter="$(echo "$rvm_ruby_string" \
| awk -F"${rvm_gemset_separator:-"@"}" '{print $1}')"
if [[ -n "$current_ruby_interpreter" &&
"$current_ruby_interpreter" == "$default_ruby_interpreter" ]]
then
__rvm_run_with_env 'default.restore' 'system' \
'rvm use system --default' 'Removing default ruby interpreter'
fi
return $?
}
__rvm_uninstall_ruby()
{
typeset dir
if (( ${rvm_ruby_selected_flag:=0} == 0 ))
then
__rvm_select
fi
if [[ -n "${rvm_ruby_string:-""}" ]]
then
for dir in "$rvm_rubies_path"
do
if [[ -d "$dir/$rvm_ruby_string" ]]
then
\nHalting the installation."
rvm_log "Removing $dir/$rvm_ruby_string..."
__rvm_rm_rf "$dir/$rvm_ruby_string"
else
rvm_log "$dir/$rvm_ruby_string has already been removed."
fi
done
if [[ -e "${rvm_bin_path}/$rvm_ruby_string" ]]
then
rm -f "${rvm_bin_path}/$rvm_ruby_string"
fi
if [[ -d "${rvm_externals_path}/$rvm_ruby_string" ]]
then
rvm_log "Removing ${rvm_externals_path}/$rvm_ruby_string..."
__rvm_rm_rf "${rvm_externals_path}/$rvm_ruby_string"
fi
__rvm_remove_install_record "$rvm_ruby_string"
__rvm_remove_gemsets
__rvm_check_default
else
rvm_error "Cannot uninstall unknown package '$rvm_ruby_string'"
fi
unset rvm_uninstall_flag
return 0
}
__rvm_remove_ruby()
{
typeset dir
if (( ${rvm_ruby_selected_flag:=0} == 0 ))
then
__rvm_select
fi
if [[ -n "${rvm_ruby_string:-""}" ]]
then
for dir in "${rvm_src_path}" "${rvm_rubies_path}"
do
if [[ -d "$dir/$rvm_ruby_string" ]]
then
rvm_log "Removing $dir/$rvm_ruby_string..."
__rvm_rm_rf "$dir/$rvm_ruby_string"
else
rvm_log "it seems that $dir/$rvm_ruby_string is already non existent."
fi
done
if [[ -e "${rvm_bin_path}/$rvm_ruby_string" ]]
then
rm -f "${rvm_bin_path}/$rvm_ruby_string"
fi
if [[ -d "${rvm_externals_path}/$rvm_ruby_string" ]]
then
rvm_log "Removing ${rvm_externals_path}/$rvm_ruby_string..."
__rvm_rm_rf "${rvm_externals_path}/$rvm_ruby_string"
fi
__rvm_check_default
__rvm_remove_install_record "$rvm_ruby_string"
__rvm_remove_gemsets
__rvm_remove_archives
__rvm_remove_aliases
__rvm_remove_wrappers
__rvm_remove_environments
__rvm_remove_binaries
else
rvm_error "Cannot remove unknown package '$rvm_ruby_string'"
return 1
fi
unset rvm_remove_flag
return 0
}
__rvm_reinstall_ruby()
{
typeset _params
_params=("$@")
__rvm_remove_ruby "${_params[@]}"
__rvm_install_ruby "${_params[@]}"
}
__rvm_remove_gemsets()
{
typeset gemset gemsets
if (( ${rvm_gems_flag:=0} == 1 ))
then
rvm_log "Removing $rvm_ruby_string gemsets..."
gemsets=( $(find -L "${rvm_gems_path:-"$rvm_path/gems"}" -maxdepth 1 "${name_opt}" "${rvm_ruby_string}*" -type d))
for gemset in "${gemsets[@]}"
do
if [[ -d "$gemset" ]]
then
__rvm_rm_rf "$gemset"
fi
done
fi
}
__rvm_remove_wrappers()
{
rvm_log "Removing $rvm_ruby_string wrappers..."
typeset wrapper wrappers
wrappers=($(find "$rvm_wrappers_path" -maxdepth 1 -mindepth 1 -type d "${name_opt}" "*$rvm_ruby_string*" 2>/dev/null))
for wrapper in "${wrappers[@]}"
do
__rvm_rm_rf "$wrapper"
done
return 0
}
__rvm_remove_environments()
{
rvm_log "Removing $rvm_ruby_string environments..."
typeset environments environment
environments=($(find "$rvm_environments_path" -maxdepth 1 -mindepth 1 -type f "${name_opt}" "*$rvm_ruby_string*" ))
for environment in "${environments[@]}"
do
if [[ -e "$environment" ]]
then
__rvm_rm_rf "$environment"
fi
done
return 0
}
__rvm_remove_aliases()
{
rvm_log "Removing $rvm_ruby_string aliases..."
typeset alias_name aliases
aliases=($(awk '/'$rvm_ruby_string'/' "$rvm_path/config/alias" | sed 's/=.*//'))
for alias_name in "${aliases[@]}"
do
# Remove from alias key-value store
"$rvm_scripts_path/alias" delete "$alias_name" >/dev/null 2>&1
done
}
__rvm_remove_archives()
{
if (( ${rvm_archive_flag:=0} == 1 ))
then
rvm_log "Removing $rvm_ruby_string archives..."
rm -f ${rvm_archives_path}/${rvm_ruby_package_file}.*
fi
}
__rvm_remove_binaries()
{
rvm_log "Removing $rvm_ruby_string binaries..."
# Iterate over all binaries and check for symlinked wrappers etc.
typeset binary_name binaries full_binary_path
binaries=($(find "${rvm_bin_path}" -maxdepth 1 -mindepth 1 "${name_opt}" "*$rvm_ruby_string*" ))
for full_binary_path in "${binaries[@]}"
do
if [[ -L "$full_binary_path" ]] &&
"$rvm_scripts_path/match" "$(readlink "$full_binary_path")" "$rvm_ruby_string"
then
rm -f "$full_binary_path"
fi
done ; unset binaries
return 0
}
__rvm_post_install()
{
case "$rvm_ruby_interpreter" in
(jruby|ree|rbx) true ;; #skip
(*)
(( ${#binaries[@]} > 0 )) || binaries=(gem irb erb ri rdoc testrb rake)
;;
esac
if (( ${#binaries[@]} > 0 ))
then
rvm_log "$rvm_ruby_string - adjusting #shebangs for (${binaries[@]})."
for binary in "${binaries[@]}"
do
if
[[ -e "$rvm_ruby_home/bin/$binary" || -e "${rvm_src_path}/$rvm_ruby_string/bin/$binary" ]]
then
if
[[ "${rvm_src_path}/$rvm_ruby_string" != "$rvm_ruby_home" &&
-f "${rvm_src_path}/$rvm_ruby_string/bin/$binary" ]]
then
cp -f "${rvm_src_path}/$rvm_ruby_string/bin/$binary" "$rvm_ruby_home/bin/$binary"
elif
[[ -f "$rvm_ruby_gem_home/bin/$binary" ]]
then
cp -f "$rvm_ruby_gem_home/bin/$binary" "$rvm_ruby_home/bin/$binary"
fi
__rvm_inject_gem_env "$rvm_ruby_home/bin/$binary"
__rvm_inject_ruby_shebang "$rvm_ruby_home/bin/$binary"
chmod +x "$rvm_ruby_home/bin/$binary"
fi
done
fi
binaries=(gem irb erb ri rdoc testrb rake) #reset
# Import the initial gemsets, unless skipped.
if (( ${rvm_skip_gemsets_flag:-0} == 0 ))
then
__rvm_run_with_env "gemsets.initial" "$rvm_ruby_string" \
"'$rvm_scripts_path/gemsets' initial" \
"$rvm_ruby_string - #importing default gemsets ($rvm_gemsets_path/)"
else
rvm_log "Skipped importing default gemsets"
fi
__rvm_irbrc
__rvm_generate_default_docs
}
__rvm_generate_default_docs()
{
if [[ "$rvm_docs_flag" == "1" && "$rvm_ruby_interpreter" != "macruby" ]]
then
__rvm_run_with_env "docs.generate" "$rvm_ruby_string" \
"rvm docs generate-ri" "Attempting to generate ri documentation..."
fi
}
__rvm_inject_ruby_shebang()
{
typeset actual_file
__rvm_actual_file $1
if [[ -f "$actual_file" ]]
then
sed -e '1,1s=.*=#!'"/usr/bin/env ruby=" ${actual_file} > "${actual_file}.new"
mv "${actual_file}.new" "${actual_file}" ; chmod +x "$actual_file"
fi
}
__rvm_inject_gem_env()
{
typeset actual_file string
__rvm_actual_file $1
if [[ -s "$actual_file" ]]
then
if [[ -n "$(head -n 1 "$actual_file" | awk '/[j]*ruby/')" ]]
then
string="ENV['GEM_HOME']=ENV['GEM_HOME'] || '$rvm_ruby_gem_home'\nENV['GEM_PATH']=ENV['GEM_PATH'] ||
'$rvm_ruby_gem_path'\nENV['PATH']='$rvm_ruby_gem_home/bin:$rvm_ruby_global_gems_path/bin:$rvm_ruby_home/bin:' +
ENV['PATH']\n"
elif [[ -n "$(head -n 1 "$actual_file" | awk '/bash/')" ]]
then
string="GEM_HOME=\${GEM_HOME:-'$rvm_ruby_gem_home'}\nGEM_PATH=\${GEM_PATH:'$rvm_ruby_gem_home:$rvm_ruby_global_gems_path'}\nPATH=$rvm_ruby_gem_home/bin:$rvm_ruby_global_gems_path/bin:$rvm_ruby_home/
bin:\$PATH\n"
fi
if [[ -n "$string" ]]
then
awk "NR==2 {print \"$string\"} {print}" "$actual_file" \
> "$actual_file.new"
mv $actual_file.new $actual_file
chmod +x "$actual_file"
fi
fi
return 0
}
__rvm_actual_file()
{
if [[ -L "$1" ]]
then # If the file is a symlink,
actual_file="$(readlink $1)" # read the link target so we can preserve it.
else
actual_file="$1"
fi
return 0
}
__rvm_manage_rubies()
{
typeset manage_result bin_line
manage_result=0
rvm_gemset_name=""
rvm_ruby_selected_flag=0
rvm_ruby_gem_home="${rvm_ruby_gem_home:-""//${rvm_gemset_separator:-"@"}*}"
rvm_ruby_string="${rvm_ruby_string:-""//${rvm_gemset_separator:-"@"}*}"
# Given list of ruby strings.
if [[ -n "${rubies_string:-""}" ]]
then
rubies=(${rubies_string//,/ })
for rvm_ruby_string in "${rubies[@]}"
do
current_ruby_string="$rvm_ruby_string"
rvm_hook="before_install"
source "$rvm_scripts_path/hook"
eval "__rvm_${action}_ruby"
result="$?"
if (( result > 0 && manage_result == 0 ))
then
manage_result="$result"
fi
if (( result == 0 )) && [[ "$action" == "install" ]]
then
__rvm_record_install "$current_ruby_string"
fi
unset current_ruby_string
__rvm_unset_ruby_variables
done
else # all
if [[ "$action" != "install" && "$action" != "remove" &&
"$action" != "uninstall" ]]
then
typeset ruby_string
while read -r ruby_string
do # Keep this on second line damnit!
if [[ -x "$ruby_string" ]]
then
rvm_ruby_string="$ruby_string"
eval "__rvm_${action}_ruby"
result="$?"
if (( result > 0 && manage_result == 0 ))
then
manage_result="$result"
fi
# record as current_manage_string to prevent it being overridden.
if (( result == 0 )) && [[ "$action" == "install" ]]
then
__rvm_record_install "$ruby_string"
fi
__rvm_unset_ruby_variables
fi
done < <(builtin cd "$rvm_rubies_path" ; \
find . -maxdepth 1 -mindepth 1 -type d 2> /dev/null | sed -e 's#./##g')
else
rvm_warn 'Really? '"$action"' all? See "rvm list known" and limit the selection to something more sane please :)'
fi
fi
# TODO: This should return the exit status of the command that got called.
return $manage_result
}
__rvm_record_ruby_configs()
{
for dir in "$rvm_path/rubies/"*
do
string=${dir##*/}
if [[ "${string}" == default ]] ; then continue ; fi
if [[ -x "${rvm_path}/rubies/${string}/bin/ruby" ]]
then
if [[ -s "${rvm_path}/rubies/${string}/config" ]]
then
continue
else
"${rvm_path}/rubies/${string}/bin/ruby" -rrbconfig \
-e 'File.open(RbConfig::CONFIG["prefix"] + "/config","w") { |file| RbConfig::CONFIG.each_pair{|key,value|
file.write("#{key.gsub(/\.|-/,"_")}=\"#{value.gsub("$","\\$")}\"\n")} }' >/dev/null 2>&1
fi
fi
done
}
__rvm_compatibility_flag_configuration()
{
typeset flag
flag="$1"
if ! shift
then
rvm_error "__rvm_compability_flag_configuration requires one param."
return 1
fi
if [[ ${rvm_19_flag:-0} == 1 ]]
then
rvm_configure_flags="${rvm_configure_flags:-} ${flag}1.9"
elif [[ ${rvm_18_flag:-0} == 1 ]]
then
rvm_configure_flags="${rvm_configure_flags:-} ${flag}1.8"
fi
}
1.19. hooks
1.19.1. after_use
#!/usr/bin/env bash
after_use_hooks=($(
find -L "${rvm_path:-"$HOME/.rvm"}/hooks" -iname 'after_use_*' -type f
))
for after_use_hook in "${after_use_hooks[@]}"
do
if [[ -x "${after_use_hook}" ]]
then
__rvm_conditionally_do_with_env . "${after_use_hook}" >&2
fi
done
1.19.2. after_cd
#!/usr/bin/env bash
after_cd_hooks=($(
find -L "${rvm_path:-"$HOME/.rvm"}/hooks" -iname 'after_cd_*' -type f
))
for after_cd_hook in "${after_cd_hooks[@]}"
do
if [[ -x "${after_cd_hook}" ]]
then
__rvm_conditionally_do_with_env . "${after_cd_hook}" >&2
fi
done
1.19.3. after_use_jruby
#!/usr/bin/env bash
. "${rvm_path}/scripts/functions/hooks/jruby"
if [[ "${rvm_ruby_string}" =~ "jruby" ]]
then
jruby_ngserver_start
jruby_options_append "--ng" "${PROJECT_JRUBY_OPTS[@]}"
else
jruby_options_remove "--ng" "${PROJECT_JRUBY_OPTS[@]}"
jruby_clean_project_options
fi
1.19.4. .gitkeep
1.19.5. after_cd_bundler
#!/usr/bin/env bash
BUNDLER_BIN_PATH=""
# see BUNDLE_BIN is set in the current directories .bundle/config
if grep BUNDLE_BIN .bundle/config >/dev/null 2>/dev/null
then
BUNDLER_BIN_PATH=$(grep BUNDLE_BIN .bundle/config | cut -d ' ' -f 2 -)
# Expand the bundler stub path
eval BUNDLER_BIN_PATH=$BUNDLER_BIN_PATH
if [[ $path[1] == $BUNDLER_BIN_PATH ]]
then
# Already there
echo Already on path
else
if [[ "${BUNDLER_BIN_PATH}" =~ "^$PWD" ]]
then
# Prompt the user before adding a bin directory in the current (project) directory to the path
echo -n "The bundler binstubs directory is in the current directory, this may be unsafe. Are you sure you want to add
it to the path(Y/N)? "
trusted=0
while (( ! trusted ));do
printf "%s" ' Yes or No: [y/N]? '
read response
value="$(echo -n "${response}" | tr '[[:upper:]]' '[[:lower:]]' | __rvm_strip)"
case "${value:-n}" in
y|yes)
trusted=1
;;
n|no)
break
;;
esac
done
if (( trusted )); then
export PATH=$BUNDLER_BIN_PATH:$PATH
export LAST_BUNDLER_BIN_PATH=$BUNDLER_BIN_PATH
fi
else
export PATH=$BUNDLER_BIN_PATH:$PATH
export LAST_BUNDLER_BIN_PATH=$BUNDLER_BIN_PATH
fi
fi
else
# There is no BUNDLE_BIN setting
if [[ -n "${LAST_BUNDLER_BIN_PATH}" ]]
then
export PATH
PATH=":${PATH}:"
PATH="${PATH//:${LAST_BUNDLER_BIN_PATH}:/:}"
PATH="${PATH//::/:}"
PATH="${PATH#:}"
PATH="${PATH%:}"
fi
fi
1.19.6. after_use_jruby_opts
#!/usr/bin/env bash
. "${rvm_path}/scripts/functions/hooks/jruby"
if [[ "${rvm_ruby_string}" =~ "jruby" ]]
then
jruby_options_append "${PROJECT_JRUBY_OPTS[@]}"
else
jruby_options_remove "${PROJECT_JRUBY_OPTS[@]}"
jruby_clean_project_options
fi
1.19.7. after_install_codesign
#!/usr/bin/env bash
####################################################
# Signing compiled ruby for OSX, for details visit #
# https://rvm.io/rubies/codesign/
#
####################################################
# Go to subprocess so we can use returns and 'use' ruby temporarily
(
# Require Mac OS
[[ "$(/usr/bin/uname -s 2>/dev/null)" == Darwin ]] || return 1
# Require 10.7 - FIXME: Should be 10.7 or newer.
[[ "$(/usr/bin/sw_vers -productVersion)" == 10.7* ]] || return 2
# Require rvm_codesign_identity
[[ -n "${rvm_codesign_identity:-}" ]] || {
rvm_warn "'rvm_codesign_identity' is not set, please set it in ~/.rvmrc"
return 3
}
# Require using ruby - btw this should not happen
__rvm_use || {
rvm_warn "can not use ruby which was just installed ... so can not sign it neither"
return 4
}
# Find out ruby executable to sign
typeset _ruby_name
_ruby_name="$(sed -n '/^ruby_install_name=/ {s/ruby_install_name="\(.*\)"/\1/; p; };' "$MY_RUBY_HOME/config" )"
# Sign ruby
/usr/bin/codesign -f -s "${rvm_codesign_identity}" "$(which "${_ruby_name}")"
)
1.20. man
1.20.1. man1
1.20.1.1. rvm.1
'\" t
.\"
Title: rvm
.\"
Author: [FIXME: author] [see http://docbook.sf.net/el/author]
.\" Generator: DocBook XSL Stylesheets v1.75.2 <http://docbook.sf.net/>
.\"
Date: 07/16/2010
.\"
Manual: [FIXME: manual]
.\"
Source: [FIXME: source]
.\" Language: English
.\"
.TH "RVM" "1" "07/16/2010" "[FIXME: source]" "[FIXME: manual]"
.\" ----------------------------------------------------------------.\" * set default formatting
.\" ----------------------------------------------------------------.\" disable hyphenation
.nh
.\" disable justification (adjust text to left margin only)
.ad l
.\" ----------------------------------------------------------------.\" * MAIN CONTENT STARTS HERE *
.\" ----------------------------------------------------------------.SH "NAME"
rvm \- The Ruby Version Manager
.SH "SYNOPSIS"
.sp
\fBrvm\fR [\fIFLAGS\fR] [\fIOPTIONS\fR] \fIACTION\fR [\fIIMPLEMENTATION\fR[,\fIIMPLEMENTATION\fR[,\fI\&...\fR]]
.SH "DESCRIPTION"
.sp
RVM is a command line tool which allows us to easily install, manage and work with multiple ruby environments from
interpreters to sets of gems\&.
.SH "FLAGS"
.PP
\fB\-\-head\fR
.RS 4
with update, updates rvm to git head version\&.
.RE
.PP
\fB\-\-rubygems\fR
.RS 4
with update, updates rubygems for selected ruby
.RE
.PP
\fB\-\-default\fR
.RS 4
with ruby select, sets a default ruby for new shells\&.
.RE
.PP
\fB\-\-debug\fR
.RS 4
Toggle debug mode on for very verbose output\&.
.RE
.PP
\fB\-\-trace\fR
.RS 4
Toggle trace mode on to see EVERYTHING rvm is doing\&.
.RE
.PP
\fB\-\-force\fR
.RS 4
Force install, removes old install & source before install\&.
.RE
.PP
\fB\-\-summary\fR
.RS 4
Used with rubydo to print out a summary of the commands run\&.
.RE
.PP
\fB\-\-latest\fR
.RS 4
with gemset \-\-dump skips version strings for latest gem\&.
.RE
.PP
\fB\-\-gems\fR
.RS 4
with uninstall/remove removes gems with the interpreter\&.
.RE
.PP
\fB\-\-docs\fR
.RS 4
with install, attempt to generate ri after installation\&.
.RE
.PP
\fB\-\-reconfigure\fR
.RS 4
Force \&./configure on install even if Makefile already exists\&.
.RE
.SH "OPTIONS"
.PP
\fB\-v, \-\-version\fR
.RS 4
Emit rvm version loaded for current shell\&.
.RE
.PP
\fB\-l, \-\-level\fR
.RS 4
patch level to use with rvm use / install
.RE
.PP
\fB\-\-bin\fR
.RS 4
path for binaries to be placed (\fI~/\&.rvm/bin/\fR)
.RE
.PP
\fB\-\-source\fR
.RS 4
src directory to use (\fI~/\&.rvm/src/\fR)
.RE
.PP
\fB\-\-archives\fR
.RS 4
directory for downladed files (\fI~/\&.rvm/archives/\fR)
.RE
.PP
\fB\-S\fR
.RS 4
Specify a script file to attempt to load and run (rubydo)\&.
.RE
.PP
\fB\-e\fR
.RS 4
Execute code from the command line\&.
.RE
.PP
\fB\-G\fR
.RS 4
root gem path to use
.RE
.PP
\fB\-\-gems\fR
.RS 4
Used to set the
\fIgems_flag\fR, use with
\fIremove\fR
to remove gems\&.
.RE
.PP
\fB\-\-archive\fR
.RS 4
Used to set the
\fIarchive_flag\fR, use with
\fIremove\fR
to remove archive\&.
.RE
.PP
\fB\-\-patch\fR, \fB\-\-patches\fR
.RS 4
With any ruby build from source, allows you to specify patch paths and patch names to be applied prior to building\&. Values
should be a relative / absolute path to a patch or the name of known patch / patchset\&. Optionally, paths or names may be
followed by
\fI%someinteger\fR
\- e\&.g\&.
\fI\-\-patches mypatch%2\fR
\- where the number following the % specifies the value of the \-p argument to patch, defaulting to two\&.
.RE
.PP
\fB\-C, \-\-configure\fR
.RS 4
custom configure options\&. If you need to pass several configure options then append them comma separated:
\fI\-C \-\-\&...,\-\-\&...,\-\-\&...\fR\&.
.RE
.PP
\fB\-\-nice\fR
.RS 4
process niceness (for slow computers, default 0)
.RE
.PP
\fB\-\-ree\-options\fR
.RS 4
Options passed directly to ree\(cqs
\fI\&./installer\fR
on the command line\&.
.RE
.SH "ACTIONS"
.PP
\fBusage\fR
.RS 4
Show this usage information\&.
.RE
.PP
\fBversion\fR
.RS 4
Show the rvm version installed in rvm_path\&.
.RE
.PP
\fBuse\fR
.RS 4
Setup current shell to use a specific ruby version\&.
.RE
.PP
\fBreload\fR
.RS 4
Reload rvm source itself (useful after changing rvm source)\&.
.RE
.PP
\fBdo\fR
.RS 4
Executes the command against either all or a listed subset of rubies. eg. rvm do gem --version ; rvm 1.8.7,1.9.2 do rake -version
.RE
.PP
\fBenv\fR
.RS 4
Displays information about an environment specified but the given ruby string\&. Useful for getting a sourceable path or an
evaluatable set of shell variable declarations\&.
.RE
.PP
\fBimplode\fR
.RS 4
(seppuku) removes the rvm installation completely\&. This means everything in $rvm_path (\fI~/\&.rvm\fR)\&. This does not
touch your profiles. However, this means that you must manually clean up your profiles and remove the lines which source
RVM.
\fIscripts/rvm\fR\&.
.RE
.PP
\fBupdate\fR
.RS 4
Upgrades rvm to the latest version\&. (If you experience bugs try this first with \-\-head)\&.
.RE
.PP
\fBget\fR
.RS 4
RVM get will 'get' the version you specify. This must be one of latest or head\&. With no arguments the rvm get help section
will be shown.\&.
.RE
.PP
\fBreset\fR
.RS 4
Remove current and stored default & system settings\&. (If you experience odd behavior try this second)\&.
.RE
.PP
\fBinfo\fR
.RS 4
Show the
\fBcurrent\fR
environment information for current ruby\&.
.RE
.PP
\fBdebug\fR
.RS 4
Show info plus additional information for common issues\&.
.RE
.PP
\fBinstall\fR
.RS 4
Install one or many ruby versions\&.
http://rvm\&.io/rubies/installing/
.RE
.PP
\fBuninstall\fR
.RS 4
Uninstall one or many ruby versions, leaves their sources\&.
.RE
.PP
\fBremove\fR
.RS 4
Uninstall one or many ruby versions and remove their sources\&.
.RE
.PP
\fBwrapper\fR
.RS 4
Generates a set of wrapper executables for a given ruby with the specified ruby and gemset combination\&. Used under the
hood for passenger support and the like\&.
.RE
.PP
\fBruby\fR
.RS 4
Runs a named ruby file against specified and/or all rubies\&.
.RE
.PP
\fBgem\fR
.RS 4
Runs a gem command using selected ruby\(cqs
\fIgem\fR\&.
.RE
.PP
\fBrake\fR
.RS 4
Runs a rake task against specified and/or all rubies\&.
.RE
.PP
\fBtests\fR
.RS 4
Runs
\fIrake test\fR
across selected ruby versions\&.
.RE
.PP
\fBspecs\fR
.RS 4
Runs
\fIrake spec\fR
across selected ruby versions\&.
.RE
.PP
\fBmonitor\fR
.RS 4
Monitor cwd for testing, run
\fIrake {spec,test}\fR
on changes\&.
.RE
.PP
\fBgemset\fR
.RS 4
gemsets:
http://rvm\&.io/gemsets/
.RE
.PP
\fBgemdir\fR
.RS 4
Display the path to the current gem directory (\fI$GEM_HOME\fR)\&.
.RE
.PP
\fBsrcdir\fR
.RS 4
Display the path to rvm source directory (may be yanked)\&.
.RE
.PP
\fBfetch\fR
.RS 4
Performs an archive / src fetch only of the selected ruby\&.
.RE
.PP
\fBlist\fR
.RS 4
Show currently installed rubies, interactive output\&.
http://rvm\&.io/rubies/list/
.RE
.PP
\fBpackage\fR
.RS 4
Install a dependency package {readline,iconv,zlib,openssl}\&.
http://rvm\&.io/packages/
.RE
.PP
\fBrequirements\fR
.RS 4
Show additional OS specific dependencies/requirements for building various rubies.
.RE
.PP
\fBnotes\fR
.RS 4
Display notes. Operating system specifics are now under 'requirements'\&.
.RE
.SH "IMPLEMENTATION"
.PP
\fBruby\fR
.RS 4
MRI/YARV Ruby (The Gold Standard) {1\&.8\&.6,1\&.8\&.7,1\&.9\&.1,1\&.9\&.2\&...}
.RE
.PP
\fBjruby\fR
.RS 4
JRuby, Ruby interpreter on the Java Virtual Machine\&.
.RE
.PP
\fBrbx\fR
.RS 4
Rubinius
.RE
.PP
\fBree\fR
.RS 4
Ruby Enterprise Edition, MRI Ruby with several custom patches for performance, stability, and memory\&.
.RE
.PP
\fBmacruby\fR
.RS 4
MacRuby, insanely fast, can make real apps (Mac OS X Only)\&.
.RE
.PP
\fBmaglev\fR
.RS 4
GemStone Ruby, awesome persistent ruby object store\&.
.RE
.PP
\fBironruby\fR
.RS 4
IronRuby, NOT supported yet\&. Looking for volunteers to help\&.
.RE
.PP
\fBsystem\fR
.RS 4
Use the system ruby (eg\&. pre\-rvm state)\&.
.RE
.PP
\fBdefault\fR
.RS 4
Use rvm set default ruby and system if it hasn\(cqt been set\&.
http://rvm\&.io/rubies/default/
.RE
.SH "RESOURCES"
.sp
Main web site
.sp
Online issue\-tracker
.SH "COPYING"
.sp
Copyright (c) 2009 Wayne E\&. Seguin
.sp
See LICENCE file for details\&.
1.20.1.2. rvm.1.gz
UnSupported Binary
1.21. vboxtest
1.21.1. test_suite.sh
#!/bin/bash
############################################################################
cd "${0%/$(basename $0)}/.."
RVM_PROJECT_DIR="$(pwd)"
rvm_path=${RVM_PATH:-$RVM_PROJECT_DIR/rvm-test}
results_file=${RESULTS_FILE:-results}
messages_file=${MESSAGES_FILE:-messages}
usage="usage: %s [-P RVM_PATH] [-R RESULTS_FILE] [-M MESSAGES_FILE] [-h]\n"
option="
%s
%s\n"
while getopts "P:IR:M:h" opt
do
case $opt in
P ) rvm_path=$OPTARG ;;
R ) results_file=$OPTARG ;;
M ) messages_file=$OPTARG ;;
h ) printf "$usage" $0
printf "$option" "-P" "the rvm path"
printf "$option" "-I" "reinstall rvm"
printf "$option" "-R" "results file"
printf "$option" "-M" "messages file"
printf "$option" "-h" "prints this help"
exit 0 ;;
\? ) printf "$usage" $0
exit 2 ;;
esac
done
shift $(($OPTIND - 1))
############################################################################
#
# RVM Setup
#
export RVM_PROJECT_DIR
export rvm_path
./install > /dev/null
#
#
#
Run the test cases
echo "Started on $(hostname)"
START_TIME=$SECONDS
# A portable and efficient way of running these tests with find (see
# http://content.hccfl.edu/pollock/unix/findcmd.htm#exec)
find "$(pwd)/vboxtest/test" -name '*_test.sh' -type f -exec sh -c '
for test_case in "$@"
do "$test_case"
done
' X '{}' + 2>>"$messages_file" | tee -a "$results_file"
END_TIME=$SECONDS
echo
echo "Finished in $(($END_TIME - $START_TIME))s"
if [ -f "$messages_file" ] && [ -f "$results_file" ]
then
# A helper function to count the number of occurrences of a character in a string.
count_char () {
grep -o "$1" "$2" | wc -l | tr -d " "
}
echo
cat "$messages_file"
echo "$(count_char "\." "$results_file") pass, $(count_char "F" "$results_file") fail"
rm "$messages_file" "$results_file"
fi
1.21.2. test_helper.sh
#
#
#
#
Defines assertions and other functions needed
to run the tests.
flunk () {
echo "[$TEST_CASE:$lineno] $TEST_NAME
$1
" 1>&2
exit 1
}
assert_status_equal () {
expected=$1; actual=$2; lineno=$3
if [ $actual -ne $expected ]
then
flunk "expected exit status $expected but was $actual"
fi
}
assert_output_equal () {
expected=$(cat); actual=$1; lineno=$2
if [ "$actual" != "$expected" ]
then
echo "$expected" > "$0_$2_expected.txt"
echo "$actual"
> "$0_$2_actual.txt"
flunk "unequal stdout:
$(diff "$0_$2_expected.txt" "$0_$2_actual.txt")"
rm "$0_$2_expected.txt" "$0_$2_actual.txt"
return 1
fi
}
assert_equal () {
assert_status_equal $1 $? $3 &&
assert_output_equal "$2" $3
}
run_test_case () {
if [ "$TEST_NAME" = "" ]
then
for test_name in $(grep -oE "^ *${NAME:-test_\w+} +\(\)" "$1" | tr -d " ()")
do
if TEST_NAME="$test_name" "$1"
then printf '.'
else printf 'F'
fi
done
else
"$TEST_NAME"
fi
}
#
# RVM-specific helpers
#
initialize_rvm () {
source "$rvm_path/scripts/rvm"
__rvm_cleanse_variables
__rvm_load_rvmrc
__rvm_initialize
}
1.21.3. test
1.21.3.1. unit
1.21.3.1.1. utility_test.sh
#!/usr/bin/env bash
########################################################################
TEST_CASE=$(basename "$0")
########################################################################
. ${0%/$TEST_CASE}/../../test_helper.sh
initialize_rvm
test_match_exits_zero_if_input_matches_the_pattern () {
match "a" "a"
assert_status_equal 0 $? $LINENO
match "snark" "a"
assert_status_equal 0 $? $LINENO
match "snark" "^s"
assert_status_equal 0 $? $LINENO
match "snark" "k$"
assert_status_equal 0 $? $LINENO
match "snark" "s$"
assert_status_equal 1 $? $LINENO
match "snark" "^k"
assert_status_equal 1 $? $LINENO
match "1.9.1" "[0-9]\.[0-9]*"
assert_status_equal 0 $? $LINENO
match "snark.rb" "*\.rb$"
assert_status_equal 0 $? $LINENO
match "snark.gems" "*\.gems$"
assert_status_equal 0 $? $LINENO
match "snark.gem" "*\.gem$"
assert_status_equal 0 $? $LINENO
match "1.9.1${rvm_gemset_separator:-"@"}snark" "*${rvm_gemset_separator:-"@"}*"
assert_status_equal 0 $? $LINENO
match "1.9.1" "*${rvm_gemset_separator:-"@"}*"
assert_status_equal 1 $? $LINENO
}
run_test_case "$0"
1.22. examples
1.22.1. rvmrc
#
#
#
#
#
#
#
#
#
Example ~/.rvmrc file.
This file shows some examples of setting defaults to your own tastes.
If you wish to adjust the default ruby interpreter/version/patchlevel
settings they can be found in the $rvm_path/config/db file.
Beware that currently that file is overwritten on install so
back it up if you change anything.
# rvm Path
#
This is where rvm installs and manages everything in by default.
#
#export rvm_path="$HOME/.rvm"
# Source Path
#
This is where rvm extracts to for compiling & installing.
#
#export rvm_source_path="${rvm_path}/src"
# Log Path
#
This is where rvm logs all of it's actions to
#
(not including the 'do' actions)
#
#export rvm_log_path="${rvm_path}/log"
# Bin Path
#
This is where rvm places all of it's executable/wrapper scripts.
#export rvm_bin_path="${rvm_path}/bin"
# Gem Path
#
This is where rvm installs all gems to for each ruby
#
interpreter/version%gemset
#
#export rvm_gems_path="$rvm_path/gems"
# Gem Options
#
These options are passed to the 'gem' command in a RVM environment.
#
#export rvm_gem_options="--no-rdoc --no-ri"
# Temp Path
#
This is where rvm stores all of its temporary files.
#
#export rvm_tmp_path="${rvm_tmp_path:-"$rvm_path/tmp"}"
# Install On Use Flag
# Install rubies when used if are not installed.
#
#
#export rvm_install_on_use_flag=1
# Gemset Create on use Flag
# This will create a gemset when the gemset is used if it does not exist
#
# export rvm_gemset_create_on_use_flag=1
# Make Flags, I have 8 cpu's so I might use 7 make threads:
#
#export rvm_make_flags="-j7"
#
#
#
#
#
#
#
Source a .rvmrc file in a directory after changing to it, if it exists.
To disable this fature, set in root/home .rvmrc file:
export rvm_project_rvmrc=0
Or don't even bother sourcing rvm, it *is* optional. Always has been, you can
instead add $rvm_path/bin to your PATH and use --default to switch...
# Automatically trust project .rvmrc files
#
# export rvm_trust_rvmrcs_flag=1
# Always trust an rvmrc, even if it's contents change.
# CAUTION: Can be dangerous / security risk. Only use this feature if you know
#
what you are doing / accept the implications :)
#
# export rvm_always_trust_rvmrc_flag
#
#
#
#
#
Specify RBXOPT enviroment settings that should always be set when calling
Rubinius scripts. For example, to always run the agent when running from
an Rubinius environment, set the value to '-Xagent'
export rvm_rbx_opt
# Disable automatic system configuration of RVM via /etc/profile.d/rvm.sh:
#
# export rvm_etc_profile_flag=0
#
# Add configure flags for builds
#
# export rvm_configure_flags="--with-openssl-dir=$rvm_path/usr --with-readline-dir=$rvm_path/usr"
#
1.23. help
1.23.1. color
RVM will automatically use colors when it is possible.
To overwrite use command line parameter --color=no or --color=force.
It is also possible to set it with variable in ~/.rvmrc:
rvm_pretty_print_flag=[no|auto|force]
To change default colors use following variables in ~/.rvmrc:
rvm_error_color=red
rvm_warn_color=yellow
rvm_debug_color=magenta
rvm_notify_color=green
Available colors are:
black red green yellow blue magenta cyan white default
You can add emphasis to the color using bold/offbold.
It is also possible to change background color:
bblack bred bgreen byellow bblue bmagenta bcyan bwhite bdefault
On some terminals like xterm ( echo $TERM ) the bold and background colors give the same effect.
Use commas to put multiple definitions in one color. You can mix color, bold and background in one definition.
Specifying multiple colors/bold/background definitions will use last defined.
Using bold in one definition requires resetting it in others with offbold.
Using background in one definition requires resetting it in others with bdefault.
Example:
$ cat ~/.rvmrc
rvm_error_color=bold,red
rvm_warn_color=bold,yellow
rvm_debug_color=offbold,magenta
rvm_notify_color=offbold,green
1.23.2. implode
1.23.3. use
∴ rvm use [ruby-string]
Setup current shell to use a specific ruby version.
For a list of currently installed ruby string please run
∴ rvm list
To create a gemset if it does not already exist:
∴ rvm --create 1.9.2@funky
For creating a project .rvmrc file - From within the app's root_dir:
∴ rvm --rvmrc 1.9.2@funky
Above commands can be also combined to do it all in one pass:
∴ rvm --rvmrc --create use 1.9.2@funky
Using /home/mpapis/.rvm/gems/ruby-1.9.2-p290 with gemset funky
Do not forget to check the generated .rvmrc file - it contains many useful
comments. Note you must still 'rvm rvmrc trust' the newly created .rvmrc
Please see documentation for further information:
https://rvm.io/rvm/basics
Also, you can combine the new flags --ruby-version and --version-conf
∴ rvm --create --ruby-version use 1.9.2@funky
Using /home/mpapis/.rvm/gems/ruby-1.9.2-p290 with gemset funky
∴ rvm --create --versions-conf use 1.9.2@funky
Using /home/mpapis/.rvm/gems/ruby-1.9.2-p290 with gemset funky
These files do not need to be trusted, however, if a .rvmrc file
exists, it will override the use of .ruby-version or .versions.conf!
Please see the documentation for further information:
https://rvm.io/workflow/projects#ruby-versions
1.23.4. reset
1.23.5. uninstall
∴ rvm uninstall [ruby-string[,ruby-string[,...]]]
Uninstall one or many ruby versions, but leave their sources.
For a list of currently installed ruby string please run
rvm list
Please see documentation for further information:
https://rvm.io/rubies/removing/
1.23.6. do
∴ rvm all do some-command
Executes arbitrary commands against rvm set operations. If given a set that
matches a single ruby command, it will exec the command directly without printing
out extra rvm information.
Examples:
To execute 'ruby -v' against all installed rubies and aliases, you would run:
∴ rvm all do ruby -v
If you want to execute it against a specific ruby (without extra logging
/ data printed by rvm as is done with normal set operations), you can instead do:
∴ rvm ree do ruby -v
Since it is a set operation, normal ruby specifiers will work. As an example, to run
it against 1.9.2 and 1.8.7 you would run:
∴ rvm 1.9.2,1.8.7 do ruby -v
Or, to execute 'gem env' against all gemsets:
∴ rvm --with-rubies all-gemsets do gem env
To execute 'which ruby' in the current directory, loading a .rvmrc and falling back
to the default ruby:
∴ rvm --with-rubies default-with-rvmrc do which ruby
For more information, refer to the rvm set operations.
1.23.7. monitor
TODO
1.23.8. get
Usage:
rvm get {stable|latest|latest-x.y|x.y.z|head|master|branch|help} [--auto]
Options:
stable
- install the latest RVM stable release
latest
- install the latest RVM release
latest-x.y
- install the latest RVM release matching the x.y* pattern
x.y.z
- install a specific RVM release
head
master
- install the latest RVM development version
--auto
- automatically update shell profile files.
help
- Output this message.
Branches:
branch
branch
branch
branch
<branch>
/<branch>
<repo>/
<repo>/<branch>
Defaults:
branch: master
repo:
wayneeseguin
Examples:
rvm get branch shoes
# will fetch branch shoes from wayneeseguin/rvm repo
rvm get branch mpapis/ # will fetch branch master from mpapis/rvm
repo
1.23.9. docs
∴ rvm docs {generate,generate-ri,generate-rdoc}
Generates ri and / or rdoc documentation for the current ruby.
If you have the hanna gem installed, rdoc generation should automatically use it.
Alternatively, you can pass the --docs flag to automatically call 'rvm docs generate'
as part of the install process.
Examples:
∴ rvm docs generate
Generates both ri and rdoc documentation for the current ruby.
∴ rvm docs generate-ri
Generates only ri documentation for the current ruby.
∴ rvm docs generate-rdoc
Generates only rdoc documentation for the current ruby.
1.23.10. cron
Usage:
1. Add/Remove ruby variables to cron:
rvm cron {setup|remove}
2. Manage rvm on single command level
rvm cron command <"schedule"> <command> <params...>
Example 1 set one ruby for all cron jobs:
cd /project/dir
rvm cron setup
crontab -e
# go to project dir, or `rvm use ...`
# initialize cron with ruby settings
# add tasks to cron
After project ruby changes:
rvm cron setup
# update cron with new ruby settings
Example 2 add single job using current dir for rvm:
cd /project/dir # go to project dir, or `rvm use ...`
rvm cron command "@daily" rake calculate:stats
Refer to `man 5 crontab` for definitions of time/date, examples:
"*/5 * * * *"
"@hourly"
"* */4 * * *"
"0 6 * * *"
"0 7 * * 5"
-
Every 5 minutes
Once an hour
Every 4 hours
Everyday at 6am
Every Friday at 7am
NOTE! Do not forget to set notification email in `crontab -e`:
[email protected]
1.23.11. current
∴ rvm current
Print the current Ruby version and the name of any gemset being used.
1.23.12. list
1.23.13. install
Usage
rvm install [ruby-string]
For a partial list of valid ruby strings please run
rvm list known
For MRI Rubies you may pass configuration parameters in one of two ways:
rvm install 1.9.2 --with-iconv-dir=$HOME/.rvm --without-readline
and/or
rvm install 1.9.2 -C --with-iconv-dir=$HOME/.rvm,--without-readline
To do dirty installation using the same sources use:
rvm install --force 1.9.2
To do clean installation use:
rvm reinstall 1.9.2
Please see the documentation for further information:
https://rvm.io/rubies/installing/
1.23.14. ruby
'rvm ruby'
Given:
∴ cat test.rb
puts "patchlevel: #{RUBY_PATCHLEVEL}, release_date: #{RUBY_RELEASE_DATE}, ruby_version: #{RUBY_VERSION}, ruby_platform:
#{RUBY_PLATFORM}"
∴ rvm list
ruby:
ruby-1.8.6-p383 [x86_64]
ruby-1.8.7-p174 [x86_64]
ruby-1.9.1-head [x86_64]
=> ruby-1.9.1-p243 [x86_64]
ruby-1.9.2-preview3 [x86_64]
jruby:
jruby-1.3.1 [x86_64]
jruby-1.4.0RC3 [x86_64]
ree:
ree-1.8.6-20090610 [x86_64]
ree-1.8.7-20090928 [x86_64]
We can run the ruby program 'test.rb' against all versions of ruby installed by RVM very simply:
∴ rvm all do ruby test.rb
jruby-1.3.1: jruby 1.3.1 (ruby 1.8.6p287) (2009-06-15 2fd6c3d) (Java HotSpot(TM) 64-Bit Server VM 1.6.0_15) [x86_64java]
patchlevel: 287, release_date: 2009-06-15, ruby_version: 1.8.6, ruby_platform: java
jruby-1.4.0RC3: jruby 1.4.0RC3 (ruby 1.8.7 patchlevel 174) (2009-09-30 80c263b) (Java HotSpot(TM) 64-Bit Server VM
1.6.0_15) [x86_64-java]
patchlevel: 174, release_date: 2009-09-30, ruby_version: 1.8.7, ruby_platform: java
ree-1.8.6-20090610: ruby 1.8.6 (2008-08-11 patchlevel 287) [i686-darwin10.0.0] Ruby Enterprise Edition 20090610
patchlevel: 287, release_date: 2008-08-11, ruby_version: 1.8.6, ruby_platform: i686-darwin10.0.0
ree-1.8.7-20090928: ruby 1.8.7 (2009-06-12 patchlevel 174) [i686-darwin10.0.0], MBARI 0x6770, Ruby Enterprise Edition
20090928
patchlevel: 174, release_date: 2009-06-12, ruby_version: 1.8.7, ruby_platform: i686-darwin10.0.0
ruby-1.8.6-p383: ruby 1.8.6 (2009-08-04 patchlevel 383) [i686-darwin10.0.0]
patchlevel: 383, release_date: 2009-08-04, ruby_version: 1.8.6, ruby_platform: i686-darwin10.0.0
ruby-1.8.7-p174: ruby 1.8.7 (2009-06-12 patchlevel 174) [i686-darwin10.0.0]
patchlevel: 174, release_date: 2009-06-12, ruby_version: 1.8.7, ruby_platform: i686-darwin10.0.0
ruby-1.9.1-head: ruby 1.9.2dev (2009-09-26 trunk 25103) [x86_64-darwin10.0.0]
patchlevel: -1, release_date: 2009-09-26, ruby_version: 1.9.2, ruby_platform: x86_64-darwin10.0.0
ruby-1.9.1-p243: ruby 1.9.1p243 (2009-07-16 revision 24175) [i386-darwin10.0.0]
patchlevel: 243, release_date: 2009-07-16, ruby_version: 1.9.1, ruby_platform: i386-darwin10.0.0
ruby-1.9.2-preview3: ruby 1.9.2dev (2010-05-31 revision 28117) [x86_64-darwin10.3.0]
patchlevel: -1, release_date: 2010-05-31, ruby_version: 1.9.2, ruby_platform: x86_64-darwin10.3.0
ree-1.8.7-20090928: ruby 1.8.7 (2009-06-12 patchlevel 174) [i686-darwin10.0.0], MBARI 0x6770, Ruby Enterprise Edition
20090928
patchlevel: 174, release_date: 2009-06-12, ruby_version: 1.8.7, ruby_platform: i686-darwin10.0.0
You can also restrict the above to a subset of named top level selections:
∴ rvm 1.9.1,1.8.7,jruby do ruby test.rb
...
1.23.15. srcdir
1.23.16. pkg
1.23.17. notes
1.23.18. rvmrc
∴ rvm rvmrc {trust,untrust,trusted,load,reset} [optional-path]
∴ rvm rvmrc create {ruby-version} [--rvmrc|--ruby-version|--versions-conf]
Tools for dealing with and loading the rvmrc trust for a given directory.
All actions take an optional path to a directory to check.
Examples:
To check the status of ~/My/project, you would run:
∴ rvm rvmrc trusted ~/My/project
Or, more conventionally,
∴ cd ~/My/project && rvm rvmrc trusted
To manually set it as trusted:
∴ rvm rvmrc trust ~/My/project
Or, to reset the trust and force a prompt:
∴ rvm rvmrc reset ~/My/project
∴ rvm rvmrc reset all
Finally, to load the rvmrc in a directory, you would run:
∴ rvm rvmrc load ~/My/project
Or,
∴ cd ~/My/project && rvm rvmrc load
Note that this replaces 'rvm load-rvmrc'. Note that load implicity trusts the
rvmrc, even if it is set to untrusted.
Creating project rvmrc files can easily be done with the following command:
∴ rvm --rvmrc --create use 1.9.2@funky
Or for scripting,
∴ rvm rvmrc create 1.9.2@funky
Above command will create both the gemset 'funky', and a project rvmrc file in the current directory.
From RVM 1.11.0 new project files are available.
- ∴ rvm rvmrc create 1.9.2@funky --ruby-version
- ∴ rvm rvmrc create 1.9.2@funky --versions-conf
- https://rvm.io/workflow/projects/#ruby-versions
They do not require trusting:
1.23.19. debug
Debug
TODO
Documentation:
TODO
1.23.20. benchmark
Benchmark
If you have a bit of code that you would like to benchmark, across several versions of ruby all at once, you can now do this
easily with RVM. Given:
∴ cat increment.rb
y=0
1000.times do |x|
y = x + 1
end
We can benchmark this code against multiple ruby versions very easily:
∴ rvm 1.8.6,1.8.7,1.9.1,ree benchmark increment.rb
Documentation:
https://rvm.io/set/benchmark/
1.23.21. migrate
∴ rvm migrate from to
Efficiently moves the gems from one ruby to another.
Like 'rvm gemset copy' but removes the gems from the source
ruby afterwards and runs it against all gemsets for a given
ruby.
Examples:
To migrate all gemsets from rc2 of 1.9.2 to the first release, p0,
you would run:
∴ rvm migrate 1.9.2-rc2 1.9.2-p0
1.23.22. gemdir
1.23.23. alt.md
# RVM is not the only Ruby enVironment Manager
Other implementations allowing to switch ruby environment:
-
https://github.com/vertiginous/pik (Windows)
https://github.com/kwatch/versionswitcher
https://github.com/wilmoore/ruby-version
https://github.com/sam/rb-switch
https://github.com/jayferd/ry
https://github.com/niw/rubies
https://github.com/hmans/rbfu
https://github.com/nkryptic/sandbox
https://github.com/sstephenson/rbenv
https://github.com/cpetschnig/switch-ruby
https://github.com/mugenken/p5-Ruby-VersionManager (Perl!)
http://zentest.rubyforge.org/ZenTest/Multiruby.html (Ruby)
http://www.dribin.org/dave/blog/archives/2006/01/07/rails_encap/ (Tutorial)
http://www.mjwall.com/2008/08/multiple-versions-of-ruby-with-stow/ (Tutorial)
# RVM is not the only Ruby Version Manager
Other implementations allowing to install ruby versions:
- you can use your system to install ruby,
most distributions come with ruby 1.8 already installed
- https://github.com/vertiginous/pik (Windows)
- https://github.com/kwatch/versionswitcher
- https://github.com/jayferd/ry
- https://github.com/sstephenson/ruby-build
- https://github.com/mugenken/p5-Ruby-VersionManager (Perl!)
# RVM IDE support
RVM is supported by the following IDE products:
- [RubyMine](http://www.jetbrains.com/ruby/)
- Vim [rvm.vim](https://github.com/tpope/vim-rvm)
# Editing
To add a new implementation click "Edit this file" here:
https://github.com/wayneeseguin/rvm/blob/master/help/alt.md
1.23.24. repair
∴ rvm repair {symlinks,environments,archives,all}
Runs the repair process(es) against given parts of rvm.
Examples:
To regenerate all of the environment files inside your rvm/environments
directory, you would run:
∴ rvm repair environments
To check for stale symlinks caused by rvm in your rvm_bin_path, you would run:
∴ rvm repair symlinks
To verify all downloaded archives have the correct md5, you would run:
∴ rvm repair archives
Or, to do all of the above, you can run:
∴ rvm repair all
1.23.25. tests
1.23.26. info
∴ rvm info [ruby_string[,ruby_string[,...] [section,[section[,...]
where sections are one of:
system rvm ruby homes binaries environment debug
Both ruby strings and sections are optional arguments.
By default, with no parameters, rvm info will output all sections except debug.
To display system rvm debug information:
∴ rvm debug
which will display all sections including debug for the current or specified interpreters.
Example:
∴ rvm info 1.9.2-head,1.8.7 homes,binaries,environment
ruby-1.9.2-head:
homes:
gem:
ruby:
"/Users/wayne/.rvm/gems/ruby-1.9.2-head"
"/Users/wayne/.rvm/rubies/ruby-1.9.2-head"
binaries:
ruby:
irb:
gem:
rake:
"/Users/wayne/.rvm/rubies/ruby-1.9.2-head/bin/ruby"
"/Users/wayne/.rvm/rubies/ruby-1.9.2-head/bin/irb"
"/Users/wayne/.rvm/rubies/ruby-1.9.2-head/bin/gem"
"/Users/wayne/.rvm/gems/ruby-1.9.2-head/bin/rake"
environment:
GEM_HOME:
GEM_PATH:
MY_RUBY_HOME:
IRBRC:
RUBYOPT:
gemset:
"/Users/wayne/.rvm/gems/ruby-1.9.2-head"
"/Users/wayne/.rvm/gems/ruby-1.9.2-head:/Users/wayne/.rvm/gems/ruby-1.9.2-head@global"
"/Users/wayne/.rvm/rubies/ruby-1.9.2-head"
"/Users/wayne/.rvm/rubies/ruby-1.9.2-head/.irbrc"
""
""
ruby-1.8.7-p249:
homes:
gem:
ruby:
"/Users/wayne/.rvm/gems/ruby-1.8.7-p249"
"/Users/wayne/.rvm/rubies/ruby-1.8.7-p249"
binaries:
ruby:
irb:
gem:
rake:
"/Users/wayne/.rvm/rubies/ruby-1.8.7-p249/bin/ruby"
"/Users/wayne/.rvm/rubies/ruby-1.8.7-p249/bin/irb"
"/Users/wayne/.rvm/rubies/ruby-1.8.7-p249/bin/gem"
"/Users/wayne/.rvm/gems/ruby-1.8.7-p249/bin/rake"
environment:
GEM_HOME:
GEM_PATH:
MY_RUBY_HOME:
IRBRC:
RUBYOPT:
gemset:
"/Users/wayne/.rvm/gems/ruby-1.8.7-p249"
"/Users/wayne/.rvm/gems/ruby-1.8.7-p249:/Users/wayne/.rvm/gems/ruby-1.8.7-p249@global"
"/Users/wayne/.rvm/rubies/ruby-1.8.7-p249"
"/Users/wayne/.rvm/rubies/ruby-1.8.7-p249/.irbrc"
""
""
1.23.27. remove
∴ rvm remove [ruby-string[,ruby-string[,...]]]
Remove one or more rubies and their sources.
For a list of currently installed rubies, please run
rvm list
Please see documentation for further information:
https://rvm.io/rubies/removing/
1.23.28. rubygems
∴ rvm rubygems [x.y.z|latest-x.y|latest|current|master|head]
Installs a specific rubygems version in the current ruby. If
'current' is specified, the most current rubygems known to RVM
will be installed.
Currently only compatible with MRI 1.8.*, 1.9.* and Ruby
Enterprise Edition. If your system is not supported, running the
command will generate an error message.
MRI 1.9.* ships with a version of RubyGems. To revert to that version
after installing a custom version via 'rvm rubygems' run:
'rvm rubygems remove'
The version can be also specified as latest-1.8
which will use latest available like 1.8.18
Also you could use "head" or "master" to use development version.
RVM and Rubygems discourage the use of development version.
Finally you can override default version with:
echo "rubygems_version=latest-1.8" >> $rvm_path/user/db
echo "ree_rubygems_version=latest-1.6" >> $rvm_path/user/db
echo "ruby_1.9.2_p136_rubygems_version=1.3.7" >> $rvm_path/user/db
1.23.29. wrapper
∴ rvm wrapper <ruby_string> [<wrapper_prefix>|--no-prefix] [binary[ binaries[ ...]]]
where ruby_string is the ruby version and gemset combination to wrap
(it can also refer to a valid project path), wrapper_prefix is what to
prepend to the name of the generated wrapper, and binary and binaries
are the names of the binaries for which you wish to provide a wrapper
(e.g. gem).
When no binaries are provided, rvm will (by default) generate wrappers for
ruby, gem, rake, irb, rdoc, ri, and testrb.
Examples:
If you wish to provide an environment-specific wrapper for rspec with a
rails 3 gemset, you could do:
∴ rvm --create ree@rails3
∴ rvm wrapper ree@rails3 r3 spec
Which would add r3_spec with the specified environment to the bin
directory where you installed rvm.
Alternatively, if you do:
∴ rvm wrapper ruby-1.9.2-head
It will create binaries named ruby, gem, rake, irb, rdoc, ri and tesrb
in the rvm bin directory.
Finally, to show another real and common use, you can use wrapper
to generate ruby executables and gems for passenger to use. Namely:
∴ rvm use ree@rails3 --passenger
is equivelant to:
∴ rvm use ree@rails3
∴ rvm wrapper ree@rails3 passenger
Which creates passenger_* binaries in the rvm bin directory using
ree and the rails3 gemset.
1.23.30. specs
1.23.31. fetch
Fetch
Performs an archive / src fetch of the current selected ruby.
Usage: ∴ rvm fetch
1.23.32. update
Removed. See 'rvm help get' for updating RVM itself.
1.23.33. build
Usage:
rvm build <ruby_string> [options]
ruby_string is of the format $interpreter-$version-$patchlevel
Options:
1.23.34. disk-usage
∴ rvm disk-usage {all,archives,repos,sources,logs,packages,rubies,gemsets}
Returns the amount of disk space used by a specific set of data associated
with rvm. All returns each, individually, along with the total space used.
Examples:
To find out how much space your rvm install is using, simply run:
∴ rvm disk-usage all
To find out how much space only your gemsets use, run:
∴ rvm disk-usage gemsets
1.23.35. tools
∴ rvm tools {identifier,path-identifier,strings,mirror,rvm-env}
Provides generic tools related to rvm environments for gaining information
about your current environment. Primarily used for scripting rvm.
Examples:
To get the expanded Ruby string for the current environment, you would run:
∴ rvm tools identifier
To get the identifier for a folder (taking into account .rvmrc files and the like),
run this instead:
∴ rvm tools path-identifier ~/path/to/directory
Lastly, you can expand example Ruby strings.
run:
E.g., to get the current ree version,
∴ rvm tools strings ree
In case of network/firewall problems, it is easy to define alternate download URLs:
∴ rvm tools mirror
It is possible to use a "shebang" (#!/usr/...) line to select the interpreter
(eg, Ruby 1.9.3) which processes a script file. However, this will work only
on recent Linux kernels (2.6.27.9 and above).
First, you need to define the shebang wrapper:
∴ rvm tools rvm-env ruby bash zsh
This will define:
/usr/bin/{ruby,bash,zsh}-rvm-env
Your scripts can then request the proper Ruby, using shebang:
#!/usr/bin/ruby-rvm-env 1.9.3
The script will be run using Ruby 1.9.3 from rvm.
Alternatively, here is a hack to make a script switch itself:
if !ENV['ruby_switch_flag']
ENV['ruby_switch_flag'] = '42'
system('rvm', '1.9.3', 'do', __FILE__, *ARGV)
exit 0
end
1.23.36. alias
Alias
RVM allows you to alias your rubies for your convenience and pleasure.
Usage
rvm [options] alias source destination
Source and Destination must be an RVM
ruby string representing an RVM installed ruby.
A gemset may be optionally included.
Creating Aliases
First select an RVM ruby.
∴ rvm alias create php ree-1.8.7-p2010.01
Using Aliases
Now that you have created an alias, you can use the alias in place of the longer rvm selector string.
∴ rvm use php
∴ ruby -v
ruby 1.8.7 (2009-12-24 patchlevel 248) [i686-darwin10.3.0], MBARI 0x6770, Ruby Enterprise Edition 2010.01
If you use any aliases that are rather funny, please hop in #rvm and let us know :)
Deleting Aliases
If you wish to delete an alias
∴ rvm alias delete dotnet
Listing Aliases
You can also list all current aliases
∴ rvm alias list
php => ree-1.8.7-p2010.01
lisp => maglev-head
python => rbx-head
Documentation:
https://rvm.io/rubies/alias/
1.23.37. upgrade
Usage:
rvm upgrade [source ruby] [destination ruby]
Description:
Upgrades the specified (already installed) source ruby to the
given destination ruby version. Will migrate gemsets, wrappers, aliases
and environment files.
The process will prompt you at each stage - if the versions look incorrect,
please cancel and perform it manually.
Examples:
$ rvm upgrade 1.9.2-p136 1.9.2-p180
$ rvm upgrade ree-2011.01 ree-2011-02
Experimental detection:
$ rvm upgrade 1.9.2
Are you sure you wish to upgrade from ruby-1.9.2-p290 to ruby-1.9.2-p318? (Y/n):
1.23.38. upgrade-notes.txt
* If you have any questions, issues and/or ideas for improvement please
fork the project and issue a pull request.
* If you wish to disable the project .rvmrc file functionality, set
rvm_project_rvmrc=0 in either /etc/rvmrc or ~/.rvmrc.
then log out and back in.
* You _must_ read 'rvm requirements' for additional OS specific requirements for
various rubies, and native-extension gems. Expect failures until those are met!
* For screen users, please do not forget to read https://rvm.io/workflow/screen/.
You will need to add 'shell -${SHELL}' to your $HOME/.screenrc to properly load RVM.
* rvm_trust_rvmrcs has been changed to rvm_trust_rvmrcs_flag for consistency
* Project rvmrc files are now checked for trust whenever they change, as
promised by the note displayed during the review process
* Ruby package dependency list for your OS is given by:
rvm requirements
* If you encounter any issues with a ruby 'X' your best bet is to:
rvm get head && rvm reinstall X
* If you see the following error message: Unknown alias name: 'default'
re-set your default ruby, this is due to a change in how default works.
* after_use and after_cd hook now supports multiple files with after_*_*
the custom hooks can be easily turned on/off by:
chmod +x $rvm_path/hooks/after_cd_[hook_name]
chmod -x $rvm_path/hooks/after_use_[hook_name]
* If your shell exits on entering a directory with freshly checked out sources
you should update .rvmrc file, and replace any `exit ` with `return `.
* If you wish to use RVM in an interactive fashion in other shells
then place the following line at the end of your shell's loading files
(.bashrc or .bash_profile for bash and .zshenv for zsh),
after all PATH/variable settings:
[[ -s "${rvm_scripts_path}/rvm" ]] && source "${rvm_scripts_path}/rvm"
# This loads RVM into a shell session.
* On some systems (like Ubuntu) rvmsudo requires following changes to work properly:
http://stackoverflow.com/questions/257616/sudo-changes-path-why
* To update RVM loading code append '--auto' to 'rvm get ...'
* In case you have some old RVM files/rubies in '/usr/local/bin' or '$HOME/bin' feel free to remove them,
they were copied there because of bug in path detection.
* ZSH 4.3.15 is buggy, be careful with it, it can break RVM, especially multiuser installations,
You should consider downgrading ZSH to 4.3.12 which has proven to work more reliable with RVM.
* Optionally you can run \`rvm tools rvm-env ruby bash\` which will generate
shebang wrappers for easier selecting ruby in scripts.
* RVM comes with set of default gems including 'bundler', 'rake', 'rubygems-bundler' and 'rvm' gems,
if you do not wish to get this gems install RVM with this flag: --without-gems="rvm rubygems-bundler"
this option is remembered, it's enough to use it once.
1.23.39. user
RVM mixed mode can be enabled on multiuser installations.
To use rubies and gemsets from user home run:
rvm user all
To use only gemsets from user home run:
rvm user gemsets
It is also possible to add this settings as default for new user accounts:
sudo rvm user [all|gemsets] --skel
1.23.40. reinstall
Usage
rvm reinstall [ruby-string]
It is equivalent to:
rvm remove [ruby-string]
rvm install [ruby-string]
Please see the documentation for further information:
https://rvm.io/rubies/installing/
1.23.41. rake
Rake
RVM allows you to run rake tasks across multiple ruby versions, for example:
∴ rvm all do rake spec
or:
∴ rvm 1.8.6,1.9.1 do rake spec
JSON Summary
Add a --json flag prior to the word 'do' and a JSON summary will be printed out at the end of the run.
YAML Summary
Add a --yaml flag prior to the word 'do' and a YAML summary will be printed out at the end of the run.
1.23.42. cleanup
∴ rvm cleanup {all,archives,repos,sources,logs}
Performs general cleanup for the specific set of rvm directories.
Useful for reclaiming used disk space from rvm compiles
Examples:
To reclaim all of the space used by archives, repository clones,
source files (and associated temporary compile file) and logs, you'd
run:
∴ rvm cleanup all
If instead you only wanted to clean up source files, you'd run:
∴ rvm cleanup sources
Please note that sometimes having archives and sources around are desirable.
Namely, you need the sources to install something such as ruby-debug under
1.9.
1.23.43. gemset
Usage:
rvm gemset [action]
rvm --force gemset [action]
Actions:
import,export,create,copy,rename,empty,delete,name,dir,list,list_all,gemdir,install,pristine,clear,use,update,unpack,globalc
ache
Description:
Commands for working with and manipulating gemsets within RVM.
Any command is run in context of current ruby/gemset; call 'rvm current' to find out which is currently used.
Note that 'system' supports only exporting/importing gems.
Rejection:
If you do not want to use gemsets and want to ignore them you can use
command line flag `--ignore-gemsets`:
rvm use 1.9.3@my_project --ignore-gemsets
it will ignore @my_project and @global -
only default gemset will be set.
It can be persisted with:
echo "export rvm_ignore_gemsets_flag=1" >> ~/.rvmrc
1.23.44. snapshot
∴ rvm snapshot {load,save} filename
Saves or creates a snapshot of the given rvm install. This includes:
*
*
*
*
*
*
Settings
Aliases
Rubies
Gemsets
Packages
Your Default
Ideally to easily maintain a consistent environment among machines
/ to back up your environment.
Please note that this is still considered experimental to a large degree.
1.24. contrib
1.24.1. gemset_snapshot
#!/usr/bin/env bash
printf "\nBeginning snapshot of the current environment gem list into snapshot.gems\n"
file_name="snapshot.gems"
gems=($(gem list | sed 's#[\(|\)]##g' | sed 's#, #,#g' | \tr ' ' ';'))
for gem in "${gems[@]}" ; do
name="$(echo $gem | awk -F';' '{print $1}')"
versions=($(echo $gem | awk -F';' '{print $2}' | sed 's#,# #g'))
for version in "${versions[@]}" ; do
echo "$name -v$version" >> "$file_name"
done ; unset version versions
done ; unset file_name
printf "\nCompleted snapshot of the current environment gem list into snapshot.gems\n"
exit $?
1.24.2. ps1_functions
#!/usr/bin/env bash
#
# Source this file in your ~/.bash_profile or interactive startup file.
# This is done like so:
#
#
[[ -s "$HOME/.rvm/contrib/ps1_functions" ]] &&
#
source "$HOME/.rvm/contrib/ps1_functions"
#
# Then in order to set your prompt you simply do the following for example
#
# Examples:
#
#
ps1_set --prompt ∫
#
#
or
#
#
ps1_set --prompt ∴
#
# This will yield a prompt like the following, for example,
#
# 00:00:50 wayneeseguin@GeniusAir:~/projects/db0/rvm/rvm (git:master:156d0b4)
# ∴
#
ps1_titlebar()
{
case $TERM in
(xterm*|rxvt*)
printf "%s" "\033]0;\\u@\\h: \W\\007"
;;
esac
}
ruby-1.8.7-p334@rvm
ps1_identity()
{
if (( $UID == 0 )) ; then
printf "%s" "\[\033[31m\]\\u\[\033[0m\]@\[\033[36m\]\\h\[\033[35m\]:\w\[\033[0m\] "
else
printf "%s" "\[\033[32m\]\\u\[\033[0m\]@\[\033[36m\]\\h\[\033[35m\]:\w\[\033[0m\] "
fi
}
ps1_git()
{
local branch="" sha1="" line="" attr="" color=0
shopt -s extglob # Important, for our nice matchers :)
command -v git >/dev/null 2>&1 || {
printf " \033[1;37m\033[41m[git not found]\033[m "
return 0
}
branch=$(git symbolic-ref -q HEAD 2>/dev/null) || return 0 # Not in git repo.
branch=${branch##refs/heads/}
# Now we display the branch.
sha1=$(git rev-parse --short --quiet HEAD)
case "${branch:-"(no branch)"}" in
production|prod) attr="1;37m\033[" ; color=41 ;; # red
master|deploy)
color=31
;; # red
stage|staging)
color=33
;; # yellow
dev|develop|development) color=34
;; # blue
next)
color=36
;; # gray
*)
if [[ -n "${branch}" ]] ; then # Feature Branch :)
color=32 # green
else
color=0 # reset
fi
;;
esac
[[ $color -gt 0 ]] &&
printf "\[\033[${attr}${color}m\](git:${branch}$(ps1_git_status):$sha1)\[\033[0m\] "
}
ps1_git_status()
{
local git_status="$(git status 2>/dev/null)"
[[ "${git_status}" = *deleted* ]]
&& printf "%s" "-"
[[ "${git_status}" = *Untracked[[:space:]]files:* ]] && printf "%s" "+"
[[ "${git_status}" = *modified:* ]]
&& printf "%s" "*"
}
ps1_rvm()
{
command -v rvm-prompt >/dev/null 2>&1 && printf "%s" " $(rvm-prompt) "
}
ps1_update()
{
local prompt_char='$' separator="\n" notime=0
(( $UID == 0 )) && prompt_char='#'
while [[ $# -gt 0 ]] ; do
local token="$1" ; shift
case "$token" in
--trace)
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
set -o xtrace
;;
--prompt)
prompt_char="$1"
shift
;;
--noseparator)
separator=""
;;
--separator)
separator="$1"
shift
;;
--notime)
notime=1
;;
*)
true # Ignore everything else.
;;
esac
done
\${LINENO} > "
if (( notime > 0 )) ; then
PS1="$(ps1_titlebar)$(ps1_identity)$(ps1_git)$(ps1_rvm)${separator}${prompt_char} "
else
PS1="$(ps1_titlebar)\D{%H:%M:%S} $(ps1_identity)$(ps1_git)$(ps1_rvm)${separator}${prompt_char} "
fi
}
ps2_set()
{
PS2=" \[\033[0;40m\]\[\033[0;33m\]> \[\033[1;37m\]\[\033[1m\]"
}
ps4_set()
{
export PS4="+ \${BASH_SOURCE##\${rvm_path:-}} : \${FUNCNAME[0]:+\${FUNCNAME[0]}()}
}
\${LINENO} > "
# WARNING: This clobbers your PROMPT_COMMAND so if you need to write your own, call
#
ps1_update within your PROMPT_COMMAND with the same arguments you pass
#
to ps1_set
#
# The PROMPT_COMMAND is used to help the prompt work if the separator is not a new line.
# In the event that the separtor is not a new line, the prompt line may become distored if
# you add or delete a certian number of characters, making the string wider than the
# $COLUMNS + len(your_input_line).
# This orginally was done with callbacks within the PS1 to add in things like the git
# commit, but this results in the PS1 being of an unknown width which results in the prompt
# being distored if you add or remove a certain number of characters. To work around this
# it now uses the PROMPT_COMMAND callback to re-set the PS1 with a known width of chracters
# each time a new command is entered. see PROMPT_COMMAND for more details.
#
ps1_set()
{
PROMPT_COMMAND="ps1_update $@"
}
1.24.3. bootstrap_rails_environment
#!/usr/bin/env bash
#
# Author: Wayne E. Seguin <[email protected]>
# Licence: MIT
#
#
# This script when sourced will bootstrap a Rails development environment
# on Linux and OSX
#
# Source this file so that it will leave you in the Sites directory.
rails_version="3.0.9"
ruby_version="1.9.1"
sites_path="$HOME/Sites"
abort=false
if (( UID == 0 ))
then
printf "ERROR: This script may not be sourced as the root user."
abort=true
else
if [[ ! -d "$sites_path" ]]
then
mkdir -p "$sites_path"
fi
cd "$sites_path"
printf "#\n#
Bootstrapping a Rails development environment!\n#\n"
if [[ $MACHTYPE = *linux* ]]
then
printf "#\n# Ensuring OS packges are installed, you will be prompted for your password.\n#\n"
if command -v apt-get
then
sudo apt-get install build-essential bison openssl libreadline6 libreadline6-dev curl git-core zlib1g zlib1g-dev
libssl-dev libyaml-dev libsqlite3-0 libsqlite3-dev sqlite3 libxml2-dev libxslt-dev autoconf libc6-dev
elif command -v pacman
then
sudo pacman -S --noconfirm gcc patch curl bison zlib readline libxml2 libxslt git autoconf diffutils patch make
elif command -v yum
then
sudo yum install -y gcc-c++ patch readline readline-devel zlib zlib-devel libyaml-devel libffi-devel openssl-devel
sudo yum install -y iconv-devel >/dev/null 2>&1 # NOTE: For centos 5.4 final iconv-devel might not be available :(
fi
elif [[ $MACHTYPE = *darwin* ]]
then
if [[ ! -s /Library/Developer/Shared/XcodeTools.plist ]]
then
printf "Please Install XCode Tools before sourcing this environment bootstrap script."
abort=true
fi
fi
fi
if ! $abort
then
printf "Ensuring that git is installed...\n"
if command -v git
then
printf "Found git! Moving right along.\n"
else
printf "=> Installing Git (git command not found)"
if curl -s -L -B https://rvm.io/install/git -o gitinstall
then
chmod +x "$PWD/gitinstall"
sudo bash "$PWD/gitinstall"
if [[ -f gitinstall ]]
then
rm -f gitinstall
fi
else
printf "ERROR: There was an error while attempting to install git."
exit 1
fi
fi
printf "=> Installing RVM the Ruby enVironment Manager\n https://rvm.io/rvm/install/\n"
curl -s -O -L -B https://rvm.io/releases/rvm-install-head
chmod +x rvm-install-head
"$PWD/rvm-install-head"
if [[ -f rvm-install-head ]]
then
rm -f rvm-install-head
fi
printf "=> Setting up RVM to load with new shells.\n"
echo '[[ -s "$HOME/.rvm/scripts/rvm" ]] && . "$HOME/.rvm/scripts/rvm"
>> "$HOME/.bash_profile"
# Load RVM into a shell session *as a function*'
printf "=> Loading RVM"
source ~/.rvm/scripts/rvm
printf "=> Installing Ruby 1.8.7\n
https://rvm.io/rubies/installing/"
More information about installing rubies can be found at
rvm install $ruby_version
printf "=> Using 1.8.7 and setting it as default for new shells\n
https://rvm.io/rubies/default/\n"
More information about Rubies can be found at
rvm use $ruby_version --default
printf "=> Installing Rails 3 to the default gemset.\n
https://rvm.io/gemsets/\n"
More information about gemsets can be found at
gem install rails --no-rdoc --no-ri
printf "=> Installing Bundler to the global gemset.\n
https://rvm.io/gemsets/global/\n"
rvm gemset use global
gem install bundler --no-rdoc --no-ri
rvm gemset clear
printf "=> Installing the sqlite3 Gem.\n
https://rubydoc.info/gems/sqlite3/1.3.3/frames\n"
gem install sqlite3 --no-rdoc --no-ri
printf "
Rails development environment bootstrapped, please enjoy Rails!
~Wayne E. Seguin <[email protected]>
P.S. You should now be able to generate a new Rails Application in ~/Sites with the command 'rails new <name>'
"
fi
unset ruby_version rails_version sites_path
1.24.4. hudson
1.24.4.1. rvmRake-1.0-SNAPSHOT-20100819.hpi
UnSupported Binary
1.24.4.2. README.md
# RVM Hudson Plugins
These plugins are forks of the ruby, rake and rubyMetrics plugins
for Hudson. They're designed to make it dead simple to get started
with RVM and to let you simply specify a rvm ruby string.
For more current updates, see:
* [http://github.com/Sutto/hudson-rvmRuby-plugin](http://github.com/Sutto/hudson-rvmRuby-plugin)
* [http://github.com/Sutto/hudson-rvmRake-plugin](http://github.com/Sutto/hudson-rvmRake-plugin)
* [http://github.com/Sutto/hudson-rvmRubyMetrics-plugin](http://github.com/Sutto/hudson-rvmRubyMetrics-plugin)
1.24.4.3. rvmRubyMetrics-1.0-SNAPSHOT-20100819.hpi
UnSupported Binary
1.24.4.4. rvmRuby-1.0-SNAPSHOT-20100819.hpi
UnSupported Binary
1.25. config
1.25.1. ssh.example
Host ubuntu
Port 2220
Host *
HostName localhost
User vboxtest
UserKnownHostsFile /dev/null
StrictHostKeyChecking no
IdentitiesOnly yes
ControlMaster auto
ControlPath /tmp/socket-%r@%h:%p
1.25.2. md5
MacRuby%200.5.zip=675454a8c7bc19d606d90a726e08427c
MacRuby%200.6.zip=a80afd3700c88cf95c539fc63b272faf
MacRuby%200.7.1.zip=e8245dcd03c0757dfae7e6fee913947a
MacRuby%200.7.zip=0bb60588c9ec9b1517665743bb05132f
MacRuby%200.8.zip=735ac0a70f539e00b5de6fbec09c2c5c
MacRuby%200.9.zip=fa01345e8fbfee620bbac64743a45f69
MacRuby%200.10.zip=1662d13d2f73cfc26258598f6988dcbc
MacRuby%200.11.zip=b0cc23d60484a07012bcad549cef6054
MacRuby%200.12.zip=e1c5fa1b007a1cdc38c527a47302bf5e
curl-7.19.7.tar.gz=ecb2e37e45c9933e2a963cabe03670ab
ironruby-1.0.zip=7a92888837b3507355ed391dbfc0ab83
jruby-bin-1.3.1.tar.gz=4a95db8fc93ed7219663fbede98b6117
jruby-bin-1.4.0.tar.gz=f37322c18e9134e91e064aebb4baa4c7
jruby-bin-1.4.0.zip=3a9c8a5115a679da7d7a49a56d57d4c0
jruby-bin-1.4.1.tar.gz=a4aa8c43d1b9ffd9dbc6cb738d55a034
jruby-bin-1.4.tar.gz=54dba9a88b2b3f99ac86a79828d0178b
jruby-bin-1.5.0.tar.gz=ee2b4e326e8b87858e5dd0c8e94102e6
jruby-bin-1.5.1.tar.gz=0196dcfb17354f12253eaddc1166a0ee
jruby-bin-1.5.2.tar.gz=d239deb9a108a6abbfbd6cb79cf8255b
jruby-bin-1.5.3.tar.gz=ccb0b2dbc300d8dd4ad1bd4da48b8320
jruby-bin-1.5.5.tar.gz=8e00f7d40cbf221f733d6f7a15784e9a
jruby-bin-1.5.6.tar.gz=94033a36517645b7a7ec781a3507c654
jruby-bin-1.6.0.tar.gz=f4d7e339dfc0fbaef5b878d1c0a66fbe
jruby-bin-1.6.2.tar.gz=a46f978c24a208717023bb4b8995c678
jruby-bin-1.6.3.tar.gz=694b80e4eea784cdc1eb39fb1e3132c9
jruby-bin-1.6.4.tar.gz=0e96b6f4d1c6f12b5ac480cd7ab7da78
jruby-bin-1.6.5.tar.gz=54354082673bd115f945890dc6864413
jruby-bin-1.6.5.1.tar.gz=246a7aa2b7d7e6e9e8a0c2e282cbcfd0
jruby-bin-1.6.7.tar.gz=fd1b8d7389aa92da69ea6efb4782e40a
jruby-bin-1.6.7.2.tar.gz=1e520f1b5130114464e5f1950cb24774
jruby-bin-1.7.0.preview1.tar.gz=7b9e5e1cd0d818d0199086d948f948b4
libiconv-1.13.1.tar.gz=7ab33ebd26687c744a37264a330bbe9a
ncurses.tar.gz=cce05daf61a64501ef6cd8da1f727ec6
openssl-0.9.8k.tar.gz=e555c6d58d276aec7fdc53363e338ab3
openssl-0.9.8n.tar.gz=076d8efc3ed93646bd01f04e23c07066
pkg-config-0.23.tar.gz=d922a88782b64441d06547632fd85744
readline-5.2.tar.gz=e39331f32ad14009b9ff49cc10c5e751
readline-6.0.tar.gz=b7f65a48add447693be6e86f04a63019
rubinius-1.0.0-20100514.tar.gz=b05f4e791d3712c5a50b3d210dac6eb0
rubinius-1.0.1-20100603.tar.gz=eb185703c7ae0c0210e8dcb7f783ee8e
rubinius-1.1.0-20100923.tar.gz=e2ae16238b201de09975abe19da09ea9
rubinius-1.1.1-20101116.tar.gz=b39f618eeba37c3aff215da8bca55fd7
rubinius-1.2.0-20101221.tar.gz=4284c2660f1f648942de35d4fc871f70
rubinius-1.2.1-20110215.tar.gz=e4a5127480062fddddc7ce2860b3b813
rubinius-1.2.2-20110222.tar.gz=59124378fb7ee040e9ee4e4736d89fc0
rubinius-1.2.3-20110315.tar.gz=9782dab18c2dd440af6b76e8eb5bc0f0
rubinius-1.2.4-20110705.tar.gz=403c777d19b3553e9cb36701fe002c5e
ruby-1.8.5-p115.tar.bz2=03955e3c367b9beb3efe144c9f00d689
ruby-1.8.5-p115.tar.gz=20ca6cc87eb077296806412feaac0356
ruby-1.8.5-p231.tar.bz2=327f5aa6573787432222e96195cffd1e
ruby-1.8.5-p231.tar.gz=e900cf225d55414bffe878f00a85807c
ruby-1.8.6-p286.tar.bz2=e6b6bf8f34370e433936adb7a7065e63
ruby-1.8.6-p286.tar.gz=797ea136fe43e4286c9362ee4516674e
ruby-1.8.6-p287.tar.bz2=80b5f3db12531d36e6c81fac6d05dda9
ruby-1.8.6-p287.tar.gz=6ff3420094711266c3201a0c7c2faa38
ruby-1.8.6-p369.tar.bz2=c3c1f3dd0dfbd2e17a04e59c2f12cfc8
ruby-1.8.6-p369.tar.gz=8c140ae28b4c3947b92dfad69109d90b
ruby-1.8.6-p383.tar.bz2=a48703cd982b9f0e3002700a50b0e88e
ruby-1.8.6-p383.tar.gz=4f49544d4a4d0d34e9d86c41e853db2e
ruby-1.8.6-p398.tar.bz2=fbd43dc44ee26be4d37e6bebbed6f8bd
ruby-1.8.6-p398.tar.gz=736db5f56c2d9b0136e563d049249fa8
ruby-1.8.6-p399.tar.bz2=f77c307cb72fb8808b0e85af5d05cefc
ruby-1.8.6-p399.tar.gz=c3d16cdd3c1ee8f3b7d1c399d4884e33
ruby-1.8.6-p420.tar.bz2=1c7a978e9ffd4f56dc2ad74bbd2c34f3
ruby-1.8.6-p420.tar.gz=ca1eee44f842e93b5098bc5a2bb9a40b
ruby-1.8.7-p160.tar.bz2=f8ddb886b8a81cf005f53e9a9541091d
ruby-1.8.7-p160.tar.gz=945398f97e2de6dd8ab6df68d10bb1a1
ruby-1.8.7-p174.tar.bz2=88c45aaf627b4404e5e4273cb03ba2ee
ruby-1.8.7-p174.tar.gz=18dcdfef761a745ac7da45b61776afa5
ruby-1.8.7-p248.tar.bz2=37e19d46b7d4b845f57d3389084b94a6
ruby-1.8.7-p248.tar.gz=60a65374689ac8b90be54ca9c61c48e3
ruby-1.8.7-p249.tar.bz2=37200cc956a16996bbfd25bb4068f242
ruby-1.8.7-p249.tar.gz=d7db7763cffad279952eb7e9bbfc221c
ruby-1.8.7-p299.tar.bz2=244439a87d75ab24170a9c2b451ce351
ruby-1.8.7-p299.tar.gz=43533980ee0ea57381040d4135cf9677
ruby-1.8.7-p302.tar.bz2=a6a9e37079ed8cf8726b455dad3de939
ruby-1.8.7-p302.tar.gz=a6a9e37079ed8cf8726b455dad3de939
ruby-1.8.7-p330.tar.bz2=2689719fb42c8cf0aa336f8c8933f413
ruby-1.8.7-p330.tar.gz=50a49edb787211598d08e756e733e42e
ruby-1.8.7-p334.tar.bz2=2f14f604bf981bb938ab5fc8b09eb1a6
ruby-1.8.7-p334.tar.gz=aacb6ee5dfe2367682bba56af7f415b8
ruby-1.8.7-p352.tar.bz2=0c61ea41d1b1183b219b9afe97f18f52
ruby-1.8.7-p352.tar.gz=0c33f663a10a540ea65677bb755e57a7
ruby-1.8.7-p358.tar.bz2=de35f00997f4ccee3e22dff0f2d01b8a
ruby-1.8.7-p370.tar.bz2=1e4c3194537dd8ff92e756993e55a29d
ruby-1.9.0.tar.bz2=17eb66ac3721340d21db352d8f5dec76
ruby-1.9.1-p129.tar.bz2=6fa62b20f72da471195830dec4eb2013
ruby-1.9.1-p129.tar.gz=c71f413514ee6341c627be2957023a5c
ruby-1.9.1-p243.tar.bz2=66d4f8403d13623051091347764881a0
ruby-1.9.1-p243.tar.gz=515bfd965814e718c0943abf3dde5494
ruby-1.9.1-p376.tar.bz2=e019ae9c643c5efe91be49e29781fb94
ruby-1.9.1-p376.tar.gz=ebb20550a11e7f1a2fbd6fdec2a3e0a3
ruby-1.9.1-p378.tar.bz2=5922459622a23612eb9b68a3586cb5f8
ruby-1.9.1-p378.tar.gz=9fc5941bda150ac0a33b299e1e53654c
ruby-1.9.1-p429.tar.bz2=09df32ae51b6337f7a2e3b1909b26213
ruby-1.9.1-p429.tar.gz=0f6d7630f26042e00bc59875755cf879
ruby-1.9.1-p431.tar.bz2=03179138ae95dbfae872ef49e9cc6da7
ruby-1.9.1-p431.tar.gz=23f28cffc007ed5ac72c8e9bec6837ce
ruby-1.9.2-p0.tar.bz2=d8a02cadf57d2571cd4250e248ea7e4b
ruby-1.9.2-p0.tar.gz=755aba44607c580fddc25e7c89260460
ruby-1.9.2-p136.tar.bz2=52958d35d1b437f5d9d225690de94c13
ruby-1.9.2-p136.tar.gz=6e17b200b907244478582b7d06cd512e
ruby-1.9.2-p180.tar.bz2=68510eeb7511c403b91fe5476f250538
ruby-1.9.2-p180.tar.gz=0d6953820c9918820dd916e79f4bfde8
ruby-1.9.2-p290.tar.gz=604da71839a6ae02b5b5b5e1b792d5eb
ruby-1.9.2-p290.tar.bz2=096758c3e853b839dc980b183227b182
ruby-1.9.2-p318.tar.gz=cc7bf1025128e1985882ae243f348802
ruby-1.9.2-p318.tar.bz2=be431c6cbfa27e3836a06c6315717747
ruby-1.9.2-p320.tar.gz=5ef5d9c07af207710bd9c2ad1cef4b42
ruby-1.9.3-preview1.tar.bz2=7d93dc773c5824f05c6e6630d8c4bf9b
ruby-1.9.3-preview1.tar.gz=0f0220be4cc7c51a82c1bd8f6a0969f3
ruby-1.9.3-preview1.tar.bz2=7d93dc773c5824f05c6e6630d8c4bf9b
ruby-1.9.3-rc1.tar.bz2=26f0dc51ad981e12c58b48380112fa4d
ruby-1.9.3-rc1.tar.gz=46a2a481536ca0ca0b80ad2b091df68e
ruby-1.9.3-p0.tar.bz2=65401fb3194cdccd6c1175ab29b8fdb8
ruby-1.9.3-p0.tar.gz=8e2fef56185cfbaf29d0c8329fc77c05
ruby-1.9.3-p125.tar.bz2=702529a7f8417ed79f628b77d8061aa5
ruby-1.9.3-p125.tar.gz=e3ea86b9d3fc2d3ec867f66969ae3b92
ruby-1.9.3-p194.tar.bz2=2278eff4cfed3cbc0653bc73085caa34
ruby-1.9.3-p194.tar.gz=bc0c715c69da4d1d8bd57069c19f6c0e
ruby-enterprise-1.8.6-20080507.tar.gz=17e3c52e73e42809f57ad0000a6cb4ab
ruby-enterprise-1.8.6-20080621.tar.gz=626fc3811eee2dc92ac27ea63d37a8b2
ruby-enterprise-1.8.6-20080623.tar.gz=0bf8a3a93c6b37bb1260cc09b05e81fd
ruby-enterprise-1.8.6-20080624.tar.gz=de58b97128aa65209f291c66eab7c4a7
ruby-enterprise-1.8.6-20080709.tar.gz=f0ded08cec64959fa388ec6a237b9c47
ruby-enterprise-1.8.6-20080810.tar.gz=bfdcf06f437af825cd9f2d321f9d1896
ruby-enterprise-1.8.6-20081205.tar.gz=50206bec9be2e08a862e5ec2e70fa693
ruby-enterprise-1.8.6-20081215.tar.gz=aab57b7d5061c1980bec5dbe311ec9b2
ruby-enterprise-1.8.6-20090113.tar.gz=e8d796a5bae0ec1029a88ba95c5d901d
ruby-enterprise-1.8.6-20090201.tar.gz=a965e6789b553efaed72191825b13713
ruby-enterprise-1.8.6-20090421.tar.gz=c777b361aadccda7988be16ede7ab15f
ruby-enterprise-1.8.6-20090520.tar.gz=156572a8296bd0440970a6bb95018a13
ruby-enterprise-1.8.6-20090610.tar.gz=0bf66ee626918464a6eccdd83c99d63a
ruby-enterprise-1.8.7-2009.10.tar.gz=3727eef7b6b1b2f31db7d091328d966e
ruby-enterprise-1.8.7-20090928.tar.gz=ae00018ce89d95419dfde370fcd485ac
ruby-enterprise-1.8.7-2010.01.tar.gz=587aaea02c86ddbb87394a340a25e554
ruby-enterprise-1.8.7-2010.02.tar.gz=4df7b09c01adfd711b0ab76837611542
ruby-enterprise-1.8.7-2011.01.tar.gz=4640634347cd8e5469cb718853e2112e
ruby-enterprise-1.8.7-2011.02.tar.gz=8c5faa11c1ddaed3f44b7294711980cc
ruby-enterprise-1.8.7-2011.03.tar.gz=038604ce25349e54363c5df9cd535ec8
ruby-enterprise-1.8.7-2011.12.tar.gz=1e5f3059d52a67ab5d91d472b756de08
ruby-enterprise-1.8.7-2012.02.tar.gz=8d086d2fe68a4c57ba76228e97fb3116
rubygems-0.4.0.tgz=86a64616548a793e1a5f825f0dd385b9
rubygems-0.5.0.tgz=80d151edd94a06bcd2452a7e272b4d96
rubygems-0.6.0.tgz=5df803f5a04654833690dd32283de741
rubygems-0.6.1.tgz=c4a0faa9f876ad805ae80d1396a29d97
rubygems-0.7.0.tgz=ede9b55343219e8b3491793aa12c46f3
rubygems-0.8.0.tgz=9ef6e3c34dcb54e295c8e57321ddc079
rubygems-0.8.1.tgz=6276d268b420c0d61796cdbf6d28dae4
rubygems-0.8.10.tgz=d26592e280c0fb24c51f2837c3f48e67
rubygems-0.8.11.tgz=aa363b428c4c1fc2e076a4ff77b957d7
rubygems-0.8.3.tgz=6e6da80f61d6e77d0ad9e531767f6fd5
rubygems-0.8.4.tgz=a2ad2d03dae8a98002c2a7cd6c3ed352
rubygems-0.8.5.tgz=b917c084e1e6e99d8e102af8dd687ddb
rubygems-0.8.6.tgz=9de98d2f62e3f91521b0207a4dcdeb5b
rubygems-0.8.7.tgz=7fc04b9f9acc0c18cbbe6222be8d0bd3
rubygems-0.8.8.tgz=a8535e9c35a4c215d6ef9268d4bc69ed
rubygems-0.9.0.tgz=5d496e1f415b8b4033ab867f01d1161f
rubygems-0.9.1.tgz=a62314cdb174ccc88a27b8924fa79e4a
rubygems-0.9.2.tgz=cc525053dd465ab6e33af382166fa808
rubygems-0.9.3.tgz=600940a22ecd79e28e0fd37ad1f1d871
rubygems-0.9.4.tgz=b5680acaa019c80ea44fe87cc2e227da
rubygems-0.9.5.tgz=91f7036a724e34cc66dd8d09348733d9
rubygems-1.0.0.tgz=b0b74eac0cbfc5a13f895ab6f803edc1
rubygems-1.0.1.tgz=0d5851084955c327ee1dc9cbd631aa5f
rubygems-1.1.0.tgz=85f994904c5b4045f0a859b29d0be717
rubygems-1.1.1.tgz=1a77c5b6b293a3ccd5261dc120641ccc
rubygems-1.2.0.tgz=b77a4234360735174d1692e6fc598402
rubygems-1.3.0.tgz=63d3dfc038710eaf532b6a133225115a
rubygems-1.3.1.tgz=a04ee6f6897077c5b75f5fd1e134c5a9
rubygems-1.3.2.tgz=6204d0a4c526a1d8fdbce746647b179a
rubygems-1.3.3.tgz=0e9697db44d812712350baf28016b4a7
rubygems-1.3.4.tgz=b17b398503253bf36a101c58f02a226f
rubygems-1.3.5.tgz=6e317335898e73beab15623cdd5f8cff
rubygems-1.3.6.tgz=789ca8e9ad1d4d3fe5f0534fcc038a0d
rubygems-1.3.7.tgz=e85cfadd025ff6ab689375adbf344bbe
rubygems-1.4.1.tgz=e915dbf79e22249d10c0fcf503a5adda
rubygems-1.4.2.tgz=b5badb7c5adda38d9866fa21ae46bbcc
rubygems-1.5.0.tgz=49bef7186bf3c0ca6ee7adf4b585bccc
rubygems-1.5.1.tgz=47577a5e33c9c6f1e3a56aff7f51d0ff
rubygems-1.5.2.tgz=3951f94c09c16c774c8bcebc94fa5374
rubygems-1.5.3.tgz=38bbbdc17aef923fb41f054cf8421116
rubygems-1.6.0.tgz=abd27b5a9002100ff74ddb398a1c9689
rubygems-1.6.1.tgz=a77c64896aaa10d64aaf34f5c1488173
rubygems-1.6.2.tgz=0c95a9869914ba1a45bf71d3b8048420
rubygems-1.8.6.tgz=8e95d0c5b377a003f3d54a49461e81d9
rubygems-1.8.9.tgz=fc399445d693c29778779e5828ee5e90
rubygems-1.8.10.tgz=5b08ee31740c9b0bd36f6c04d537e7d4
zlib-1.2.3.tar.gz=debc62758716a169df9f62e6ab2bc634
zlib-1.2.5.tar.gz=c735eab2d659a96e5a594c9e8541ad63
yaml-0.1.4.tar.gz=36c852831d02cf90508c29852361d01b
GemStone-27184.Darwin-i386.tar.gz=292b3b169656a8451cfa19c228828e5a
GemStone-27184.Linux-x86_64.tar.gz=cfabd4dd73d2656fc10243e35dd7452b
GemStone-27184.SunOS-i86pc.tar.gz=5755a0689488748dfeab3bc74572aaa8
MagLev-1.0.0.tar.gz=e02cb8ee04438451eb78df14f91a68a9
ruby-1.9.2-p320.tar.bz2=b226dfe95d92750ee7163e899b33af00
rubygems-1.8.23.tgz=178b0ebae78dbb46963c51ad29bb6bd9
1.25.3. known
# MRI Rubies
[ruby-]1.8.6[-p420]
[ruby-]1.8.7[-p370]
[ruby-]1.9.1[-p431]
[ruby-]1.9.2-p180
[ruby-]1.9.2-p290
[ruby-]1.9.2-p318
[ruby-]1.9.2[-p320]
[ruby-]1.9.2-head
[ruby-]1.9.3-preview1
[ruby-]1.9.3-rc1
[ruby-]1.9.3-p0
[ruby-]1.9.3-p125
[ruby-]1.9.3[-p194]
[ruby-]1.9.3-head
ruby-head
# GoRuby
goruby
# TheCodeShop - MRI experimental patches
tcs
# JRuby
jruby-1.2.0
jruby-1.3.1
jruby-1.4.0
jruby-1.6.5
jruby-1.6.5.1
jruby-1.6.6
jruby-1.6.7
jruby[-1.6.7.2]
jruby-head
jruby-1.7.0.preview1
# Rubinius
rbx-1.0.1
rbx-1.1.1
rbx-1.2.3
rbx-1.2.4
rbx[-head]
rbx-2.0.testing
# Ruby Enterprise Edition
ree-1.8.6
ree[-1.8.7][-2012.02]
# Kiji
kiji
# MagLev
maglev[-head]
maglev-1.0.0
# Mac OS X Snow Leopard Or Newer
macruby-0.10
macruby-0.11
macruby[-0.12]
macruby-nightly
macruby-head
# IronRuby -- Not implemented yet.
ironruby-0.9.3
ironruby-1.0-rc2
ironruby-head
1.25.4. db
#General
niceness=0
# Rubies
interpreter=ruby
ruby_version=1.9.3
ruby_configure_flags=--enable-shared --disable-install-doc
ruby_patchlevel=194
ruby_configure=--enable-shared
tcs_repo_url=git://github.com/thecodeshop/ruby.git
tcs_repo_branch=trunk
ruby_repo_url=git://github.com/ruby/ruby.git
ruby_1.0_url=http://ftp.ruby-lang.org/pub/ruby/1.0
ruby_1.2_url=http://ftp.ruby-lang.org/pub/ruby/1.2
ruby_1.3_url=http://ftp.ruby-lang.org/pub/ruby/1.3
ruby_1.4_url=http://ftp.ruby-lang.org/pub/ruby/1.4
ruby_1.5_url=http://ftp.ruby-lang.org/pub/ruby/1.5
ruby_1.6_url=http://ftp.ruby-lang.org/pub/ruby/1.6
ruby_1.7_url=http://ftp.ruby-lang.org/pub/ruby/1.7
ruby_1.8_url=http://ftp.ruby-lang.org/pub/ruby/1.8
ruby_1.9_url=http://ftp.ruby-lang.org/pub/ruby/1.9
ruby_2.0_url=http://ftp.ruby-lang.org/pub/ruby/2.0
ruby_1.9.3_patch_level=194
ruby_1.9.2_patch_level=320
ruby_1.9.1_patch_level=431
ruby_1.8.7_patch_level=370
ruby_1.8.6_patch_level=420
ruby_1.8.5_patch_level=231
rubygems_url=http://production.cf.rubygems.org/rubygems
rubygems_repo_url=git://github.com/rubygems/rubygems.git
rubygems_version=latest-1.8
# ruby_1.9.3_head_rubygems_version=1.8.5
rbx_version=head
rbx_1.0.0_patch_level=20100514
rbx_1.0.1_patch_level=20100603
rbx_1.1.0_patch_level=20100923
rbx_1.1.1_patch_level=20101116
rbx_1.2.0_patch_level=20101221
rbx_1.2.1_patch_level=20110215
rbx_1.2.2_patch_level=20110222
rbx_1.2.3_patch_level=20110315
rbx_1.2.4_patch_level=20110705
rbx_url=http://asset.rubini.us
rubinius_repo_url=git://github.com/rubinius/rubinius.git
ree_version=1.8.7
ree_configure_flags=--dont-install-useful-gems --no-dev-docs
ree_1.8.6_patch_level=20090610
ree_1.8.6_url=http://rubyforge.org/frs/download.php/58677
ree_1.8.6_repo_url=git://github.com/FooBarWidget/rubyenterpriseedition.git
ree_1.8.7_url=http://rubyenterpriseedition.googlecode.com/files
ree_1.8.7_repo_url=git://github.com/FooBarWidget/rubyenterpriseedition187-330
ree_1.8.7_patch_level=2012.02
ree_1.8.7_2010.02_url=http://rubyforge.org/frs/download.php/71096
kiji_repo_url=git://github.com/twitter/rubyenterpriseedition187-248.git
kiji_version=head
jruby_version=1.6.7.2
jruby_repo_url=git://github.com/jruby/jruby.git
jruby_url=http://jruby.org.s3.amazonaws.com/downloads
macruby_version=0.12
macruby_nightly_version=0.13
macruby_0.10_url=http://macruby.macosforge.org/files
macruby_url=https://github.com/downloads/MacRuby/MacRuby
macruby_repo_url=git://github.com/MacRuby/MacRuby.git
macruby_nightly_url=http://macruby.macosforge.org/files/nightlies/macruby_nightly-latest.pkg
maglev_version=head
maglev_url=http://glass-downloads.gemstone.com/maglev
maglev_repo_url=git://github.com/MagLev/maglev.git
ironruby_version=1.0
ironruby_repo_url=git://github.com/ironruby/ironruby.git
ironruby_1.0_url=http://rubyforge.org/frs/download.php/70179/
# Packages
readline_url=http://ftp.gnu.org/gnu/readline
libiconv_url=http://ftp.gnu.org/pub/gnu/libiconv
curl_url=http://curl.haxx.se/download
openssl_url=http://www.openssl.org/source
openssl_version=1.0.1c
zlib_url=http://prdownloads.sourceforge.net/libpng
autoconf_url=http://ftp.gnu.org/gnu/autoconf
ncurses_url=http://ftp.gnu.org/pub/gnu/ncurses
pkg-config_url=http://pkgconfig.freedesktop.org/releases
gettext_url=http://ftp.gnu.org/pub/gnu/gettext
libxml2_url=ftp://xmlsoft.org/libxml2
libxslt_url=ftp://xmlsoft.org/libxslt
yaml_url=https://rvm.io/src
glib_url=http://ftp.gnome.org/pub/gnome/sources/glib/2.23
mono_url=http://ftp.novell.com/pub/mono/sources/mono
llvm_url=https://llvm.org/svn/llvm-project/llvm/trunk
1.26. patches
1.26.1. readline-6.2
1.26.1.1. patch-shobj-conf.diff
--- support/shobj-conf.orig2009-10-29 00:20:21.000000000 +1100
+++ support/shobj-conf2011-03-24 13:43:03.000000000 +1100
@@ -157,19 +157,19 @@
;;
# Darwin/MacOS X
-darwin[89]*|darwin10*)
+darwin[89]*|darwin1[0-9]*)
SHOBJ_STATUS=supported
SHLIB_STATUS=supported
SHOBJ_CFLAGS='-fno-common'
-SHOBJ_LD='MACOSX_DEPLOYMENT_TARGET=10.3 ${CC}'
+SHOBJ_LD='${CC}'
SHLIB_LIBVERSION='$(SHLIB_MAJOR)$(SHLIB_MINOR).$(SHLIB_LIBSUFF)'
SHLIB_LIBSUFF='dylib'
-SHOBJ_LDFLAGS='-dynamiclib -dynamic -undefined dynamic_lookup -arch_only `/usr/bin/arch`'
-SHLIB_XLDFLAGS='-dynamiclib -arch_only `/usr/bin/arch` -install_name $(libdir)/$@ -current_version
$(SHLIB_MAJOR)$(SHLIB_MINOR) -compatibility_version $(SHLIB_MAJOR) -v'
+SHOBJ_LDFLAGS='-dynamiclib -dynamic -undefined dynamic_lookup'
+SHLIB_XLDFLAGS='-dynamiclib -install_name $(libdir)/$@ -current_version $(SHLIB_MAJOR)$(SHLIB_MINOR) -compatibility_version
$(SHLIB_MAJOR) -v'
SHLIB_LIBS='-lncurses'# see if -lcurses works on MacOS X 10.1
;;
@@ -186,11 +186,11 @@
SHLIB_LIBSUFF='dylib'
case "${host_os}" in
-darwin[789]*|darwin10*)SHOBJ_LDFLAGS=''
-SHLIB_XLDFLAGS='-dynamiclib -arch_only `/usr/bin/arch` -install_name $(libdir)/$@ -current_version
$(SHLIB_MAJOR)$(SHLIB_MINOR) -compatibility_version $(SHLIB_MAJOR) -v'
+darwin[789]*|darwin1[0-9]*)SHOBJ_LDFLAGS=''
+SHLIB_XLDFLAGS='-dynamiclib -install_name $(libdir)/$@ -current_version $(SHLIB_MAJOR)$(SHLIB_MINOR) -compatibility_version
$(SHLIB_MAJOR) -v'
;;
*)SHOBJ_LDFLAGS='-dynamic'
-SHLIB_XLDFLAGS='-arch_only `/usr/bin/arch` -install_name $(libdir)/$@ -current_version $(SHLIB_MAJOR)$(SHLIB_MINOR) compatibility_version $(SHLIB_MAJOR) -v'
+SHLIB_XLDFLAGS='-install_name $(libdir)/$@ -current_version $(SHLIB_MAJOR)$(SHLIB_MINOR) -compatibility_version
$(SHLIB_MAJOR) -v'
;;
esac
1.26.2. goruby
1.26.2.1. support_joke.patch
--- a/vm_opts.h
+++ b/vm_opts.h
@@ -46,6 +46,6 @@
#define OPT_STACK_CACHING
0
/* misc */
-#define SUPPORT_JOKE
+#define SUPPORT_JOKE
0
1
#endif /* RUBY_VM_OPTS_H */
1.26.3. ree
1.26.3.1. lib64.patch
--- a/installer.rb
+++ b/installer.rb
@@ -281,7 +281,7 @@
if install_autoconf_package('source', 'Ruby Enterprise Edition')
# Some installed files may have wrong permissions
# (not world-readable). So we fix this.
-if sh("chmod -R g+r,o+r,o-w #{@destdir}#{@prefix}/lib/ruby")
+if sh("chmod -R g+r,o+r,o-w #{@destdir}#{@prefix}/lib*/ruby")
if @using_system_allocator_library &&
!sh("install source/libsystem_allocator.dylib #{@destdir}#{@prefix}/lib/")
return false
@@ -307,7 +307,7 @@
def install_rubygems
# We might be installing into a fakeroot, so add the fakeroot's library
# search paths to RUBYLIB so that gem installation will work.
-basedir = "#{@destdir}#{@prefix}/lib/ruby"
+basedir = "#{@destdir}#{@prefix}/lib*/ruby"
libdir = "#{basedir}/1.8"
archname = File.basename(File.dirname(Dir["#{libdir}/*/thread.#{PlatformInfo::RUBYLIBEXT}"].first))
extlibdir = "#{libdir}/#{archname}"
1.26.3.2. fix-irb-completion.diff
diff --git a/lib/irb/completion.rb b/lib/irb/completion.rb
index 000658e..609dca3 100644
--- a/lib/irb/completion.rb
+++ b/lib/irb/completion.rb
@@ -157,7 +157,7 @@ module IRB
end
next if name != "IRB::Context" and
/^(IRB|SLex|RubyLex|RubyToken)/ =~ name
candidates.concat m.instance_methods(false)
+
candidates.concat m.instance_methods(false).map { |m| m.to_s }
}
candidates.sort!
candidates.uniq!
1.26.3.3. 1.8.7
1.26.3.3.1. no_sslv2.diff
Index: ossl_ssl.c
===================================================================
--- a/ext/openssl/ossl_ssl.c(revision 32381)
+++ b/ext/openssl/ossl_ssl.c(revision 32382)
@@ -107,9 +107,12 @@
OSSL_SSL_METHOD_ENTRY(TLSv1),
OSSL_SSL_METHOD_ENTRY(TLSv1_server),
OSSL_SSL_METHOD_ENTRY(TLSv1_client),
+#if defined(HAVE_SSLV2_METHOD) && defined(HAVE_SSLV2_SERVER_METHOD) && \
+
defined(HAVE_SSLV2_CLIENT_METHOD)
OSSL_SSL_METHOD_ENTRY(SSLv2),
OSSL_SSL_METHOD_ENTRY(SSLv2_server),
OSSL_SSL_METHOD_ENTRY(SSLv2_client),
+#endif
OSSL_SSL_METHOD_ENTRY(SSLv3),
OSSL_SSL_METHOD_ENTRY(SSLv3_server),
OSSL_SSL_METHOD_ENTRY(SSLv3_client),
1.26.3.3.2. tcmalloc.patch
diff --git a/distro/google-perftools-1.7/src/tcmalloc.cc b/distro/google-perftools-1.7/src/tcmalloc.cc
index 8d94d20..0769425 100644
--- a/distro/google-perftools-1.7/src/tcmalloc.cc
+++ b/distro/google-perftools-1.7/src/tcmalloc.cc
@@ -137,6 +137,13 @@
# define WIN32_DO_PATCHING 1
#endif
+// GLibc 2.14+ requires the hook functions be declared volatile, based on the value of the
+// define __MALLOC_HOOK_VOLATILE. For compatibility with older/non-GLibc implementations,
+// provide an empty definition.
+#if !defined(__MALLOC_HOOK_VOLATILE)
+#define __MALLOC_HOOK_VOLATILE
+#endif
+
using STL_NAMESPACE::max;
using STL_NAMESPACE::numeric_limits;
using STL_NAMESPACE::vector;
@@ -1669,5 +1676,5 @@ static void *MemalignOverride(size_t align, size_t size, const void *caller)
MallocHook::InvokeNewHook(result, size);
return result;
}
-void *(*__memalign_hook)(size_t, size_t, const void *) = MemalignOverride;
+void *(*__MALLOC_HOOK_VOLATILE __memalign_hook)(size_t, size_t, const void *) = MemalignOverride;
#endif // #ifndef TCMALLOC_FOR_DEBUGALLOCATION
1.26.3.3.3. stdout-rouge-fix.patch
diff --git a/lib/mkmf.rb b/lib/mkmf.rb
index c9e738a..7a8004d 100644
--- a/lib/mkmf.rb
+++ b/lib/mkmf.rb
@@ -201,20 +201,26 @@ end
module Logging
@log = nil
@logfile = 'mkmf.log'
- @orgerr = $stderr.dup
- @orgout = $stdout.dup
@postpone = 0
@quiet = $extmk
+
+
+
+
+
+
+
+
+
+
def self::open
@log ||= File::open(@logfile, 'w')
@log.sync = true
orgerr = $stderr.dup
orgout = $stdout.dup
$stderr.reopen(@log)
$stdout.reopen(@log)
yield
ensure
$stderr.reopen(@orgerr)
$stdout.reopen(@orgout)
if orgerr
$stderr.reopen(orgerr)
orgerr.close
end
if orgout
$stdout.reopen(orgout)
orgout.close
end
end
def self::message(*s)
1.26.3.3.4. zlib-gc-fix.diff
../../ruby/1.8.7/zlib-gc-fix.diff
1.26.3.3.5. readline-fix.diff
../../ruby/1.8.7/readline-fix.diff
1.26.3.3.6. 2010.02
1.26.3.3.6.1. tcmalloc.patch
diff --git a/distro/google-perftools-1.4/src/tcmalloc.cc b/distro/google-perftools-1.4/src/tcmalloc.cc
index 8d94d20..0769425 100644
--- a/distro/google-perftools-1.4/src/tcmalloc.cc
+++ b/distro/google-perftools-1.4/src/tcmalloc.cc
@@ -137,6 +137,13 @@
# define WIN32_DO_PATCHING 1
#endif
+// GLibc 2.14+ requires the hook functions be declared volatile, based on the value of the
+// define __MALLOC_HOOK_VOLATILE. For compatibility with older/non-GLibc implementations,
+// provide an empty definition.
+#if !defined(__MALLOC_HOOK_VOLATILE)
+#define __MALLOC_HOOK_VOLATILE
+#endif
+
using STL_NAMESPACE::max;
using STL_NAMESPACE::numeric_limits;
using STL_NAMESPACE::vector;
@@ -1669,5 +1676,5 @@ static void *MemalignOverride(size_t align, size_t size, const void *caller)
MallocHook::InvokeNewHook(result, size);
return result;
}
-void *(*__memalign_hook)(size_t, size_t, const void *) = MemalignOverride;
+void *(*__MALLOC_HOOK_VOLATILE __memalign_hook)(size_t, size_t, const void *) = MemalignOverride;
#endif // #ifndef TCMALLOC_FOR_DEBUGALLOCATION
1.26.3.4. 1.8.6
1.26.3.4.1. no_sslv2.diff
Index: ossl_ssl.c
===================================================================
--- a/ext/openssl/ossl_ssl.c(revision 32381)
+++ b/ext/openssl/ossl_ssl.c(revision 32382)
@@ -107,9 +107,12 @@
OSSL_SSL_METHOD_ENTRY(TLSv1),
OSSL_SSL_METHOD_ENTRY(TLSv1_server),
OSSL_SSL_METHOD_ENTRY(TLSv1_client),
+#if defined(HAVE_SSLV2_METHOD) && defined(HAVE_SSLV2_SERVER_METHOD) && \
+
defined(HAVE_SSLV2_CLIENT_METHOD)
OSSL_SSL_METHOD_ENTRY(SSLv2),
OSSL_SSL_METHOD_ENTRY(SSLv2_server),
OSSL_SSL_METHOD_ENTRY(SSLv2_client),
+#endif
OSSL_SSL_METHOD_ENTRY(SSLv3),
OSSL_SSL_METHOD_ENTRY(SSLv3_server),
OSSL_SSL_METHOD_ENTRY(SSLv3_client),
1.26.3.4.2. tcmalloc.patch
--- a/vendor/google-perftools-1.2/src/tcmalloc.cc
+++ b/vendor/google-perftools-1.2/src/tcmalloc.cc
@@ -137,6 +137,13 @@
# define WIN32_DO_PATCHING 1
#endif
2011-02-24 02:09:12.000000000 -0800
2011-11-11 12:46:13.704738476 -0800
+// GLibc 2.14+ requires the hook functions be declared volatile, based on the value of the
+// define __MALLOC_HOOK_VOLATILE. For compatibility with older/non-GLibc implementations,
+// provide an empty definition.
+#if !defined(__MALLOC_HOOK_VOLATILE)
+#define __MALLOC_HOOK_VOLATILE
+#endif
+
using STL_NAMESPACE::max;
using STL_NAMESPACE::numeric_limits;
using STL_NAMESPACE::vector;
@@ -1669,5 +1676,5 @@ static void *MemalignOverride(size_t align, size_t size, const void *caller)
MallocHook::InvokeNewHook(result, size);
return result;
}
-void *(*__memalign_hook)(size_t, size_t, const void *) = MemalignOverride;
+void *(*__MALLOC_HOOK_VOLATILE __memalign_hook)(size_t, size_t, const void *) = MemalignOverride;
#endif // #ifndef TCMALLOC_FOR_DEBUGALLOCATION
1.26.3.4.3. perftools-gcc46.patch
--- a/vendor/google-perftools-1.2/src/system-alloc.cc2011-11-11 20:31:45.809796278 -0800
+++ b/vendor/google-perftools-1.2/src/system-alloc.cc2011-11-11 20:33:00.067244007 -0800
@@ -31,6 +31,7 @@
// Author: Sanjay Ghemawat
#include "config.h"
+#include <stddef.h>
#if defined HAVE_STDINT_H
#include <stdint.h>
#elif defined HAVE_INTTYPES_H
1.26.3.4.4. stdout-rouge-fix.patch
--- a/lib/mkmf.rb2009-06-10 09:09:22.000000000 +0200
+++ b/lib/mkmf.rb2011-11-12 02:53:05.862766935 +0100
@@ -168,19 +168,25 @@
module Logging
@log = nil
@logfile = 'mkmf.log'
- @orgerr = $stderr.dup
- @orgout = $stdout.dup
@postpone = 0
+
+
+
+
+
+
+
+
+
+
def self::open
@log ||= File::open(@logfile, 'w')
@log.sync = true
orgerr = $stderr.dup
orgout = $stdout.dup
$stderr.reopen(@log)
$stdout.reopen(@log)
yield
ensure
$stderr.reopen(@orgerr)
$stdout.reopen(@orgout)
if orgerr
$stderr.reopen(orgerr)
orgerr.close
end
if orgout
$stdout.reopen(orgout)
orgout.close
end
end
def self::message(*s)
1.26.3.4.5. openssl-1.0.patch
From 46b84175dfac14a92fd6bcf3b03bc3c3715ab6cb Mon Sep 17 00:00:00 2001
From: nahi <nahi@b2dd03c8-39d4-4d8f-98ff-823fe69b080e>
Date: Sat, 6 Mar 2010 21:47:30 +0000
Subject: [PATCH] backport the commit from trunk:
Sun Feb 28 11:49:35 2010 NARUSE, Yui <[email protected]>
* openssl/ossl.c (OSSL_IMPL_SK2ARY): for OpenSSL 1.0.
patched by Jeroen van Meeuwen at [ruby-core:25210]
fixed by Nobuyoshi Nakada [ruby-core:25238],
Hongli Lai [ruby-core:27417],
and Motohiro KOSAKI [ruby-core:28063]
* ext/openssl/ossl_ssl.c (ossl_ssl_method_tab),
(ossl_ssl_cipher_to_ary): constified.
* ext/openssl/ossl_pkcs7.c (pkcs7_get_certs, pkcs7_get_crls):
split pkcs7_get_certs_or_crls.
git-svn-id: http://svn.ruby-lang.org/repos/ruby/branches/ruby_1_8@26838 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
--ext/openssl/ossl.c
|
6 +++--ext/openssl/ossl.h
|
7 +++++++
ext/openssl/ossl_pkcs7.c
|
40 ++++++++++++++++++++++++++++++---------ext/openssl/ossl_ssl.c
|
4 ++-ext/openssl/ossl_x509attr.c |
5 +++-ext/openssl/ossl_x509crl.c |
4 ++-6 files changed, 47 insertions(+), 19 deletions(-)
diff --git a/ext/openssl/ossl.c b/ext/openssl/ossl.c
index d4a2dc1..85ba654 100644
--- a/ext/openssl/ossl.c
+++ b/ext/openssl/ossl.c
@@ -92,7 +92,7 @@ ossl_x509_ary2sk(VALUE ary)
#define OSSL_IMPL_SK2ARY(name, type)
\
VALUE\
-ossl_##name##_sk2ary(STACK *sk)\
+ossl_##name##_sk2ary(STACK_OF(type) *sk)\
{\
type *t;\
int i, num;\
@@ -102,7 +102,7 @@ ossl_##name##_sk2ary(STACK *sk)\
OSSL_Debug("empty sk!");\
return Qnil;\
}\
num = sk_num(sk);\
+
num = sk_##type##_num(sk);\
if (num < 0) {\
OSSL_Debug("items in sk < -1???");\
return rb_ary_new();\
@@ -110,7 +110,7 @@ ossl_##name##_sk2ary(STACK *sk)\
ary = rb_ary_new2(num);\
\
for (i=0; i<num; i++) {\
-t = (type *)sk_value(sk, i);\
+t = sk_##type##_value(sk, i);\
rb_ary_push(ary, ossl_##name##_new(t));\
}\
return ary;\
diff --git a/ext/openssl/ossl.h b/ext/openssl/ossl.h
index 9215dc4..d0edb7d 100644
--- a/ext/openssl/ossl.h
+++ b/ext/openssl/ossl.h
@@ -108,6 +108,13 @@ extern VALUE eOSSLError;
} while (0)
/*
+ * Compatibility
+ */
+#if OPENSSL_VERSION_NUMBER >= 0x10000000L
+#define STACK _STACK
+#endif
+
+/*
* String to HEXString conversion
*/
int string2hex(const unsigned char *, int, char **, int *);
diff --git a/ext/openssl/ossl_pkcs7.c b/ext/openssl/ossl_pkcs7.c
index fe1ef7c..b0cc656 100644
--- a/ext/openssl/ossl_pkcs7.c
+++ b/ext/openssl/ossl_pkcs7.c
@@ -572,12 +572,11 @@ ossl_pkcs7_add_certificate(VALUE self, VALUE cert)
return self;
}
-static STACK *
-pkcs7_get_certs_or_crls(VALUE self, int want_certs)
+static STACK_OF(X509) *
+pkcs7_get_certs(VALUE self)
{
PKCS7 *pkcs7;
STACK_OF(X509) *certs;
STACK_OF(X509_CRL) *crls;
int i;
-
GetPKCS7(self, pkcs7);
@@ -585,17 +584,38 @@ pkcs7_get_certs_or_crls(VALUE self, int want_certs)
switch(i){
case NID_pkcs7_signed:
certs = pkcs7->d.sign->cert;
crls = pkcs7->d.sign->crl;
break;
case NID_pkcs7_signedAndEnveloped:
certs = pkcs7->d.signed_and_enveloped->cert;
+
break;
+
default:
+
certs = NULL;
+
}
+
+
return certs;
+}
+
+static STACK_OF(X509_CRL) *
+pkcs7_get_crls(VALUE self)
+{
+
PKCS7 *pkcs7;
+
STACK_OF(X509_CRL) *crls;
+
int i;
+
+
GetPKCS7(self, pkcs7);
+
i = OBJ_obj2nid(pkcs7->type);
+
switch(i){
+
case NID_pkcs7_signed:
+
crls = pkcs7->d.sign->crl;
+
break;
+
case NID_pkcs7_signedAndEnveloped:
crls = pkcs7->d.signed_and_enveloped->crl;
break;
default:
certs = crls = NULL;
+
crls = NULL;
}
+
return want_certs ? certs : crls;
return crls;
}
static VALUE
@@ -610,7 +630,7 @@ ossl_pkcs7_set_certificates(VALUE self, VALUE ary)
STACK_OF(X509) *certs;
X509 *cert;
+
certs = pkcs7_get_certs_or_crls(self, 1);
certs = pkcs7_get_certs(self);
while((cert = sk_X509_pop(certs))) X509_free(cert);
rb_block_call(ary, rb_intern("each"), 0, 0, ossl_pkcs7_set_certs_i, self);
@@ -620,7 +640,7 @@ ossl_pkcs7_set_certificates(VALUE self, VALUE ary)
static VALUE
ossl_pkcs7_get_certificates(VALUE self)
{
return ossl_x509_sk2ary(pkcs7_get_certs_or_crls(self, 1));
+
return ossl_x509_sk2ary(pkcs7_get_certs(self));
}
static VALUE
@@ -650,7 +670,7 @@ ossl_pkcs7_set_crls(VALUE self, VALUE ary)
STACK_OF(X509_CRL) *crls;
X509_CRL *crl;
+
crls = pkcs7_get_certs_or_crls(self, 0);
crls = pkcs7_get_crls(self);
while((crl = sk_X509_CRL_pop(crls))) X509_CRL_free(crl);
rb_block_call(ary, rb_intern("each"), 0, 0, ossl_pkcs7_set_crls_i, self);
@@ -660,7 +680,7 @@ ossl_pkcs7_set_crls(VALUE self, VALUE ary)
static VALUE
ossl_pkcs7_get_crls(VALUE self)
{
return ossl_x509crl_sk2ary(pkcs7_get_certs_or_crls(self, 0));
+
return ossl_x509crl_sk2ary(pkcs7_get_crls(self));
}
static VALUE
diff --git a/ext/openssl/ossl_ssl.c b/ext/openssl/ossl_ssl.c
index 432ca21..facf6ca 100644
--- a/ext/openssl/ossl_ssl.c
+++ b/ext/openssl/ossl_ssl.c
@@ -1291,10 +1291,10 @@ ossl_ssl_get_peer_cert_chain(VALUE self)
}
chain = SSL_get_peer_cert_chain(ssl);
if(!chain) return Qnil;
num = sk_num(chain);
+
num = sk_X509_num(chain);
ary = rb_ary_new2(num);
for (i = 0; i < num; i++){
-cert = (X509*)sk_value(chain, i);
+cert = sk_X509_value(chain, i);
rb_ary_push(ary, ossl_x509_new(cert));
}
diff --git a/ext/openssl/ossl_x509attr.c b/ext/openssl/ossl_x509attr.c
index 1f817cd..2a4c481 100644
--- a/ext/openssl/ossl_x509attr.c
+++ b/ext/openssl/ossl_x509attr.c
@@ -218,8 +218,9 @@ ossl_x509attr_get_value(VALUE self)
ossl_str_adjust(str, p);
}
else{
-length = i2d_ASN1_SET_OF_ASN1_TYPE(attr->value.set, NULL,
-i2d_ASN1_TYPE, V_ASN1_SET, V_ASN1_UNIVERSAL, 0);
+length = i2d_ASN1_SET_OF_ASN1_TYPE(attr->value.set,
+(unsigned char **) NULL, i2d_ASN1_TYPE,
+V_ASN1_SET, V_ASN1_UNIVERSAL, 0);
str = rb_str_new(0, length);
p = (unsigned char *)RSTRING_PTR(str);
i2d_ASN1_SET_OF_ASN1_TYPE(attr->value.set, &p,
diff --git a/ext/openssl/ossl_x509crl.c b/ext/openssl/ossl_x509crl.c
index 1be9640..818fdba 100644
--- a/ext/openssl/ossl_x509crl.c
+++ b/ext/openssl/ossl_x509crl.c
@@ -264,7 +264,7 @@ ossl_x509crl_get_revoked(VALUE self)
VALUE ary, revoked;
GetX509CRL(self, crl);
num = sk_X509_CRL_num(X509_CRL_get_REVOKED(crl));
num = sk_X509_REVOKED_num(X509_CRL_get_REVOKED(crl));
if (num < 0) {
OSSL_Debug("num < 0???");
return rb_ary_new();
@@ -272,7 +272,7 @@ ossl_x509crl_get_revoked(VALUE self)
ary = rb_ary_new2(num);
for(i=0; i<num; i++) {
/* NO DUP - don't free! */
-rev = (X509_REVOKED *)sk_X509_CRL_value(X509_CRL_get_REVOKED(crl), i);
+rev = sk_X509_REVOKED_value(X509_CRL_get_REVOKED(crl), i);
revoked = ossl_x509revoked_new(rev);
rb_ary_push(ary, revoked);
}
-1.7.0.3
+
1.26.4. tcs
1.26.4.1. support_joke.patch
--- a/vm_opts.h
+++ b/vm_opts.h
@@ -46,6 +46,6 @@
#define OPT_STACK_CACHING
0
/* misc */
-#define SUPPORT_JOKE
+#define SUPPORT_JOKE
0
1
#endif /* RUBY_VM_OPTS_H */
1.26.5. ruby
1.26.5.1. 1.8.7
1.26.5.1.1. osx-arch-fix.patch
diff --git a/Makefile.in b/Makefile.in
index 656ae90..f976cf1 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -45,7 +45,7 @@ XLDFLAGS = @XLDFLAGS@ $(EXTLDFLAGS)
EXTLIBS =
LIBS = @LIBS@ $(EXTLIBS)
MISSING = @LIBOBJS@ @ALLOCA@
-LDSHARED = @LIBRUBY_LDSHARED@
+LDSHARED = @LIBRUBY_LDSHARED@ $(LDFLAGS)
DLDFLAGS = @LIBRUBY_DLDFLAGS@ $(EXTLDFLAGS) @ARCH_FLAG@
SOLIBS = @SOLIBS@
MAINLIBS = @MAINLIBS@
1.26.5.1.2. no_sslv2.diff
Index: ossl_ssl.c
===================================================================
--- a/ext/openssl/ossl_ssl.c(revision 32381)
+++ b/ext/openssl/ossl_ssl.c(revision 32382)
@@ -107,9 +107,12 @@
OSSL_SSL_METHOD_ENTRY(TLSv1),
OSSL_SSL_METHOD_ENTRY(TLSv1_server),
OSSL_SSL_METHOD_ENTRY(TLSv1_client),
+#if defined(HAVE_SSLV2_METHOD) && defined(HAVE_SSLV2_SERVER_METHOD) && \
+
defined(HAVE_SSLV2_CLIENT_METHOD)
OSSL_SSL_METHOD_ENTRY(SSLv2),
OSSL_SSL_METHOD_ENTRY(SSLv2_server),
OSSL_SSL_METHOD_ENTRY(SSLv2_client),
+#endif
OSSL_SSL_METHOD_ENTRY(SSLv3),
OSSL_SSL_METHOD_ENTRY(SSLv3_server),
OSSL_SSL_METHOD_ENTRY(SSLv3_client),
1.26.5.1.3. ruby187gc.patch
--- a/intern.h(revision 31212)
+++ b/intern.h(working copy)
@@ -270,6 +270,15 @@
VALUE rb_gc_enable _((void));
VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
+VALUE rb_gc_enable_stats _((void));
+VALUE rb_gc_disable_stats _((void));
+VALUE rb_gc_allocated_size _((void));
+unsigned long rb_os_live_objects _((void));
+#ifdef HAVE_LONG_LONG
+unsigned long long rb_os_allocated_objects _((void));
+#else
+unsigned long rb_os_allocated_objects _((void));
+#endif
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
--- a/gc.c(revision 31212)
+++ b/gc.c(working copy)
@@ -22,8 +22,16 @@
#include <setjmp.h>
#include <sys/types.h>
+#ifdef _WIN32
+#include <string.h>
+#else
+#include <strings.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
+#elif defined(_WIN32)
+#include <time.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H
@@ -76,6 +84,20 @@
static VALUE nomem_error;
static void garbage_collect();
+static unsigned long live_objects = 0;
+unsigned long rb_os_live_objects()
+{ return live_objects; }
+
+#if defined(HAVE_LONG_LONG)
+static unsigned long long allocated_objects = 0;
+unsigned long long rb_os_allocated_objects()
+{ return allocated_objects; }
+#else
+static unsigned long allocated_objects = 0;
+unsigned long rb_os_allocated_objects()
+{ return allocated_objects; }
+#endif
+
int ruby_gc_stress = 0;
NORETURN(void rb_exc_jump _((VALUE)));
@@ -132,6 +154,10 @@
return bool;
}
+long gc_allocated_size = 0;
+long gc_num_allocations = 0;
+static int gc_statistics = 0;
+
void *
ruby_xmalloc(size)
long size;
@@ -156,6 +182,11 @@
}
malloc_increase += size;
+
+
+
+
+
if (gc_statistics) {
gc_allocated_size += size;
gc_num_allocations += 1;
}
return mem;
}
@@ -205,8 +236,16 @@
RUBY_CRITICAL(free(x));
}
+#if HAVE_LONG_LONG
+#define GC_TIME_TYPE LONG_LONG
+#else
+#define GC_TIME_TYPE long
+#endif
+
extern int ruby_in_compile;
static int dont_gc;
+static GC_TIME_TYPE gc_time = 0;
+static int gc_collections = 0;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -255,6 +294,139 @@
return old;
}
+/*
+ * call-seq:
+ *
GC.enable_stats
=> true or false
+ *
+ * Enables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already enabled.
+ *
+ *
GC.enable_stats
#=> false or true
+ *
GC.enable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_stats
=> true or false
+ *
+ * Disables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already disabled.
+ *
+ *
GC.disable_stats
#=> false or true
+ *
GC.disable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qfalse;
+
gc_allocated_size = 0;
+
gc_num_allocations = 0;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.clear_stats
=> nil
+ *
+ * Clears garbage collection statistics, returning nil. This resets the number
+ * of collections (GC.collections) and the time used (GC.time) to 0.
+ *
+ *
GC.clear_stats
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_clear_stats()
+{
+
gc_collections = 0;
+
gc_time = 0;
+
gc_allocated_size = 0;
+
gc_num_allocations = 0;
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.allocated_size
=> Integer
+ *
+ * Returns the size of memory (in bytes) allocated since GC statistics collection
+ * was enabled.
+ *
+ *
GC.allocated_size
#=> 35
+ *
+ */
+VALUE
+rb_gc_allocated_size()
+{
+
return INT2NUM(gc_allocated_size);
+}
+
+/*
+ * call-seq:
+ *
GC.num_allocations
=> Integer
+ *
+ * Returns the number of memory allocations since GC statistics collection
+ * was enabled.
+ *
+ *
GC.num_allocations
#=> 150
+ *
+ */
+VALUE
+rb_gc_num_allocations()
+{
+
return INT2NUM(gc_num_allocations);
+}
+
+/*
+ * call-seq:
+ *
GC.collections
=> Integer
+ *
+ * Returns the number of garbage collections performed while GC statistics collection
+ * was enabled.
+ *
+ *
GC.collections
#=> 35
+ *
+ */
+
+VALUE
+rb_gc_collections()
+{
+
return INT2NUM(gc_collections);
+}
+
+/*
+ * call-seq:
+ *
GC.time
=> Integer
+ *
+ * Returns the time spent during garbage collection while GC statistics collection
+ * was enabled (in micro seconds).
+ *
+ *
GC.time
#=> 20000
+ *
+ */
+
+VALUE
+rb_gc_time()
+{
+#if HAVE_LONG_LONG
+
return LL2NUM(gc_time);
+#else
+
return LONG2NUM(gc_time);
+#endif
+}
+
VALUE rb_mGC;
static struct gc_list {
@@ -346,7 +518,7 @@
static RVALUE *freelist = 0;
static RVALUE *deferred_final_list = 0;
-#define HEAPS_INCREMENT 10
+static int heaps_increment = 10;
static struct heaps_slot {
void *membase;
RVALUE *slot;
@@ -355,13 +527,164 @@
static int heaps_length = 0;
static int heaps_used
= 0;
-#define HEAP_MIN_SLOTS 10000
-static int heap_slots = HEAP_MIN_SLOTS;
+static int heap_min_slots = 10000;
+static int heap_slots = 10000;
-#define FREE_MIN 4096
+static int heap_free_min = 4096;
+static int heap_slots_increment = 10000;
+static double heap_slots_growth_factor = 1.8;
+static
+
+static
+
+static
+
static
long initial_malloc_limit = GC_MALLOC_LIMIT;
int verbose_gc_stats = Qfalse;
FILE* gc_data_file = NULL;
RVALUE *himem, *lomem;
+static void set_gc_parameters()
+{
+
char *gc_stats_ptr, *min_slots_ptr, *free_min_ptr, *heap_slots_incr_ptr,
+
*heap_incr_ptr, *malloc_limit_ptr, *gc_heap_file_ptr, *heap_slots_growth_factor_ptr;
+
+
gc_data_file = stderr;
+
+
gc_stats_ptr = getenv("RUBY_GC_STATS");
+
if (gc_stats_ptr != NULL) {
+ int gc_stats_i = atoi(gc_stats_ptr);
+ if (gc_stats_i > 0) {
+
verbose_gc_stats = Qtrue;
+ }
+
}
+
+
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
+
if (gc_heap_file_ptr != NULL) {
+ FILE* data_file = fopen(gc_heap_file_ptr, "w");
+ if (data_file != NULL) {
+
gc_data_file = data_file;
+ }
+ else {
+
fprintf(stderr,
+
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
+ }
+
}
+
+
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
+
if (min_slots_ptr != NULL) {
+ int min_slots_i = atoi(min_slots_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_MIN_SLOTS=%s\n", min_slots_ptr);
+
}
+ if (min_slots_i > 0) {
+
heap_slots = min_slots_i;
+
heap_min_slots = min_slots_i;
+ }
+
}
+
+
free_min_ptr = getenv("RUBY_HEAP_FREE_MIN");
+
if (free_min_ptr != NULL) {
+ int free_min_i = atoi(free_min_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_FREE_MIN=%s\n", free_min_ptr);
+ }
+ if (free_min_i > 0) {
+
heap_free_min = free_min_i;
+ }
+
}
+
+
heap_incr_ptr = getenv("RUBY_HEAP_INCREMENT");
+
if (heap_incr_ptr != NULL) {
+ int heap_incr_i = atoi(heap_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_INCREMENT=%s\n", heap_incr_ptr);
+ }
+ if (heap_incr_i > 0) {
+
heaps_increment = heap_incr_i;
+ }
+
}
+
+
heap_slots_incr_ptr = getenv("RUBY_HEAP_SLOTS_INCREMENT");
+
if (heap_slots_incr_ptr != NULL) {
+ int heap_slots_incr_i = atoi(heap_slots_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
+ }
+ if (heap_slots_incr_i > 0) {
+
heap_slots_increment = heap_slots_incr_i;
+ }
+
}
+
+
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
+
if (heap_slots_growth_factor_ptr != NULL) {
+ double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
+ }
+ if (heap_slots_growth_factor_d > 0) {
+
heap_slots_growth_factor = heap_slots_growth_factor_d;
+ }
+
}
+
+
malloc_limit_ptr = getenv("RUBY_GC_MALLOC_LIMIT");
+
if (malloc_limit_ptr != NULL) {
+ int malloc_limit_i = atol(malloc_limit_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_GC_MALLOC_LIMIT=%s\n", malloc_limit_ptr);
+ }
+ if (malloc_limit_i > 0) {
+
initial_malloc_limit = malloc_limit_i;
+ }
+
}
+}
+
+/*
+ * call-seq:
+ *
GC.dump
=> nil
+ *
+ * dumps information about the current GC data structures to the GC log file
+ *
+ *
GC.dump
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_dump()
+{
+
int i;
+
+
for (i = 0; i < heaps_used; i++) {
+ int heap_size = heaps[i].limit;
+ fprintf(gc_data_file, "HEAP[%2d]: size=%7d\n", i, heap_size);
+
}
+
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.log String => String
+ *
+ * Logs string to the GC data file and returns it.
+ *
+ *
GC.log "manual GC call"
#=> "manual GC call"
+ *
+ */
+
+VALUE
+rb_gc_log(self, original_str)
+
VALUE self, original_str;
+{
+
if (original_str == Qnil) {
+
fprintf(gc_data_file, "\n");
+
}
+
else {
+
VALUE str = StringValue(original_str);
+
char *p = RSTRING(str)->ptr;
+
fprintf(gc_data_file, "%s\n", p);
+
}
+
return original_str;
+}
+
static void
add_heap()
{
@@ -372,7 +695,7 @@
struct heaps_slot *p;
int length;
-heaps_length += HEAPS_INCREMENT;
+heaps_length += heaps_increment;
length = heaps_length*sizeof(struct heaps_slot);
RUBY_CRITICAL(
if (heaps_used > 0) {
@@ -388,10 +711,10 @@
for (;;) {
RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
if (p == 0) {
if (heap_slots == HEAP_MIN_SLOTS) {
+
if (heap_slots == heap_min_slots) {
rb_memerror();
}
heap_slots = HEAP_MIN_SLOTS;
+
heap_slots = heap_min_slots;
continue;
}
heaps[heaps_used].membase = p;
@@ -407,8 +730,9 @@
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots *= 1.8;
if (heap_slots <= 0) heap_slots = HEAP_MIN_SLOTS;
+
heap_slots += heap_slots_increment;
+
heap_slots_increment *= heap_slots_growth_factor;
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
p->as.free.flags = 0;
@@ -442,6 +766,8 @@
RANY(obj)->file = ruby_sourcefile;
RANY(obj)->line = ruby_sourceline;
#endif
+
live_objects++;
+
allocated_objects++;
return obj;
}
@@ -1102,6 +1428,39 @@
}
}
+static char* obj_type(int tp)
+{
+
switch (tp) {
+case T_NIL
: return "NIL";
+case T_OBJECT : return "OBJECT";
+case T_CLASS : return "CLASS";
+case T_ICLASS : return "ICLASS";
+case T_MODULE : return "MODULE";
+case T_FLOAT : return "FLOAT";
+case T_STRING : return "STRING";
+case T_REGEXP : return "REGEXP";
+case T_ARRAY : return "ARRAY";
+case T_FIXNUM : return "FIXNUM";
+case T_HASH
: return "HASH";
+case T_STRUCT : return "STRUCT";
+case T_BIGNUM : return "BIGNUM";
+case T_FILE
: return "FILE";
+
+case T_TRUE
: return "TRUE";
+case T_FALSE : return "FALSE";
+case T_DATA
: return "DATA";
+case T_MATCH : return "MATCH";
+case T_SYMBOL : return "SYMBOL";
+
+case T_BLKTAG : return "BLKTAG";
+case T_UNDEF : return "UNDEF";
+case T_VARMAP : return "VARMAP";
+case T_SCOPE : return "SCOPE";
+case T_NODE
: return "NODE";
+default: return "____";
+
}
+}
+
static void
free_unused_heaps()
{
@@ -1133,14 +1492,24 @@
int i;
unsigned long live = 0;
unsigned long free_min = 0;
+
live_objects = 0;
+
+
+
+
+
+
+
+
+
+
+
unsigned long really_freed = 0;
int free_counts[256];
int live_counts[256];
int do_gc_stats = gc_statistics & verbose_gc_stats;
for (i = 0; i < heaps_used; i++) {
free_min += heaps[i].limit;
}
free_min = free_min * 0.2;
if (free_min < FREE_MIN)
free_min = FREE_MIN;
if (free_min < heap_free_min)
free_min = heap_free_min;
if (do_gc_stats) {
for (i = 0 ; i< 256; i++) { free_counts[i] = live_counts[i] = 0; }
}
if (ruby_in_compile && ruby_parser_stack_on_heap()) {
/* should not reclaim nodes during compilation
if yacc's semantic stack is not allocated on machine stack */
@@ -1171,6 +1540,11 @@
p = heaps[i].slot; pend = p + heaps[i].limit;
while (p < pend) {
if (!(p->as.basic.flags & FL_MARK)) {
+
if (p->as.basic.flags) {
+
if (do_gc_stats) {
+
really_freed++;
+
}
+
}
if (p->as.basic.flags &&
((deferred = obj_free((VALUE)p)) ||
((FL_TEST(p, FL_FINALIZE)) && need_call_final))) {
@@ -1183,6 +1557,12 @@
final_list = p;
}
else {
+
if (do_gc_stats) {
+
int obt = p->as.basic.flags & T_MASK;
+
if (obt) {
+
free_counts[obt]++;
+
}
+
}
add_freelist(p);
}
n++;
@@ -1193,7 +1573,10 @@
}
else {
RBASIC(p)->flags &= ~FL_MARK;
-live++;
+live_objects++;
+if (do_gc_stats) {
+ live_counts[RANY((VALUE)p)->as.basic.flags & T_MASK]++;
+}
}
p++;
}
@@ -1211,8 +1594,8 @@
}
}
if (malloc_increase > malloc_limit) {
-malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
-if (malloc_limit < GC_MALLOC_LIMIT) malloc_limit = GC_MALLOC_LIMIT;
+
malloc_limit += (malloc_increase - malloc_limit) * (double)live_objects / (live_objects + freed);
+
if (malloc_limit < initial_malloc_limit) malloc_limit = initial_malloc_limit;
}
malloc_increase = 0;
if (freed < free_min) {
@@ -1220,6 +1603,20 @@
}
during_gc = 0;
+
+
+
+
+
+
+
+
+
+
+
+
+
+
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects: %.7d\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0) {
fprintf(gc_data_file,
"kept %.7d / freed %.7d objects of type %s\n",
live_counts[i], free_counts[i], obj_type(i));
}
}
}
/* clear finalization list */
if (final_list) {
deferred_final_list = final_list;
@@ -1431,6 +1828,7 @@
struct gc_list *list;
struct FRAME * volatile frame; /* gcc 2.7.2.3 -O2 bug??
jmp_buf save_regs_gc_mark;
+
struct timeval gctv1, gctv2;
SET_STACK_END;
*/
#ifdef HAVE_NATIVETHREAD
@@ -1447,6 +1845,14 @@
if (during_gc) return;
during_gc++;
+
+
+
+
+
+
+
+
if (gc_statistics) {
gc_collections++;
gettimeofday(&gctv1, NULL);
if (verbose_gc_stats) {
fprintf(gc_data_file, "Garbage collection started\n");
}
}
init_mark_stack();
gc_mark((VALUE)ruby_current_node, 0);
@@ -1522,6 +1928,16 @@
} while (!MARK_STACK_EMPTY);
gc_sweep();
if (gc_statistics) {
GC_TIME_TYPE musecs_used;
gettimeofday(&gctv2, NULL);
musecs_used = ((GC_TIME_TYPE)(gctv2.tv_sec - gctv1.tv_sec) * 1000000) + (gctv2.tv_usec - gctv1.tv_usec);
gc_time += musecs_used;
+
+
+
+
+
+
+
+
+
+
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
}
}
}
void
@@ -1703,6 +2119,7 @@
if (!rb_gc_stack_start) {
Init_stack(0);
}
+
set_gc_parameters();
add_heap();
}
@@ -2147,6 +2564,33 @@
return (VALUE)((long)obj|FIXNUM_FLAG);
}
+/* call-seq:
+ * ObjectSpace.live_objects => number
+ *
+ * Returns the count of objects currently allocated in the system. This goes
+ * down after the garbage collector runs.
+ */
+static
+VALUE os_live_objects(VALUE self)
+{ return ULONG2NUM(live_objects); }
+
+/* call-seq:
+ * ObjectSpace.allocated_objects => number
+ *
+ * Returns the count of objects allocated since the Ruby interpreter has
+ * started. This number can only increase. To know how many objects are
+ * currently allocated, use ObjectSpace::live_objects
+ */
+static
+VALUE os_allocated_objects(VALUE self)
+{
+#if defined(HAVE_LONG_LONG)
+
return ULL2NUM(allocated_objects);
+#else
+
return ULONG2NUM(allocated_objects);
+#endif
+}
+
/*
* The <code>GC</code> module provides an interface to Ruby's mark and
* sweep garbage collection mechanism. Some of the underlying methods
@@ -2166,6 +2610,16 @@
rb_define_singleton_method(rb_mGC, "stress=", gc_stress_set, 1);
rb_define_method(rb_mGC, "garbage_collect", rb_gc_start, 0);
+
+
+
+
+
+
+
+
+
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"clear_stats", rb_gc_clear_stats, 0);
"allocated_size", rb_gc_allocated_size, 0);
"num_allocations", rb_gc_num_allocations, 0);
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
rb_define_module_function(rb_mObSpace, "garbage_collect", rb_gc_start, 0);
@@ -2173,6 +2627,8 @@
rb_define_module_function(rb_mObSpace, "remove_finalizer", rm_final, 1);
rb_define_module_function(rb_mObSpace, "finalizers", finals, 0);
rb_define_module_function(rb_mObSpace, "call_finalizer", call_final, 1);
+
rb_define_module_function(rb_mObSpace, "live_objects", os_live_objects, 0);
+
rb_define_module_function(rb_mObSpace, "allocated_objects", os_allocated_objects, 0);
rb_define_module_function(rb_mObSpace, "define_finalizer", define_final, -1);
rb_define_module_function(rb_mObSpace, "undefine_finalizer", undefine_final, 1);
1.26.5.1.4. hs.patch
diff --git a/eval.c b/eval.c
index b705302..909cd3d 100644
--- a/eval.c
+++ b/eval.c
@@ -73,6 +73,7 @@ char *strrchr _((const char*,const char));
#endif
#include <time.h>
+#include <sys/mman.h>
#ifdef __BEOS__
#include <net/socket.h>
@@ -1022,7 +1023,7 @@ static struct tag *prot_tag;
_tag.blkid = 0;\
prot_tag = &_tag
-#define PROT_NONE
Qfalse/* 0 */
+#define PROT_EMPTY Qfalse/* 0 */
#define PROT_THREAD Qtrue/* 2 */
#define PROT_FUNC
INT2FIX(0)/* 1 */
#define PROT_LOOP
INT2FIX(1)/* 3 */
@@ -1234,7 +1235,7 @@ error_print()
if (NIL_P(ruby_errinfo)) return;
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if (EXEC_TAG() == 0) {
errat = get_backtrace(ruby_errinfo);
}
@@ -1395,7 +1396,7 @@ ruby_init()
/* default visibility is private at toplevel */
SCOPE_SET(SCOPE_PRIVATE);
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
rb_call_inits();
ruby_class = rb_cObject;
@@ -1529,7 +1530,7 @@ ruby_options(argc, argv)
int state;
Init_stack((void*)&state);
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
ruby_process_options(argc, argv);
}
@@ -1546,7 +1547,7 @@ void rb_exec_end_proc _((void));
static void
ruby_finalize_0()
{
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
if (EXEC_TAG() == 0) {
rb_trap_exit();
}
@@ -1584,7 +1585,7 @@ ruby_cleanup(ex)
Init_stack((void *)&state);
ruby_finalize_0();
errs[0] = ruby_errinfo;
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
PUSH_ITER(ITER_NOT);
if ((state = EXEC_TAG()) == 0) {
rb_thread_cleanup();
@@ -1635,7 +1636,7 @@ ruby_exec_internal()
{
int state;
+
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
PUSH_ITER(ITER_NOT);
/* default visibility is private at toplevel */
SCOPE_SET(SCOPE_PRIVATE);
@@ -1857,7 +1858,7 @@ rb_eval_cmd(cmd, arg, level)
}
if (TYPE(cmd) != T_STRING) {
PUSH_ITER(ITER_NOT);
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
ruby_safe_level = level;
if ((state = EXEC_TAG()) == 0) {
val = rb_funcall2(cmd, rb_intern("call"), RARRAY(arg)->len, RARRAY(arg)->ptr);
@@ -1879,7 +1880,7 @@ rb_eval_cmd(cmd, arg, level)
ruby_safe_level = level;
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
val = eval(ruby_top_self, cmd, Qnil, 0, 0);
}
@@ -2386,7 +2387,7 @@ is_defined(self, node, buf)
val = self;
if (node->nd_recv == (NODE *)1) goto check_bound;
case NODE_CALL:
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
val = rb_eval(self, node->nd_recv);
}
@@ -2488,7 +2489,7 @@ is_defined(self, node, buf)
break;
case NODE_COLON2:
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
val = rb_eval(self, node->nd_head);
}
@@ -2537,7 +2538,7 @@ is_defined(self, node, buf)
goto again;
default:
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
rb_eval(self, node);
}
@@ -2741,7 +2742,7 @@ call_trace_func(event, node, self, id, klass)
klass = rb_iv_get(klass, "__attached__");
}
}
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
raised = rb_thread_reset_raised(th);
if ((state = EXEC_TAG()) == 0) {
srcfile = rb_str_new2(ruby_sourcefile?ruby_sourcefile:"(ruby)");
@@ -3304,7 +3305,7 @@ rb_eval(self, n)
volatile VALUE e_info = ruby_errinfo;
volatile int rescuing = 0;
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
retry_entry:
result = rb_eval(self, node->nd_head);
@@ -3353,7 +3354,7 @@ rb_eval(self, n)
break;
case NODE_ENSURE:
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
result = rb_eval(self, node->nd_head);
}
@@ -3571,7 +3572,7 @@ rb_eval(self, n)
ruby_frame = &frame;
PUSH_SCOPE();
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if (node->nd_rval) {
saved_cref = ruby_cref;
ruby_cref = (NODE*)node->nd_rval;
@@ -4197,7 +4198,7 @@ module_setup(module, n)
}
+
PUSH_CREF(module);
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
EXEC_EVENT_HOOK(RUBY_EVENT_CLASS, n, ruby_cbase,
ruby_frame->last_func, ruby_frame->last_class);
@@ -4604,7 +4605,7 @@ rb_longjmp(tag, mesg)
VALUE e = ruby_errinfo;
int status;
+
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((status = EXEC_TAG()) == 0) {
StringValue(e);
warn_printf("Exception `%s' at %s:%d - %s\n",
@@ -4978,7 +4979,7 @@ rb_yield_0(val, self, klass, flags, avalue)
var = block->var;
if (var) {
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
NODE *bvar = NULL;
block_var:
@@ -5051,7 +5052,7 @@ rb_yield_0(val, self, klass, flags, avalue)
ruby_current_node = node;
PUSH_ITER(block->iter);
PUSH_TAG(lambda ? PROT_NONE : PROT_YIELD);
PUSH_TAG(lambda ? PROT_EMPTY : PROT_YIELD);
if ((state = EXEC_TAG()) == 0) {
redo:
if (nd_type(node) == NODE_CFUNC || nd_type(node) == NODE_IFUNC) {
@@ -5464,7 +5465,7 @@ rb_rescue2(b_proc, data1, r_proc, data2, va_alist)
VALUE eclass;
va_list args;
+
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
switch (state = EXEC_TAG()) {
case TAG_RETRY:
if (!handle) break;
@@ -5522,7 +5523,7 @@ rb_protect(proc, data, state)
VALUE result = Qnil;/* OK */
int status;
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
cont_protect = (VALUE)rb_node_newnode(NODE_MEMO, cont_protect, 0, 0);
if ((status = EXEC_TAG()) == 0) {
result = (*proc)(data);
@@ -5550,7 +5551,7 @@ rb_ensure(b_proc, data1, e_proc, data2)
volatile VALUE result = Qnil;
VALUE retval;
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
result = (*b_proc)(data1);
}
@@ -5577,7 +5578,7 @@ rb_with_disable_interrupt(proc, data)
int thr_critical = rb_thread_critical;
rb_thread_critical = Qtrue;
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((status = EXEC_TAG()) == 0) {
result = (*proc)(data);
}
@@ -6264,7 +6265,7 @@ rb_funcall_rescue(recv, mid, n, va_alist)
va_init_list(ar, n);
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((status = EXEC_TAG()) == 0) {
result = vafuncall(recv, mid, n, &ar);
}
@@ -6539,7 +6540,7 @@ eval(self, src, scope, file, line)
if (TYPE(ruby_class) == T_ICLASS) {
ruby_class = RBASIC(ruby_class)->klass;
}
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
NODE *node;
@@ -6698,7 +6699,7 @@ exec_under(func, under, cbase, args)
mode = scope_vmode;
SCOPE_SET(SCOPE_PUBLIC);
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
val = (*func)(args);
}
@@ -7009,7 +7010,7 @@ rb_load(fname, wrap)
PUSH_SCOPE();
/* default visibility is private at loading toplevel */
SCOPE_SET(SCOPE_PRIVATE);
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
state = EXEC_TAG();
last_func = ruby_frame->last_func;
last_node = ruby_current_node;
@@ -7068,7 +7069,7 @@ rb_load_protect(fname, wrap, state)
{
int status;
+
PUSH_TAG(PROT_NONE);
PUSH_TAG(PROT_EMPTY);
if ((status = EXEC_TAG()) == 0) {
rb_load(fname, wrap);
}
@@ -7389,7 +7390,7 @@ rb_require_safe(fname, safe)
saved.node = ruby_current_node;
saved.func = ruby_frame->last_func;
saved.safe = ruby_safe_level;
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
VALUE feature, path;
long handle;
@@ -8097,7 +8098,7 @@ rb_exec_end_proc()
tmp_end_procs = link = ephemeral_end_procs;
ephemeral_end_procs = 0;
while (link) {
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
if ((status = EXEC_TAG()) == 0) {
ruby_safe_level = link->safe;
(*link->func)(link->data);
@@ -8115,7 +8116,7 @@ rb_exec_end_proc()
tmp_end_procs = link = end_procs;
end_procs = 0;
while (link) {
PUSH_TAG(PROT_NONE);
+
PUSH_TAG(PROT_EMPTY);
if ((status = EXEC_TAG()) == 0) {
ruby_safe_level = link->safe;
(*link->func)(link->data);
@@ -8852,7 +8853,7 @@ proc_invoke(proc, args, self, klass)
ruby_block = &_block;
PUSH_ITER(ITER_CUR);
ruby_frame->iter = ITER_CUR;
PUSH_TAG(pcall ? PROT_LAMBDA : PROT_NONE);
+
PUSH_TAG(pcall ? PROT_LAMBDA : PROT_EMPTY);
state = EXEC_TAG();
if (state == 0) {
proc_set_safe_level(proc);
@@ -10179,6 +10180,7 @@ win32_set_exception_list(p)
int rb_thread_pending = 0;
VALUE rb_cThread;
+static unsigned int rb_thread_stack_size;
extern VALUE rb_last_status;
@@ -10406,12 +10408,20 @@ thread_mark(th)
rb_gc_mark(th->thread);
if (th->join) rb_gc_mark(th->join->thread);
+
+
+
+
+
+
+
+
+
+
+
+
+
rb_gc_mark(th->klass);
rb_gc_mark(th->wrapper);
rb_gc_mark((VALUE)th->cref);
if (curr_thread == th) {
rb_gc_mark(ruby_class);
rb_gc_mark(ruby_wrapper);
rb_gc_mark((VALUE)ruby_cref);
rb_gc_mark((VALUE)ruby_scope);
rb_gc_mark((VALUE)ruby_dyna_vars);
} else {
rb_gc_mark(th->klass);
rb_gc_mark(th->wrapper);
rb_gc_mark((VALUE)th->cref);
rb_gc_mark((VALUE)th->scope);
rb_gc_mark((VALUE)th->dyna_vars);
}
-
rb_gc_mark((VALUE)th->scope);
rb_gc_mark((VALUE)th->dyna_vars);
rb_gc_mark(th->errinfo);
rb_gc_mark(th->last_status);
rb_gc_mark(th->last_line);
@@ -10421,11 +10431,11 @@ thread_mark(th)
rb_gc_mark_maybe(th->sandbox);
/* mark data in copied stack */
if (th == curr_thread) return;
if (th == main_thread) return;
if (th->status == THREAD_KILLED) return;
if (th->stk_len == 0) return; /* stack not active, no need to mark. */
if (th->stk_ptr) {
-rb_gc_mark_locations(th->stk_ptr, th->stk_ptr+th->stk_len);
+
if (th->stk_ptr && th != curr_thread) {
+
rb_gc_mark_locations(th->stk_pos, th->stk_base);
#if defined(THINK_C) || defined(__human68k__)
rb_gc_mark_locations(th->stk_ptr+2, th->stk_ptr+th->stk_len+2);
#endif
@@ -10435,24 +10445,30 @@ thread_mark(th)
}
#endif
}
frame = th->frame;
+
+
if (curr_thread == th)
+
frame = ruby_frame;
+
else
+
frame = th->frame;
+
while (frame && frame != top_frame) {
-frame = ADJ(frame);
rb_gc_mark_frame(frame);
if (frame->tmp) {
struct FRAME *tmp = frame->tmp;
while (tmp && tmp != top_frame) {
+
-tmp = ADJ(tmp);
rb_gc_mark_frame(tmp);
tmp = tmp->prev;
}
}
frame = frame->prev;
}
block = th->block;
+
+
if (curr_thread == th)
+
block = ruby_block;
+
else
+
block = th->block;
+
while (block) {
-block = ADJ(block);
rb_gc_mark_frame(&block->frame);
block = block->prev;
}
@@ -10515,7 +10531,7 @@ static inline void
stack_free(th)
rb_thread_t th;
{
if (th->stk_ptr) free(th->stk_ptr);
+ if (th->stk_ptr) munmap(th->stk_ptr, th->stk_size);
th->stk_ptr = 0;
#ifdef __ia64
if (th->bstr_ptr) free(th->bstr_ptr);
@@ -10576,35 +10592,8 @@ rb_thread_save_context(th)
static VALUE tval;
len = ruby_stack_length(&pos);
th->stk_len = 0;
th->stk_pos = pos;
if (len > th->stk_max) {
-VALUE *ptr = realloc(th->stk_ptr, sizeof(VALUE) * len);
-if (!ptr) rb_memerror();
-th->stk_ptr = ptr;
-th->stk_max = len;
}
th->stk_len = len;
FLUSH_REGISTER_WINDOWS;
MEMCPY(th->stk_ptr, th->stk_pos, VALUE, th->stk_len);
-#ifdef __ia64
th->bstr_pos = rb_gc_register_stack_start;
len = (VALUE*)rb_ia64_bsp() - th->bstr_pos;
th->bstr_len = 0;
if (len > th->bstr_max) {
VALUE *ptr = realloc(th->bstr_ptr, sizeof(VALUE) * len);
if (!ptr) rb_memerror();
th->bstr_ptr = ptr;
th->bstr_max = len;
}
th->bstr_len = len;
rb_ia64_flushrs();
MEMCPY(th->bstr_ptr, th->bstr_pos, VALUE, th->bstr_len);
-#endif
-#ifdef SAVE_WIN32_EXCEPTION_LIST
th->win32_exception_list = win32_get_exception_list();
-#endif
+
th->stk_pos = pos;
th->frame = ruby_frame;
th->scope = ruby_scope;
ruby_scope->flags |= SCOPE_DONT_RECYCLE;
@@ -10714,11 +10703,6 @@ rb_thread_restore_context_0(rb_thread_t th, int exit)
#endif
tmp = th;
ex = exit;
FLUSH_REGISTER_WINDOWS;
MEMCPY(tmp->stk_pos, tmp->stk_ptr, VALUE, tmp->stk_len);
-#ifdef __ia64
MEMCPY(tmp->bstr_pos, tmp->bstr_ptr, VALUE, tmp->bstr_len);
-#endif
tval = rb_lastline_get();
rb_lastline_set(tmp->last_line);
@@ -10809,8 +10793,8 @@ rb_thread_restore_context(th, exit)
rb_thread_t th;
int exit;
{
if (!th->stk_ptr) rb_bug("unsaved context");
stack_extend(th, exit);
+
if (!th->stk_ptr && th != main_thread) rb_bug("unsaved context");
+
rb_thread_restore_context_0(th, exit);
}
static void
@@ -10829,7 +10813,6 @@ rb_thread_die(th)
{
th->thgroup = 0;
th->status = THREAD_KILLED;
stack_free(th);
}
static void
@@ -12096,6 +12079,7 @@ rb_thread_group(thread)
\
th->stk_ptr = 0;\
th->stk_len = 0;\
+
th->stk_size = 0;\
th->stk_max = 0;\
th->wait_for = 0;\
IA64_INIT(th->bstr_ptr = 0);\
@@ -12143,6 +12127,48 @@ rb_thread_alloc(klass)
THREAD_ALLOC(th);
th->thread = Data_Wrap_Struct(klass, thread_mark, thread_free, th);
+
/* if main_thread != NULL, then this is NOT the main thread, so
+
* we create a heap-stack
+
*/
+
if (main_thread) {
+
/* Allocate stack, don't forget to add 1 extra word because of the MATH below */
+
unsigned int pagesize = getpagesize();
+
unsigned int total_size = rb_thread_stack_size + pagesize + sizeof(int);
+
void *stack_area = NULL;
+
+
stack_area = mmap(NULL, total_size, PROT_READ | PROT_WRITE | PROT_EXEC,
+MAP_PRIVATE | MAP_ANON, -1, 0);
+
+
if (stack_area == MAP_FAILED) {
+fprintf(stderr, "Thread stack allocation failed!\n");
+rb_memerror();
+
}
+
+
th->stk_ptr = th->stk_pos = stack_area;
+
th->stk_size = total_size;
+
+
if (mprotect(th->stk_ptr, pagesize, PROT_NONE) == -1) {
+fprintf(stderr, "Failed to create thread guard region: %s\n", strerror(errno));
+rb_memerror();
+
}
+
+
th->guard = th->stk_ptr + (pagesize/sizeof(VALUE *));
+
+
/* point stk_base at the top of the stack */
+
/* ASSUMPTIONS:
+
* 1.) The address returned by malloc is "suitably aligned" for anything on this system
+
* 2.) Adding a value that is "aligned" for this platform should not unalign the address
+
*
returned from malloc.
+
* 3.) Don't push anything on to the stack, otherwise it'll get unaligned.
+
* 4.) x86_64 ABI says aligned AFTER arguments have been pushed. You *must* then do a call[lq]
+
*
or push[lq] something else on to the stack if you inted to do a ret.
+
*/
+
th->stk_base = th->stk_ptr + ((total_size - sizeof(int))/sizeof(VALUE *));
+
th->stk_len = rb_thread_stack_size;
+
} else {
+
th->stk_ptr = th->stk_pos = rb_gc_stack_start;
+
}
+
for (vars = th->dyna_vars; vars; vars = vars->next) {
if (FL_TEST(vars, DVAR_DONT_RECYCLE)) break;
FL_SET(vars, DVAR_DONT_RECYCLE);
@@ -12246,17 +12272,22 @@ rb_thread_stop_timer()
int rb_thread_tick = THREAD_TICK;
#endif
+struct thread_start_args {
+ VALUE (*fn)();
+ void *arg;
+ rb_thread_t th;
+} new_th;
+
+static VALUE
+rb_thread_start_2();
+
static VALUE
rb_thread_start_0(fn, arg, th)
VALUE (*fn)();
void *arg;
rb_thread_t th;
{
volatile rb_thread_t th_save = th;
volatile VALUE thread = th->thread;
struct BLOCK *volatile saved_block = 0;
enum rb_thread_status status;
int state;
if (OBJ_FROZEN(curr_thread->thgroup)) {
rb_raise(rb_eThreadError,
@@ -12284,16 +12315,41 @@ rb_thread_start_0(fn, arg, th)
return thread;
}
if (ruby_block) {/* should nail down higher blocks */
-struct BLOCK dummy;
+
new_th.fn = fn;
+
new_th.arg = arg;
+
new_th.th = th;
+
+#if defined(__i386__)
+
__asm__ __volatile__ ("movl %0, %%esp\n\t"
+
"calll *%1\n"
+
:: "r" (th->stk_base),
+
"r" (rb_thread_start_2));
+#elif defined(__x86_64__)
+
__asm__ __volatile__ ("movq %0, %%rsp\n\t"
+
"callq *%1\n"
+
:: "r" (th->stk_base),
+
"r" (rb_thread_start_2));
+#else
+
#error unsupported architecture!
+#endif
+
/* NOTREACHED */
+
return 0;
+}
-dummy.prev = ruby_block;
-blk_copy_prev(&dummy);
-saved_block = ruby_block = dummy.prev;
}
scope_dup(ruby_scope);
+static VALUE
+rb_thread_start_2()
+{
+
volatile rb_thread_t th = new_th.th;
+
volatile rb_thread_t th_save = th;
+
volatile VALUE thread = th->thread;
+
struct BLOCK *volatile saved_block = 0;
+
enum rb_thread_status status;
+
int state;
+
struct tag *tag;
+
struct RVarmap *vars;
+
struct FRAME dummy_frame;
+
if (!th->next) {
if (!th->next) {
/* merge in thread list */
th->prev = curr_thread;
curr_thread->next->prev = th;
@@ -12301,13 +12357,27 @@ rb_thread_start_0(fn, arg, th)
curr_thread->next = th;
th->priority = curr_thread->priority;
th->thgroup = curr_thread->thgroup;
+
}
+
curr_thread = th;
+
+
dummy_frame = *ruby_frame;
+
dummy_frame.prev = top_frame;
+
ruby_frame = &dummy_frame;
+
+
if (ruby_block) {/* should nail down higher blocks */
+struct BLOCK dummy;
+
+dummy.prev = ruby_block;
+blk_copy_prev(&dummy);
+saved_block = ruby_block = dummy.prev;
}
+
+
scope_dup(ruby_scope);
PUSH_TAG(PROT_THREAD);
if ((state = EXEC_TAG()) == 0) {
if (THREAD_SAVE_CONTEXT(th) == 0) {
curr_thread = th;
th->result = (*fn)(arg, th);
+
th->result = (*new_th.fn)(new_th.arg, th);
}
th = th_save;
}
@@ -12644,6 +12714,43 @@ rb_thread_cleanup()
END_FOREACH_FROM(curr, th);
}
+/*
+ * call-seq:
+ *
Thread.stack_size
=> fixnum
+ *
+ * Returns the thread stack size in bytes
+ */
+static VALUE
+rb_thread_stacksize_get()
+{
+ return INT2FIX(rb_thread_stack_size);
+}
+
+/*
+ * call-seq:
+ *
Thread.stack_size= fixnum => Qnil
+ *
+ * Sets the global thread stacksize and returns Qnil.
+ */
+static VALUE
+rb_thread_stacksize_set(obj, val)
+
VALUE obj;
+
VALUE val;
+{
+
+ unsigned int size = FIX2UINT(val);
+
+ /* 16byte alignment works for both x86 and x86_64 */
+ if (size & (~0xf)) {
+
size += 0x10;
+
size = size & (~0xf);
+ }
+
+ rb_thread_stack_size = size;
+
+ return Qnil;
+}
+
int rb_thread_critical;
@@ -13473,7 +13580,7 @@ rb_exec_recursive(func, obj, arg)
int state;
hash = recursive_push(hash, objid);
-PUSH_TAG(PROT_NONE);
+PUSH_TAG(PROT_EMPTY);
if ((state = EXEC_TAG()) == 0) {
result = (*func) (obj, arg, Qfalse);
}
@@ -13500,6 +13607,8 @@ Init_Thread()
{
VALUE cThGroup;
+
+
rb_thread_stack_size = (1024 * 1024);
recursive_key = rb_intern("__recursive_key__");
rb_eThreadError = rb_define_class("ThreadError", rb_eStandardError);
rb_cThread = rb_define_class("Thread", rb_cObject);
@@ -13524,6 +13633,9 @@ Init_Thread()
rb_define_singleton_method(rb_cThread, "abort_on_exception", rb_thread_s_abort_exc, 0);
rb_define_singleton_method(rb_cThread, "abort_on_exception=", rb_thread_s_abort_exc_set, 1);
+
+
+
rb_define_singleton_method(rb_cThread, "stack_size", rb_thread_stacksize_get, 0);
rb_define_singleton_method(rb_cThread, "stack_size=", rb_thread_stacksize_set, 1);
rb_define_method(rb_cThread, "run", rb_thread_run, 0);
rb_define_method(rb_cThread, "wakeup", rb_thread_wakeup, 0);
rb_define_method(rb_cThread, "kill", rb_thread_kill, 0);
diff --git a/gc.c b/gc.c
index a564f0b..d6d654d 100644
--- a/gc.c
+++ b/gc.c
@@ -506,12 +506,12 @@ stack_end_address(VALUE **stack_end_p)
# define STACK_END (stack_end)
#endif
#if STACK_GROW_DIRECTION < 0
-# define STACK_LENGTH (rb_gc_stack_start - STACK_END)
+# define STACK_LENGTH(start) ((start) - STACK_END)
#elif STACK_GROW_DIRECTION > 0
-# define STACK_LENGTH (STACK_END - rb_gc_stack_start + 1)
+# define STACK_LENGTH(start) (STACK_END - (start) + 1)
#else
-# define STACK_LENGTH ((STACK_END < rb_gc_stack_start) ? rb_gc_stack_start - STACK_END\
: STACK_END - rb_gc_stack_start + 1)
+# define STACK_LENGTH(start) ((STACK_END < (start)) ? (start) - STACK_END\
+
: STACK_END - (start) + 1)
#endif
#if STACK_GROW_DIRECTION > 0
# define STACK_UPPER(x, a, b) a
@@ -534,27 +534,36 @@ stack_grow_direction(addr)
#define GC_WATER_MARK 512
-#define CHECK_STACK(ret) do {\
+#define CHECK_STACK(ret, start) do {\
SET_STACK_END;\
(ret) = (STACK_LENGTH > STACK_LEVEL_MAX + GC_WATER_MARK);\
+
(ret) = (STACK_LENGTH(start) > STACK_LEVEL_MAX + GC_WATER_MARK);\
} while (0)
size_t
ruby_stack_length(p)
VALUE **p;
{
SET_STACK_END;
if (p) *p = STACK_UPPER(STACK_END, rb_gc_stack_start, STACK_END);
return STACK_LENGTH;
+ SET_STACK_END;
+ VALUE *start;
+ if (rb_curr_thread == rb_main_thread) {
+
start = rb_gc_stack_start;
+ } else {
+
start = rb_curr_thread->stk_base;
+ }
+ if (p) *p = STACK_UPPER(STACK_END, start, STACK_END);
+ return STACK_LENGTH(start);
}
int
ruby_stack_check()
{
int ret;
CHECK_STACK(ret);
return ret;
+ int ret;
+ if (rb_curr_thread == rb_main_thread) {
+
CHECK_STACK(ret, rb_gc_stack_start);
+ } else {
+
CHECK_STACK(ret, rb_curr_thread->stk_base);
+ }
+ return ret;
}
#define MARK_STACK_MAX 1024
@@ -1441,10 +1450,13 @@ garbage_collect()
init_mark_stack();
+
+
+
+
+
+
gc_mark((VALUE)ruby_current_node, 0);
/* mark frame stack */
for (frame = ruby_frame; frame; frame = frame->prev) {
if (rb_curr_thread == rb_main_thread)
frame = ruby_frame;
else
frame = rb_main_thread->frame;
for (; frame; frame = frame->prev) {
rb_gc_mark_frame(frame);
if (frame->tmp) {
struct FRAME *tmp = frame->tmp;
@@ -1454,16 +1466,35 @@ garbage_collect()
}
}
}
gc_mark((VALUE)ruby_scope, 0);
gc_mark((VALUE)ruby_dyna_vars, 0);
+
+
if (rb_curr_thread == rb_main_thread) {
+
gc_mark((VALUE)ruby_current_node, 0);
+
gc_mark((VALUE)ruby_scope, 0);
+
gc_mark((VALUE)ruby_dyna_vars, 0);
+
} else {
+
gc_mark((VALUE)rb_main_thread->node, 0);
+
gc_mark((VALUE)rb_main_thread->scope, 0);
+
gc_mark((VALUE)rb_main_thread->dyna_vars, 0);
+
+
/* scan the current thread's stack */
+
rb_gc_mark_locations((VALUE*)STACK_END, rb_curr_thread->stk_base);
+
}
+
if (finalizer_table) {
-mark_tbl(finalizer_table, 0);
+
mark_tbl(finalizer_table, 0);
}
FLUSH_REGISTER_WINDOWS;
/* This assumes that all registers are saved into the jmp_buf (and stack) */
rb_setjmp(save_regs_gc_mark);
mark_locations_array((VALUE*)save_regs_gc_mark, sizeof(save_regs_gc_mark) / sizeof(VALUE *));
+
+
+
+
+
+
+
/* If this is not the main thread, we need to scan the C stack, so
* set STACK_END to the end of the C stack.
*/
if (rb_curr_thread != rb_main_thread)
STACK_END = rb_main_thread->stk_pos;
#if STACK_GROW_DIRECTION < 0
rb_gc_mark_locations((VALUE*)STACK_END, rb_gc_stack_start);
#elif STACK_GROW_DIRECTION > 0
@@ -1483,6 +1514,7 @@ garbage_collect()
rb_gc_mark_locations((VALUE*)((char*)STACK_END + 2),
(VALUE*)((char*)rb_gc_stack_start + 2));
#endif
+
rb_gc_mark_threads();
/* mark protected global variables */
diff --git a/lib/logger.rb b/lib/logger.rb
index 15d95fc..5a6d467 100644
--- a/lib/logger.rb
+++ b/lib/logger.rb
@@ -170,7 +170,7 @@ require 'monitor'
class Logger
VERSION = "1.2.6"
- id, name, rev = %w$Id$
+ id, name, rev = %w$Id logger.rb 1234$
ProgName = "#{name.chomp(",v")}/#{rev}"
class Error < RuntimeError; end
diff --git a/node.h b/node.h
index c209fa5..740e66a 100644
--- a/node.h
+++ b/node.h
@@ -411,8 +411,11 @@ struct rb_thread {
size_t stk_len;
size_t stk_max;
+
size_t stk_size;
VALUE *stk_ptr;
VALUE *stk_pos;
+
VALUE *stk_base;
+
VALUE *guard;
#ifdef __ia64
size_t bstr_len;
size_t bstr_max;
diff --git a/signal.c b/signal.c
index fb21fd3..acac6a7 100644
--- a/signal.c
+++ b/signal.c
@@ -14,6 +14,7 @@
#include
#include
+#include
#include
#include
"ruby.h"
"rubysig.h"
"node.h"
<signal.h>
<stdio.h>
@@ -428,15 +429,22 @@ typedef RETSIGTYPE (*sighandler_t)_((int));
static sighandler_t
ruby_signal(signum, handler)
int signum;
sighandler_t handler;
+
void *handler;
{
struct sigaction sigact, old;
rb_trap_accept_nativethreads[signum] = 0;
+
+
+
+
+
+
+
+
+
sigact.sa_handler = handler;
if (signum == SIGSEGV || signum == SIGBUS) {
sigact.sa_sigaction = handler;
sigact.sa_flags = (SA_ONSTACK | SA_RESETHAND | SA_SIGINFO);
} else {
sigact.sa_handler = handler;
sigact.sa_flags = 0;
}
sigemptyset(&sigact.sa_mask);
sigact.sa_flags = 0;
# ifdef SA_NOCLDWAIT
if (signum == SIGCHLD && handler == SIG_IGN)
sigact.sa_flags |= SA_NOCLDWAIT;
@@ -599,7 +607,132 @@ sighandler(sig)
}
}
+#include <stdio.h>
+#ifdef HAVE_STDARG_PROTOTYPES
+#include <stdarg.h>
+#define va_init_list(a,b) va_start(a,b)
+#else
+#include <varargs.h>
+#define va_init_list(a,b) va_start(a)
+#endif
+
+void
+#ifdef HAVE_STDARG_PROTOTYPES
+sig_printf(const char *fmt, ...)
+#else
+ sig_printf(fmt, va_alist)
+
const char *fmt;
+
va_dcl
+#endif
+{
+ char buf[BUFSIZ];
+ va_list args;
+ FILE *out = stderr;
+
+ va_init_list(args, fmt);
+ vfprintf(out, fmt, args);
+ va_end(args);
+ fprintf(out, "\n");
+}
+
+static void
+dump_machine_state(uc)
+
ucontext_t *uc;
+{
+ const char *dump64 =
+
" ----------------- Register state dump ----------------------\n"
+
"rax = 0x%.16x rbx
= 0x%.16x rcx = 0x%.16x rdx = 0x%.16x\n"
+
"rdi = 0x%.16x rsi
= 0x%.16x rbp = 0x%.16x rsp = 0x%.16x\n"
+
"r8 = 0x%.16x r9
= 0x%.16x r10 = 0x%.16x r11 = 0x%.16x\n"
+
"r12 = 0x%.16x r13
= 0x%.16x r14 = 0x%.16x r15 = 0x%.16x\n"
+
"rip = 0x%.16x rflags = 0x%.16x cs = 0x%.16x fs = 0x%.16x\n"
+
"gs = 0x%.16x";
+
+ const char *dump32 =
+
" ----------------- Register state dump -------------------\n"
+
"eax = 0x%.8x ebx
= 0x%.8x ecx = 0x%.8x edx = 0x%.8x\n"
+
"edi = 0x%.8x esi
= 0x%.8x ebp = 0x%.8x esp = 0x%.8x\n"
+
"ss = 0x%.8x eflags = 0x%.8x eip = 0x%.8x cs = 0x%.8x\n"
+
"ds = 0x%.8x es
= 0x%.8x fs = 0x%.8x gs = 0x%.8x\n";
+
+#if defined(__LP64__) && defined(__APPLE__)
+ sig_printf(dump64, uc->uc_mcontext->__ss.__rax, uc->uc_mcontext->__ss.__rbx,
+
uc->uc_mcontext->__ss.__rcx, uc->uc_mcontext->__ss.__rdx, uc->uc_mcontext->__ss.__rdi,
+
uc->uc_mcontext->__ss.__rsi, uc->uc_mcontext->__ss.__rbp, uc->uc_mcontext->__ss.__rsp,
+
uc->uc_mcontext->__ss.__r8, uc->uc_mcontext->__ss.__r9, uc->uc_mcontext->__ss.__r10,
+
uc->uc_mcontext->__ss.__r11, uc->uc_mcontext->__ss.__r12, uc->uc_mcontext->__ss.__r13,
+
uc->uc_mcontext->__ss.__r14, uc->uc_mcontext->__ss.__r15, uc->uc_mcontext->__ss.__rip,
+
uc->uc_mcontext->__ss.__rflags, uc->uc_mcontext->__ss.__cs, uc->uc_mcontext->__ss.__fs,
+
uc->uc_mcontext->__ss.__gs);
+#elif !defined(__LP64__) && defined(__APPLE__)
+ sig_printf(dump32, uc->uc_mcontext->__ss.__eax, uc->uc_mcontext->__ss.__ebx,
+
uc->uc_mcontext->__ss.__ecx, uc->uc_mcontext->__ss.__edx,
+
uc->uc_mcontext->__ss.__edi, uc->uc_mcontext->__ss.__esi,
+
uc->uc_mcontext->__ss.__ebp, uc->uc_mcontext->__ss.__esp,
+
uc->uc_mcontext->__ss.__ss, uc->uc_mcontext->__ss.__eflags,
+
uc->uc_mcontext->__ss.__eip, uc->uc_mcontext->__ss.__cs,
+
uc->uc_mcontext->__ss.__ds, uc->uc_mcontext->__ss.__es,
+
uc->uc_mcontext->__ss.__fs, uc->uc_mcontext->__ss.__gs);
+#elif defined(__i386__)
+ sig_printf(dump32, uc->uc_mcontext.gregs[REG_EAX], uc->uc_mcontext.gregs[REG_EBX],
+
uc->uc_mcontext.gregs[REG_ECX], uc->uc_mcontext.gregs[REG_EDX],
+
uc->uc_mcontext.gregs[REG_EDI], uc->uc_mcontext.gregs[REG_ESI],
+
uc->uc_mcontext.gregs[REG_EBP], uc->uc_mcontext.gregs[REG_ESP],
+
uc->uc_mcontext.gregs[REG_SS], uc->uc_mcontext.gregs[REG_EFL],
+
uc->uc_mcontext.gregs[REG_EIP], uc->uc_mcontext.gregs[REG_EIP],
+
uc->uc_mcontext.gregs[REG_DS], uc->uc_mcontext.gregs[REG_ES],
+
uc->uc_mcontext.gregs[REG_FS], uc->uc_mcontext.gregs[REG_FS]);
+#elif defined(__x86_64__)
+ sig_printf(dump64, uc->uc_mcontext.gregs[REG_RAX], uc->uc_mcontext.gregs[REG_RBX],
+
uc->uc_mcontext.gregs[REG_RCX], uc->uc_mcontext.gregs[REG_RDX],
+
uc->uc_mcontext.gregs[REG_RDI], uc->uc_mcontext.gregs[REG_RSI],
+
uc->uc_mcontext.gregs[REG_RBP], uc->uc_mcontext.gregs[REG_RSP],
+
uc->uc_mcontext.gregs[REG_R8], uc->uc_mcontext.gregs[REG_R9],
+
uc->uc_mcontext.gregs[REG_R10], uc->uc_mcontext.gregs[REG_R11],
+
uc->uc_mcontext.gregs[REG_R12], uc->uc_mcontext.gregs[REG_R13],
+
uc->uc_mcontext.gregs[REG_R14], uc->uc_mcontext.gregs[REG_R15],
+
uc->uc_mcontext.gregs[REG_RIP], uc->uc_mcontext.gregs[REG_EFL],
+
uc->uc_mcontext.gregs[REG_CSGSFS]);
+#else
+#endif
+}
+
+static int
+check_guard(caddr_t fault_addr, rb_thread_t th) {
+ if(fault_addr <= (caddr_t)rb_curr_thread->guard &&
+
fault_addr >= (caddr_t)rb_curr_thread->stk_ptr) {
+
return 1;
+ }
+ return 0;
+}
+
#ifdef SIGBUS
+#ifdef POSIX_SIGNAL
+static void sigbus _((int, siginfo_t*, void*));
+static void
+sigbus(sig, ip, context)
+
int sig;
+
siginfo_t *ip;
+
void *context;
+{
+#if defined(HAVE_NATIVETHREAD) && defined(HAVE_NATIVETHREAD_KILL)
+ if (!is_ruby_native_thread() && !rb_trap_accept_nativethreads[sig]) {
+
sigsend_to_ruby_thread(sig);
+
return;
+ }
+#endif
+
+ dump_machine_state(context);
+ if (check_guard((caddr_t)ip->si_addr, rb_curr_thread)) {
+
/* we hit the guard page, print out a warning to help app developers */
+
rb_bug("Thread stack overflow! Try increasing it!");
+ } else {
+
rb_bug("Bus Error");
+ }
+}
+
+#else /* !defined(POSIX_SIGNAL) */
+
static RETSIGTYPE sigbus _((int));
static RETSIGTYPE
sigbus(sig)
@@ -615,8 +748,38 @@ sigbus(sig)
rb_bug("Bus Error");
}
#endif
+#endif
+
#ifdef SIGSEGV
+#ifdef POSIX_SIGNAL
+static void sigsegv _((int, siginfo_t*, void*));
+static void
+sigsegv(sig, ip, context)
+
int sig;
+
siginfo_t *ip;
+
void *context;
+{
+#if defined(HAVE_NATIVETHREAD) && defined(HAVE_NATIVETHREAD_KILL)
+ if (!is_ruby_native_thread() && !rb_trap_accept_nativethreads[sig]) {
+
sigsend_to_ruby_thread(sig);
+
return;
+ }
+#endif
+
+ extern int ruby_gc_stress;
+ ruby_gc_stress = 0;
+ dump_machine_state(context);
+ if (check_guard((caddr_t)ip->si_addr, rb_curr_thread)) {
+
/* we hit the guard page, print out a warning to help app developers */
+
rb_bug("Thread stack overflow! Try increasing it!");
+ } else {
+
rb_bug("Segmentation fault");
+ }
+}
+
+#else /* !defined(POSIX_SIGNAL) */
+
static RETSIGTYPE sigsegv _((int));
static RETSIGTYPE
sigsegv(sig)
@@ -634,6 +797,7 @@ sigsegv(sig)
rb_bug("Segmentation fault");
}
#endif
+#endif
#ifdef SIGPIPE
static RETSIGTYPE sigpipe _((int));
@@ -705,7 +869,8 @@ static VALUE
trap(arg)
struct trap_arg *arg;
{
sighandler_t func, oldfunc;
+
sighandler_t oldfunc;
+
void *func;
VALUE command, oldcmd;
int sig = -1;
const char *s;
@@ -952,6 +1117,20 @@ sig_list()
}
static void
+create_sigstack()
+{
+ stack_t ss;
+ ss.ss_size = SIGSTKSZ;
+ ss.ss_sp = malloc(ss.ss_size);
+ ss.ss_flags = 0;
+ if (sigaltstack(&ss, NULL) < 0) {
+
free(ss.ss_sp);
+
fprintf(stderr, "Couldn't create signal stack! Error %d: %s\n", errno, strerror(errno));
+
exit(1);
+ }
+}
+
+static void
install_sighandler(signum, handler)
int signum;
sighandler_t handler;
@@ -960,7 +1139,7 @@ install_sighandler(signum, handler)
old = ruby_signal(signum, handler);
if (old != SIG_DFL) {
-ruby_signal(signum, old);
+
ruby_signal(signum, old);
}
}
@@ -1089,6 +1268,8 @@ Init_signal()
rb_alias(rb_eSignal, rb_intern("signm"), rb_intern("message"));
rb_define_method(rb_eInterrupt, "initialize", interrupt_init, -1);
+
+
create_sigstack();
install_sighandler(SIGINT, sighandler);
#ifdef SIGHUP
install_sighandler(SIGHUP, sighandler);
1.26.5.1.5. railsbench.patch
diff --git a/gc.c b/gc.c
index 52b1c23..f774022 100644
--- a/gc.c
+++ b/gc.c
@@ -22,8 +22,16 @@
#include <setjmp.h>
#include <sys/types.h>
+#ifdef _WIN32
+#include <string.h>
+#else
+#include <strings.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
+#elif defined(_WIN32)
+#include <time.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H
@@ -42,7 +50,6 @@ void rb_io_fptr_finalize _((struct rb_io_t*));
#ifdef __CYGWIN__
int _setjmp(), _longjmp();
#endif
/* Make alloca work the best possible way. */
#ifdef __GNUC__
# ifndef atarist
@@ -205,8 +212,17 @@ ruby_xfree(x)
RUBY_CRITICAL(free(x));
}
+#if HAVE_LONG_LONG
+#define GC_TIME_TYPE LONG_LONG
+#else
+#define GC_TIME_TYPE long
+#endif
+
extern int ruby_in_compile;
static int dont_gc;
+static int gc_statistics = 0;
+static GC_TIME_TYPE gc_time = 0;
+static int gc_collections = 0;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -241,7 +257,7 @@ rb_gc_enable()
* Disables garbage collection, returning <code>true</code> if garbage
* collection was already disabled.
*
- *
GC.disable
#=> false
+ *
GC.disable
#=> false or true
*
GC.disable
#=> true
*
*/
@@ -255,6 +271,104 @@ rb_gc_disable()
return old;
}
+/*
+ * call-seq:
+ *
GC.enable_stats
=> true or false
+ *
+ * Enables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already enabled.
+ *
+ *
GC.enable_stats
#=> false or true
+ *
GC.enable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_stats
=> true or false
+ *
+ * Disables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already disabled.
+ *
+ *
GC.disable_stats
#=> false or true
+ *
GC.disable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qfalse;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.clear_stats
=> nil
+ *
+ * Clears garbage collection statistics, returning nil. This resets the number
+ * of collections (GC.collections) and the time used (GC.time) to 0.
+ *
+ *
GC.clear_stats
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_clear_stats()
+{
+
gc_collections = 0;
+
gc_time = 0;
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.collections
=> Integer
+ *
+ * Returns the number of garbage collections performed while GC statistics collection
+ * was enabled.
+ *
+ *
GC.collections
#=> 35
+ *
+ */
+
+VALUE
+rb_gc_collections()
+{
+
return INT2NUM(gc_collections);
+}
+
+/*
+ * call-seq:
+ *
GC.time
=> Integer
+ *
+ * Returns the time spent during garbage collection while GC statistics collection
+ * was enabled (in micro seconds).
+ *
+ *
GC.time
#=> 20000
+ *
+ */
+
+VALUE
+rb_gc_time()
+{
+#if HAVE_LONG_LONG
+
return LL2NUM(gc_time);
+#else
+
return LONG2NUM(gc_time);
+#endif
+}
+
+
VALUE rb_mGC;
static struct gc_list {
@@ -346,7 +460,7 @@ typedef struct RVALUE {
static RVALUE *freelist = 0;
static RVALUE *deferred_final_list = 0;
-#define HEAPS_INCREMENT 10
+static int heaps_increment = 10;
static struct heaps_slot {
void *membase;
RVALUE *slot;
@@ -355,13 +469,165 @@ static struct heaps_slot {
static int heaps_length = 0;
static int heaps_used
= 0;
-#define HEAP_MIN_SLOTS 10000
-static int heap_slots = HEAP_MIN_SLOTS;
+static int heap_min_slots = 10000;
+static int heap_slots = 10000;
+
+static int heap_free_min = 4096;
+static int heap_slots_increment = 10000;
+static double heap_slots_growth_factor = 1.8;
+
+static long initial_malloc_limit = GC_MALLOC_LIMIT;
-#define FREE_MIN
4096
+static int verbose_gc_stats = Qfalse;
+
+static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
+static void set_gc_parameters()
+{
+
char *gc_stats_ptr, *min_slots_ptr, *free_min_ptr, *heap_slots_incr_ptr,
+
*heap_incr_ptr, *malloc_limit_ptr, *gc_heap_file_ptr, *heap_slots_growth_factor_ptr;
+
+
gc_data_file = stderr;
+
+
gc_stats_ptr = getenv("RUBY_GC_STATS");
+
if (gc_stats_ptr != NULL) {
+int gc_stats_i = atoi(gc_stats_ptr);
+if (gc_stats_i > 0) {
+
verbose_gc_stats = Qtrue;
+}
+
}
+
+
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
+
if (gc_heap_file_ptr != NULL) {
+FILE* data_file = fopen(gc_heap_file_ptr, "w");
+if (data_file != NULL) {
+
gc_data_file = data_file;
+}
+else {
+
fprintf(stderr,
+
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
+}
+
}
+
+
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
+
if (min_slots_ptr != NULL) {
+int min_slots_i = atoi(min_slots_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_MIN_SLOTS=%s\n", min_slots_ptr);
+
}
+if (min_slots_i > 0) {
+
heap_slots = min_slots_i;
+
heap_min_slots = min_slots_i;
+}
+
}
+
+
free_min_ptr = getenv("RUBY_HEAP_FREE_MIN");
+
if (free_min_ptr != NULL) {
+int free_min_i = atoi(free_min_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_FREE_MIN=%s\n", free_min_ptr);
+}
+if (free_min_i > 0) {
+
heap_free_min = free_min_i;
+}
+
}
+
+
heap_incr_ptr = getenv("RUBY_HEAP_INCREMENT");
+
if (heap_incr_ptr != NULL) {
+int heap_incr_i = atoi(heap_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_INCREMENT=%s\n", heap_incr_ptr);
+}
+if (heap_incr_i > 0) {
+
heaps_increment = heap_incr_i;
+}
+
}
+
+
heap_slots_incr_ptr = getenv("RUBY_HEAP_SLOTS_INCREMENT");
+
if (heap_slots_incr_ptr != NULL) {
+int heap_slots_incr_i = atoi(heap_slots_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
+}
+if (heap_slots_incr_i > 0) {
+
heap_slots_increment = heap_slots_incr_i;
+}
+
}
+
+
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
+
if (heap_slots_growth_factor_ptr != NULL) {
+double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
+}
+if (heap_slots_growth_factor_d > 0) {
+
heap_slots_growth_factor = heap_slots_growth_factor_d;
+}
+
}
+
+
malloc_limit_ptr = getenv("RUBY_GC_MALLOC_LIMIT");
+
if (malloc_limit_ptr != NULL) {
+int malloc_limit_i = atol(malloc_limit_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_GC_MALLOC_LIMIT=%s\n", malloc_limit_ptr);
+}
+if (malloc_limit_i > 0) {
+
initial_malloc_limit = malloc_limit_i;
+}
+
}
+}
+
+/*
+ * call-seq:
+ *
GC.dump
=> nil
+ *
+ * dumps information about the current GC data structures to the GC log file
+ *
+ *
GC.dump
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_dump()
+{
+
int i;
+
+
for (i = 0; i < heaps_used; i++) {
+int heap_size = heaps[i].limit;
+fprintf(gc_data_file, "HEAP[%2d]: size=%7d\n", i, heap_size);
+
}
+
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.log String => String
+ *
+ * Logs string to the GC data file and returns it.
+ *
+ *
GC.log "manual GC call"
#=> "manual GC call"
+ *
+ */
+
+VALUE
+rb_gc_log(self, original_str)
+
VALUE self, original_str;
+{
+
if (original_str == Qnil) {
+
fprintf(gc_data_file, "\n");
+
}
+
else {
+
VALUE str = StringValue(original_str);
+
char *p = RSTRING(str)->ptr;
+
fprintf(gc_data_file, "%s\n", p);
+
}
+
return original_str;
+}
+
+
static void
add_heap()
{
@@ -372,7 +638,7 @@ add_heap()
struct heaps_slot *p;
int length;
-heaps_length += HEAPS_INCREMENT;
+heaps_length += heaps_increment;
length = heaps_length*sizeof(struct heaps_slot);
RUBY_CRITICAL(
if (heaps_used > 0) {
@@ -388,10 +654,10 @@ add_heap()
for (;;) {
RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
if (p == 0) {
if (heap_slots == HEAP_MIN_SLOTS) {
+
if (heap_slots == heap_min_slots) {
rb_memerror();
}
heap_slots = HEAP_MIN_SLOTS;
+
heap_slots = heap_min_slots;
continue;
}
heaps[heaps_used].membase = p;
@@ -407,8 +673,9 @@ add_heap()
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots *= 1.8;
if (heap_slots <= 0) heap_slots = HEAP_MIN_SLOTS;
+
heap_slots += heap_slots_increment;
+
heap_slots_increment *= heap_slots_growth_factor;
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
p->as.free.flags = 0;
@@ -1102,6 +1369,39 @@ finalize_list(p)
}
}
+static char* obj_type(int tp)
+{
+
switch (tp) {
+case T_NIL
: return "NIL";
+case T_OBJECT : return "OBJECT";
+case T_CLASS : return "CLASS";
+case T_ICLASS : return "ICLASS";
+case T_MODULE : return "MODULE";
+case T_FLOAT : return "FLOAT";
+case T_STRING : return "STRING";
+case T_REGEXP : return "REGEXP";
+case T_ARRAY : return "ARRAY";
+case T_FIXNUM : return "FIXNUM";
+case T_HASH
: return "HASH";
+case T_STRUCT : return "STRUCT";
+case T_BIGNUM : return "BIGNUM";
+case T_FILE
: return "FILE";
+
+case T_TRUE
: return "TRUE";
+case T_FALSE : return "FALSE";
+case T_DATA
: return "DATA";
+case T_MATCH : return "MATCH";
+case T_SYMBOL : return "SYMBOL";
+
+case T_BLKTAG : return "BLKTAG";
+case T_UNDEF : return "UNDEF";
+case T_VARMAP : return "VARMAP";
+case T_SCOPE : return "SCOPE";
+case T_NODE
: return "NODE";
+default: return "____";
+
}
+}
+
static void
free_unused_heaps()
{
@@ -1134,12 +1434,21 @@ gc_sweep()
unsigned long live = 0;
unsigned long free_min = 0;
+
+
+
+
+
unsigned long really_freed = 0;
int free_counts[256];
int live_counts[256];
int do_gc_stats = gc_statistics & verbose_gc_stats;
for (i = 0; i < heaps_used; i++) {
free_min += heaps[i].limit;
}
free_min = free_min * 0.2;
if (free_min < FREE_MIN)
free_min = FREE_MIN;
if (free_min < heap_free_min)
free_min = heap_free_min;
+
+
+
+
if (do_gc_stats) {
+for (i = 0 ; i< 256; i++) { free_counts[i] = live_counts[i] = 0; }
+
}
if (ruby_in_compile && ruby_parser_stack_on_heap()) {
/* should not reclaim nodes during compilation
@@ -1174,6 +1483,9 @@ gc_sweep()
if (p->as.basic.flags &&
((deferred = obj_free((VALUE)p)) ||
((FL_TEST(p, FL_FINALIZE)) && need_call_final))) {
+
if (do_gc_stats) {
+really_freed++;
+
}
if (!deferred) {
p->as.free.flags = T_DEFERRED;
RDATA(p)->dfree = 0;
@@ -1183,6 +1495,12 @@ gc_sweep()
final_list = p;
}
else {
+
if (do_gc_stats) {
+
int obt = p->as.basic.flags & T_MASK;
+
if (obt) {
+
free_counts[obt]++;
+
}
+
}
add_freelist(p);
}
n++;
@@ -1194,6 +1512,9 @@ gc_sweep()
else {
RBASIC(p)->flags &= ~FL_MARK;
live++;
+if (do_gc_stats) {
+
live_counts[RANY((VALUE)p)->as.basic.flags & T_MASK]++;
+ }
}
p++;
}
@@ -1212,7 +1533,7 @@ gc_sweep()
}
if (malloc_increase > malloc_limit) {
malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
-if (malloc_limit < GC_MALLOC_LIMIT) malloc_limit = GC_MALLOC_LIMIT;
+if (malloc_limit < initial_malloc_limit) malloc_limit = initial_malloc_limit;
}
malloc_increase = 0;
if (freed < free_min) {
@@ -1220,6 +1541,20 @@ gc_sweep()
}
during_gc = 0;
+
if (do_gc_stats) {
+fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
+fprintf(gc_data_file, "live objects: %.7d\n", live);
+fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
+fprintf(gc_data_file, "freed objects: %.7d\n", really_freed);
+for(i=0; i<256; i++) {
+
if (free_counts[i]>0) {
+fprintf(gc_data_file,
+"kept %.7d / freed %.7d objects of type %s\n",
+live_counts[i], free_counts[i], obj_type(i));
+
}
+}
+
}
+
/* clear finalization list */
if (final_list) {
deferred_final_list = final_list;
@@ -1423,6 +1758,7 @@ garbage_collect()
struct gc_list *list;
struct FRAME * volatile frame; /* gcc 2.7.2.3 -O2 bug?? */
jmp_buf save_regs_gc_mark;
+
struct timeval gctv1, gctv2;
SET_STACK_END;
#ifdef HAVE_NATIVETHREAD
@@ -1439,6 +1775,14 @@ garbage_collect()
if (during_gc) return;
during_gc++;
+
if (gc_statistics) {
+
gc_collections++;
+gettimeofday(&gctv1, NULL);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "Garbage collection started\n");
+}
+
}
+
init_mark_stack();
gc_mark((VALUE)ruby_current_node, 0);
@@ -1514,6 +1858,17 @@ garbage_collect()
} while (!MARK_STACK_EMPTY);
gc_sweep();
+
+
if (gc_statistics) {
+
GC_TIME_TYPE musecs_used;
+gettimeofday(&gctv2, NULL);
+musecs_used = ((GC_TIME_TYPE)(gctv2.tv_sec - gctv1.tv_sec) * 1000000) + (gctv2.tv_usec - gctv1.tv_usec);
+gc_time += musecs_used;
+
+if (verbose_gc_stats) {
+
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
+}
+
}
}
void
@@ -1695,6 +2050,7 @@ Init_heap()
if (!rb_gc_stack_start) {
Init_stack(0);
}
+
set_gc_parameters();
add_heap();
}
@@ -2163,6 +2519,14 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "stress=", gc_stress_set, 1);
rb_define_method(rb_mGC, "garbage_collect", rb_gc_start, 0);
+
+
+
+
+
+
+
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"clear_stats", rb_gc_clear_stats, 0);
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
rb_define_module_function(rb_mObSpace, "garbage_collect", rb_gc_start, 0);
1.26.5.1.6. fix-irb-completion.diff
diff --git a/lib/irb/completion.rb b/lib/irb/completion.rb
index 000658e..609dca3 100644
--- a/lib/irb/completion.rb
+++ b/lib/irb/completion.rb
@@ -157,7 +157,7 @@ module IRB
end
next if name != "IRB::Context" and
/^(IRB|SLex|RubyLex|RubyToken)/ =~ name
candidates.concat m.instance_methods(false)
+
candidates.concat m.instance_methods(false).map { |m| m.to_s }
}
candidates.sort!
candidates.uniq!
1.26.5.1.7. stdout-rouge-fix.patch
diff --git a/lib/mkmf.rb b/lib/mkmf.rb
index c9e738a..7a8004d 100644
--- a/lib/mkmf.rb
+++ b/lib/mkmf.rb
@@ -201,20 +201,26 @@ end
module Logging
@log = nil
@logfile = 'mkmf.log'
- @orgerr = $stderr.dup
- @orgout = $stdout.dup
@postpone = 0
@quiet = $extmk
+
+
+
+
+
+
+
+
+
+
def self::open
@log ||= File::open(@logfile, 'w')
@log.sync = true
orgerr = $stderr.dup
orgout = $stdout.dup
$stderr.reopen(@log)
$stdout.reopen(@log)
yield
ensure
$stderr.reopen(@orgerr)
$stdout.reopen(@orgout)
if orgerr
$stderr.reopen(orgerr)
orgerr.close
end
if orgout
$stdout.reopen(orgout)
orgout.close
end
end
def self::message(*s)
1.26.5.1.8. zlib-gc-fix.diff
diff --git a/ext/zlib/zlib.c b/ext/zlib/zlib.c
index b87e691..5f701ab 100644
--- a/ext/zlib/zlib.c
+++ b/ext/zlib/zlib.c
@@ -610,6 +610,7 @@ zstream_append_input(z, src, len)
}
#define zstream_append_input2(z,v)\
RB_GC_GUARD(v),\
zstream_append_input((z), RSTRING(v)->ptr, RSTRING(v)->len)
+
static void
1.26.5.1.9. readline-fix.diff
diff --git a/ext/readline/extconf.rb b/ext/readline/extconf.rb
index b820c0b..f299cba 100644
--- a/ext/readline/extconf.rb
+++ b/ext/readline/extconf.rb
@@ -59,6 +59,9 @@ have_func("rl_cleanup_after_signal")
have_func("rl_clear_signals")
have_func("rl_vi_editing_mode")
have_func("rl_emacs_editing_mode")
+# workaround for native windows.
+/mswin|bccwin|mingw/ !~ RUBY_PLATFORM && have_readline_var("rl_catch_sigwinch")
+/mswin|bccwin|mingw/ !~ RUBY_PLATFORM && have_readline_var("rl_catch_signals")
have_func("replace_history_entry")
have_func("remove_history")
create_makefile("readline")
diff --git a/ext/readline/readline.c b/ext/readline/readline.c
index c9acaad..637cb99 100644
--- a/ext/readline/readline.c
+++ b/ext/readline/readline.c
@@ -833,6 +833,12 @@ Init_readline()
#ifdef HAVE_RL_EVENT_HOOK
rl_event_hook = readline_event;
#endif
+#ifdef HAVE_RL_CATCH_SIGNALS
+
rl_catch_signals = 0;
+#endif
+#ifdef HAVE_RL_CATCH_SIGWINCH
+
rl_catch_sigwinch = 0;
+#endif
#ifdef HAVE_RL_CLEAR_SIGNALS
rl_clear_signals();
#endif
1.26.5.1.10. p357
1.26.5.1.10.1. railsexpress
1.26.5.1.10.1.1. 07-fork-support-for-gc-logging.patch
diff --git a/gc.c b/gc.c
index 9ad716f..a3cbe91 100644
--- a/gc.c
+++ b/gc.c
@@ -223,6 +223,8 @@ static int dont_gc;
static int gc_statistics = 0;
static GC_TIME_TYPE gc_time = 0;
static int gc_collections = 0;
+static int verbose_gc_stats = Qfalse;
+static FILE* gc_data_file = NULL;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -368,9 +370,148 @@ rb_gc_time()
#endif
}
VALUE rb_mGC;
+/*
+ * call-seq:
+ *
GC.enable_trace
=> true or false
+ *
+ * Enables garbage collection tracing, returning <code>true</code> if garbage
+ * collection tracing was already enabled.
+ *
+ *
GC.enable_trace
#=> false or true
+ *
GC.enable_trace
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_trace()
+{
+
int old = verbose_gc_stats;
+
verbose_gc_stats = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_trace
=> true or false
+ *
+ * Disables garbage collection tracing, returning <code>true</code> if garbage
+ * collection tracing was already disabled.
+ *
+ *
GC.disable_trace
#=> false or true
+ *
GC.disable_trace
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_trace()
+{
+
int old = verbose_gc_stats;
+
verbose_gc_stats = Qfalse;
+
return old;
+}
+
+char* GC_LOGFILE_IVAR = "@gc_logfile_name";
+
+/*
+ * call-seq:
+ *
GC.log_file(filename=nil, mode="w")
=> boolean
+ *
+ * Changes the GC data log file. Closes the currently open logfile.
+ * Returns true if the file was successfully opened for
+ * writing. Returns false if the file could not be opened for
+ * writing. Returns the name of the current logfile (or nil) if no
+ * parameter is given. Restores logging to stderr when given nil as
+ * an argument.
+ *
+ *
GC.log_file
#=> nil
+ *
GC.log_file "/tmp/gc.log"
#=> true
+ *
GC.log_file
#=> "/tmp/gc.log"
+ *
GC.log_file nil
#=> true
+ *
+ */
+
+VALUE
+rb_gc_log_file(int argc, VALUE *argv, VALUE self)
+{
+
VALUE filename = Qnil;
+
VALUE mode_str = Qnil;
+
FILE* f = NULL;
+
char* mode = "w";
+
+
VALUE current_logfile_name = rb_iv_get(rb_mGC, GC_LOGFILE_IVAR);
+
+
if (argc==0)
+
return current_logfile_name;
+
+
rb_scan_args(argc, argv, "02", &filename, &mode_str);
+
+
if (filename == Qnil) {
+
/* close current logfile and reset logfile to stderr */
+
if (gc_data_file != stderr) {
+
fclose(gc_data_file);
+
gc_data_file = stderr;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, Qnil);
+
}
+
return Qtrue;
+
}
+
+
/* we have a real logfile name */
+
filename = StringValue(filename);
+
+
if (rb_equal(current_logfile_name, filename) == Qtrue) {
+
/* do nothing if we get the file name we're already logging to */
+
return Qtrue;
+
}
+
+
/* get mode for file opening */
+
if (mode_str != Qnil)
+
{
+
mode = RSTRING(StringValue(mode_str))->ptr;
+
}
+
+
/* try to open file in given mode */
+
if (f = fopen(RSTRING(filename)->ptr, mode)) {
+
if (gc_data_file != stderr) {
+
fclose(gc_data_file);
+
}
+
gc_data_file = f;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, filename);
+
} else {
+
return Qfalse;
+
}
+
return Qtrue;
+}
+
+
+/*
+ * Called from process.c before a fork. Flushes the gc log file to
+ * avoid writing the buffered output twice (once in the parent, and
+ * once in the child).
+ */
+void
+rb_gc_before_fork()
+{
+ /* flush gc log file */
+ fflush(gc_data_file);
+}
+
+/*
+ * Called from process.c after a fork in the child process. Turns off
+ * logging, disables GC stats and resets all gc counters and timing
+ * information.
+ */
+void
+rb_gc_after_fork()
+{
+
rb_gc_disable_stats();
+
rb_gc_clear_stats();
+
rb_gc_disable_trace();
+
gc_data_file = stderr;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, Qnil);
+}
+
static struct gc_list {
VALUE *varptr;
struct gc_list *next;
@@ -477,10 +618,6 @@ static double heap_slots_growth_factor = 1.8;
static long initial_malloc_limit = GC_MALLOC_LIMIT;
-static int verbose_gc_stats = Qfalse;
-static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
static void set_gc_parameters()
@@ -496,6 +633,8 @@ static void set_gc_parameters()
if (gc_stats_i > 0) {
verbose_gc_stats = Qtrue;
}
+
/* child processes should not inherit RUBY_GC_STATS */
+
unsetenv("RUBY_GC_STATS");
}
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
@@ -508,6 +647,8 @@ static void set_gc_parameters()
fprintf(stderr,
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
}
+
/* child processes should not inherit RUBY_GC_DATA_FILE to avoid clobbering */
+
unsetenv("RUBY_GC_DATA_FILE");
}
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
@@ -2619,6 +2760,9 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "dump_file_and_line_info", rb_gc_dump_file_and_line_info, -1);
#endif
rb_define_singleton_method(rb_mGC, "log", rb_gc_log, 1);
+
rb_define_singleton_method(rb_mGC, "log_file", rb_gc_log_file, -1);
+
rb_define_singleton_method(rb_mGC, "enable_trace", rb_gc_enable_trace, 0);
+
rb_define_singleton_method(rb_mGC, "disable_trace", rb_gc_disable_trace, 0);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
diff --git a/intern.h b/intern.h
index 950ae9d..99696f1 100644
--- a/intern.h
+++ b/intern.h
@@ -270,6 +270,8 @@ void rb_gc_call_finalizer_at_exit _((void));
VALUE rb_gc_enable _((void));
VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
+void rb_gc_before_fork _((void));
+void rb_gc_after_fork _((void));
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
diff --git a/process.c b/process.c
index 8f6285d..ea28cb8 100644
--- a/process.c
+++ b/process.c
@@ -1330,6 +1330,8 @@ rb_f_fork(obj)
fflush(stderr);
#endif
+
+
rb_gc_before_fork();
before_exec();
pid = fork();
after_exec();
@@ -1339,6 +1341,7 @@ rb_f_fork(obj)
#ifdef linux
after_exec();
#endif
+
rb_gc_after_fork();
rb_thread_atfork();
if (rb_block_given_p()) {
int status;
@@ -1574,10 +1577,12 @@ rb_f_system(argc, argv)
chfunc = signal(SIGCHLD, SIG_DFL);
retry:
+
rb_gc_before_fork();
before_exec();
pid = fork();
if (pid == 0) {
/* child process */
+
rb_gc_after_fork();
rb_thread_atfork();
rb_protect(proc_exec_args, (VALUE)&earg, NULL);
_exit(127);
1.26.5.1.10.1.2. 08-track-malloc-size.patch
diff --git a/gc.c b/gc.c
index a3cbe91..30a1219 100644
--- a/gc.c
+++ b/gc.c
@@ -79,6 +79,17 @@ void *alloca ();
static unsigned long malloc_increase = 0;
static unsigned long malloc_limit = GC_MALLOC_LIMIT;
+
+#ifdef HAVE_LONG_LONG
+static unsigned LONG_LONG gc_allocated_size = 0;
+static unsigned LONG_LONG gc_num_allocations = 0;
+#else
+static unsigned long gc_allocated_size = 0;
+static unsigned long gc_num_allocations = 0;
+#endif
+static int gc_statistics = 0;
+
+
static void run_final();
static VALUE nomem_error;
static void garbage_collect();
@@ -163,6 +174,11 @@ ruby_xmalloc(size)
}
malloc_increase += size;
+
if (gc_statistics) {
+
gc_allocated_size += size;
+gc_num_allocations += 1;
+
}
+
return mem;
}
@@ -220,7 +236,6 @@ ruby_xfree(x)
extern int ruby_in_compile;
static int dont_gc;
-static int gc_statistics = 0;
static GC_TIME_TYPE gc_time = 0;
static int gc_collections = 0;
static int verbose_gc_stats = Qfalse;
@@ -329,11 +344,55 @@ rb_gc_clear_stats()
{
gc_collections = 0;
gc_time = 0;
+
gc_allocated_size = 0;
+
gc_num_allocations = 0;
return Qnil;
}
/*
* call-seq:
+ *
GC.allocated_size
=> Integer
+ *
+ * Returns the size of memory (in bytes) allocated since GC statistics collection
+ * was enabled.
+ *
+ *
GC.allocated_size
#=> 35
+ *
+ */
+VALUE
+rb_gc_allocated_size()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_allocated_size);
+#else
+
return ULONG2NUM(gc_allocated_size);
+#endif
+}
+
+/*
+ * call-seq:
+ *
GC.num_allocations
=> Integer
+ *
+ * Returns the number of memory allocations since GC statistics collection
+ * was enabled.
+ *
+ *
GC.num_allocations
#=> 150
+ *
+ */
+VALUE
+rb_gc_num_allocations()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_num_allocations);
+#else
+
return ULONG2NUM(gc_num_allocations);
+#endif
+}
+
+/*
+
+/*
+ * call-seq:
*
GC.collections
=> Integer
*
* Returns the number of garbage collections performed while GC statistics collection
@@ -2753,6 +2812,8 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "enable_stats", rb_gc_enable_stats, 0);
rb_define_singleton_method(rb_mGC, "disable_stats", rb_gc_disable_stats, 0);
rb_define_singleton_method(rb_mGC, "clear_stats", rb_gc_clear_stats, 0);
+
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
+
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
diff --git a/intern.h b/intern.h
index 99696f1..1117614 100644
--- a/intern.h
+++ b/intern.h
@@ -272,6 +272,8 @@ VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
+VALUE rb_gc_allocated_size _((void));
+VALUE rb_gc_num_allocations _((void));
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.10.1.3. 13-add-trace-stats-enabled-methods.patch
diff --git a/gc.c b/gc.c
index 57740d2..2c34932 100644
--- a/gc.c
+++ b/gc.c
@@ -350,6 +350,22 @@ rb_gc_disable_stats()
/*
* call-seq:
+ *
GC.stats_enabled?
=> true or false
+ *
+ * Check whether GC stats have been enabled.
+ *
+ *
GC.stats_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_stats_enabled()
+{
+
return gc_statistics ? Qtrue : Qfalse;
+}
+
+/*
+ * call-seq:
*
GC.clear_stats
=> nil
*
* Clears garbage collection statistics, returning nil. This resets the number
@@ -491,6 +507,22 @@ rb_gc_disable_trace()
return old;
}
+/*
+ * call-seq:
+ *
GC.trace_enabled?
=> true or false
+ *
+ * Check whether GC tracing has been enabled.
+ *
+ *
GC.trace_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_trace_enabled()
+{
+
return verbose_gc_stats ? Qtrue : Qfalse;
+}
+
char* GC_LOGFILE_IVAR = "@gc_logfile_name";
/*
@@ -2887,6 +2919,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
@@ -2902,6 +2935,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"stats_enabled?", rb_gc_stats_enabled, 0);
"clear_stats", rb_gc_clear_stats, 0);
"allocated_size", rb_gc_allocated_size, 0);
"num_allocations", rb_gc_num_allocations, 0);
"log_file", rb_gc_log_file, -1);
"enable_trace", rb_gc_enable_trace, 0);
"disable_trace", rb_gc_disable_trace, 0);
"trace_enabled?", rb_gc_trace_enabled, 0);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
1.26.5.1.10.1.4. 12-heap-slot-size.patch
diff --git a/gc.c b/gc.c
index 7db1ef6..57740d2 100644
--- a/gc.c
+++ b/gc.c
@@ -2891,6 +2891,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
+
rb_define_const(rb_mGC, "HEAP_SLOT_SIZE", INT2FIX(sizeof(RVALUE)));
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
1.26.5.1.10.1.5. 14-track-live-dataset-size.patch
diff --git a/gc.c b/gc.c
index 2c34932..0ce7e68 100644
--- a/gc.c
+++ b/gc.c
@@ -89,6 +89,7 @@ static unsigned long gc_num_allocations = 0;
#endif
static int gc_statistics = 0;
+static unsigned long heap_slots_live_after_last_gc = 0;
static void run_final();
static VALUE nomem_error;
@@ -465,6 +466,23 @@ rb_gc_time()
#endif
}
+/*
+ * call-seq:
+ *
GC.heap_slots_live_after_last_gc
=> Integer
+ *
+ * Returns the number of heap slots which were live after the last garbage collection.
+ *
+ *
GC.heap_slots_live_after_last_gc
#=> 231223
+ *
+ */
+VALUE
+rb_gc_heap_slots_live_after_last_gc()
+{
+
return ULONG2NUM(heap_slots_live_after_last_gc);
+}
+
+
+
VALUE rb_mGC;
/*
@@ -1903,6 +1921,7 @@ gc_sweep()
}
during_gc = 0;
live_objects = live;
+
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2924,6 +2943,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
+
rb_define_singleton_method(rb_mGC, "heap_slots_live_after_last_gc", rb_gc_heap_slots_live_after_last_gc, 0);
rb_define_const(rb_mGC, "HEAP_SLOT_SIZE", INT2FIX(sizeof(RVALUE)));
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
1.26.5.1.10.1.6. 15-add-object-size-information-to-heap-dump.patch
diff --git a/gc.c b/gc.c
index 0ce7e68..53450bf 100644
--- a/gc.c
+++ b/gc.c
@@ -953,9 +953,21 @@ rb_gc_dump_file_and_line_info(int argc, VALUE *argv)
if (!p->as.basic.klass) {
fprintf(f, "__unknown__");
} else {
fprintf(f, rb_obj_classname((VALUE)p));
+
fprintf(f, "%s", rb_obj_classname((VALUE)p));
}
}
+
/* print object size for some known object types */
+
switch (TYPE(p)) {
+
case T_STRING:
+
fprintf(f, ":%lu", RSTRING(p)->len);
+
break;
+
case T_ARRAY:
+
fprintf(f, ":%lu", RARRAY(p)->len);
+
break;
+
case T_HASH:
+
fprintf(f, ":%d", RHASH(p)->tbl->num_entries);
+
break;
+
}
}
fprintf(f, "\n");
}
@@ -1924,10 +1936,10 @@ gc_sweep()
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7d\n", really_freed);
fprintf(gc_data_file, "objects processed: %.7lu\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7lu\n", live);
fprintf(gc_data_file, "freelist objects : %.7lu\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7lu\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0 || live_counts[i]>0) {
fprintf(gc_data_file,
@@ -2258,7 +2270,7 @@ garbage_collect()
gc_time += musecs_used;
+
+
+
+
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
fprintf(gc_data_file, "GC time: %ld msec\n", (long)(musecs_used / 1000));
fflush(gc_data_file);
}
+
}
1.26.5.1.10.1.7. 11-fix-heap-size-growth-logic.patch
diff --git a/gc.c b/gc.c
index 21b3f6b..7db1ef6 100644
--- a/gc.c
+++ b/gc.c
@@ -694,6 +694,7 @@ static int heap_size = 0;
static
static
+static
static
int heap_free_min = 4096;
int heap_slots_increment = 10000;
int initial_heap_slots_increment = 10000;
double heap_slots_growth_factor = 1.8;
static long initial_malloc_limit = GC_MALLOC_LIMIT;
@@ -771,14 +772,13 @@ static void set_gc_parameters()
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
}
if (heap_slots_incr_i > 0) {
heap_slots_increment = heap_slots_incr_i;
}
+
heap_slots_increment = heap_slots_incr_i;
+
initial_heap_slots_increment = heap_slots_increment;
}
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
if (heap_slots_growth_factor_ptr != NULL) {
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
double heap_slots_growth_factor_d = atof(heap_slots_growth_factor_ptr);
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
}
@@ -988,8 +988,13 @@ add_heap()
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots += heap_slots_increment;
heap_slots_increment *= heap_slots_growth_factor;
+
if (heaps_used == 1)
+
heap_slots = initial_heap_slots_increment;
+
else {
+
heap_slots_increment *= heap_slots_growth_factor;
+
heap_slots += heap_slots_increment;
+
}
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
@@ -1879,6 +1884,7 @@ gc_sweep()
live_counts[i], free_counts[i], obj_type(i));
}
}
+
rb_gc_dump();
fflush(gc_data_file);
}
1.26.5.1.10.1.8. 04-display-full-stack-trace.patch
diff --git a/eval.c b/eval.c
index 6ff2560..fb3307c 100644
--- a/eval.c
+++ b/eval.c
@@ -1325,8 +1325,8 @@ error_print()
int truncate = eclass == rb_eSysStackError;
#define
-#define
-#define
+#define
+#define
TRACE_MAX (TRACE_HEAD+TRACE_TAIL+5)
TRACE_HEAD 8
TRACE_TAIL 5
TRACE_HEAD 100
TRACE_TAIL 100
ep = RARRAY(errat);
for (i=1; i<ep->len; i++) {
1.26.5.1.10.1.9. 06-heap-dump-support.patch
diff --git a/configure.in b/configure.in
index 62b34a8..4be088c 100644
--- a/configure.in
+++ b/configure.in
@@ -1595,6 +1595,14 @@ fi
LDFLAGS="-L. $LDFLAGS"
AC_SUBST(ARCHFILE)
+dnl enable gc debugging
+AC_ARG_ENABLE(gcdebug,
+
[ --enable-gcdebug
build garbage collector with debugging enabled. ],
+
[enable_gcdebug=$enableval])
+if test "$enable_gcdebug" = 'yes'; then
+
AC_DEFINE(GC_DEBUG, 1)
+fi
+
dnl build rdoc index if requested
RDOCTARGET=""
AC_ARG_ENABLE(install-doc,
diff --git a/gc.c b/gc.c
index ab71d22..9ad716f 100644
--- a/gc.c
+++ b/gc.c
@@ -411,7 +411,6 @@ rb_gc_unregister_address(addr)
}
}
-#undef GC_DEBUG
void
rb_global_variable(var)
@@ -602,6 +601,85 @@ rb_gc_dump()
return Qnil;
}
+
+static char* obj_type(int tp);
+
+#ifdef GC_DEBUG
+/*
+ * call-seq:
+ *
GC.dump_file_and_line_info(String, boolean)
=> nil
+ *
+ * dumps information on which currently allocated object was created by which file and on which line
+ *
+ *
GC.dump_file_and_line_info(String, boolean)
#=> nil
+ *
+ * The second parameter specifies whether class names should be included in the dump.
+ * Note that including class names will allocate additional string objects on the heap.
+ *
+ */
+
+VALUE
+rb_gc_dump_file_and_line_info(int argc, VALUE *argv)
+{
+ VALUE filename, str, include_classnames = Qnil;
+ char *fname = NULL;
+ char *klass = NULL;
+ FILE* f = NULL;
+ int i,n = 0;
+
+ rb_scan_args(argc, argv, "11", &filename, &include_classnames);
+
+ str = StringValue(filename);
+ fname = RSTRING(str)->ptr;
+ f = fopen(fname, "w");
+
+ for (i = 0; i < heaps_used; i++) {
+
RVALUE *p, *pend;
+
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
for (;p < pend; p++) {
+
if (p->as.basic.flags) {
+
fprintf(f, "%s:%s:%d", obj_type(p->as.basic.flags & T_MASK), p->file, p->line);
+
// rb_obj_classname will create objects on the heap, we need a better solution
+
if (include_classnames == Qtrue) {
+
/* write the class */
+
fprintf(f, ":");
+
switch (TYPE(p)) {
+
case T_NONE:
+
fprintf(f, "__none__");
+
break;
+
case T_BLKTAG:
+
fprintf(f, "__blktag__");
+
break;
+
case T_UNDEF:
+
fprintf(f, "__undef__");
+
break;
+
case T_VARMAP:
+
fprintf(f, "__varmap__");
+
break;
+
case T_SCOPE:
+
fprintf(f, "__scope__");
+
break;
+
case T_NODE:
+
fprintf(f, "__node__");
+
break;
+
default:
+
if (!p->as.basic.klass) {
+
fprintf(f, "__unknown__");
+
} else {
+
fprintf(f, rb_obj_classname((VALUE)p));
+
}
+
}
+
}
+
fprintf(f, "\n");
+
}
+
}
+ }
+ fclose(f);
+ return Qnil;
+}
+#endif
+
/*
* call-seq:
*
GC.log String => String
@@ -1066,6 +1144,11 @@ gc_mark(ptr, lev)
if (obj->as.basic.flags & FL_MARK) return; /* already marked */
obj->as.basic.flags |= FL_MARK;
+#ifdef GC_DEBUG
+
/* mark our new reference point for sourcefile objects */
+
mark_source_filename(RANY(obj)->file);
+#endif
+
if (lev > GC_LEVEL_MAX || (lev == 0 && ruby_stack_check())) {
if (!mark_stack_overflow) {
if (mark_stack_ptr - mark_stack < MARK_STACK_MAX) {
@@ -1104,6 +1187,11 @@ gc_mark_children(ptr, lev)
if (obj->as.basic.flags & FL_MARK) return; /* already marked */
obj->as.basic.flags |= FL_MARK;
+#ifdef GC_DEBUG
+
/* mark our new reference point for sourcefile objects */
+
mark_source_filename(RANY(obj)->file);
+#endif
+
marking:
if (FL_TEST(obj, FL_EXIVAR)) {
rb_mark_generic_ivar(ptr);
@@ -1550,6 +1638,7 @@ gc_sweep()
live_counts[i], free_counts[i], obj_type(i));
}
}
+
fflush(gc_data_file);
}
/* clear finalization list */
@@ -2526,6 +2615,9 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+#ifdef GC_DEBUG
+
rb_define_singleton_method(rb_mGC,
+#endif
rb_define_singleton_method(rb_mGC,
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"dump_file_and_line_info", rb_gc_dump_file_and_line_info, -1);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
1.26.5.1.10.1.10. 01-ignore-generated-files.patch
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..00c347a
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,95 @@
+.ext
+.installed.list
+.rbconfig.time
+Makefile
+autom4te.cache/
+config.h
+config.status
+configure
+ext/Win32API/Makefile
+ext/bigdecimal/Makefile
+ext/curses/Makefile
+ext/dbm/Makefile
+ext/digest/Makefile
+ext/digest/bubblebabble/Makefile
+ext/digest/md5/Makefile
+ext/digest/rmd160/Makefile
+ext/digest/sha1/Makefile
+ext/digest/sha2/Makefile
+ext/dl/Makefile
+ext/dl/call.func
+ext/dl/callback.func
+ext/dl/cbtable.func
+ext/dl/dlconfig.h
+ext/dl/dlconfig.rb
+ext/enumerator/Makefile
+ext/etc/Makefile
+ext/fcntl/Makefile
+ext/gdbm/Makefile
+ext/iconv/Makefile
+ext/io/wait/Makefile
+ext/nkf/Makefile
+ext/openssl/Makefile
+ext/openssl/extconf.h
+ext/pty/Makefile
+ext/racc/cparse/Makefile
+ext/readline/Makefile
+ext/sdbm/Makefile
+ext/socket/Makefile
+ext/stringio/Makefile
+ext/strscan/Makefile
+ext/syck/Makefile
+ext/syslog/Makefile
+ext/thread/Makefile
+ext/tk/Makefile
+ext/tk/tkutil/Makefile
+ext/win32ole/Makefile
+ext/win32ole/.document
+ext/zlib/Makefile
+largefile.h
+miniruby
+parse.c
+rbconfig.rb
+ruby
+enc.mk
+ext/bigdecimal/extconf.h
+ext/continuation/
+ext/coverage/
+ext/curses/extconf.h
+ext/dbm/extconf.h
+ext/digest/bubblebabble/extconf.h
+ext/digest/extconf.h
+ext/digest/md5/extconf.h
+ext/digest/rmd160/extconf.h
+ext/digest/sha1/extconf.h
+ext/digest/sha2/extconf.h
+ext/dl/callback.h
+ext/dl/extconf.h
+ext/etc/extconf.h
+ext/fcntl/extconf.h
+ext/fiber/
+ext/iconv/extconf.h
+ext/io/wait/extconf.h
+ext/json/
+ext/nkf/extconf.h
+ext/pty/extconf.h
+ext/racc/cparse/extconf.h
+ext/readline/extconf.h
+ext/ripper/
+ext/sdbm/extconf.h
+ext/socket/constants.h
+ext/socket/extconf.h
+ext/stringio/extconf.h
+ext/strscan/extconf.h
+ext/syck/extconf.h
+ext/syslog/extconf.h
+ext/tk/extconf.h
+ext/tk/tkutil/extconf.h
+ext/zlib/extconf.h
+miniprelude.c
+prelude.c
+revision.h
+*.dylib
+*.log
+*.dSYM
+patches-ruby*
1.26.5.1.10.1.11. 03-railsbench-gc-patch.patch
diff --git a/gc.c b/gc.c
index fa45cd1..ab71d22 100644
--- a/gc.c
+++ b/gc.c
@@ -22,8 +22,16 @@
#include <setjmp.h>
#include <sys/types.h>
+#ifdef _WIN32
+#include <string.h>
+#else
+#include <strings.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
+#elif defined(_WIN32)
+#include <time.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H
@@ -42,7 +50,6 @@ void rb_io_fptr_finalize _((struct rb_io_t*));
#ifdef __CYGWIN__
int _setjmp(), _longjmp();
#endif
/* Make alloca work the best possible way. */
#ifdef __GNUC__
# ifndef atarist
@@ -86,12 +93,12 @@ rb_memerror()
rb_thread_t th = rb_curr_thread;
if (!nomem_error ||
-(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
-fprintf(stderr, "[FATAL] failed to allocate memory\n");
-exit(1);
+
(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
+
fprintf(stderr, "[FATAL] failed to allocate memory\n");
+
exit(1);
}
if (rb_thread_raised_p(th, RAISED_NOMEMORY)) {
-rb_exc_jump(nomem_error);
+
rb_exc_jump(nomem_error);
}
rb_thread_raised_set(th, RAISED_NOMEMORY);
rb_exc_raise(nomem_error);
@@ -139,7 +146,7 @@ ruby_xmalloc(size)
void *mem;
if (size < 0) {
-rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
+
rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
}
if (size == 0) size = 1;
@@ -148,11 +155,11 @@ ruby_xmalloc(size)
}
RUBY_CRITICAL(mem = malloc(size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = malloc(size));
-if (!mem) {
rb_memerror();
-}
+
garbage_collect();
+
RUBY_CRITICAL(mem = malloc(size));
+
if (!mem) {
+
rb_memerror();
+
}
}
malloc_increase += size;
@@ -179,17 +186,17 @@ ruby_xrealloc(ptr, size)
void *mem;
if (size < 0) {
-rb_raise(rb_eArgError, "negative re-allocation size");
+
rb_raise(rb_eArgError, "negative re-allocation size");
}
if (!ptr) return xmalloc(size);
if (size == 0) size = 1;
if (ruby_gc_stress) garbage_collect();
RUBY_CRITICAL(mem = realloc(ptr, size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = realloc(ptr, size));
-if (!mem) {
rb_memerror();
+
garbage_collect();
+
RUBY_CRITICAL(mem = realloc(ptr, size));
+
if (!mem) {
+
rb_memerror();
}
}
malloc_increase += size;
@@ -202,11 +209,20 @@ ruby_xfree(x)
void *x;
{
if (x)
-RUBY_CRITICAL(free(x));
+
RUBY_CRITICAL(free(x));
}
+#if HAVE_LONG_LONG
+#define GC_TIME_TYPE LONG_LONG
+#else
+#define GC_TIME_TYPE long
+#endif
+
extern int ruby_in_compile;
static int dont_gc;
+static int gc_statistics = 0;
+static GC_TIME_TYPE gc_time = 0;
+static int gc_collections = 0;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -241,7 +257,7 @@ rb_gc_enable()
* Disables garbage collection, returning <code>true</code> if garbage
* collection was already disabled.
*
- *
GC.disable
#=> false
+ *
GC.disable
#=> false or true
*
GC.disable
#=> true
*
*/
@@ -255,6 +271,104 @@ rb_gc_disable()
return old;
}
+/*
+ * call-seq:
+ *
GC.enable_stats
=> true or false
+ *
+ * Enables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already enabled.
+ *
+ *
GC.enable_stats
#=> false or true
+ *
GC.enable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_stats
=> true or false
+ *
+ * Disables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already disabled.
+ *
+ *
GC.disable_stats
#=> false or true
+ *
GC.disable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qfalse;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.clear_stats
=> nil
+ *
+ * Clears garbage collection statistics, returning nil. This resets the number
+ * of collections (GC.collections) and the time used (GC.time) to 0.
+ *
+ *
GC.clear_stats
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_clear_stats()
+{
+
gc_collections = 0;
+
gc_time = 0;
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.collections
=> Integer
+ *
+ * Returns the number of garbage collections performed while GC statistics collection
+ * was enabled.
+ *
+ *
GC.collections
#=> 35
+ *
+ */
+
+VALUE
+rb_gc_collections()
+{
+
return INT2NUM(gc_collections);
+}
+
+/*
+ * call-seq:
+ *
GC.time
=> Integer
+ *
+ * Returns the time spent during garbage collection while GC statistics collection
+ * was enabled (in micro seconds).
+ *
+ *
GC.time
#=> 20000
+ *
+ */
+
+VALUE
+rb_gc_time()
+{
+#if HAVE_LONG_LONG
+
return LL2NUM(gc_time);
+#else
+
return LONG2NUM(gc_time);
+#endif
+}
+
+
VALUE rb_mGC;
static struct gc_list {
@@ -281,19 +395,19 @@ rb_gc_unregister_address(addr)
struct gc_list *tmp = global_List;
if (tmp->varptr == addr) {
-global_List = tmp->next;
-RUBY_CRITICAL(free(tmp));
-return;
+
global_List = tmp->next;
+
RUBY_CRITICAL(free(tmp));
+
return;
}
while (tmp->next) {
-if (tmp->next->varptr == addr) {
struct gc_list *t = tmp->next;
+
if (tmp->next->varptr == addr) {
+
struct gc_list *t = tmp->next;
-}
-tmp
+
+
+
+
+
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
= tmp->next;
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
}
tmp = tmp->next;
}
}
@@ -312,26 +426,26 @@ rb_global_variable(var)
typedef struct RVALUE {
union {
-struct {
unsigned long flags;/* always 0 for freed obj */
struct RVALUE *next;
-} free;
-struct RBasic basic;
-struct RObject object;
-struct RClass klass;
-struct RFloat flonum;
-struct RString string;
-struct RArray array;
-struct RRegexp regexp;
-struct RHash
hash;
-struct RData
data;
-struct RStruct rstruct;
-struct RBignum bignum;
-struct RFile
file;
-struct RNode
node;
-struct RMatch match;
-struct RVarmap varmap;
-struct SCOPE
scope;
+
struct {
+
unsigned long flags;
/* always 0 for freed obj */
+
struct RVALUE *next;
+
} free;
+
struct RBasic basic;
+
struct RObject object;
+
struct RClass klass;
+
struct RFloat flonum;
+
struct RString string;
+
struct RArray array;
+
struct RRegexp regexp;
+
struct RHash
hash;
+
struct RData
data;
+
struct RStruct rstruct;
+
struct RBignum bignum;
+
struct RFile
file;
+
struct RNode
node;
+
struct RMatch match;
+
struct RVarmap varmap;
+
struct SCOPE
scope;
} as;
#ifdef GC_DEBUG
char *file;
@@ -346,7 +460,7 @@ typedef struct RVALUE {
static RVALUE *freelist = 0;
static RVALUE *deferred_final_list = 0;
-#define HEAPS_INCREMENT 10
+static int heaps_increment = 10;
static struct heaps_slot {
void *membase;
RVALUE *slot;
@@ -355,45 +469,197 @@ static struct heaps_slot {
static int heaps_length = 0;
static int heaps_used
= 0;
-#define HEAP_MIN_SLOTS 10000
-static int heap_slots = HEAP_MIN_SLOTS;
+static int heap_min_slots = 10000;
+static int heap_slots = 10000;
-#define FREE_MIN 4096
+static int heap_free_min = 4096;
+static int heap_slots_increment = 10000;
+static double heap_slots_growth_factor = 1.8;
+
+static long initial_malloc_limit = GC_MALLOC_LIMIT;
+
+static int verbose_gc_stats = Qfalse;
+
+static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
+static void set_gc_parameters()
+{
+
char *gc_stats_ptr, *min_slots_ptr, *free_min_ptr, *heap_slots_incr_ptr,
+
*heap_incr_ptr, *malloc_limit_ptr, *gc_heap_file_ptr, *heap_slots_growth_factor_ptr;
+
+
gc_data_file = stderr;
+
+
gc_stats_ptr = getenv("RUBY_GC_STATS");
+
if (gc_stats_ptr != NULL) {
+
int gc_stats_i = atoi(gc_stats_ptr);
+
if (gc_stats_i > 0) {
+
verbose_gc_stats = Qtrue;
+
}
+
}
+
+
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
+
if (gc_heap_file_ptr != NULL) {
+
FILE* data_file = fopen(gc_heap_file_ptr, "w");
+
if (data_file != NULL) {
+
gc_data_file = data_file;
+
}
+
else {
+
fprintf(stderr,
+
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
+
}
+
}
+
+
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
+
if (min_slots_ptr != NULL) {
+
int min_slots_i = atoi(min_slots_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_MIN_SLOTS=%s\n", min_slots_ptr);
+
}
+
if (min_slots_i > 0) {
+
heap_slots = min_slots_i;
+
heap_min_slots = min_slots_i;
+
}
+
}
+
+
free_min_ptr = getenv("RUBY_HEAP_FREE_MIN");
+
if (free_min_ptr != NULL) {
+
int free_min_i = atoi(free_min_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_FREE_MIN=%s\n", free_min_ptr);
+
}
+
if (free_min_i > 0) {
+
heap_free_min = free_min_i;
+
}
+
}
+
+
heap_incr_ptr = getenv("RUBY_HEAP_INCREMENT");
+
if (heap_incr_ptr != NULL) {
+
int heap_incr_i = atoi(heap_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_INCREMENT=%s\n", heap_incr_ptr);
+
}
+
if (heap_incr_i > 0) {
+
heaps_increment = heap_incr_i;
+
}
+
}
+
+
heap_slots_incr_ptr = getenv("RUBY_HEAP_SLOTS_INCREMENT");
+
if (heap_slots_incr_ptr != NULL) {
+
int heap_slots_incr_i = atoi(heap_slots_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
+
}
+
if (heap_slots_incr_i > 0) {
+
heap_slots_increment = heap_slots_incr_i;
+
}
+
}
+
+
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
+
if (heap_slots_growth_factor_ptr != NULL) {
+
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
+
}
+
if (heap_slots_growth_factor_d > 0) {
+
heap_slots_growth_factor = heap_slots_growth_factor_d;
+
}
+
}
+
+
malloc_limit_ptr = getenv("RUBY_GC_MALLOC_LIMIT");
+
if (malloc_limit_ptr != NULL) {
+
int malloc_limit_i = atol(malloc_limit_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_GC_MALLOC_LIMIT=%s\n", malloc_limit_ptr);
+
}
+
if (malloc_limit_i > 0) {
+
initial_malloc_limit = malloc_limit_i;
+
}
+
}
+}
+
+/*
+ * call-seq:
+ *
GC.dump
=> nil
+ *
+ * dumps information about the current GC data structures to the GC log file
+ *
+ *
GC.dump
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_dump()
+{
+
int i;
+
+
for (i = 0; i < heaps_used; i++) {
+
int heap_size = heaps[i].limit;
+
fprintf(gc_data_file, "HEAP[%2d]: size=%7d\n", i, heap_size);
+
}
+
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.log String => String
+ *
+ * Logs string to the GC data file and returns it.
+ *
+ *
GC.log "manual GC call"
#=> "manual GC call"
+ *
+ */
+
+VALUE
+rb_gc_log(self, original_str)
+
VALUE self, original_str;
+{
+
if (original_str == Qnil) {
+
fprintf(gc_data_file, "\n");
+
}
+
else {
+
VALUE str = StringValue(original_str);
+
char *p = RSTRING(str)->ptr;
+
fprintf(gc_data_file, "%s\n", p);
+
}
+
return original_str;
+}
+
+
static void
add_heap()
{
RVALUE *p, *pend;
if (heaps_used == heaps_length) {
-/* Realloc heaps */
-struct heaps_slot *p;
-int length;
-heaps_length += HEAPS_INCREMENT;
-length = heaps_length*sizeof(struct heaps_slot);
-RUBY_CRITICAL(
if (heaps_used > 0) {
-p = (struct heaps_slot *)realloc(heaps, length);
-if (p) heaps = p;
}
else {
-p = heaps = (struct heaps_slot *)malloc(length);
});
-if (p == 0) rb_memerror();
+
/* Realloc heaps */
+
struct heaps_slot *p;
+
int length;
+
+
heaps_length += heaps_increment;
+
length = heaps_length*sizeof(struct heaps_slot);
+
RUBY_CRITICAL(
+
if (heaps_used > 0) {
+
p = (struct heaps_slot *)realloc(heaps, length);
+
if (p) heaps = p;
+
}
+
else {
+
p = heaps = (struct heaps_slot *)malloc(length);
+
});
+
if (p == 0) rb_memerror();
}
for (;;) {
-RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
-if (p == 0) {
if (heap_slots == HEAP_MIN_SLOTS) {
-rb_memerror();
}
heap_slots = HEAP_MIN_SLOTS;
continue;
-}
+
RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
+
if (p == 0) {
+
if (heap_slots == heap_min_slots) {
+
rb_memerror();
+
}
+
heap_slots = heap_min_slots;
+
continue;
+
}
heaps[heaps_used].membase = p;
if ((VALUE)p % sizeof(RVALUE) == 0)
heap_slots += 1;
@@ -401,25 +667,26 @@ add_heap()
p = (RVALUE*)((VALUE)p + sizeof(RVALUE) - ((VALUE)p % sizeof(RVALUE)));
heaps[heaps_used].slot = p;
heaps[heaps_used].limit = heap_slots;
-break;
+
break;
}
pend = p + heap_slots;
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots *= 1.8;
if (heap_slots <= 0) heap_slots = HEAP_MIN_SLOTS;
+
heap_slots += heap_slots_increment;
+
heap_slots_increment *= heap_slots_growth_factor;
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
-p->as.free.flags = 0;
-p->as.free.next = freelist;
-freelist = p;
-p++;
+
p->as.free.flags = 0;
+
p->as.free.next = freelist;
+
freelist = p;
+
p++;
}
}
#define RANY(o) ((RVALUE*)(o))
-int
+int
rb_during_gc()
{
return during_gc;
@@ -431,7 +698,7 @@ rb_newobj()
VALUE obj;
if (during_gc)
-rb_bug("object allocation during garbage collection phase");
+
rb_bug("object allocation during garbage collection phase");
if (ruby_gc_stress || !freelist) garbage_collect();
@@ -580,13 +847,13 @@ rb_source_filename(f)
st_data_t name;
if (!st_lookup(source_filenames, (st_data_t)f, &name)) {
-long len = strlen(f) + 1;
-char *ptr = ALLOC_N(char, len + 1);
-name = (st_data_t)ptr;
-*ptr++ = 0;
-MEMCPY(ptr, f, char, len);
-st_add_direct(source_filenames, (st_data_t)ptr, name);
-return ptr;
+
long len = strlen(f) + 1;
+
char *ptr = ALLOC_N(char, len + 1);
+
name = (st_data_t)ptr;
+
*ptr++ = 0;
+
MEMCPY(ptr, f, char, len);
+
st_add_direct(source_filenames, (st_data_t)ptr, name);
+
return ptr;
}
return (char *)name + 1;
}
@@ -596,7 +863,7 @@ mark_source_filename(f)
char *f;
{
if (f) {
-f[-1] = 1;
+
f[-1] = 1;
}
}
@@ -605,12 +872,12 @@ sweep_source_filename(key, value)
char *key, *value;
{
if (*value) {
-*value = 0;
-return ST_CONTINUE;
+
*value = 0;
+
return ST_CONTINUE;
}
else {
-free(value);
-return ST_DELETE;
+
free(value);
+
return ST_DELETE;
}
}
@@ -625,14 +892,14 @@ gc_mark_all()
init_mark_stack();
for (i = 0; i < heaps_used; i++) {
-p = heaps[i].slot; pend = p + heaps[i].limit;
-while (p < pend) {
if ((p->as.basic.flags & FL_MARK) &&
-(p->as.basic.flags != FL_MARK)) {
-gc_mark_children((VALUE)p, 0);
}
p++;
-}
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
while (p < pend) {
+
if ((p->as.basic.flags & FL_MARK) &&
+
(p->as.basic.flags != FL_MARK)) {
+
gc_mark_children((VALUE)p, 0);
+
}
+
p++;
+
}
}
}
@@ -647,8 +914,8 @@ gc_mark_rest()
init_mark_stack();
while(p != tmp_arry){
-p--;
-gc_mark_children(*p, 0);
+
+
p--;
gc_mark_children(*p, 0);
}
}
@@ -665,9 +932,9 @@ is_pointer_to_heap(ptr)
/* check if p looks like a pointer */
for (i=0; i < heaps_used; i++) {
-heap_org = heaps[i].slot;
-if (heap_org <= p && p < heap_org + heaps[i].limit)
return Qtrue;
+
heap_org = heaps[i].slot;
+
if (heap_org <= p && p < heap_org + heaps[i].limit)
+
return Qtrue;
}
return Qfalse;
}
@@ -680,10 +947,10 @@ mark_locations_array(x, n)
VALUE v;
while (n--) {
v = *x;
-if (is_pointer_to_heap((void *)v)) {
gc_mark(v, 0);
-}
-x++;
+
if (is_pointer_to_heap((void *)v)) {
+
gc_mark(v, 0);
+
}
+
x++;
}
}
@@ -780,7 +1047,7 @@ rb_gc_mark_maybe(obj)
VALUE obj;
{
if (is_pointer_to_heap((void *)obj)) {
-gc_mark(obj, 0);
+
gc_mark(obj, 0);
}
}
@@ -828,7 +1095,7 @@ gc_mark_children(ptr, lev)
{
register RVALUE *obj = RANY(ptr);
+
goto marking;/* skip */
goto marking;
/* skip */
again:
obj = RANY(ptr);
@@ -839,148 +1106,148 @@ gc_mark_children(ptr, lev)
marking:
if (FL_TEST(obj, FL_EXIVAR)) {
-rb_mark_generic_ivar(ptr);
+
rb_mark_generic_ivar(ptr);
}
switch (obj->as.basic.flags & T_MASK) {
case T_NIL:
case T_FIXNUM:
-rb_bug("rb_gc_mark() called for broken object");
-break;
+
rb_bug("rb_gc_mark() called for broken object");
+
break;
case T_NODE:
-mark_source_filename(obj->as.node.nd_file);
-switch (nd_type(obj)) {
- case NODE_IF:/* 1,2,3 */
- case NODE_FOR:
- case NODE_ITER:
- case NODE_CREF:
- case NODE_WHEN:
- case NODE_MASGN:
- case NODE_RESCUE:
- case NODE_RESBODY:
- case NODE_CLASS:
gc_mark((VALUE)obj->as.node.u2.node, lev);
/* fall through */
- case NODE_BLOCK:/* 1,3 */
- case NODE_ARRAY:
- case NODE_DSTR:
- case NODE_DXSTR:
- case NODE_DREGX:
- case NODE_DREGX_ONCE:
- case NODE_FBODY:
- case NODE_ENSURE:
- case NODE_CALL:
- case NODE_DEFS:
- case NODE_OP_ASGN1:
gc_mark((VALUE)obj->as.node.u1.node, lev);
/* fall through */
- case NODE_SUPER:/* 3 */
- case NODE_FCALL:
- case NODE_DEFN:
- case NODE_NEWLINE:
ptr = (VALUE)obj->as.node.u3.node;
goto again;
- case NODE_WHILE:/* 1,2 */
- case NODE_UNTIL:
- case NODE_AND:
- case NODE_OR:
- case NODE_CASE:
- case NODE_SCLASS:
- case NODE_DOT2:
- case NODE_DOT3:
- case NODE_FLIP2:
- case NODE_FLIP3:
- case NODE_MATCH2:
- case NODE_MATCH3:
- case NODE_OP_ASGN_OR:
- case NODE_OP_ASGN_AND:
- case NODE_MODULE:
- case NODE_ALIAS:
- case NODE_VALIAS:
- case NODE_ARGS:
gc_mark((VALUE)obj->as.node.u1.node, lev);
/* fall through */
- case NODE_METHOD:/* 2 */
- case NODE_NOT:
- case NODE_GASGN:
- case NODE_LASGN:
- case NODE_DASGN:
- case NODE_DASGN_CURR:
- case NODE_IASGN:
- case NODE_CVDECL:
- case NODE_CVASGN:
- case NODE_COLON3:
- case NODE_OPT_N:
- case NODE_EVSTR:
- case NODE_UNDEF:
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- case NODE_HASH:/* 1 */
- case NODE_LIT:
- case NODE_STR:
- case NODE_XSTR:
- case NODE_DEFINED:
- case NODE_MATCH:
- case NODE_RETURN:
- case NODE_BREAK:
- case NODE_NEXT:
- case NODE_YIELD:
- case NODE_COLON2:
- case NODE_SPLAT:
- case NODE_TO_ARY:
- case NODE_SVALUE:
ptr = (VALUE)obj->as.node.u1.node;
goto again;
- case NODE_SCOPE:/* 2,3 */
- case NODE_BLOCK_PASS:
- case NODE_CDECL:
gc_mark((VALUE)obj->as.node.u3.node, lev);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- case NODE_ZARRAY:/* - */
- case NODE_ZSUPER:
- case NODE_CFUNC:
- case NODE_VCALL:
- case NODE_GVAR:
- case NODE_LVAR:
- case NODE_DVAR:
- case NODE_IVAR:
- case NODE_CVAR:
- case NODE_NTH_REF:
- case NODE_BACK_REF:
- case NODE_REDO:
- case NODE_RETRY:
- case NODE_SELF:
- case NODE_NIL:
- case NODE_TRUE:
- case NODE_FALSE:
- case NODE_ATTRSET:
- case NODE_BLOCK_ARG:
- case NODE_POSTEXE:
break;
- case NODE_ALLOCA:
mark_locations_array((VALUE*)obj->as.node.u1.value,
- obj->as.node.u3.cnt);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- default:/* unlisted NODE */
if (is_pointer_to_heap(obj->as.node.u1.node)) {
-gc_mark((VALUE)obj->as.node.u1.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u2.node)) {
-gc_mark((VALUE)obj->as.node.u2.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u3.node)) {
-gc_mark((VALUE)obj->as.node.u3.node, lev);
}
-}
-return;/* no need to mark class. */
+
mark_source_filename(obj->as.node.nd_file);
+
switch (nd_type(obj)) {
+
case NODE_IF:
/* 1,2,3 */
+
case NODE_FOR:
+
case NODE_ITER:
+
case NODE_CREF:
+
case NODE_WHEN:
+
case NODE_MASGN:
+
case NODE_RESCUE:
+
case NODE_RESBODY:
+
case NODE_CLASS:
+
gc_mark((VALUE)obj->as.node.u2.node, lev);
+
/* fall through */
+
case NODE_BLOCK:
/* 1,3 */
+
case NODE_ARRAY:
+
case NODE_DSTR:
+
case NODE_DXSTR:
+
case NODE_DREGX:
+
case NODE_DREGX_ONCE:
+
case NODE_FBODY:
+
case NODE_ENSURE:
+
case NODE_CALL:
+
case NODE_DEFS:
+
case NODE_OP_ASGN1:
+
gc_mark((VALUE)obj->as.node.u1.node, lev);
+
/* fall through */
+
case NODE_SUPER:
/* 3 */
+
case NODE_FCALL:
+
case NODE_DEFN:
+
case NODE_NEWLINE:
+
ptr = (VALUE)obj->as.node.u3.node;
+
goto again;
+
+
case NODE_WHILE:
/* 1,2 */
+
case NODE_UNTIL:
+
case NODE_AND:
+
case NODE_OR:
+
case NODE_CASE:
+
case NODE_SCLASS:
+
case NODE_DOT2:
+
case NODE_DOT3:
+
case NODE_FLIP2:
+
case NODE_FLIP3:
+
case NODE_MATCH2:
+
case NODE_MATCH3:
+
case NODE_OP_ASGN_OR:
+
case NODE_OP_ASGN_AND:
+
case NODE_MODULE:
+
case NODE_ALIAS:
+
case NODE_VALIAS:
+
case NODE_ARGS:
+
gc_mark((VALUE)obj->as.node.u1.node, lev);
+
/* fall through */
+
case NODE_METHOD:
/* 2 */
+
case NODE_NOT:
+
case NODE_GASGN:
+
case NODE_LASGN:
+
case NODE_DASGN:
+
case NODE_DASGN_CURR:
+
case NODE_IASGN:
+
case NODE_CVDECL:
+
case NODE_CVASGN:
+
case NODE_COLON3:
+
case NODE_OPT_N:
+
case NODE_EVSTR:
+
case NODE_UNDEF:
+
ptr = (VALUE)obj->as.node.u2.node;
+
goto again;
+
+
case NODE_HASH:
/* 1 */
+
case NODE_LIT:
+
case NODE_STR:
+
case NODE_XSTR:
+
case NODE_DEFINED:
+
case NODE_MATCH:
+
case NODE_RETURN:
+
case NODE_BREAK:
+
case NODE_NEXT:
+
case NODE_YIELD:
+
case NODE_COLON2:
+
case NODE_SPLAT:
+
case NODE_TO_ARY:
+
case NODE_SVALUE:
+
ptr = (VALUE)obj->as.node.u1.node;
+
goto again;
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
case NODE_SCOPE:
/* 2,3 */
case NODE_BLOCK_PASS:
case NODE_CDECL:
gc_mark((VALUE)obj->as.node.u3.node, lev);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
case NODE_ZARRAY:
/* - */
case NODE_ZSUPER:
case NODE_CFUNC:
case NODE_VCALL:
case NODE_GVAR:
case NODE_LVAR:
case NODE_DVAR:
case NODE_IVAR:
case NODE_CVAR:
case NODE_NTH_REF:
case NODE_BACK_REF:
case NODE_REDO:
case NODE_RETRY:
case NODE_SELF:
case NODE_NIL:
case NODE_TRUE:
case NODE_FALSE:
case NODE_ATTRSET:
case NODE_BLOCK_ARG:
case NODE_POSTEXE:
break;
case NODE_ALLOCA:
mark_locations_array((VALUE*)obj->as.node.u1.value,
obj->as.node.u3.cnt);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
default:
/* unlisted NODE */
if (is_pointer_to_heap(obj->as.node.u1.node)) {
gc_mark((VALUE)obj->as.node.u1.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u2.node)) {
gc_mark((VALUE)obj->as.node.u2.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u3.node)) {
gc_mark((VALUE)obj->as.node.u3.node, lev);
}
}
return;
/* no need to mark class. */
}
gc_mark(obj->as.basic.klass, lev);
@@ -988,92 +1255,92 @@ gc_mark_children(ptr, lev)
case T_ICLASS:
case T_CLASS:
case T_MODULE:
-mark_tbl(obj->as.klass.m_tbl, lev);
-mark_tbl(obj->as.klass.iv_tbl, lev);
-ptr = obj->as.klass.super;
-goto again;
+
mark_tbl(obj->as.klass.m_tbl, lev);
+
mark_tbl(obj->as.klass.iv_tbl, lev);
+
ptr = obj->as.klass.super;
+
goto again;
case T_ARRAY:
-if (FL_TEST(obj, ELTS_SHARED)) {
ptr = obj->as.array.aux.shared;
goto again;
-}
-else {
long i, len = obj->as.array.len;
VALUE *ptr = obj->as.array.ptr;
+
if (FL_TEST(obj, ELTS_SHARED)) {
+
ptr = obj->as.array.aux.shared;
+
goto again;
+
}
+
else {
+
long i, len = obj->as.array.len;
+
VALUE *ptr = obj->as.array.ptr;
for (i=0; i
-gc_mark(*ptr++,
}
-}
-break;
+
for
+
+
}
+
}
+
break;
< len; i++) {
lev);
(i=0; i < len; i++) {
gc_mark(*ptr++, lev);
case T_HASH:
-mark_hash(obj->as.hash.tbl, lev);
-ptr = obj->as.hash.ifnone;
-goto again;
+
mark_hash(obj->as.hash.tbl, lev);
+
+
ptr = obj->as.hash.ifnone;
goto again;
case T_STRING:
#define STR_ASSOC FL_USER3
/* copied from string.c */
-if (FL_TEST(obj, ELTS_SHARED|STR_ASSOC)) {
ptr = obj->as.string.aux.shared;
goto again;
-}
-break;
+
if (FL_TEST(obj, ELTS_SHARED|STR_ASSOC)) {
+
ptr = obj->as.string.aux.shared;
+
goto again;
+
}
+
break;
case T_DATA:
-if (obj->as.data.dmark) (*obj->as.data.dmark)(DATA_PTR(obj));
-break;
+
if (obj->as.data.dmark) (*obj->as.data.dmark)(DATA_PTR(obj));
+
break;
case T_OBJECT:
-mark_tbl(obj->as.object.iv_tbl, lev);
-break;
+
mark_tbl(obj->as.object.iv_tbl, lev);
+
break;
case
case
case
case
case
-break;
+
T_FILE:
T_REGEXP:
T_FLOAT:
T_BIGNUM:
T_BLKTAG:
break;
case T_MATCH:
-if (obj->as.match.str) {
ptr = obj->as.match.str;
goto again;
-}
-break;
+
if (obj->as.match.str) {
+
ptr = obj->as.match.str;
+
goto again;
+
}
+
break;
case T_VARMAP:
-gc_mark(obj->as.varmap.val, lev);
-ptr = (VALUE)obj->as.varmap.next;
-goto again;
+
gc_mark(obj->as.varmap.val, lev);
+
ptr = (VALUE)obj->as.varmap.next;
+
goto again;
case T_SCOPE:
-if (obj->as.scope.local_vars && (obj->as.scope.flags & SCOPE_MALLOC)) {
int n = obj->as.scope.local_tbl[0]+1;
VALUE *vars = &obj->as.scope.local_vars[-1];
+
if (obj->as.scope.local_vars && (obj->as.scope.flags & SCOPE_MALLOC)) {
+
int n = obj->as.scope.local_tbl[0]+1;
+
VALUE *vars = &obj->as.scope.local_vars[-1];
while (n--) {
-gc_mark(*vars++, lev);
}
-}
-break;
+
while (n--) {
+
gc_mark(*vars++, lev);
+
}
+
}
+
break;
case T_STRUCT:
-{
+
+
+
long len = obj->as.rstruct.len;
VALUE *ptr = obj->as.rstruct.ptr;
{
long len = obj->as.rstruct.len;
VALUE *ptr = obj->as.rstruct.ptr;
while (len--) {
-gc_mark(*ptr++, lev);
}
-}
-break;
+
while (len--) {
+
gc_mark(*ptr++, lev);
+
}
+
}
+
break;
default:
-rb_bug("rb_gc_mark(): unknown data type 0x%lx(0x%lx) %s",
obj->as.basic.flags & T_MASK, obj,
is_pointer_to_heap(obj) ? "corrupted object" : "non object");
+
rb_bug("rb_gc_mark(): unknown data type 0x%lx(0x%lx) %s",
+
obj->as.basic.flags & T_MASK, obj,
+
is_pointer_to_heap(obj) ? "corrupted object" : "non object");
}
}
@@ -1102,22 +1369,55 @@ finalize_list(p)
}
}
+static char* obj_type(int tp)
+{
+
switch (tp) {
+
case T_NIL
: return "NIL";
+
case T_OBJECT : return "OBJECT";
+
case T_CLASS : return "CLASS";
+
case T_ICLASS : return "ICLASS";
+
case T_MODULE : return "MODULE";
+
case T_FLOAT : return "FLOAT";
+
case T_STRING : return "STRING";
+
case T_REGEXP : return "REGEXP";
+
case T_ARRAY : return "ARRAY";
+
case T_FIXNUM : return "FIXNUM";
+
case T_HASH
: return "HASH";
+
case T_STRUCT : return "STRUCT";
+
case T_BIGNUM : return "BIGNUM";
+
case T_FILE
: return "FILE";
+
+
case T_TRUE
: return "TRUE";
+
case T_FALSE : return "FALSE";
+
case T_DATA
: return "DATA";
+
case T_MATCH : return "MATCH";
+
case T_SYMBOL : return "SYMBOL";
+
+
case T_BLKTAG : return "BLKTAG";
+
case T_UNDEF : return "UNDEF";
+
case T_VARMAP : return "VARMAP";
+
case T_SCOPE : return "SCOPE";
+
case T_NODE
: return "NODE";
+
default: return "____";
+
}
+}
+
static void
free_unused_heaps()
{
int i, j;
for (i = j = 1; j < heaps_used; i++) {
-if (heaps[i].limit == 0) {
free(heaps[i].membase);
heaps_used--;
-}
-else {
if (i != j) {
-heaps[j] = heaps[i];
}
j++;
-}
+
if (heaps[i].limit == 0) {
+
free(heaps[i].membase);
+
heaps_used--;
+
}
+
else {
+
if (i != j) {
+
heaps[j] = heaps[i];
+
}
+
j++;
+
}
}
}
@@ -1134,24 +1434,33 @@ gc_sweep()
unsigned long live = 0;
unsigned long free_min = 0;
+
+
+
+
+
+
+
+
+
+
unsigned long really_freed = 0;
int free_counts[256];
int live_counts[256];
int do_gc_stats = gc_statistics & verbose_gc_stats;
for (i = 0; i < heaps_used; i++) {
free_min += heaps[i].limit;
}
free_min = free_min * 0.2;
if (free_min < FREE_MIN)
free_min = FREE_MIN;
if (free_min < heap_free_min)
free_min = heap_free_min;
if (do_gc_stats) {
for (i = 0 ; i< 256; i++) { free_counts[i] = live_counts[i] = 0; }
+
}
if (ruby_in_compile && ruby_parser_stack_on_heap()) {
-/* should not reclaim nodes during compilation
+
/* should not reclaim nodes during compilation
if yacc's semantic stack is not allocated on machine stack */
-for (i = 0; i < heaps_used; i++) {
p = heaps[i].slot; pend = p + heaps[i].limit;
while (p < pend) {
-if (!(p->as.basic.flags&FL_MARK) && BUILTIN_TYPE(p) == T_NODE)
gc_mark((VALUE)p, 0);
-p++;
}
-}
+
for (i = 0; i < heaps_used; i++) {
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
while (p < pend) {
+
if (!(p->as.basic.flags&FL_MARK) && BUILTIN_TYPE(p) == T_NODE)
+
gc_mark((VALUE)p, 0);
+
p++;
+
}
+
}
}
mark_source_filename(ruby_sourcefile);
@@ -1172,7 +1481,7 @@ gc_sweep()
while (p < pend) {
if (!(p->as.basic.flags & FL_MARK)) {
if (p->as.basic.flags &&
((deferred = obj_free((VALUE)p)) ||
+
(((do_gc_stats && really_freed++), deferred = obj_free((VALUE)p)) ||
((FL_TEST(p, FL_FINALIZE)) && need_call_final))) {
if (!deferred) {
p->as.free.flags = T_DEFERRED;
@@ -1183,6 +1492,12 @@ gc_sweep()
final_list = p;
}
else {
+
if (do_gc_stats) {
+
int obt = p->as.basic.flags & T_MASK;
+
if (obt) {
+
free_counts[obt]++;
+
}
+
}
add_freelist(p);
}
n++;
@@ -1194,6 +1509,9 @@ gc_sweep()
else {
RBASIC(p)->flags &= ~FL_MARK;
live++;
+
if (do_gc_stats) {
+
live_counts[RANY((VALUE)p)->as.basic.flags & T_MASK]++;
+
}
}
p++;
}
@@ -1211,15 +1529,29 @@ gc_sweep()
}
}
if (malloc_increase > malloc_limit) {
-malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
-if (malloc_limit < GC_MALLOC_LIMIT) malloc_limit = GC_MALLOC_LIMIT;
+
malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
+
if (malloc_limit < initial_malloc_limit) malloc_limit = initial_malloc_limit;
}
malloc_increase = 0;
if (freed < free_min) {
-add_heap();
+
add_heap();
}
during_gc = 0;
+
+
+
+
+
+
+
+
+
+
+
+
+
+
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7d\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0 || live_counts[i]>0) {
fprintf(gc_data_file,
"kept %.7d / freed %.7d objects of type %s\n",
live_counts[i], free_counts[i], obj_type(i));
}
}
}
/* clear finalization list */
if (final_list) {
deferred_final_list = final_list;
@@ -1260,51 +1592,51 @@ obj_free(obj)
case T_FIXNUM:
case T_TRUE:
case T_FALSE:
-rb_bug("obj_free() called for broken object");
-break;
+
+
}
rb_bug("obj_free() called for broken object");
break;
if (FL_TEST(obj, FL_EXIVAR)) {
-rb_free_generic_ivar((VALUE)obj);
+
rb_free_generic_ivar((VALUE)obj);
}
switch (BUILTIN_TYPE(obj)) {
case T_OBJECT:
-if (RANY(obj)->as.object.iv_tbl) {
st_free_table(RANY(obj)->as.object.iv_tbl);
-}
-break;
+
if (RANY(obj)->as.object.iv_tbl) {
+
st_free_table(RANY(obj)->as.object.iv_tbl);
+
}
+
break;
case T_MODULE:
case T_CLASS:
-rb_clear_cache_by_class((VALUE)obj);
-st_free_table(RANY(obj)->as.klass.m_tbl);
-if (RANY(obj)->as.object.iv_tbl) {
st_free_table(RANY(obj)->as.object.iv_tbl);
-}
-break;
+
rb_clear_cache_by_class((VALUE)obj);
+
st_free_table(RANY(obj)->as.klass.m_tbl);
+
if (RANY(obj)->as.object.iv_tbl) {
+
st_free_table(RANY(obj)->as.object.iv_tbl);
+
}
+
break;
case T_STRING:
-if (RANY(obj)->as.string.ptr && !FL_TEST(obj, ELTS_SHARED)) {
RUBY_CRITICAL(free(RANY(obj)->as.string.ptr));
-}
-break;
+
if (RANY(obj)->as.string.ptr && !FL_TEST(obj, ELTS_SHARED)) {
+
RUBY_CRITICAL(free(RANY(obj)->as.string.ptr));
+
}
+
break;
case T_ARRAY:
-if (RANY(obj)->as.array.ptr && !FL_TEST(obj, ELTS_SHARED)) {
RUBY_CRITICAL(free(RANY(obj)->as.array.ptr));
-}
-break;
+
if (RANY(obj)->as.array.ptr && !FL_TEST(obj, ELTS_SHARED)) {
+
RUBY_CRITICAL(free(RANY(obj)->as.array.ptr));
+
}
+
break;
case T_HASH:
-if (RANY(obj)->as.hash.tbl) {
st_free_table(RANY(obj)->as.hash.tbl);
-}
-break;
+
if (RANY(obj)->as.hash.tbl) {
+
st_free_table(RANY(obj)->as.hash.tbl);
+
}
+
break;
case T_REGEXP:
-if (RANY(obj)->as.regexp.ptr) {
re_free_pattern(RANY(obj)->as.regexp.ptr);
-}
-if (RANY(obj)->as.regexp.str) {
RUBY_CRITICAL(free(RANY(obj)->as.regexp.str));
-}
-break;
+
if (RANY(obj)->as.regexp.ptr) {
+
re_free_pattern(RANY(obj)->as.regexp.ptr);
+
}
+
if (RANY(obj)->as.regexp.str) {
+
RUBY_CRITICAL(free(RANY(obj)->as.regexp.str));
+
}
+
break;
case T_DATA:
if (DATA_PTR(obj)) {
if ((long)RANY(obj)->as.data.dfree == -1) {
@@ -1317,11 +1649,11 @@ obj_free(obj)
}
break;
case T_MATCH:
-if (RANY(obj)->as.match.regs) {
re_free_registers(RANY(obj)->as.match.regs);
RUBY_CRITICAL(free(RANY(obj)->as.match.regs));
-}
-break;
+
if (RANY(obj)->as.match.regs) {
+
re_free_registers(RANY(obj)->as.match.regs);
+
RUBY_CRITICAL(free(RANY(obj)->as.match.regs));
+
}
+
break;
case T_FILE:
if (RANY(obj)->as.file.fptr) {
struct rb_io_t *fptr = RANY(obj)->as.file.fptr;
@@ -1332,19 +1664,19 @@ obj_free(obj)
}
break;
case T_ICLASS:
-/* iClass shares table with the module */
-break;
+
/* iClass shares table with the module */
+
break;
case T_FLOAT:
case T_VARMAP:
case T_BLKTAG:
-break;
+
break;
case T_BIGNUM:
-if (RANY(obj)->as.bignum.digits) {
RUBY_CRITICAL(free(RANY(obj)->as.bignum.digits));
-}
-break;
+
if (RANY(obj)->as.bignum.digits) {
+
RUBY_CRITICAL(free(RANY(obj)->as.bignum.digits));
+
}
+
break;
case T_NODE:
switch (nd_type(obj)) {
case NODE_SCOPE:
@@ -1359,7 +1691,7 @@ obj_free(obj)
break;/* no need to free iv_tbl */
case T_SCOPE:
-if (RANY(obj)->as.scope.local_vars &&
+
if (RANY(obj)->as.scope.local_vars &&
RANY(obj)->as.scope.flags != SCOPE_ALLOCA) {
VALUE *vars = RANY(obj)->as.scope.local_vars-1;
if (!(RANY(obj)->as.scope.flags & SCOPE_CLONE) && vars[0] == 0)
@@ -1370,14 +1702,14 @@ obj_free(obj)
break;
case T_STRUCT:
-if (RANY(obj)->as.rstruct.ptr) {
RUBY_CRITICAL(free(RANY(obj)->as.rstruct.ptr));
-}
-break;
+
if (RANY(obj)->as.rstruct.ptr) {
+
RUBY_CRITICAL(free(RANY(obj)->as.rstruct.ptr));
+
}
+
break;
default:
-rb_bug("gc_sweep(): unknown data type 0x%lx(0x%lx)",
RANY(obj)->as.basic.flags & T_MASK, obj);
+
rb_bug("gc_sweep(): unknown data type 0x%lx(0x%lx)",
+
RANY(obj)->as.basic.flags & T_MASK, obj);
}
return 0;
@@ -1407,18 +1739,18 @@ _rb_setjmp:\n\
typedef unsigned long rb_jmp_buf[6];
__asm__ (".align 4\n\
_rb_setjmp:\n\
-pushl%ebp\n\
-movl%esp,%ebp\n\
-movl8(%ebp),%ebp\n\
-movl%eax,(%ebp)\n\
-movl%ebx,4(%ebp)\n\
-movl%ecx,8(%ebp)\n\
-movl%edx,12(%ebp)\n\
-movl%esi,16(%ebp)\n\
-movl%edi,20(%ebp)\n\
-popl%ebp\n\
-xorl%eax,%eax\n\
-ret");
+
pushl
%ebp\n\
+
movl
%esp,%ebp\n\
+
movl
8(%ebp),%ebp\n\
+
movl
%eax,(%ebp)\n\
+
movl
%ebx,4(%ebp)\n\
+
movl
%ecx,8(%ebp)\n\
+
movl
%edx,12(%ebp)\n\
+
movl
%esi,16(%ebp)\n\
+
movl
%edi,20(%ebp)\n\
+
popl
%ebp\n\
+
xorl
%eax,%eax\n\
+
ret");
#endif
#endif
int rb_setjmp (rb_jmp_buf);
@@ -1431,41 +1763,50 @@ garbage_collect()
struct gc_list *list;
struct FRAME * volatile frame; /* gcc 2.7.2.3 -O2 bug??
jmp_buf save_regs_gc_mark;
+
struct timeval gctv1, gctv2;
SET_STACK_END;
*/
#ifdef HAVE_NATIVETHREAD
if (!is_ruby_native_thread()) {
-rb_bug("cross-thread violation on rb_gc()");
+
rb_bug("cross-thread violation on rb_gc()");
}
#endif
if (dont_gc || during_gc) {
-if (!freelist) {
add_heap();
-}
-return;
+
if (!freelist) {
+
add_heap();
+
}
+
return;
}
if (during_gc) return;
during_gc++;
+
+
+
+
+
+
+
+
if (gc_statistics) {
gc_collections++;
gettimeofday(&gctv1, NULL);
if (verbose_gc_stats) {
fprintf(gc_data_file, "Garbage collection started\n");
}
}
init_mark_stack();
gc_mark((VALUE)ruby_current_node, 0);
/* mark frame stack */
for (frame = ruby_frame; frame; frame = frame->prev) {
-rb_gc_mark_frame(frame);
-if (frame->tmp) {
struct FRAME *tmp = frame->tmp;
while (tmp) {
-rb_gc_mark_frame(tmp);
-tmp = tmp->prev;
}
-}
+
rb_gc_mark_frame(frame);
+
if (frame->tmp) {
+
struct FRAME *tmp = frame->tmp;
+
while (tmp) {
+
rb_gc_mark_frame(tmp);
+
tmp = tmp->prev;
+
}
+
}
}
gc_mark((VALUE)ruby_scope, 0);
gc_mark((VALUE)ruby_dyna_vars, 0);
if (finalizer_table) {
-mark_tbl(finalizer_table, 0);
+
mark_tbl(finalizer_table, 0);
}
FLUSH_REGISTER_WINDOWS;
@@ -1478,9 +1819,9 @@ garbage_collect()
rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
#else
if ((VALUE*)STACK_END < rb_gc_stack_start)
-rb_gc_mark_locations((VALUE*)STACK_END, rb_gc_stack_start);
+
rb_gc_mark_locations((VALUE*)STACK_END, rb_gc_stack_start);
else
-rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
+
rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
#endif
#ifdef __ia64
/* mark backing store (flushed register window on the stack) */
@@ -1489,13 +1830,13 @@ garbage_collect()
#endif
#if defined(__human68k__) || defined(__mc68000__)
rb_gc_mark_locations((VALUE*)((char*)STACK_END + 2),
- (VALUE*)((char*)rb_gc_stack_start + 2));
+
(VALUE*)((char*)rb_gc_stack_start + 2));
#endif
rb_gc_mark_threads();
/* mark protected global variables */
for (list = global_List; list; list = list->next) {
-rb_gc_mark_maybe(*list->varptr);
+
rb_gc_mark_maybe(*list->varptr);
}
rb_mark_end_proc();
rb_gc_mark_global_tbl();
@@ -1510,18 +1851,30 @@ garbage_collect()
/* gc_mark objects whose marking are not completed*/
do {
-while (!MARK_STACK_EMPTY) {
if (mark_stack_overflow){
-gc_mark_all();
}
else {
-gc_mark_rest();
}
-}
-rb_gc_abort_threads();
+
while (!MARK_STACK_EMPTY) {
+
if (mark_stack_overflow){
+
gc_mark_all();
+
}
+
else {
+
gc_mark_rest();
+
}
+
}
+
rb_gc_abort_threads();
} while (!MARK_STACK_EMPTY);
gc_sweep();
+
+
+
+
+
+
+
+
+
+
+
+
if (gc_statistics) {
GC_TIME_TYPE musecs_used;
gettimeofday(&gctv2, NULL);
musecs_used = ((GC_TIME_TYPE)(gctv2.tv_sec - gctv1.tv_sec) * 1000000) + (gctv2.tv_usec - gctv1.tv_usec);
gc_time += musecs_used;
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
fflush(gc_data_file);
}
}
}
void
@@ -1588,8 +1941,8 @@ Init_stack(addr)
memset(&m, 0, sizeof(m));
VirtualQuery(&m, &m, sizeof(m));
rb_gc_stack_start =
-STACK_UPPER((VALUE *)&m, (VALUE *)m.BaseAddress,
(VALUE *)((char *)m.BaseAddress + m.RegionSize) - 1);
+
STACK_UPPER((VALUE *)&m, (VALUE *)m.BaseAddress,
+
(VALUE *)((char *)m.BaseAddress + m.RegionSize) - 1);
#elif defined(STACK_END_ADDRESS)
{
extern void *STACK_END_ADDRESS;
@@ -1599,24 +1952,24 @@ Init_stack(addr)
if (!addr) addr = (void *)&addr;
STACK_UPPER(&addr, addr, ++addr);
if (rb_gc_stack_start) {
-if (STACK_UPPER(&addr,
-rb_gc_stack_start > addr,
-rb_gc_stack_start < addr))
rb_gc_stack_start = addr;
-return;
+
if (STACK_UPPER(&addr,
+
rb_gc_stack_start > addr,
+
rb_gc_stack_start < addr))
+
rb_gc_stack_start = addr;
+
return;
}
rb_gc_stack_start = addr;
#endif
#ifdef HAVE_GETRLIMIT
{
-struct rlimit rlim;
+
struct rlimit rlim;
-if (getrlimit(RLIMIT_STACK, &rlim) == 0) {
unsigned int space = rlim.rlim_cur/5;
+
if (getrlimit(RLIMIT_STACK, &rlim) == 0) {
+
unsigned int space = rlim.rlim_cur/5;
-}
+
+
+
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (rlim.rlim_cur - space) / sizeof(VALUE);
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (rlim.rlim_cur - space) / sizeof(VALUE);
}
}
#endif
}
@@ -1652,16 +2005,16 @@ void ruby_init_stack(VALUE *addr
}
#elif defined _WIN32
{
-MEMORY_BASIC_INFORMATION mi;
-DWORD size;
-DWORD space;
-if (VirtualQuery(&mi, &mi, sizeof(mi))) {
size = (char *)mi.BaseAddress - (char *)mi.AllocationBase;
space = size / 5;
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (size - space) / sizeof(VALUE);
-}
+
MEMORY_BASIC_INFORMATION mi;
+
DWORD size;
+
+
+
+
+
+
+
+
DWORD space;
if (VirtualQuery(&mi, &mi, sizeof(mi))) {
size = (char *)mi.BaseAddress - (char *)mi.AllocationBase;
space = size / 5;
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (size - space) / sizeof(VALUE);
}
}
#endif
}
@@ -1701,8 +2054,9 @@ void
Init_heap()
{
if (!rb_gc_stack_start) {
-Init_stack(0);
+
Init_stack(0);
}
+
set_gc_parameters();
add_heap();
}
@@ -1715,7 +2069,7 @@ os_obj_of(of)
volatile VALUE v;
for (i = 0; i < heaps_used; i++) {
-RVALUE *p, *pend;
+
RVALUE *p, *pend;
p = heaps[i].slot; pend = p + heaps[i].limit;
for (;p < pend; p++) {
@@ -1808,8 +2162,8 @@ add_final(os, block)
{
rb_warn("ObjectSpace::add_finalizer is deprecated; use define_finalizer");
if (!rb_respond_to(block, rb_intern("call"))) {
-rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
- rb_obj_classname(block));
+
rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
+
rb_obj_classname(block));
}
rb_ary_push(finalizers, block);
return block;
@@ -1864,7 +2218,7 @@ undefine_final(os, obj)
VALUE os, obj;
{
if (finalizer_table) {
-st_delete(finalizer_table, (st_data_t*)&obj, 0);
+
st_delete(finalizer_table, (st_data_t*)&obj, 0);
}
return obj;
}
@@ -1888,11 +2242,11 @@ define_final(argc, argv, os)
rb_scan_args(argc, argv, "11", &obj, &block);
if (argc == 1) {
-block = rb_block_proc();
+
block = rb_block_proc();
}
else if (!rb_respond_to(block, rb_intern("call"))) {
-rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
- rb_obj_classname(block));
+
rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
+
rb_obj_classname(block));
}
need_call_final = 1;
if (!FL_ABLE(obj)) {
@@ -1905,10 +2259,10 @@ define_final(argc, argv, os)
OBJ_FREEZE(block);
if (!finalizer_table) {
-finalizer_table = st_init_numtable();
+
finalizer_table = st_init_numtable();
}
if (st_lookup(finalizer_table, obj, &table)) {
-rb_ary_push(table, block);
+
rb_ary_push(table, block);
}
else {
table = rb_ary_new3(1, block);
@@ -1927,7 +2281,7 @@ rb_gc_copy_finalizer(dest, obj)
if (!finalizer_table) return;
if (!FL_TEST(obj, FL_FINALIZE)) return;
if (st_lookup(finalizer_table, obj, &table)) {
-st_insert(finalizer_table, dest, table);
+
st_insert(finalizer_table, dest, table);
}
RBASIC(dest)->flags |= FL_FINALIZE;
}
@@ -1957,18 +2311,18 @@ run_final(obj)
args[1] = 0;
args[2] = (VALUE)ruby_safe_level;
for (i=0; i<RARRAY(finalizers)->len; i++) {
-args[0] = RARRAY(finalizers)->ptr[i];
-if (!args[1]) args[1] = rb_ary_new3(1, objid);
-rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
+
+
+
args[0] = RARRAY(finalizers)->ptr[i];
if (!args[1]) args[1] = rb_ary_new3(1, objid);
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
}
if (finalizer_table && st_delete(finalizer_table, (st_data_t*)&obj, &table)) {
-for (i=0; i<RARRAY(table)->len; i++) {
VALUE final = RARRAY(table)->ptr[i];
args[0] = RARRAY(final)->ptr[1];
if (!args[1]) args[1] = rb_ary_new3(1, objid);
args[2] = FIX2INT(RARRAY(final)->ptr[0]);
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
-}
+
for (i=0; i<RARRAY(table)->len; i++) {
+
VALUE final = RARRAY(table)->ptr[i];
+
args[0] = RARRAY(final)->ptr[1];
+
if (!args[1]) args[1] = rb_ary_new3(1, objid);
+
args[2] = FIX2INT(RARRAY(final)->ptr[0]);
+
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
+
}
}
rb_thread_critical = critical_save;
}
@@ -1980,8 +2334,8 @@ rb_gc_finalize_deferred()
deferred_final_list = 0;
if (p) {
-finalize_list(p);
-free_unused_heaps();
+
finalize_list(p);
+
free_unused_heaps();
}
}
@@ -2061,7 +2415,7 @@ id2ref(obj, objid)
if (ptr == Qfalse) return Qfalse;
if (ptr == Qnil) return Qnil;
if (FIXNUM_P(ptr)) return (VALUE)ptr;
ptr = objid ^ FIXNUM_FLAG;/* unset FIXNUM_FLAG */
+
ptr = objid ^ FIXNUM_FLAG; /* unset FIXNUM_FLAG */
if ((ptr % sizeof(RVALUE)) == (4 << 2)) {
ID symid = ptr / sizeof(RVALUE);
@@ -2075,7 +2429,7 @@ id2ref(obj, objid)
rb_raise(rb_eRangeError, "0x%lx is not id value", p0);
}
if (BUILTIN_TYPE(ptr) == 0 || RBASIC(ptr)->klass == 0) {
-rb_raise(rb_eRangeError, "0x%lx is recycled object", p0);
+
rb_raise(rb_eRangeError, "0x%lx is recycled object", p0);
}
return (VALUE)ptr;
}
@@ -2166,6 +2520,14 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "stress=", gc_stress_set, 1);
rb_define_method(rb_mGC, "garbage_collect", rb_gc_start, 0);
+
+
+
+
+
+
+
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"clear_stats", rb_gc_clear_stats, 0);
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
rb_define_module_function(rb_mObSpace, "garbage_collect", rb_gc_start, 0);
@@ -2188,7 +2550,7 @@ Init_GC()
+
rb_global_variable(&nomem_error);
nomem_error = rb_exc_new3(rb_eNoMemError,
rb_obj_freeze(rb_str_new2("failed to allocate memory")));
rb_obj_freeze(rb_str_new2("failed to allocate memory")));
OBJ_TAINT(nomem_error);
OBJ_FREEZE(nomem_error);
1.26.5.1.10.1.12. 05-better-source-file-tracing.patch
diff --git a/eval.c b/eval.c
index fb3307c..356226e 100644
--- a/eval.c
+++ b/eval.c
@@ -1161,7 +1161,7 @@ static VALUE trace_func = 0;
static int tracing = 0;
static void call_trace_func _((rb_event_t,NODE*,VALUE,ID,VALUE));
-#if 0
+#if 1
#define SET_CURRENT_SOURCE() (ruby_sourcefile = ruby_current_node->nd_file, \
ruby_sourceline = nd_line(ruby_current_node))
#else
1.26.5.1.10.1.13. 16-caller-for-all-threads.patch
diff --git a/eval.c b/eval.c
index 356226e..a0fdc55 100644
--- a/eval.c
+++ b/eval.c
@@ -8199,6 +8199,17 @@ rb_f_method_name()
}
}
+/* Hash (Thread => Backtrace) used to collect backtrace for each threads. */
+static VALUE backtrace_for_each_thread;
+
+static int backtrace_level_for_each_thread;
+
+static VALUE
+switch_thread_context_to_collect_backtrace(rb_thread_t next);
+
+static VALUE
+rb_f_caller_for_all_threads();
+
void
Init_eval()
{
@@ -8244,6 +8255,7 @@ Init_eval()
rb_define_global_function("fail", rb_f_raise, -1);
+
rb_define_global_function("caller", rb_f_caller, -1);
rb_define_global_function("caller_for_all_threads", rb_f_caller_for_all_threads, -1);
rb_define_global_function("exit", rb_f_exit, -1);
rb_define_global_function("abort", rb_f_abort, -1);
@@ -10599,6 +10611,7 @@ static int
th_sig, th_safe;
#define RESTORE_RAISE5
#define RESTORE_SIGNAL6
#define RESTORE_EXIT7
+#define RESTORE_BACKTRACE8
extern VALUE *rb_gc_stack_start;
#ifdef __ia64
@@ -10705,6 +10718,15 @@ rb_thread_switch(n)
}
rb_exc_raise(th_raise_exception);
break;
+
case RESTORE_BACKTRACE:
+
rb_hash_aset(backtrace_for_each_thread, curr_thread->thread,
+
backtrace(backtrace_level_for_each_thread));
+
if (curr_thread != main_thread) {
+
switch_thread_context_to_collect_backtrace(curr_thread->next);
+
} else {
+
/* Circled back to main thread, cycle is complete. */
+
}
+
break;
case RESTORE_NORMAL:
default:
break;
@@ -13875,3 +13897,74 @@ rb_throw(tag, val)
argv[1] = val;
rb_f_throw(2, argv);
}
+
+static VALUE
+switch_thread_context_to_collect_backtrace(rb_thread_t next)
+{
+
if (THREAD_SAVE_CONTEXT(curr_thread)) {
+
return Qnil;
+
}
+
curr_thread = next;
+
rb_thread_restore_context(next, RESTORE_BACKTRACE);
+
return Qnil;
+}
+
+
+/*
+ * call-seq:
+ *
caller_for_all_threads(start=1)
=> array
+ *
+ * Returns the current execution stack for all threads
+ * ---a hash whose keys are thread instances and values
+ * the thread caller backtrace.
+ *
+ * Backtraces are array of hashes indicating location on the
+ * stack. Hash keys include ``<em>:line</em>'' or ``<em>:file</em>''
+ * and ``<em>:method'</em>''.
+ *
+ * The optional _start_ parameter
+ * determines the number of initial stack entries to omit from the
+ * result.
+ *
+ *
def a(skip)
+ *
caller_for_all_threads(skip)
+ *
end
+ *
def b(skip)
+ *
a(skip)
+ *
end
+ *
def c(skip)
+ *
b(skip)
+ *
end
+ *
c(0)
#=> ["prog:2:in `a'", "prog:5:in `b'", "prog:8:in `c'", "prog:10"]
+ *
c(1)
#=> ["prog:5:in `b'", "prog:8:in `c'", "prog:11"]
+ *
c(2)
#=> ["prog:8:in `c'", "prog:12"]
+ *
c(3)
#=> ["prog:13"]
+ */
+static VALUE
+rb_f_caller_for_all_threads(argc, argv)
+
int argc;
+
VALUE *argv;
+{
+
volatile int critical;
+
VALUE level;
+VALUE result;
+
+
rb_scan_args(argc, argv, "01", &level);
+
backtrace_level_for_each_thread = NIL_P(level) ? 0 : NUM2INT(level);
+if (backtrace_level_for_each_thread < 0) {
+rb_raise(rb_eArgError, "negative level (%d)", backtrace_level_for_each_thread);
+}
+
+critical = rb_thread_critical;
+rb_thread_critical = Qtrue;
+
+
backtrace_for_each_thread = rb_hash_new();
+
switch_thread_context_to_collect_backtrace(main_thread->next);
+
+result = backtrace_for_each_thread;
+backtrace_for_each_thread = Qnil;
+backtrace_for_each_thread = 0;
+
+rb_thread_critical = critical;
+
return result;
+}
diff --git a/test/callerforallthreads/test_caller_for_each_thread.rb
b/test/callerforallthreads/test_caller_for_each_thread.rb
new file mode 100644
index 0000000..6aebaed
--- /dev/null
+++ b/test/callerforallthreads/test_caller_for_each_thread.rb
@@ -0,0 +1,95 @@
+# -*- ruby-indent-level: 4 -*+require 'thread'
+require 'test/unit'
+
+class AClassWithNestedmethods
+
+ def an_ultra_nested_method(skip)
+
caller_for_all_threads skip
+ end
+
+ def a_nested_method(skip)
+
an_ultra_nested_method skip
+ end
+
+ def a_method(skip=0)
+
a_nested_method skip
+ end
+
+end
+
+class CallerForEachThreadTest < Test::Unit::TestCase
+
+ def testCollectMeaningfulBacktraceForASingleThread
+
backtraces = AClassWithNestedmethods.new.a_method
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":8:in `an_ultra_nested_method'", backtrace[0]
+
assert_equal __FILE__ + ":12:in `a_nested_method'", backtrace[1]
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[2]
+
assert_equal __FILE__ + ":24:in `testCollectMeaningfulBacktraceForASingleThread'",
+
backtrace[3]
+ end
+
+ def testCanSkipFirstStackEntries
+
backtraces = AClassWithNestedmethods.new.a_method 2
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[0]
+
assert_equal __FILE__ + ":35:in `testCanSkipFirstStackEntries'",
+
backtrace[1]
+ end
+
+ def testCollectMeaningfulBacktraceForMultipleThreads
+
first_thread = Thread.new do
+
loop do
+
Thread.pass
+
sleep 1
+
end
+
end
+
+
second_thread = Thread.new do
+
loop do
+
Thread.pass
+
sleep 1
+
end
+
end
+
+
backtraces = AClassWithNestedmethods.new.a_method
+
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_match __FILE__ + ":8:in `an_ultra_nested_method'", backtrace[0]
+
assert_match __FILE__ + ":12:in `a_nested_method'", backtrace[1]
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[2]
+
assert_equal __FILE__ + ":58:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[3]
+
+
backtrace = backtraces[first_thread]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":47:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[0]
+
assert_equal __FILE__ + ":45:in `loop'",
+
backtrace[1]
+
assert_equal __FILE__ + ":45:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[2]
+
assert_equal __FILE__ + ":44:in `initialize'",backtrace[3]
+
assert_equal __FILE__ + ":44:in `new'", backtrace[4]
+
assert_equal __FILE__ + ":44:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[5]
+
+
backtrace = backtraces[second_thread]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":53:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[0]
+
assert_equal __FILE__ + ":52:in `loop'", backtrace[1]
+
assert_equal __FILE__ + ":52:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[2]
+
assert_equal __FILE__ + ":51:in `initialize'",backtrace[3]
+
assert_equal __FILE__ + ":51:in `new'", backtrace[4]
+
assert_equal __FILE__ + ":51:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[5]
+ end
+
+end
+
1.26.5.1.10.1.14. 09-track-object-allocation.patch
diff --git a/gc.c b/gc.c
index 30a1219..5b42b90 100644
--- a/gc.c
+++ b/gc.c
@@ -96,6 +96,26 @@ static void garbage_collect();
int ruby_gc_stress = 0;
+static unsigned long live_objects = 0;
+unsigned long rb_os_live_objects()
+{
+
return live_objects;
+}
+
+#if defined(HAVE_LONG_LONG)
+static unsigned LONG_LONG allocated_objects = 0;
+unsigned LONG_LONG rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#else
+static unsigned long allocated_objects = 0;
+unsigned long rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#endif
+
NORETURN(void rb_exc_jump _((VALUE)));
void
@@ -987,6 +1007,8 @@ rb_newobj()
RANY(obj)->file = ruby_sourcefile;
RANY(obj)->line = ruby_sourceline;
#endif
+
live_objects++;
+
allocated_objects++;
return obj;
}
@@ -1825,6 +1847,7 @@ gc_sweep()
add_heap();
}
during_gc = 0;
+
live_objects = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2790,6 +2813,35 @@ rb_obj_id(VALUE obj)
return (VALUE)((long)obj|FIXNUM_FLAG);
}
+/* call-seq:
+ * ObjectSpace.live_objects => number
+ *
+ * Returns the count of objects currently allocated in the system. This goes
+ * down after the garbage collector runs.
+ */
+static
+VALUE os_live_objects(VALUE self)
+{
+
return ULONG2NUM(live_objects);
+}
+
+/* call-seq:
+ * ObjectSpace.allocated_objects => number
+ *
+ * Returns the count of objects allocated since the Ruby interpreter has
+ * started. This number can only increase. To know how many objects are
+ * currently allocated, use ObjectSpace::live_objects
+ */
+static
+VALUE os_allocated_objects(VALUE self)
+{
+#if defined(HAVE_LONG_LONG)
+
return ULL2NUM(allocated_objects);
+#else
+
return ULONG2NUM(allocated_objects);
+#endif
+}
+
/*
* The <code>GC</code> module provides an interface to Ruby's mark and
* sweep garbage collection mechanism. Some of the underlying methods
@@ -2833,6 +2885,9 @@ Init_GC()
rb_define_module_function(rb_mObSpace, "finalizers", finals, 0);
rb_define_module_function(rb_mObSpace, "call_finalizer", call_final, 1);
+
+
+
rb_define_module_function(rb_mObSpace, "live_objects", os_live_objects, 0);
rb_define_module_function(rb_mObSpace, "allocated_objects", os_allocated_objects, 0);
rb_define_module_function(rb_mObSpace, "define_finalizer", define_final, -1);
rb_define_module_function(rb_mObSpace, "undefine_finalizer", undefine_final, 1);
diff --git a/intern.h b/intern.h
index 1117614..a87661d 100644
--- a/intern.h
+++ b/intern.h
@@ -274,6 +274,12 @@ void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
VALUE rb_gc_allocated_size _((void));
VALUE rb_gc_num_allocations _((void));
+unsigned long rb_os_live_objects _((void));
+#ifdef HAVE_LONG_LONG
+unsigned LONG_LONG rb_os_allocated_objects _((void));
+#else
+unsigned long rb_os_allocated_objects _((void));
+#endif
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.10.1.15. 02-sigvtalrm-fix.patch
diff --git a/eval.c b/eval.c
index 7886e17..6ff2560 100644
--- a/eval.c
+++ b/eval.c
@@ -12461,6 +12461,11 @@ rb_thread_start_0(fn, arg, th)
curr_thread->next = th;
th->priority = curr_thread->priority;
th->thgroup = curr_thread->thgroup;
+#if defined(HAVE_SETITIMER) || defined(_THREAD_SAFE)
+
if (!thread_init) {
+
rb_thread_start_timer();
+
}
+#endif
}
START_TIMER();
@@ -13189,7 +13194,9 @@ rb_thread_atfork()
main_thread = curr_thread;
curr_thread->next = curr_thread;
curr_thread->prev = curr_thread;
STOP_TIMER();
+#if defined(HAVE_SETITIMER) || defined(_THREAD_SAFE)
+
rb_thread_stop_timer();
+#endif
}
1.26.5.1.10.1.16. 10-expose-heap-slots.patch
diff --git a/gc.c b/gc.c
index 5b42b90..21b3f6b 100644
--- a/gc.c
+++ b/gc.c
@@ -690,6 +690,7 @@ static int heaps_used
= 0;
static int heap_min_slots = 10000;
static int heap_slots = 10000;
+static int heap_size = 0;
static int heap_free_min = 4096;
static int heap_slots_increment = 10000;
@@ -800,6 +801,21 @@ static void set_gc_parameters()
/*
* call-seq:
+ *
GC.heap_slots
=> Integer
+ *
+ * Returns the number of heap slots available for object allocations.
+ *
+ *
GC.heap_slots
#=> 10000
+ *
+ */
+VALUE
+rb_gc_heap_slots()
+{
+
return INT2NUM(heap_size);
+}
+
+/*
+ * call-seq:
*
GC.dump
=> nil
*
* dumps information about the current GC data structures to the GC log file
@@ -967,6 +983,7 @@ add_heap()
heaps[heaps_used].limit = heap_slots;
break;
}
+
heap_size += heap_slots;
pend = p + heap_slots;
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
@@ -1828,6 +1845,7 @@ gc_sweep()
if (n == heaps[i].limit && freed > free_min) {
RVALUE *pp;
+
heap_size -= n;
heaps[i].limit = 0;
for (pp = final_list; pp != final; pp = pp->as.free.next) {
pp->as.free.flags |= FL_SINGLETON; /* freeing page mark */
@@ -2866,6 +2884,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "clear_stats", rb_gc_clear_stats, 0);
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
+
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
diff --git a/intern.h b/intern.h
index a87661d..e8f3209 100644
--- a/intern.h
+++ b/intern.h
@@ -274,6 +274,7 @@ void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
VALUE rb_gc_allocated_size _((void));
VALUE rb_gc_num_allocations _((void));
+VALUE rb_gc_heap_slots _((void));
unsigned long rb_os_live_objects _((void));
#ifdef HAVE_LONG_LONG
unsigned LONG_LONG rb_os_allocated_objects _((void));
1.26.5.1.11. p352
1.26.5.1.11.1. railsexpress
1.26.5.1.11.1.1. 07-fork-support-for-gc-logging.patch
diff --git a/gc.c b/gc.c
index 9ad716f..a3cbe91 100644
--- a/gc.c
+++ b/gc.c
@@ -223,6 +223,8 @@ static int dont_gc;
static int gc_statistics = 0;
static GC_TIME_TYPE gc_time = 0;
static int gc_collections = 0;
+static int verbose_gc_stats = Qfalse;
+static FILE* gc_data_file = NULL;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -368,9 +370,148 @@ rb_gc_time()
#endif
}
VALUE rb_mGC;
+/*
+ * call-seq:
+ *
GC.enable_trace
=> true or false
+ *
+ * Enables garbage collection tracing, returning <code>true</code> if garbage
+ * collection tracing was already enabled.
+ *
+ *
GC.enable_trace
#=> false or true
+ *
GC.enable_trace
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_trace()
+{
+
int old = verbose_gc_stats;
+
verbose_gc_stats = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_trace
=> true or false
+ *
+ * Disables garbage collection tracing, returning <code>true</code> if garbage
+ * collection tracing was already disabled.
+ *
+ *
GC.disable_trace
#=> false or true
+ *
GC.disable_trace
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_trace()
+{
+
int old = verbose_gc_stats;
+
verbose_gc_stats = Qfalse;
+
return old;
+}
+
+char* GC_LOGFILE_IVAR = "@gc_logfile_name";
+
+/*
+ * call-seq:
+ *
GC.log_file(filename=nil, mode="w")
=> boolean
+ *
+ * Changes the GC data log file. Closes the currently open logfile.
+ * Returns true if the file was successfully opened for
+ * writing. Returns false if the file could not be opened for
+ * writing. Returns the name of the current logfile (or nil) if no
+ * parameter is given. Restores logging to stderr when given nil as
+ * an argument.
+ *
+ *
GC.log_file
#=> nil
+ *
GC.log_file "/tmp/gc.log"
#=> true
+ *
GC.log_file
#=> "/tmp/gc.log"
+ *
GC.log_file nil
#=> true
+ *
+ */
+
+VALUE
+rb_gc_log_file(int argc, VALUE *argv, VALUE self)
+{
+
VALUE filename = Qnil;
+
VALUE mode_str = Qnil;
+
FILE* f = NULL;
+
char* mode = "w";
+
+
VALUE current_logfile_name = rb_iv_get(rb_mGC, GC_LOGFILE_IVAR);
+
+
if (argc==0)
+
return current_logfile_name;
+
+
rb_scan_args(argc, argv, "02", &filename, &mode_str);
+
+
if (filename == Qnil) {
+
/* close current logfile and reset logfile to stderr */
+
if (gc_data_file != stderr) {
+
fclose(gc_data_file);
+
gc_data_file = stderr;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, Qnil);
+
}
+
return Qtrue;
+
}
+
+
/* we have a real logfile name */
+
filename = StringValue(filename);
+
+
if (rb_equal(current_logfile_name, filename) == Qtrue) {
+
/* do nothing if we get the file name we're already logging to */
+
return Qtrue;
+
}
+
+
/* get mode for file opening */
+
if (mode_str != Qnil)
+
{
+
mode = RSTRING(StringValue(mode_str))->ptr;
+
}
+
+
/* try to open file in given mode */
+
if (f = fopen(RSTRING(filename)->ptr, mode)) {
+
if (gc_data_file != stderr) {
+
fclose(gc_data_file);
+
}
+
gc_data_file = f;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, filename);
+
} else {
+
return Qfalse;
+
}
+
return Qtrue;
+}
+
+
+/*
+ * Called from process.c before a fork. Flushes the gc log file to
+ * avoid writing the buffered output twice (once in the parent, and
+ * once in the child).
+ */
+void
+rb_gc_before_fork()
+{
+ /* flush gc log file */
+ fflush(gc_data_file);
+}
+
+/*
+ * Called from process.c after a fork in the child process. Turns off
+ * logging, disables GC stats and resets all gc counters and timing
+ * information.
+ */
+void
+rb_gc_after_fork()
+{
+
rb_gc_disable_stats();
+
rb_gc_clear_stats();
+
rb_gc_disable_trace();
+
gc_data_file = stderr;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, Qnil);
+}
+
static struct gc_list {
VALUE *varptr;
struct gc_list *next;
@@ -477,10 +618,6 @@ static double heap_slots_growth_factor = 1.8;
static long initial_malloc_limit = GC_MALLOC_LIMIT;
-static int verbose_gc_stats = Qfalse;
-static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
static void set_gc_parameters()
@@ -496,6 +633,8 @@ static void set_gc_parameters()
if (gc_stats_i > 0) {
verbose_gc_stats = Qtrue;
}
+
/* child processes should not inherit RUBY_GC_STATS */
+
unsetenv("RUBY_GC_STATS");
}
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
@@ -508,6 +647,8 @@ static void set_gc_parameters()
fprintf(stderr,
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
}
+
/* child processes should not inherit RUBY_GC_DATA_FILE to avoid clobbering */
+
unsetenv("RUBY_GC_DATA_FILE");
}
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
@@ -2619,6 +2760,9 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "dump_file_and_line_info", rb_gc_dump_file_and_line_info, -1);
#endif
rb_define_singleton_method(rb_mGC, "log", rb_gc_log, 1);
+
rb_define_singleton_method(rb_mGC, "log_file", rb_gc_log_file, -1);
+
rb_define_singleton_method(rb_mGC, "enable_trace", rb_gc_enable_trace, 0);
+
rb_define_singleton_method(rb_mGC, "disable_trace", rb_gc_disable_trace, 0);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
diff --git a/intern.h b/intern.h
index 950ae9d..99696f1 100644
--- a/intern.h
+++ b/intern.h
@@ -270,6 +270,8 @@ void rb_gc_call_finalizer_at_exit _((void));
VALUE rb_gc_enable _((void));
VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
+void rb_gc_before_fork _((void));
+void rb_gc_after_fork _((void));
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
diff --git a/process.c b/process.c
index 8f6285d..ea28cb8 100644
--- a/process.c
+++ b/process.c
@@ -1330,6 +1330,8 @@ rb_f_fork(obj)
fflush(stderr);
#endif
+
+
rb_gc_before_fork();
before_exec();
pid = fork();
after_exec();
@@ -1339,6 +1341,7 @@ rb_f_fork(obj)
#ifdef linux
after_exec();
#endif
+
rb_gc_after_fork();
rb_thread_atfork();
if (rb_block_given_p()) {
int status;
@@ -1574,10 +1577,12 @@ rb_f_system(argc, argv)
chfunc = signal(SIGCHLD, SIG_DFL);
retry:
+
rb_gc_before_fork();
before_exec();
pid = fork();
if (pid == 0) {
/* child process */
+
rb_gc_after_fork();
rb_thread_atfork();
rb_protect(proc_exec_args, (VALUE)&earg, NULL);
_exit(127);
1.26.5.1.11.1.2. 08-track-malloc-size.patch
diff --git a/gc.c b/gc.c
index a3cbe91..30a1219 100644
--- a/gc.c
+++ b/gc.c
@@ -79,6 +79,17 @@ void *alloca ();
static unsigned long malloc_increase = 0;
static unsigned long malloc_limit = GC_MALLOC_LIMIT;
+
+#ifdef HAVE_LONG_LONG
+static unsigned LONG_LONG gc_allocated_size = 0;
+static unsigned LONG_LONG gc_num_allocations = 0;
+#else
+static unsigned long gc_allocated_size = 0;
+static unsigned long gc_num_allocations = 0;
+#endif
+static int gc_statistics = 0;
+
+
static void run_final();
static VALUE nomem_error;
static void garbage_collect();
@@ -163,6 +174,11 @@ ruby_xmalloc(size)
}
malloc_increase += size;
+
if (gc_statistics) {
+
gc_allocated_size += size;
+gc_num_allocations += 1;
+
}
+
return mem;
}
@@ -220,7 +236,6 @@ ruby_xfree(x)
extern int ruby_in_compile;
static int dont_gc;
-static int gc_statistics = 0;
static GC_TIME_TYPE gc_time = 0;
static int gc_collections = 0;
static int verbose_gc_stats = Qfalse;
@@ -329,11 +344,55 @@ rb_gc_clear_stats()
{
gc_collections = 0;
gc_time = 0;
+
gc_allocated_size = 0;
+
gc_num_allocations = 0;
return Qnil;
}
/*
* call-seq:
+ *
GC.allocated_size
=> Integer
+ *
+ * Returns the size of memory (in bytes) allocated since GC statistics collection
+ * was enabled.
+ *
+ *
GC.allocated_size
#=> 35
+ *
+ */
+VALUE
+rb_gc_allocated_size()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_allocated_size);
+#else
+
return ULONG2NUM(gc_allocated_size);
+#endif
+}
+
+/*
+ * call-seq:
+ *
GC.num_allocations
=> Integer
+ *
+ * Returns the number of memory allocations since GC statistics collection
+ * was enabled.
+ *
+ *
GC.num_allocations
#=> 150
+ *
+ */
+VALUE
+rb_gc_num_allocations()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_num_allocations);
+#else
+
return ULONG2NUM(gc_num_allocations);
+#endif
+}
+
+/*
+
+/*
+ * call-seq:
*
GC.collections
=> Integer
*
* Returns the number of garbage collections performed while GC statistics collection
@@ -2753,6 +2812,8 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "enable_stats", rb_gc_enable_stats, 0);
rb_define_singleton_method(rb_mGC, "disable_stats", rb_gc_disable_stats, 0);
rb_define_singleton_method(rb_mGC, "clear_stats", rb_gc_clear_stats, 0);
+
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
+
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
diff --git a/intern.h b/intern.h
index 99696f1..1117614 100644
--- a/intern.h
+++ b/intern.h
@@ -272,6 +272,8 @@ VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
+VALUE rb_gc_allocated_size _((void));
+VALUE rb_gc_num_allocations _((void));
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.11.1.3. 13-add-trace-stats-enabled-methods.patch
diff --git a/gc.c b/gc.c
index 57740d2..2c34932 100644
--- a/gc.c
+++ b/gc.c
@@ -350,6 +350,22 @@ rb_gc_disable_stats()
/*
* call-seq:
+ *
GC.stats_enabled?
=> true or false
+ *
+ * Check whether GC stats have been enabled.
+ *
+ *
GC.stats_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_stats_enabled()
+{
+
return gc_statistics ? Qtrue : Qfalse;
+}
+
+/*
+ * call-seq:
*
GC.clear_stats
=> nil
*
* Clears garbage collection statistics, returning nil. This resets the number
@@ -491,6 +507,22 @@ rb_gc_disable_trace()
return old;
}
+/*
+ * call-seq:
+ *
GC.trace_enabled?
=> true or false
+ *
+ * Check whether GC tracing has been enabled.
+ *
+ *
GC.trace_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_trace_enabled()
+{
+
return verbose_gc_stats ? Qtrue : Qfalse;
+}
+
char* GC_LOGFILE_IVAR = "@gc_logfile_name";
/*
@@ -2887,6 +2919,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
@@ -2902,6 +2935,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"stats_enabled?", rb_gc_stats_enabled, 0);
"clear_stats", rb_gc_clear_stats, 0);
"allocated_size", rb_gc_allocated_size, 0);
"num_allocations", rb_gc_num_allocations, 0);
"log_file", rb_gc_log_file, -1);
"enable_trace", rb_gc_enable_trace, 0);
"disable_trace", rb_gc_disable_trace, 0);
"trace_enabled?", rb_gc_trace_enabled, 0);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
1.26.5.1.11.1.4. 12-heap-slot-size.patch
diff --git a/gc.c b/gc.c
index 7db1ef6..57740d2 100644
--- a/gc.c
+++ b/gc.c
@@ -2891,6 +2891,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
+
rb_define_const(rb_mGC, "HEAP_SLOT_SIZE", INT2FIX(sizeof(RVALUE)));
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
1.26.5.1.11.1.5. 14-track-live-dataset-size.patch
diff --git a/gc.c b/gc.c
index 2c34932..0ce7e68 100644
--- a/gc.c
+++ b/gc.c
@@ -89,6 +89,7 @@ static unsigned long gc_num_allocations = 0;
#endif
static int gc_statistics = 0;
+static unsigned long heap_slots_live_after_last_gc = 0;
static void run_final();
static VALUE nomem_error;
@@ -465,6 +466,23 @@ rb_gc_time()
#endif
}
+/*
+ * call-seq:
+ *
GC.heap_slots_live_after_last_gc
=> Integer
+ *
+ * Returns the number of heap slots which were live after the last garbage collection.
+ *
+ *
GC.heap_slots_live_after_last_gc
#=> 231223
+ *
+ */
+VALUE
+rb_gc_heap_slots_live_after_last_gc()
+{
+
return ULONG2NUM(heap_slots_live_after_last_gc);
+}
+
+
+
VALUE rb_mGC;
/*
@@ -1903,6 +1921,7 @@ gc_sweep()
}
during_gc = 0;
live_objects = live;
+
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2924,6 +2943,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
+
rb_define_singleton_method(rb_mGC, "heap_slots_live_after_last_gc", rb_gc_heap_slots_live_after_last_gc, 0);
rb_define_const(rb_mGC, "HEAP_SLOT_SIZE", INT2FIX(sizeof(RVALUE)));
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
1.26.5.1.11.1.6. 15-add-object-size-information-to-heap-dump.patch
diff --git a/gc.c b/gc.c
index 0ce7e68..53450bf 100644
--- a/gc.c
+++ b/gc.c
@@ -953,9 +953,21 @@ rb_gc_dump_file_and_line_info(int argc, VALUE *argv)
if (!p->as.basic.klass) {
fprintf(f, "__unknown__");
} else {
fprintf(f, rb_obj_classname((VALUE)p));
+
fprintf(f, "%s", rb_obj_classname((VALUE)p));
}
}
+
/* print object size for some known object types */
+
switch (TYPE(p)) {
+
case T_STRING:
+
fprintf(f, ":%lu", RSTRING(p)->len);
+
break;
+
case T_ARRAY:
+
fprintf(f, ":%lu", RARRAY(p)->len);
+
break;
+
case T_HASH:
+
fprintf(f, ":%d", RHASH(p)->tbl->num_entries);
+
break;
+
}
}
fprintf(f, "\n");
}
@@ -1924,10 +1936,10 @@ gc_sweep()
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7d\n", really_freed);
fprintf(gc_data_file, "objects processed: %.7lu\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7lu\n", live);
fprintf(gc_data_file, "freelist objects : %.7lu\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7lu\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0 || live_counts[i]>0) {
fprintf(gc_data_file,
@@ -2258,7 +2270,7 @@ garbage_collect()
gc_time += musecs_used;
+
+
+
+
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
fprintf(gc_data_file, "GC time: %ld msec\n", (long)(musecs_used / 1000));
fflush(gc_data_file);
}
+
}
1.26.5.1.11.1.7. 11-fix-heap-size-growth-logic.patch
diff --git a/gc.c b/gc.c
index 21b3f6b..7db1ef6 100644
--- a/gc.c
+++ b/gc.c
@@ -694,6 +694,7 @@ static int heap_size = 0;
static
static
+static
static
int heap_free_min = 4096;
int heap_slots_increment = 10000;
int initial_heap_slots_increment = 10000;
double heap_slots_growth_factor = 1.8;
static long initial_malloc_limit = GC_MALLOC_LIMIT;
@@ -771,14 +772,13 @@ static void set_gc_parameters()
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
}
if (heap_slots_incr_i > 0) {
heap_slots_increment = heap_slots_incr_i;
}
+
heap_slots_increment = heap_slots_incr_i;
+
initial_heap_slots_increment = heap_slots_increment;
}
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
if (heap_slots_growth_factor_ptr != NULL) {
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
double heap_slots_growth_factor_d = atof(heap_slots_growth_factor_ptr);
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
}
@@ -988,8 +988,13 @@ add_heap()
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots += heap_slots_increment;
heap_slots_increment *= heap_slots_growth_factor;
+
if (heaps_used == 1)
+
heap_slots = initial_heap_slots_increment;
+
else {
+
heap_slots_increment *= heap_slots_growth_factor;
+
heap_slots += heap_slots_increment;
+
}
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
@@ -1879,6 +1884,7 @@ gc_sweep()
live_counts[i], free_counts[i], obj_type(i));
}
}
+
rb_gc_dump();
fflush(gc_data_file);
}
1.26.5.1.11.1.8. 04-display-full-stack-trace.patch
diff --git a/eval.c b/eval.c
index 6ff2560..fb3307c 100644
--- a/eval.c
+++ b/eval.c
@@ -1325,8 +1325,8 @@ error_print()
int truncate = eclass == rb_eSysStackError;
#define
-#define
-#define
+#define
+#define
TRACE_MAX (TRACE_HEAD+TRACE_TAIL+5)
TRACE_HEAD 8
TRACE_TAIL 5
TRACE_HEAD 100
TRACE_TAIL 100
ep = RARRAY(errat);
for (i=1; i<ep->len; i++) {
1.26.5.1.11.1.9. 06-heap-dump-support.patch
diff --git a/configure.in b/configure.in
index 62b34a8..4be088c 100644
--- a/configure.in
+++ b/configure.in
@@ -1595,6 +1595,14 @@ fi
LDFLAGS="-L. $LDFLAGS"
AC_SUBST(ARCHFILE)
+dnl enable gc debugging
+AC_ARG_ENABLE(gcdebug,
+
[ --enable-gcdebug
build garbage collector with debugging enabled. ],
+
[enable_gcdebug=$enableval])
+if test "$enable_gcdebug" = 'yes'; then
+
AC_DEFINE(GC_DEBUG, 1)
+fi
+
dnl build rdoc index if requested
RDOCTARGET=""
AC_ARG_ENABLE(install-doc,
diff --git a/gc.c b/gc.c
index ab71d22..9ad716f 100644
--- a/gc.c
+++ b/gc.c
@@ -411,7 +411,6 @@ rb_gc_unregister_address(addr)
}
}
-#undef GC_DEBUG
void
rb_global_variable(var)
@@ -602,6 +601,85 @@ rb_gc_dump()
return Qnil;
}
+
+static char* obj_type(int tp);
+
+#ifdef GC_DEBUG
+/*
+ * call-seq:
+ *
GC.dump_file_and_line_info(String, boolean)
=> nil
+ *
+ * dumps information on which currently allocated object was created by which file and on which line
+ *
+ *
GC.dump_file_and_line_info(String, boolean)
#=> nil
+ *
+ * The second parameter specifies whether class names should be included in the dump.
+ * Note that including class names will allocate additional string objects on the heap.
+ *
+ */
+
+VALUE
+rb_gc_dump_file_and_line_info(int argc, VALUE *argv)
+{
+ VALUE filename, str, include_classnames = Qnil;
+ char *fname = NULL;
+ char *klass = NULL;
+ FILE* f = NULL;
+ int i,n = 0;
+
+ rb_scan_args(argc, argv, "11", &filename, &include_classnames);
+
+ str = StringValue(filename);
+ fname = RSTRING(str)->ptr;
+ f = fopen(fname, "w");
+
+ for (i = 0; i < heaps_used; i++) {
+
RVALUE *p, *pend;
+
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
for (;p < pend; p++) {
+
if (p->as.basic.flags) {
+
fprintf(f, "%s:%s:%d", obj_type(p->as.basic.flags & T_MASK), p->file, p->line);
+
// rb_obj_classname will create objects on the heap, we need a better solution
+
if (include_classnames == Qtrue) {
+
/* write the class */
+
fprintf(f, ":");
+
switch (TYPE(p)) {
+
case T_NONE:
+
fprintf(f, "__none__");
+
break;
+
case T_BLKTAG:
+
fprintf(f, "__blktag__");
+
break;
+
case T_UNDEF:
+
fprintf(f, "__undef__");
+
break;
+
case T_VARMAP:
+
fprintf(f, "__varmap__");
+
break;
+
case T_SCOPE:
+
fprintf(f, "__scope__");
+
break;
+
case T_NODE:
+
fprintf(f, "__node__");
+
break;
+
default:
+
if (!p->as.basic.klass) {
+
fprintf(f, "__unknown__");
+
} else {
+
fprintf(f, rb_obj_classname((VALUE)p));
+
}
+
}
+
}
+
fprintf(f, "\n");
+
}
+
}
+ }
+ fclose(f);
+ return Qnil;
+}
+#endif
+
/*
* call-seq:
*
GC.log String => String
@@ -1066,6 +1144,11 @@ gc_mark(ptr, lev)
if (obj->as.basic.flags & FL_MARK) return; /* already marked */
obj->as.basic.flags |= FL_MARK;
+#ifdef GC_DEBUG
+
/* mark our new reference point for sourcefile objects */
+
mark_source_filename(RANY(obj)->file);
+#endif
+
if (lev > GC_LEVEL_MAX || (lev == 0 && ruby_stack_check())) {
if (!mark_stack_overflow) {
if (mark_stack_ptr - mark_stack < MARK_STACK_MAX) {
@@ -1104,6 +1187,11 @@ gc_mark_children(ptr, lev)
if (obj->as.basic.flags & FL_MARK) return; /* already marked */
obj->as.basic.flags |= FL_MARK;
+#ifdef GC_DEBUG
+
/* mark our new reference point for sourcefile objects */
+
mark_source_filename(RANY(obj)->file);
+#endif
+
marking:
if (FL_TEST(obj, FL_EXIVAR)) {
rb_mark_generic_ivar(ptr);
@@ -1550,6 +1638,7 @@ gc_sweep()
live_counts[i], free_counts[i], obj_type(i));
}
}
+
fflush(gc_data_file);
}
/* clear finalization list */
@@ -2526,6 +2615,9 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+#ifdef GC_DEBUG
+
rb_define_singleton_method(rb_mGC,
+#endif
rb_define_singleton_method(rb_mGC,
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"dump_file_and_line_info", rb_gc_dump_file_and_line_info, -1);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
1.26.5.1.11.1.10. 01-ignore-generated-files.patch
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..00c347a
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,95 @@
+.ext
+.installed.list
+.rbconfig.time
+Makefile
+autom4te.cache/
+config.h
+config.status
+configure
+ext/Win32API/Makefile
+ext/bigdecimal/Makefile
+ext/curses/Makefile
+ext/dbm/Makefile
+ext/digest/Makefile
+ext/digest/bubblebabble/Makefile
+ext/digest/md5/Makefile
+ext/digest/rmd160/Makefile
+ext/digest/sha1/Makefile
+ext/digest/sha2/Makefile
+ext/dl/Makefile
+ext/dl/call.func
+ext/dl/callback.func
+ext/dl/cbtable.func
+ext/dl/dlconfig.h
+ext/dl/dlconfig.rb
+ext/enumerator/Makefile
+ext/etc/Makefile
+ext/fcntl/Makefile
+ext/gdbm/Makefile
+ext/iconv/Makefile
+ext/io/wait/Makefile
+ext/nkf/Makefile
+ext/openssl/Makefile
+ext/openssl/extconf.h
+ext/pty/Makefile
+ext/racc/cparse/Makefile
+ext/readline/Makefile
+ext/sdbm/Makefile
+ext/socket/Makefile
+ext/stringio/Makefile
+ext/strscan/Makefile
+ext/syck/Makefile
+ext/syslog/Makefile
+ext/thread/Makefile
+ext/tk/Makefile
+ext/tk/tkutil/Makefile
+ext/win32ole/Makefile
+ext/win32ole/.document
+ext/zlib/Makefile
+largefile.h
+miniruby
+parse.c
+rbconfig.rb
+ruby
+enc.mk
+ext/bigdecimal/extconf.h
+ext/continuation/
+ext/coverage/
+ext/curses/extconf.h
+ext/dbm/extconf.h
+ext/digest/bubblebabble/extconf.h
+ext/digest/extconf.h
+ext/digest/md5/extconf.h
+ext/digest/rmd160/extconf.h
+ext/digest/sha1/extconf.h
+ext/digest/sha2/extconf.h
+ext/dl/callback.h
+ext/dl/extconf.h
+ext/etc/extconf.h
+ext/fcntl/extconf.h
+ext/fiber/
+ext/iconv/extconf.h
+ext/io/wait/extconf.h
+ext/json/
+ext/nkf/extconf.h
+ext/pty/extconf.h
+ext/racc/cparse/extconf.h
+ext/readline/extconf.h
+ext/ripper/
+ext/sdbm/extconf.h
+ext/socket/constants.h
+ext/socket/extconf.h
+ext/stringio/extconf.h
+ext/strscan/extconf.h
+ext/syck/extconf.h
+ext/syslog/extconf.h
+ext/tk/extconf.h
+ext/tk/tkutil/extconf.h
+ext/zlib/extconf.h
+miniprelude.c
+prelude.c
+revision.h
+*.dylib
+*.log
+*.dSYM
+patches-ruby*
1.26.5.1.11.1.11. 03-railsbench-gc-patch.patch
diff --git a/gc.c b/gc.c
index fa45cd1..ab71d22 100644
--- a/gc.c
+++ b/gc.c
@@ -22,8 +22,16 @@
#include <setjmp.h>
#include <sys/types.h>
+#ifdef _WIN32
+#include <string.h>
+#else
+#include <strings.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
+#elif defined(_WIN32)
+#include <time.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H
@@ -42,7 +50,6 @@ void rb_io_fptr_finalize _((struct rb_io_t*));
#ifdef __CYGWIN__
int _setjmp(), _longjmp();
#endif
/* Make alloca work the best possible way. */
#ifdef __GNUC__
# ifndef atarist
@@ -86,12 +93,12 @@ rb_memerror()
rb_thread_t th = rb_curr_thread;
if (!nomem_error ||
-(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
-fprintf(stderr, "[FATAL] failed to allocate memory\n");
-exit(1);
+
(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
+
fprintf(stderr, "[FATAL] failed to allocate memory\n");
+
exit(1);
}
if (rb_thread_raised_p(th, RAISED_NOMEMORY)) {
-rb_exc_jump(nomem_error);
+
rb_exc_jump(nomem_error);
}
rb_thread_raised_set(th, RAISED_NOMEMORY);
rb_exc_raise(nomem_error);
@@ -139,7 +146,7 @@ ruby_xmalloc(size)
void *mem;
if (size < 0) {
-rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
+
rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
}
if (size == 0) size = 1;
@@ -148,11 +155,11 @@ ruby_xmalloc(size)
}
RUBY_CRITICAL(mem = malloc(size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = malloc(size));
-if (!mem) {
rb_memerror();
-}
+
garbage_collect();
+
RUBY_CRITICAL(mem = malloc(size));
+
if (!mem) {
+
rb_memerror();
+
}
}
malloc_increase += size;
@@ -179,17 +186,17 @@ ruby_xrealloc(ptr, size)
void *mem;
if (size < 0) {
-rb_raise(rb_eArgError, "negative re-allocation size");
+
rb_raise(rb_eArgError, "negative re-allocation size");
}
if (!ptr) return xmalloc(size);
if (size == 0) size = 1;
if (ruby_gc_stress) garbage_collect();
RUBY_CRITICAL(mem = realloc(ptr, size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = realloc(ptr, size));
-if (!mem) {
rb_memerror();
+
garbage_collect();
+
RUBY_CRITICAL(mem = realloc(ptr, size));
+
if (!mem) {
+
rb_memerror();
}
}
malloc_increase += size;
@@ -202,11 +209,20 @@ ruby_xfree(x)
void *x;
{
if (x)
-RUBY_CRITICAL(free(x));
+
RUBY_CRITICAL(free(x));
}
+#if HAVE_LONG_LONG
+#define GC_TIME_TYPE LONG_LONG
+#else
+#define GC_TIME_TYPE long
+#endif
+
extern int ruby_in_compile;
static int dont_gc;
+static int gc_statistics = 0;
+static GC_TIME_TYPE gc_time = 0;
+static int gc_collections = 0;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -241,7 +257,7 @@ rb_gc_enable()
* Disables garbage collection, returning <code>true</code> if garbage
* collection was already disabled.
*
- *
GC.disable
#=> false
+ *
GC.disable
#=> false or true
*
GC.disable
#=> true
*
*/
@@ -255,6 +271,104 @@ rb_gc_disable()
return old;
}
+/*
+ * call-seq:
+ *
GC.enable_stats
=> true or false
+ *
+ * Enables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already enabled.
+ *
+ *
GC.enable_stats
#=> false or true
+ *
GC.enable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_stats
=> true or false
+ *
+ * Disables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already disabled.
+ *
+ *
GC.disable_stats
#=> false or true
+ *
GC.disable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qfalse;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.clear_stats
=> nil
+ *
+ * Clears garbage collection statistics, returning nil. This resets the number
+ * of collections (GC.collections) and the time used (GC.time) to 0.
+ *
+ *
GC.clear_stats
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_clear_stats()
+{
+
gc_collections = 0;
+
gc_time = 0;
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.collections
=> Integer
+ *
+ * Returns the number of garbage collections performed while GC statistics collection
+ * was enabled.
+ *
+ *
GC.collections
#=> 35
+ *
+ */
+
+VALUE
+rb_gc_collections()
+{
+
return INT2NUM(gc_collections);
+}
+
+/*
+ * call-seq:
+ *
GC.time
=> Integer
+ *
+ * Returns the time spent during garbage collection while GC statistics collection
+ * was enabled (in micro seconds).
+ *
+ *
GC.time
#=> 20000
+ *
+ */
+
+VALUE
+rb_gc_time()
+{
+#if HAVE_LONG_LONG
+
return LL2NUM(gc_time);
+#else
+
return LONG2NUM(gc_time);
+#endif
+}
+
+
VALUE rb_mGC;
static struct gc_list {
@@ -281,19 +395,19 @@ rb_gc_unregister_address(addr)
struct gc_list *tmp = global_List;
if (tmp->varptr == addr) {
-global_List = tmp->next;
-RUBY_CRITICAL(free(tmp));
-return;
+
global_List = tmp->next;
+
RUBY_CRITICAL(free(tmp));
+
return;
}
while (tmp->next) {
-if (tmp->next->varptr == addr) {
struct gc_list *t = tmp->next;
+
if (tmp->next->varptr == addr) {
+
struct gc_list *t = tmp->next;
-}
-tmp
+
+
+
+
+
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
= tmp->next;
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
}
tmp = tmp->next;
}
}
@@ -312,26 +426,26 @@ rb_global_variable(var)
typedef struct RVALUE {
union {
-struct {
unsigned long flags;/* always 0 for freed obj */
struct RVALUE *next;
-} free;
-struct RBasic basic;
-struct RObject object;
-struct RClass klass;
-struct RFloat flonum;
-struct RString string;
-struct RArray array;
-struct RRegexp regexp;
-struct RHash
hash;
-struct RData
data;
-struct RStruct rstruct;
-struct RBignum bignum;
-struct RFile
file;
-struct RNode
node;
-struct RMatch match;
-struct RVarmap varmap;
-struct SCOPE
scope;
+
struct {
+
unsigned long flags;
/* always 0 for freed obj */
+
struct RVALUE *next;
+
} free;
+
struct RBasic basic;
+
struct RObject object;
+
struct RClass klass;
+
struct RFloat flonum;
+
struct RString string;
+
struct RArray array;
+
struct RRegexp regexp;
+
struct RHash
hash;
+
struct RData
data;
+
struct RStruct rstruct;
+
struct RBignum bignum;
+
struct RFile
file;
+
struct RNode
node;
+
struct RMatch match;
+
struct RVarmap varmap;
+
struct SCOPE
scope;
} as;
#ifdef GC_DEBUG
char *file;
@@ -346,7 +460,7 @@ typedef struct RVALUE {
static RVALUE *freelist = 0;
static RVALUE *deferred_final_list = 0;
-#define HEAPS_INCREMENT 10
+static int heaps_increment = 10;
static struct heaps_slot {
void *membase;
RVALUE *slot;
@@ -355,45 +469,197 @@ static struct heaps_slot {
static int heaps_length = 0;
static int heaps_used
= 0;
-#define HEAP_MIN_SLOTS 10000
-static int heap_slots = HEAP_MIN_SLOTS;
+static int heap_min_slots = 10000;
+static int heap_slots = 10000;
-#define FREE_MIN 4096
+static int heap_free_min = 4096;
+static int heap_slots_increment = 10000;
+static double heap_slots_growth_factor = 1.8;
+
+static long initial_malloc_limit = GC_MALLOC_LIMIT;
+
+static int verbose_gc_stats = Qfalse;
+
+static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
+static void set_gc_parameters()
+{
+
char *gc_stats_ptr, *min_slots_ptr, *free_min_ptr, *heap_slots_incr_ptr,
+
*heap_incr_ptr, *malloc_limit_ptr, *gc_heap_file_ptr, *heap_slots_growth_factor_ptr;
+
+
gc_data_file = stderr;
+
+
gc_stats_ptr = getenv("RUBY_GC_STATS");
+
if (gc_stats_ptr != NULL) {
+
int gc_stats_i = atoi(gc_stats_ptr);
+
if (gc_stats_i > 0) {
+
verbose_gc_stats = Qtrue;
+
}
+
}
+
+
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
+
if (gc_heap_file_ptr != NULL) {
+
FILE* data_file = fopen(gc_heap_file_ptr, "w");
+
if (data_file != NULL) {
+
gc_data_file = data_file;
+
}
+
else {
+
fprintf(stderr,
+
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
+
}
+
}
+
+
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
+
if (min_slots_ptr != NULL) {
+
int min_slots_i = atoi(min_slots_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_MIN_SLOTS=%s\n", min_slots_ptr);
+
}
+
if (min_slots_i > 0) {
+
heap_slots = min_slots_i;
+
heap_min_slots = min_slots_i;
+
}
+
}
+
+
free_min_ptr = getenv("RUBY_HEAP_FREE_MIN");
+
if (free_min_ptr != NULL) {
+
int free_min_i = atoi(free_min_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_FREE_MIN=%s\n", free_min_ptr);
+
}
+
if (free_min_i > 0) {
+
heap_free_min = free_min_i;
+
}
+
}
+
+
heap_incr_ptr = getenv("RUBY_HEAP_INCREMENT");
+
if (heap_incr_ptr != NULL) {
+
int heap_incr_i = atoi(heap_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_INCREMENT=%s\n", heap_incr_ptr);
+
}
+
if (heap_incr_i > 0) {
+
heaps_increment = heap_incr_i;
+
}
+
}
+
+
heap_slots_incr_ptr = getenv("RUBY_HEAP_SLOTS_INCREMENT");
+
if (heap_slots_incr_ptr != NULL) {
+
int heap_slots_incr_i = atoi(heap_slots_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
+
}
+
if (heap_slots_incr_i > 0) {
+
heap_slots_increment = heap_slots_incr_i;
+
}
+
}
+
+
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
+
if (heap_slots_growth_factor_ptr != NULL) {
+
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
+
}
+
if (heap_slots_growth_factor_d > 0) {
+
heap_slots_growth_factor = heap_slots_growth_factor_d;
+
}
+
}
+
+
malloc_limit_ptr = getenv("RUBY_GC_MALLOC_LIMIT");
+
if (malloc_limit_ptr != NULL) {
+
int malloc_limit_i = atol(malloc_limit_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_GC_MALLOC_LIMIT=%s\n", malloc_limit_ptr);
+
}
+
if (malloc_limit_i > 0) {
+
initial_malloc_limit = malloc_limit_i;
+
}
+
}
+}
+
+/*
+ * call-seq:
+ *
GC.dump
=> nil
+ *
+ * dumps information about the current GC data structures to the GC log file
+ *
+ *
GC.dump
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_dump()
+{
+
int i;
+
+
for (i = 0; i < heaps_used; i++) {
+
int heap_size = heaps[i].limit;
+
fprintf(gc_data_file, "HEAP[%2d]: size=%7d\n", i, heap_size);
+
}
+
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.log String => String
+ *
+ * Logs string to the GC data file and returns it.
+ *
+ *
GC.log "manual GC call"
#=> "manual GC call"
+ *
+ */
+
+VALUE
+rb_gc_log(self, original_str)
+
VALUE self, original_str;
+{
+
if (original_str == Qnil) {
+
fprintf(gc_data_file, "\n");
+
}
+
else {
+
VALUE str = StringValue(original_str);
+
char *p = RSTRING(str)->ptr;
+
fprintf(gc_data_file, "%s\n", p);
+
}
+
return original_str;
+}
+
+
static void
add_heap()
{
RVALUE *p, *pend;
if (heaps_used == heaps_length) {
-/* Realloc heaps */
-struct heaps_slot *p;
-int length;
-heaps_length += HEAPS_INCREMENT;
-length = heaps_length*sizeof(struct heaps_slot);
-RUBY_CRITICAL(
if (heaps_used > 0) {
-p = (struct heaps_slot *)realloc(heaps, length);
-if (p) heaps = p;
}
else {
-p = heaps = (struct heaps_slot *)malloc(length);
});
-if (p == 0) rb_memerror();
+
/* Realloc heaps */
+
struct heaps_slot *p;
+
int length;
+
+
heaps_length += heaps_increment;
+
length = heaps_length*sizeof(struct heaps_slot);
+
RUBY_CRITICAL(
+
if (heaps_used > 0) {
+
p = (struct heaps_slot *)realloc(heaps, length);
+
if (p) heaps = p;
+
}
+
else {
+
p = heaps = (struct heaps_slot *)malloc(length);
+
});
+
if (p == 0) rb_memerror();
}
for (;;) {
-RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
-if (p == 0) {
if (heap_slots == HEAP_MIN_SLOTS) {
-rb_memerror();
}
heap_slots = HEAP_MIN_SLOTS;
continue;
-}
+
RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
+
if (p == 0) {
+
if (heap_slots == heap_min_slots) {
+
rb_memerror();
+
}
+
heap_slots = heap_min_slots;
+
continue;
+
}
heaps[heaps_used].membase = p;
if ((VALUE)p % sizeof(RVALUE) == 0)
heap_slots += 1;
@@ -401,25 +667,26 @@ add_heap()
p = (RVALUE*)((VALUE)p + sizeof(RVALUE) - ((VALUE)p % sizeof(RVALUE)));
heaps[heaps_used].slot = p;
heaps[heaps_used].limit = heap_slots;
-break;
+
break;
}
pend = p + heap_slots;
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots *= 1.8;
if (heap_slots <= 0) heap_slots = HEAP_MIN_SLOTS;
+
heap_slots += heap_slots_increment;
+
heap_slots_increment *= heap_slots_growth_factor;
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
-p->as.free.flags = 0;
-p->as.free.next = freelist;
-freelist = p;
-p++;
+
p->as.free.flags = 0;
+
p->as.free.next = freelist;
+
freelist = p;
+
p++;
}
}
#define RANY(o) ((RVALUE*)(o))
-int
+int
rb_during_gc()
{
return during_gc;
@@ -431,7 +698,7 @@ rb_newobj()
VALUE obj;
if (during_gc)
-rb_bug("object allocation during garbage collection phase");
+
rb_bug("object allocation during garbage collection phase");
if (ruby_gc_stress || !freelist) garbage_collect();
@@ -580,13 +847,13 @@ rb_source_filename(f)
st_data_t name;
if (!st_lookup(source_filenames, (st_data_t)f, &name)) {
-long len = strlen(f) + 1;
-char *ptr = ALLOC_N(char, len + 1);
-name = (st_data_t)ptr;
-*ptr++ = 0;
-MEMCPY(ptr, f, char, len);
-st_add_direct(source_filenames, (st_data_t)ptr, name);
-return ptr;
+
long len = strlen(f) + 1;
+
char *ptr = ALLOC_N(char, len + 1);
+
name = (st_data_t)ptr;
+
*ptr++ = 0;
+
MEMCPY(ptr, f, char, len);
+
st_add_direct(source_filenames, (st_data_t)ptr, name);
+
return ptr;
}
return (char *)name + 1;
}
@@ -596,7 +863,7 @@ mark_source_filename(f)
char *f;
{
if (f) {
-f[-1] = 1;
+
f[-1] = 1;
}
}
@@ -605,12 +872,12 @@ sweep_source_filename(key, value)
char *key, *value;
{
if (*value) {
-*value = 0;
-return ST_CONTINUE;
+
*value = 0;
+
return ST_CONTINUE;
}
else {
-free(value);
-return ST_DELETE;
+
free(value);
+
return ST_DELETE;
}
}
@@ -625,14 +892,14 @@ gc_mark_all()
init_mark_stack();
for (i = 0; i < heaps_used; i++) {
-p = heaps[i].slot; pend = p + heaps[i].limit;
-while (p < pend) {
if ((p->as.basic.flags & FL_MARK) &&
-(p->as.basic.flags != FL_MARK)) {
-gc_mark_children((VALUE)p, 0);
}
p++;
-}
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
while (p < pend) {
+
if ((p->as.basic.flags & FL_MARK) &&
+
(p->as.basic.flags != FL_MARK)) {
+
gc_mark_children((VALUE)p, 0);
+
}
+
p++;
+
}
}
}
@@ -647,8 +914,8 @@ gc_mark_rest()
init_mark_stack();
while(p != tmp_arry){
-p--;
-gc_mark_children(*p, 0);
+
+
p--;
gc_mark_children(*p, 0);
}
}
@@ -665,9 +932,9 @@ is_pointer_to_heap(ptr)
/* check if p looks like a pointer */
for (i=0; i < heaps_used; i++) {
-heap_org = heaps[i].slot;
-if (heap_org <= p && p < heap_org + heaps[i].limit)
return Qtrue;
+
heap_org = heaps[i].slot;
+
if (heap_org <= p && p < heap_org + heaps[i].limit)
+
return Qtrue;
}
return Qfalse;
}
@@ -680,10 +947,10 @@ mark_locations_array(x, n)
VALUE v;
while (n--) {
v = *x;
-if (is_pointer_to_heap((void *)v)) {
gc_mark(v, 0);
-}
-x++;
+
if (is_pointer_to_heap((void *)v)) {
+
gc_mark(v, 0);
+
}
+
x++;
}
}
@@ -780,7 +1047,7 @@ rb_gc_mark_maybe(obj)
VALUE obj;
{
if (is_pointer_to_heap((void *)obj)) {
-gc_mark(obj, 0);
+
gc_mark(obj, 0);
}
}
@@ -828,7 +1095,7 @@ gc_mark_children(ptr, lev)
{
register RVALUE *obj = RANY(ptr);
+
goto marking;/* skip */
goto marking;
/* skip */
again:
obj = RANY(ptr);
@@ -839,148 +1106,148 @@ gc_mark_children(ptr, lev)
marking:
if (FL_TEST(obj, FL_EXIVAR)) {
-rb_mark_generic_ivar(ptr);
+
rb_mark_generic_ivar(ptr);
}
switch (obj->as.basic.flags & T_MASK) {
case T_NIL:
case T_FIXNUM:
-rb_bug("rb_gc_mark() called for broken object");
-break;
+
rb_bug("rb_gc_mark() called for broken object");
+
break;
case T_NODE:
-mark_source_filename(obj->as.node.nd_file);
-switch (nd_type(obj)) {
- case NODE_IF:/* 1,2,3 */
- case NODE_FOR:
- case NODE_ITER:
- case NODE_CREF:
- case NODE_WHEN:
- case NODE_MASGN:
- case NODE_RESCUE:
- case NODE_RESBODY:
- case NODE_CLASS:
gc_mark((VALUE)obj->as.node.u2.node, lev);
/* fall through */
- case NODE_BLOCK:/* 1,3 */
- case NODE_ARRAY:
- case NODE_DSTR:
- case NODE_DXSTR:
- case NODE_DREGX:
- case NODE_DREGX_ONCE:
- case NODE_FBODY:
- case NODE_ENSURE:
- case NODE_CALL:
- case NODE_DEFS:
- case NODE_OP_ASGN1:
gc_mark((VALUE)obj->as.node.u1.node, lev);
/* fall through */
- case NODE_SUPER:/* 3 */
- case NODE_FCALL:
- case NODE_DEFN:
- case NODE_NEWLINE:
ptr = (VALUE)obj->as.node.u3.node;
goto again;
- case NODE_WHILE:/* 1,2 */
- case NODE_UNTIL:
- case NODE_AND:
- case NODE_OR:
- case NODE_CASE:
- case NODE_SCLASS:
- case NODE_DOT2:
- case NODE_DOT3:
- case NODE_FLIP2:
- case NODE_FLIP3:
- case NODE_MATCH2:
- case NODE_MATCH3:
- case NODE_OP_ASGN_OR:
- case NODE_OP_ASGN_AND:
- case NODE_MODULE:
- case NODE_ALIAS:
- case NODE_VALIAS:
- case NODE_ARGS:
gc_mark((VALUE)obj->as.node.u1.node, lev);
/* fall through */
- case NODE_METHOD:/* 2 */
- case NODE_NOT:
- case NODE_GASGN:
- case NODE_LASGN:
- case NODE_DASGN:
- case NODE_DASGN_CURR:
- case NODE_IASGN:
- case NODE_CVDECL:
- case NODE_CVASGN:
- case NODE_COLON3:
- case NODE_OPT_N:
- case NODE_EVSTR:
- case NODE_UNDEF:
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- case NODE_HASH:/* 1 */
- case NODE_LIT:
- case NODE_STR:
- case NODE_XSTR:
- case NODE_DEFINED:
- case NODE_MATCH:
- case NODE_RETURN:
- case NODE_BREAK:
- case NODE_NEXT:
- case NODE_YIELD:
- case NODE_COLON2:
- case NODE_SPLAT:
- case NODE_TO_ARY:
- case NODE_SVALUE:
ptr = (VALUE)obj->as.node.u1.node;
goto again;
- case NODE_SCOPE:/* 2,3 */
- case NODE_BLOCK_PASS:
- case NODE_CDECL:
gc_mark((VALUE)obj->as.node.u3.node, lev);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- case NODE_ZARRAY:/* - */
- case NODE_ZSUPER:
- case NODE_CFUNC:
- case NODE_VCALL:
- case NODE_GVAR:
- case NODE_LVAR:
- case NODE_DVAR:
- case NODE_IVAR:
- case NODE_CVAR:
- case NODE_NTH_REF:
- case NODE_BACK_REF:
- case NODE_REDO:
- case NODE_RETRY:
- case NODE_SELF:
- case NODE_NIL:
- case NODE_TRUE:
- case NODE_FALSE:
- case NODE_ATTRSET:
- case NODE_BLOCK_ARG:
- case NODE_POSTEXE:
break;
- case NODE_ALLOCA:
mark_locations_array((VALUE*)obj->as.node.u1.value,
- obj->as.node.u3.cnt);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- default:/* unlisted NODE */
if (is_pointer_to_heap(obj->as.node.u1.node)) {
-gc_mark((VALUE)obj->as.node.u1.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u2.node)) {
-gc_mark((VALUE)obj->as.node.u2.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u3.node)) {
-gc_mark((VALUE)obj->as.node.u3.node, lev);
}
-}
-return;/* no need to mark class. */
+
mark_source_filename(obj->as.node.nd_file);
+
switch (nd_type(obj)) {
+
case NODE_IF:
/* 1,2,3 */
+
case NODE_FOR:
+
case NODE_ITER:
+
case NODE_CREF:
+
case NODE_WHEN:
+
case NODE_MASGN:
+
case NODE_RESCUE:
+
case NODE_RESBODY:
+
case NODE_CLASS:
+
gc_mark((VALUE)obj->as.node.u2.node, lev);
+
/* fall through */
+
case NODE_BLOCK:
/* 1,3 */
+
case NODE_ARRAY:
+
case NODE_DSTR:
+
case NODE_DXSTR:
+
case NODE_DREGX:
+
case NODE_DREGX_ONCE:
+
case NODE_FBODY:
+
case NODE_ENSURE:
+
case NODE_CALL:
+
case NODE_DEFS:
+
case NODE_OP_ASGN1:
+
gc_mark((VALUE)obj->as.node.u1.node, lev);
+
/* fall through */
+
case NODE_SUPER:
/* 3 */
+
case NODE_FCALL:
+
case NODE_DEFN:
+
case NODE_NEWLINE:
+
ptr = (VALUE)obj->as.node.u3.node;
+
goto again;
+
+
case NODE_WHILE:
/* 1,2 */
+
case NODE_UNTIL:
+
case NODE_AND:
+
case NODE_OR:
+
case NODE_CASE:
+
case NODE_SCLASS:
+
case NODE_DOT2:
+
case NODE_DOT3:
+
case NODE_FLIP2:
+
case NODE_FLIP3:
+
case NODE_MATCH2:
+
case NODE_MATCH3:
+
case NODE_OP_ASGN_OR:
+
case NODE_OP_ASGN_AND:
+
case NODE_MODULE:
+
case NODE_ALIAS:
+
case NODE_VALIAS:
+
case NODE_ARGS:
+
gc_mark((VALUE)obj->as.node.u1.node, lev);
+
/* fall through */
+
case NODE_METHOD:
/* 2 */
+
case NODE_NOT:
+
case NODE_GASGN:
+
case NODE_LASGN:
+
case NODE_DASGN:
+
case NODE_DASGN_CURR:
+
case NODE_IASGN:
+
case NODE_CVDECL:
+
case NODE_CVASGN:
+
case NODE_COLON3:
+
case NODE_OPT_N:
+
case NODE_EVSTR:
+
case NODE_UNDEF:
+
ptr = (VALUE)obj->as.node.u2.node;
+
goto again;
+
+
case NODE_HASH:
/* 1 */
+
case NODE_LIT:
+
case NODE_STR:
+
case NODE_XSTR:
+
case NODE_DEFINED:
+
case NODE_MATCH:
+
case NODE_RETURN:
+
case NODE_BREAK:
+
case NODE_NEXT:
+
case NODE_YIELD:
+
case NODE_COLON2:
+
case NODE_SPLAT:
+
case NODE_TO_ARY:
+
case NODE_SVALUE:
+
ptr = (VALUE)obj->as.node.u1.node;
+
goto again;
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
case NODE_SCOPE:
/* 2,3 */
case NODE_BLOCK_PASS:
case NODE_CDECL:
gc_mark((VALUE)obj->as.node.u3.node, lev);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
case NODE_ZARRAY:
/* - */
case NODE_ZSUPER:
case NODE_CFUNC:
case NODE_VCALL:
case NODE_GVAR:
case NODE_LVAR:
case NODE_DVAR:
case NODE_IVAR:
case NODE_CVAR:
case NODE_NTH_REF:
case NODE_BACK_REF:
case NODE_REDO:
case NODE_RETRY:
case NODE_SELF:
case NODE_NIL:
case NODE_TRUE:
case NODE_FALSE:
case NODE_ATTRSET:
case NODE_BLOCK_ARG:
case NODE_POSTEXE:
break;
case NODE_ALLOCA:
mark_locations_array((VALUE*)obj->as.node.u1.value,
obj->as.node.u3.cnt);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
default:
/* unlisted NODE */
if (is_pointer_to_heap(obj->as.node.u1.node)) {
gc_mark((VALUE)obj->as.node.u1.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u2.node)) {
gc_mark((VALUE)obj->as.node.u2.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u3.node)) {
gc_mark((VALUE)obj->as.node.u3.node, lev);
}
}
return;
/* no need to mark class. */
}
gc_mark(obj->as.basic.klass, lev);
@@ -988,92 +1255,92 @@ gc_mark_children(ptr, lev)
case T_ICLASS:
case T_CLASS:
case T_MODULE:
-mark_tbl(obj->as.klass.m_tbl, lev);
-mark_tbl(obj->as.klass.iv_tbl, lev);
-ptr = obj->as.klass.super;
-goto again;
+
mark_tbl(obj->as.klass.m_tbl, lev);
+
mark_tbl(obj->as.klass.iv_tbl, lev);
+
ptr = obj->as.klass.super;
+
goto again;
case T_ARRAY:
-if (FL_TEST(obj, ELTS_SHARED)) {
ptr = obj->as.array.aux.shared;
goto again;
-}
-else {
long i, len = obj->as.array.len;
VALUE *ptr = obj->as.array.ptr;
+
if (FL_TEST(obj, ELTS_SHARED)) {
+
ptr = obj->as.array.aux.shared;
+
goto again;
+
}
+
else {
+
long i, len = obj->as.array.len;
+
VALUE *ptr = obj->as.array.ptr;
for (i=0; i
-gc_mark(*ptr++,
}
-}
-break;
+
for
+
+
}
+
}
+
break;
< len; i++) {
lev);
(i=0; i < len; i++) {
gc_mark(*ptr++, lev);
case T_HASH:
-mark_hash(obj->as.hash.tbl, lev);
-ptr = obj->as.hash.ifnone;
-goto again;
+
mark_hash(obj->as.hash.tbl, lev);
+
+
ptr = obj->as.hash.ifnone;
goto again;
case T_STRING:
#define STR_ASSOC FL_USER3
/* copied from string.c */
-if (FL_TEST(obj, ELTS_SHARED|STR_ASSOC)) {
ptr = obj->as.string.aux.shared;
goto again;
-}
-break;
+
if (FL_TEST(obj, ELTS_SHARED|STR_ASSOC)) {
+
ptr = obj->as.string.aux.shared;
+
goto again;
+
}
+
break;
case T_DATA:
-if (obj->as.data.dmark) (*obj->as.data.dmark)(DATA_PTR(obj));
-break;
+
if (obj->as.data.dmark) (*obj->as.data.dmark)(DATA_PTR(obj));
+
break;
case T_OBJECT:
-mark_tbl(obj->as.object.iv_tbl, lev);
-break;
+
mark_tbl(obj->as.object.iv_tbl, lev);
+
break;
case
case
case
case
case
-break;
+
T_FILE:
T_REGEXP:
T_FLOAT:
T_BIGNUM:
T_BLKTAG:
break;
case T_MATCH:
-if (obj->as.match.str) {
ptr = obj->as.match.str;
goto again;
-}
-break;
+
if (obj->as.match.str) {
+
ptr = obj->as.match.str;
+
goto again;
+
}
+
break;
case T_VARMAP:
-gc_mark(obj->as.varmap.val, lev);
-ptr = (VALUE)obj->as.varmap.next;
-goto again;
+
gc_mark(obj->as.varmap.val, lev);
+
ptr = (VALUE)obj->as.varmap.next;
+
goto again;
case T_SCOPE:
-if (obj->as.scope.local_vars && (obj->as.scope.flags & SCOPE_MALLOC)) {
int n = obj->as.scope.local_tbl[0]+1;
VALUE *vars = &obj->as.scope.local_vars[-1];
+
if (obj->as.scope.local_vars && (obj->as.scope.flags & SCOPE_MALLOC)) {
+
int n = obj->as.scope.local_tbl[0]+1;
+
VALUE *vars = &obj->as.scope.local_vars[-1];
while (n--) {
-gc_mark(*vars++, lev);
}
-}
-break;
+
while (n--) {
+
gc_mark(*vars++, lev);
+
}
+
}
+
break;
case T_STRUCT:
-{
+
+
+
long len = obj->as.rstruct.len;
VALUE *ptr = obj->as.rstruct.ptr;
{
long len = obj->as.rstruct.len;
VALUE *ptr = obj->as.rstruct.ptr;
while (len--) {
-gc_mark(*ptr++, lev);
}
-}
-break;
+
while (len--) {
+
gc_mark(*ptr++, lev);
+
}
+
}
+
break;
default:
-rb_bug("rb_gc_mark(): unknown data type 0x%lx(0x%lx) %s",
obj->as.basic.flags & T_MASK, obj,
is_pointer_to_heap(obj) ? "corrupted object" : "non object");
+
rb_bug("rb_gc_mark(): unknown data type 0x%lx(0x%lx) %s",
+
obj->as.basic.flags & T_MASK, obj,
+
is_pointer_to_heap(obj) ? "corrupted object" : "non object");
}
}
@@ -1102,22 +1369,55 @@ finalize_list(p)
}
}
+static char* obj_type(int tp)
+{
+
switch (tp) {
+
case T_NIL
: return "NIL";
+
case T_OBJECT : return "OBJECT";
+
case T_CLASS : return "CLASS";
+
case T_ICLASS : return "ICLASS";
+
case T_MODULE : return "MODULE";
+
case T_FLOAT : return "FLOAT";
+
case T_STRING : return "STRING";
+
case T_REGEXP : return "REGEXP";
+
case T_ARRAY : return "ARRAY";
+
case T_FIXNUM : return "FIXNUM";
+
case T_HASH
: return "HASH";
+
case T_STRUCT : return "STRUCT";
+
case T_BIGNUM : return "BIGNUM";
+
case T_FILE
: return "FILE";
+
+
case T_TRUE
: return "TRUE";
+
case T_FALSE : return "FALSE";
+
case T_DATA
: return "DATA";
+
case T_MATCH : return "MATCH";
+
case T_SYMBOL : return "SYMBOL";
+
+
case T_BLKTAG : return "BLKTAG";
+
case T_UNDEF : return "UNDEF";
+
case T_VARMAP : return "VARMAP";
+
case T_SCOPE : return "SCOPE";
+
case T_NODE
: return "NODE";
+
default: return "____";
+
}
+}
+
static void
free_unused_heaps()
{
int i, j;
for (i = j = 1; j < heaps_used; i++) {
-if (heaps[i].limit == 0) {
free(heaps[i].membase);
heaps_used--;
-}
-else {
if (i != j) {
-heaps[j] = heaps[i];
}
j++;
-}
+
if (heaps[i].limit == 0) {
+
free(heaps[i].membase);
+
heaps_used--;
+
}
+
else {
+
if (i != j) {
+
heaps[j] = heaps[i];
+
}
+
j++;
+
}
}
}
@@ -1134,24 +1434,33 @@ gc_sweep()
unsigned long live = 0;
unsigned long free_min = 0;
+
+
+
+
+
+
+
+
+
+
unsigned long really_freed = 0;
int free_counts[256];
int live_counts[256];
int do_gc_stats = gc_statistics & verbose_gc_stats;
for (i = 0; i < heaps_used; i++) {
free_min += heaps[i].limit;
}
free_min = free_min * 0.2;
if (free_min < FREE_MIN)
free_min = FREE_MIN;
if (free_min < heap_free_min)
free_min = heap_free_min;
if (do_gc_stats) {
for (i = 0 ; i< 256; i++) { free_counts[i] = live_counts[i] = 0; }
+
}
if (ruby_in_compile && ruby_parser_stack_on_heap()) {
-/* should not reclaim nodes during compilation
+
/* should not reclaim nodes during compilation
if yacc's semantic stack is not allocated on machine stack */
-for (i = 0; i < heaps_used; i++) {
p = heaps[i].slot; pend = p + heaps[i].limit;
while (p < pend) {
-if (!(p->as.basic.flags&FL_MARK) && BUILTIN_TYPE(p) == T_NODE)
gc_mark((VALUE)p, 0);
-p++;
}
-}
+
for (i = 0; i < heaps_used; i++) {
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
while (p < pend) {
+
if (!(p->as.basic.flags&FL_MARK) && BUILTIN_TYPE(p) == T_NODE)
+
gc_mark((VALUE)p, 0);
+
p++;
+
}
+
}
}
mark_source_filename(ruby_sourcefile);
@@ -1172,7 +1481,7 @@ gc_sweep()
while (p < pend) {
if (!(p->as.basic.flags & FL_MARK)) {
if (p->as.basic.flags &&
((deferred = obj_free((VALUE)p)) ||
+
(((do_gc_stats && really_freed++), deferred = obj_free((VALUE)p)) ||
((FL_TEST(p, FL_FINALIZE)) && need_call_final))) {
if (!deferred) {
p->as.free.flags = T_DEFERRED;
@@ -1183,6 +1492,12 @@ gc_sweep()
final_list = p;
}
else {
+
if (do_gc_stats) {
+
int obt = p->as.basic.flags & T_MASK;
+
if (obt) {
+
free_counts[obt]++;
+
}
+
}
add_freelist(p);
}
n++;
@@ -1194,6 +1509,9 @@ gc_sweep()
else {
RBASIC(p)->flags &= ~FL_MARK;
live++;
+
if (do_gc_stats) {
+
live_counts[RANY((VALUE)p)->as.basic.flags & T_MASK]++;
+
}
}
p++;
}
@@ -1211,15 +1529,29 @@ gc_sweep()
}
}
if (malloc_increase > malloc_limit) {
-malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
-if (malloc_limit < GC_MALLOC_LIMIT) malloc_limit = GC_MALLOC_LIMIT;
+
malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
+
if (malloc_limit < initial_malloc_limit) malloc_limit = initial_malloc_limit;
}
malloc_increase = 0;
if (freed < free_min) {
-add_heap();
+
add_heap();
}
during_gc = 0;
+
+
+
+
+
+
+
+
+
+
+
+
+
+
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7d\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0 || live_counts[i]>0) {
fprintf(gc_data_file,
"kept %.7d / freed %.7d objects of type %s\n",
live_counts[i], free_counts[i], obj_type(i));
}
}
}
/* clear finalization list */
if (final_list) {
deferred_final_list = final_list;
@@ -1260,51 +1592,51 @@ obj_free(obj)
case T_FIXNUM:
case T_TRUE:
case T_FALSE:
-rb_bug("obj_free() called for broken object");
-break;
+
+
}
rb_bug("obj_free() called for broken object");
break;
if (FL_TEST(obj, FL_EXIVAR)) {
-rb_free_generic_ivar((VALUE)obj);
+
rb_free_generic_ivar((VALUE)obj);
}
switch (BUILTIN_TYPE(obj)) {
case T_OBJECT:
-if (RANY(obj)->as.object.iv_tbl) {
st_free_table(RANY(obj)->as.object.iv_tbl);
-}
-break;
+
if (RANY(obj)->as.object.iv_tbl) {
+
st_free_table(RANY(obj)->as.object.iv_tbl);
+
}
+
break;
case T_MODULE:
case T_CLASS:
-rb_clear_cache_by_class((VALUE)obj);
-st_free_table(RANY(obj)->as.klass.m_tbl);
-if (RANY(obj)->as.object.iv_tbl) {
st_free_table(RANY(obj)->as.object.iv_tbl);
-}
-break;
+
rb_clear_cache_by_class((VALUE)obj);
+
st_free_table(RANY(obj)->as.klass.m_tbl);
+
if (RANY(obj)->as.object.iv_tbl) {
+
st_free_table(RANY(obj)->as.object.iv_tbl);
+
}
+
break;
case T_STRING:
-if (RANY(obj)->as.string.ptr && !FL_TEST(obj, ELTS_SHARED)) {
RUBY_CRITICAL(free(RANY(obj)->as.string.ptr));
-}
-break;
+
if (RANY(obj)->as.string.ptr && !FL_TEST(obj, ELTS_SHARED)) {
+
RUBY_CRITICAL(free(RANY(obj)->as.string.ptr));
+
}
+
break;
case T_ARRAY:
-if (RANY(obj)->as.array.ptr && !FL_TEST(obj, ELTS_SHARED)) {
RUBY_CRITICAL(free(RANY(obj)->as.array.ptr));
-}
-break;
+
if (RANY(obj)->as.array.ptr && !FL_TEST(obj, ELTS_SHARED)) {
+
RUBY_CRITICAL(free(RANY(obj)->as.array.ptr));
+
}
+
break;
case T_HASH:
-if (RANY(obj)->as.hash.tbl) {
st_free_table(RANY(obj)->as.hash.tbl);
-}
-break;
+
if (RANY(obj)->as.hash.tbl) {
+
st_free_table(RANY(obj)->as.hash.tbl);
+
}
+
break;
case T_REGEXP:
-if (RANY(obj)->as.regexp.ptr) {
re_free_pattern(RANY(obj)->as.regexp.ptr);
-}
-if (RANY(obj)->as.regexp.str) {
RUBY_CRITICAL(free(RANY(obj)->as.regexp.str));
-}
-break;
+
if (RANY(obj)->as.regexp.ptr) {
+
re_free_pattern(RANY(obj)->as.regexp.ptr);
+
}
+
if (RANY(obj)->as.regexp.str) {
+
RUBY_CRITICAL(free(RANY(obj)->as.regexp.str));
+
}
+
break;
case T_DATA:
if (DATA_PTR(obj)) {
if ((long)RANY(obj)->as.data.dfree == -1) {
@@ -1317,11 +1649,11 @@ obj_free(obj)
}
break;
case T_MATCH:
-if (RANY(obj)->as.match.regs) {
re_free_registers(RANY(obj)->as.match.regs);
RUBY_CRITICAL(free(RANY(obj)->as.match.regs));
-}
-break;
+
if (RANY(obj)->as.match.regs) {
+
re_free_registers(RANY(obj)->as.match.regs);
+
RUBY_CRITICAL(free(RANY(obj)->as.match.regs));
+
}
+
break;
case T_FILE:
if (RANY(obj)->as.file.fptr) {
struct rb_io_t *fptr = RANY(obj)->as.file.fptr;
@@ -1332,19 +1664,19 @@ obj_free(obj)
}
break;
case T_ICLASS:
-/* iClass shares table with the module */
-break;
+
/* iClass shares table with the module */
+
break;
case T_FLOAT:
case T_VARMAP:
case T_BLKTAG:
-break;
+
break;
case T_BIGNUM:
-if (RANY(obj)->as.bignum.digits) {
RUBY_CRITICAL(free(RANY(obj)->as.bignum.digits));
-}
-break;
+
if (RANY(obj)->as.bignum.digits) {
+
RUBY_CRITICAL(free(RANY(obj)->as.bignum.digits));
+
}
+
break;
case T_NODE:
switch (nd_type(obj)) {
case NODE_SCOPE:
@@ -1359,7 +1691,7 @@ obj_free(obj)
break;/* no need to free iv_tbl */
case T_SCOPE:
-if (RANY(obj)->as.scope.local_vars &&
+
if (RANY(obj)->as.scope.local_vars &&
RANY(obj)->as.scope.flags != SCOPE_ALLOCA) {
VALUE *vars = RANY(obj)->as.scope.local_vars-1;
if (!(RANY(obj)->as.scope.flags & SCOPE_CLONE) && vars[0] == 0)
@@ -1370,14 +1702,14 @@ obj_free(obj)
break;
case T_STRUCT:
-if (RANY(obj)->as.rstruct.ptr) {
RUBY_CRITICAL(free(RANY(obj)->as.rstruct.ptr));
-}
-break;
+
if (RANY(obj)->as.rstruct.ptr) {
+
RUBY_CRITICAL(free(RANY(obj)->as.rstruct.ptr));
+
}
+
break;
default:
-rb_bug("gc_sweep(): unknown data type 0x%lx(0x%lx)",
RANY(obj)->as.basic.flags & T_MASK, obj);
+
rb_bug("gc_sweep(): unknown data type 0x%lx(0x%lx)",
+
RANY(obj)->as.basic.flags & T_MASK, obj);
}
return 0;
@@ -1407,18 +1739,18 @@ _rb_setjmp:\n\
typedef unsigned long rb_jmp_buf[6];
__asm__ (".align 4\n\
_rb_setjmp:\n\
-pushl%ebp\n\
-movl%esp,%ebp\n\
-movl8(%ebp),%ebp\n\
-movl%eax,(%ebp)\n\
-movl%ebx,4(%ebp)\n\
-movl%ecx,8(%ebp)\n\
-movl%edx,12(%ebp)\n\
-movl%esi,16(%ebp)\n\
-movl%edi,20(%ebp)\n\
-popl%ebp\n\
-xorl%eax,%eax\n\
-ret");
+
pushl
%ebp\n\
+
movl
%esp,%ebp\n\
+
movl
8(%ebp),%ebp\n\
+
movl
%eax,(%ebp)\n\
+
movl
%ebx,4(%ebp)\n\
+
movl
%ecx,8(%ebp)\n\
+
movl
%edx,12(%ebp)\n\
+
movl
%esi,16(%ebp)\n\
+
movl
%edi,20(%ebp)\n\
+
popl
%ebp\n\
+
xorl
%eax,%eax\n\
+
ret");
#endif
#endif
int rb_setjmp (rb_jmp_buf);
@@ -1431,41 +1763,50 @@ garbage_collect()
struct gc_list *list;
struct FRAME * volatile frame; /* gcc 2.7.2.3 -O2 bug??
jmp_buf save_regs_gc_mark;
+
struct timeval gctv1, gctv2;
SET_STACK_END;
*/
#ifdef HAVE_NATIVETHREAD
if (!is_ruby_native_thread()) {
-rb_bug("cross-thread violation on rb_gc()");
+
rb_bug("cross-thread violation on rb_gc()");
}
#endif
if (dont_gc || during_gc) {
-if (!freelist) {
add_heap();
-}
-return;
+
if (!freelist) {
+
add_heap();
+
}
+
return;
}
if (during_gc) return;
during_gc++;
+
+
+
+
+
+
+
+
if (gc_statistics) {
gc_collections++;
gettimeofday(&gctv1, NULL);
if (verbose_gc_stats) {
fprintf(gc_data_file, "Garbage collection started\n");
}
}
init_mark_stack();
gc_mark((VALUE)ruby_current_node, 0);
/* mark frame stack */
for (frame = ruby_frame; frame; frame = frame->prev) {
-rb_gc_mark_frame(frame);
-if (frame->tmp) {
struct FRAME *tmp = frame->tmp;
while (tmp) {
-rb_gc_mark_frame(tmp);
-tmp = tmp->prev;
}
-}
+
rb_gc_mark_frame(frame);
+
if (frame->tmp) {
+
struct FRAME *tmp = frame->tmp;
+
while (tmp) {
+
rb_gc_mark_frame(tmp);
+
tmp = tmp->prev;
+
}
+
}
}
gc_mark((VALUE)ruby_scope, 0);
gc_mark((VALUE)ruby_dyna_vars, 0);
if (finalizer_table) {
-mark_tbl(finalizer_table, 0);
+
mark_tbl(finalizer_table, 0);
}
FLUSH_REGISTER_WINDOWS;
@@ -1478,9 +1819,9 @@ garbage_collect()
rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
#else
if ((VALUE*)STACK_END < rb_gc_stack_start)
-rb_gc_mark_locations((VALUE*)STACK_END, rb_gc_stack_start);
+
rb_gc_mark_locations((VALUE*)STACK_END, rb_gc_stack_start);
else
-rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
+
rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
#endif
#ifdef __ia64
/* mark backing store (flushed register window on the stack) */
@@ -1489,13 +1830,13 @@ garbage_collect()
#endif
#if defined(__human68k__) || defined(__mc68000__)
rb_gc_mark_locations((VALUE*)((char*)STACK_END + 2),
- (VALUE*)((char*)rb_gc_stack_start + 2));
+
(VALUE*)((char*)rb_gc_stack_start + 2));
#endif
rb_gc_mark_threads();
/* mark protected global variables */
for (list = global_List; list; list = list->next) {
-rb_gc_mark_maybe(*list->varptr);
+
rb_gc_mark_maybe(*list->varptr);
}
rb_mark_end_proc();
rb_gc_mark_global_tbl();
@@ -1510,18 +1851,30 @@ garbage_collect()
/* gc_mark objects whose marking are not completed*/
do {
-while (!MARK_STACK_EMPTY) {
if (mark_stack_overflow){
-gc_mark_all();
}
else {
-gc_mark_rest();
}
-}
-rb_gc_abort_threads();
+
while (!MARK_STACK_EMPTY) {
+
if (mark_stack_overflow){
+
gc_mark_all();
+
}
+
else {
+
gc_mark_rest();
+
}
+
}
+
rb_gc_abort_threads();
} while (!MARK_STACK_EMPTY);
gc_sweep();
+
+
+
+
+
+
+
+
+
+
+
+
if (gc_statistics) {
GC_TIME_TYPE musecs_used;
gettimeofday(&gctv2, NULL);
musecs_used = ((GC_TIME_TYPE)(gctv2.tv_sec - gctv1.tv_sec) * 1000000) + (gctv2.tv_usec - gctv1.tv_usec);
gc_time += musecs_used;
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
fflush(gc_data_file);
}
}
}
void
@@ -1588,8 +1941,8 @@ Init_stack(addr)
memset(&m, 0, sizeof(m));
VirtualQuery(&m, &m, sizeof(m));
rb_gc_stack_start =
-STACK_UPPER((VALUE *)&m, (VALUE *)m.BaseAddress,
(VALUE *)((char *)m.BaseAddress + m.RegionSize) - 1);
+
STACK_UPPER((VALUE *)&m, (VALUE *)m.BaseAddress,
+
(VALUE *)((char *)m.BaseAddress + m.RegionSize) - 1);
#elif defined(STACK_END_ADDRESS)
{
extern void *STACK_END_ADDRESS;
@@ -1599,24 +1952,24 @@ Init_stack(addr)
if (!addr) addr = (void *)&addr;
STACK_UPPER(&addr, addr, ++addr);
if (rb_gc_stack_start) {
-if (STACK_UPPER(&addr,
-rb_gc_stack_start > addr,
-rb_gc_stack_start < addr))
rb_gc_stack_start = addr;
-return;
+
if (STACK_UPPER(&addr,
+
rb_gc_stack_start > addr,
+
rb_gc_stack_start < addr))
+
rb_gc_stack_start = addr;
+
return;
}
rb_gc_stack_start = addr;
#endif
#ifdef HAVE_GETRLIMIT
{
-struct rlimit rlim;
+
struct rlimit rlim;
-if (getrlimit(RLIMIT_STACK, &rlim) == 0) {
unsigned int space = rlim.rlim_cur/5;
+
if (getrlimit(RLIMIT_STACK, &rlim) == 0) {
+
unsigned int space = rlim.rlim_cur/5;
-}
+
+
+
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (rlim.rlim_cur - space) / sizeof(VALUE);
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (rlim.rlim_cur - space) / sizeof(VALUE);
}
}
#endif
}
@@ -1652,16 +2005,16 @@ void ruby_init_stack(VALUE *addr
}
#elif defined _WIN32
{
-MEMORY_BASIC_INFORMATION mi;
-DWORD size;
-DWORD space;
-if (VirtualQuery(&mi, &mi, sizeof(mi))) {
size = (char *)mi.BaseAddress - (char *)mi.AllocationBase;
space = size / 5;
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (size - space) / sizeof(VALUE);
-}
+
MEMORY_BASIC_INFORMATION mi;
+
DWORD size;
+
+
+
+
+
+
+
+
DWORD space;
if (VirtualQuery(&mi, &mi, sizeof(mi))) {
size = (char *)mi.BaseAddress - (char *)mi.AllocationBase;
space = size / 5;
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (size - space) / sizeof(VALUE);
}
}
#endif
}
@@ -1701,8 +2054,9 @@ void
Init_heap()
{
if (!rb_gc_stack_start) {
-Init_stack(0);
+
Init_stack(0);
}
+
set_gc_parameters();
add_heap();
}
@@ -1715,7 +2069,7 @@ os_obj_of(of)
volatile VALUE v;
for (i = 0; i < heaps_used; i++) {
-RVALUE *p, *pend;
+
RVALUE *p, *pend;
p = heaps[i].slot; pend = p + heaps[i].limit;
for (;p < pend; p++) {
@@ -1808,8 +2162,8 @@ add_final(os, block)
{
rb_warn("ObjectSpace::add_finalizer is deprecated; use define_finalizer");
if (!rb_respond_to(block, rb_intern("call"))) {
-rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
- rb_obj_classname(block));
+
rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
+
rb_obj_classname(block));
}
rb_ary_push(finalizers, block);
return block;
@@ -1864,7 +2218,7 @@ undefine_final(os, obj)
VALUE os, obj;
{
if (finalizer_table) {
-st_delete(finalizer_table, (st_data_t*)&obj, 0);
+
st_delete(finalizer_table, (st_data_t*)&obj, 0);
}
return obj;
}
@@ -1888,11 +2242,11 @@ define_final(argc, argv, os)
rb_scan_args(argc, argv, "11", &obj, &block);
if (argc == 1) {
-block = rb_block_proc();
+
block = rb_block_proc();
}
else if (!rb_respond_to(block, rb_intern("call"))) {
-rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
- rb_obj_classname(block));
+
rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
+
rb_obj_classname(block));
}
need_call_final = 1;
if (!FL_ABLE(obj)) {
@@ -1905,10 +2259,10 @@ define_final(argc, argv, os)
OBJ_FREEZE(block);
if (!finalizer_table) {
-finalizer_table = st_init_numtable();
+
finalizer_table = st_init_numtable();
}
if (st_lookup(finalizer_table, obj, &table)) {
-rb_ary_push(table, block);
+
rb_ary_push(table, block);
}
else {
table = rb_ary_new3(1, block);
@@ -1927,7 +2281,7 @@ rb_gc_copy_finalizer(dest, obj)
if (!finalizer_table) return;
if (!FL_TEST(obj, FL_FINALIZE)) return;
if (st_lookup(finalizer_table, obj, &table)) {
-st_insert(finalizer_table, dest, table);
+
st_insert(finalizer_table, dest, table);
}
RBASIC(dest)->flags |= FL_FINALIZE;
}
@@ -1957,18 +2311,18 @@ run_final(obj)
args[1] = 0;
args[2] = (VALUE)ruby_safe_level;
for (i=0; i<RARRAY(finalizers)->len; i++) {
-args[0] = RARRAY(finalizers)->ptr[i];
-if (!args[1]) args[1] = rb_ary_new3(1, objid);
-rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
+
+
+
args[0] = RARRAY(finalizers)->ptr[i];
if (!args[1]) args[1] = rb_ary_new3(1, objid);
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
}
if (finalizer_table && st_delete(finalizer_table, (st_data_t*)&obj, &table)) {
-for (i=0; i<RARRAY(table)->len; i++) {
VALUE final = RARRAY(table)->ptr[i];
args[0] = RARRAY(final)->ptr[1];
if (!args[1]) args[1] = rb_ary_new3(1, objid);
args[2] = FIX2INT(RARRAY(final)->ptr[0]);
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
-}
+
for (i=0; i<RARRAY(table)->len; i++) {
+
VALUE final = RARRAY(table)->ptr[i];
+
args[0] = RARRAY(final)->ptr[1];
+
if (!args[1]) args[1] = rb_ary_new3(1, objid);
+
args[2] = FIX2INT(RARRAY(final)->ptr[0]);
+
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
+
}
}
rb_thread_critical = critical_save;
}
@@ -1980,8 +2334,8 @@ rb_gc_finalize_deferred()
deferred_final_list = 0;
if (p) {
-finalize_list(p);
-free_unused_heaps();
+
finalize_list(p);
+
free_unused_heaps();
}
}
@@ -2061,7 +2415,7 @@ id2ref(obj, objid)
if (ptr == Qfalse) return Qfalse;
if (ptr == Qnil) return Qnil;
if (FIXNUM_P(ptr)) return (VALUE)ptr;
ptr = objid ^ FIXNUM_FLAG;/* unset FIXNUM_FLAG */
+
ptr = objid ^ FIXNUM_FLAG; /* unset FIXNUM_FLAG */
if ((ptr % sizeof(RVALUE)) == (4 << 2)) {
ID symid = ptr / sizeof(RVALUE);
@@ -2075,7 +2429,7 @@ id2ref(obj, objid)
rb_raise(rb_eRangeError, "0x%lx is not id value", p0);
}
if (BUILTIN_TYPE(ptr) == 0 || RBASIC(ptr)->klass == 0) {
-rb_raise(rb_eRangeError, "0x%lx is recycled object", p0);
+
rb_raise(rb_eRangeError, "0x%lx is recycled object", p0);
}
return (VALUE)ptr;
}
@@ -2166,6 +2520,14 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "stress=", gc_stress_set, 1);
rb_define_method(rb_mGC, "garbage_collect", rb_gc_start, 0);
+
+
+
+
+
+
+
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"clear_stats", rb_gc_clear_stats, 0);
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
rb_define_module_function(rb_mObSpace, "garbage_collect", rb_gc_start, 0);
@@ -2188,7 +2550,7 @@ Init_GC()
+
rb_global_variable(&nomem_error);
nomem_error = rb_exc_new3(rb_eNoMemError,
rb_obj_freeze(rb_str_new2("failed to allocate memory")));
rb_obj_freeze(rb_str_new2("failed to allocate memory")));
OBJ_TAINT(nomem_error);
OBJ_FREEZE(nomem_error);
1.26.5.1.11.1.12. 05-better-source-file-tracing.patch
diff --git a/eval.c b/eval.c
index fb3307c..356226e 100644
--- a/eval.c
+++ b/eval.c
@@ -1161,7 +1161,7 @@ static VALUE trace_func = 0;
static int tracing = 0;
static void call_trace_func _((rb_event_t,NODE*,VALUE,ID,VALUE));
-#if 0
+#if 1
#define SET_CURRENT_SOURCE() (ruby_sourcefile = ruby_current_node->nd_file, \
ruby_sourceline = nd_line(ruby_current_node))
#else
1.26.5.1.11.1.13. 16-caller-for-all-threads.patch
diff --git a/eval.c b/eval.c
index 356226e..a0fdc55 100644
--- a/eval.c
+++ b/eval.c
@@ -8199,6 +8199,17 @@ rb_f_method_name()
}
}
+/* Hash (Thread => Backtrace) used to collect backtrace for each threads. */
+static VALUE backtrace_for_each_thread;
+
+static int backtrace_level_for_each_thread;
+
+static VALUE
+switch_thread_context_to_collect_backtrace(rb_thread_t next);
+
+static VALUE
+rb_f_caller_for_all_threads();
+
void
Init_eval()
{
@@ -8244,6 +8255,7 @@ Init_eval()
rb_define_global_function("fail", rb_f_raise, -1);
+
rb_define_global_function("caller", rb_f_caller, -1);
rb_define_global_function("caller_for_all_threads", rb_f_caller_for_all_threads, -1);
rb_define_global_function("exit", rb_f_exit, -1);
rb_define_global_function("abort", rb_f_abort, -1);
@@ -10599,6 +10611,7 @@ static int
th_sig, th_safe;
#define RESTORE_RAISE5
#define RESTORE_SIGNAL6
#define RESTORE_EXIT7
+#define RESTORE_BACKTRACE8
extern VALUE *rb_gc_stack_start;
#ifdef __ia64
@@ -10705,6 +10718,15 @@ rb_thread_switch(n)
}
rb_exc_raise(th_raise_exception);
break;
+
case RESTORE_BACKTRACE:
+
rb_hash_aset(backtrace_for_each_thread, curr_thread->thread,
+
backtrace(backtrace_level_for_each_thread));
+
if (curr_thread != main_thread) {
+
switch_thread_context_to_collect_backtrace(curr_thread->next);
+
} else {
+
/* Circled back to main thread, cycle is complete. */
+
}
+
break;
case RESTORE_NORMAL:
default:
break;
@@ -13875,3 +13897,74 @@ rb_throw(tag, val)
argv[1] = val;
rb_f_throw(2, argv);
}
+
+static VALUE
+switch_thread_context_to_collect_backtrace(rb_thread_t next)
+{
+
if (THREAD_SAVE_CONTEXT(curr_thread)) {
+
return Qnil;
+
}
+
curr_thread = next;
+
rb_thread_restore_context(next, RESTORE_BACKTRACE);
+
return Qnil;
+}
+
+
+/*
+ * call-seq:
+ *
caller_for_all_threads(start=1)
=> array
+ *
+ * Returns the current execution stack for all threads
+ * ---a hash whose keys are thread instances and values
+ * the thread caller backtrace.
+ *
+ * Backtraces are array of hashes indicating location on the
+ * stack. Hash keys include ``<em>:line</em>'' or ``<em>:file</em>''
+ * and ``<em>:method'</em>''.
+ *
+ * The optional _start_ parameter
+ * determines the number of initial stack entries to omit from the
+ * result.
+ *
+ *
def a(skip)
+ *
caller_for_all_threads(skip)
+ *
end
+ *
def b(skip)
+ *
a(skip)
+ *
end
+ *
def c(skip)
+ *
b(skip)
+ *
end
+ *
c(0)
#=> ["prog:2:in `a'", "prog:5:in `b'", "prog:8:in `c'", "prog:10"]
+ *
c(1)
#=> ["prog:5:in `b'", "prog:8:in `c'", "prog:11"]
+ *
c(2)
#=> ["prog:8:in `c'", "prog:12"]
+ *
c(3)
#=> ["prog:13"]
+ */
+static VALUE
+rb_f_caller_for_all_threads(argc, argv)
+
int argc;
+
VALUE *argv;
+{
+
volatile int critical;
+
VALUE level;
+VALUE result;
+
+
rb_scan_args(argc, argv, "01", &level);
+
backtrace_level_for_each_thread = NIL_P(level) ? 0 : NUM2INT(level);
+if (backtrace_level_for_each_thread < 0) {
+rb_raise(rb_eArgError, "negative level (%d)", backtrace_level_for_each_thread);
+}
+
+critical = rb_thread_critical;
+rb_thread_critical = Qtrue;
+
+
backtrace_for_each_thread = rb_hash_new();
+
switch_thread_context_to_collect_backtrace(main_thread->next);
+
+result = backtrace_for_each_thread;
+backtrace_for_each_thread = Qnil;
+backtrace_for_each_thread = 0;
+
+rb_thread_critical = critical;
+
return result;
+}
diff --git a/test/callerforallthreads/test_caller_for_each_thread.rb
b/test/callerforallthreads/test_caller_for_each_thread.rb
new file mode 100644
index 0000000..6aebaed
--- /dev/null
+++ b/test/callerforallthreads/test_caller_for_each_thread.rb
@@ -0,0 +1,95 @@
+# -*- ruby-indent-level: 4 -*+require 'thread'
+require 'test/unit'
+
+class AClassWithNestedmethods
+
+ def an_ultra_nested_method(skip)
+
caller_for_all_threads skip
+ end
+
+ def a_nested_method(skip)
+
an_ultra_nested_method skip
+ end
+
+ def a_method(skip=0)
+
a_nested_method skip
+ end
+
+end
+
+class CallerForEachThreadTest < Test::Unit::TestCase
+
+ def testCollectMeaningfulBacktraceForASingleThread
+
backtraces = AClassWithNestedmethods.new.a_method
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":8:in `an_ultra_nested_method'", backtrace[0]
+
assert_equal __FILE__ + ":12:in `a_nested_method'", backtrace[1]
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[2]
+
assert_equal __FILE__ + ":24:in `testCollectMeaningfulBacktraceForASingleThread'",
+
backtrace[3]
+ end
+
+ def testCanSkipFirstStackEntries
+
backtraces = AClassWithNestedmethods.new.a_method 2
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[0]
+
assert_equal __FILE__ + ":35:in `testCanSkipFirstStackEntries'",
+
backtrace[1]
+ end
+
+ def testCollectMeaningfulBacktraceForMultipleThreads
+
first_thread = Thread.new do
+
loop do
+
Thread.pass
+
sleep 1
+
end
+
end
+
+
second_thread = Thread.new do
+
loop do
+
Thread.pass
+
sleep 1
+
end
+
end
+
+
backtraces = AClassWithNestedmethods.new.a_method
+
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_match __FILE__ + ":8:in `an_ultra_nested_method'", backtrace[0]
+
assert_match __FILE__ + ":12:in `a_nested_method'", backtrace[1]
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[2]
+
assert_equal __FILE__ + ":58:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[3]
+
+
backtrace = backtraces[first_thread]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":47:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[0]
+
assert_equal __FILE__ + ":45:in `loop'",
+
backtrace[1]
+
assert_equal __FILE__ + ":45:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[2]
+
assert_equal __FILE__ + ":44:in `initialize'",backtrace[3]
+
assert_equal __FILE__ + ":44:in `new'", backtrace[4]
+
assert_equal __FILE__ + ":44:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[5]
+
+
backtrace = backtraces[second_thread]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":53:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[0]
+
assert_equal __FILE__ + ":52:in `loop'", backtrace[1]
+
assert_equal __FILE__ + ":52:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[2]
+
assert_equal __FILE__ + ":51:in `initialize'",backtrace[3]
+
assert_equal __FILE__ + ":51:in `new'", backtrace[4]
+
assert_equal __FILE__ + ":51:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[5]
+ end
+
+end
+
1.26.5.1.11.1.14. 09-track-object-allocation.patch
diff --git a/gc.c b/gc.c
index 30a1219..5b42b90 100644
--- a/gc.c
+++ b/gc.c
@@ -96,6 +96,26 @@ static void garbage_collect();
int ruby_gc_stress = 0;
+static unsigned long live_objects = 0;
+unsigned long rb_os_live_objects()
+{
+
return live_objects;
+}
+
+#if defined(HAVE_LONG_LONG)
+static unsigned LONG_LONG allocated_objects = 0;
+unsigned LONG_LONG rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#else
+static unsigned long allocated_objects = 0;
+unsigned long rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#endif
+
NORETURN(void rb_exc_jump _((VALUE)));
void
@@ -987,6 +1007,8 @@ rb_newobj()
RANY(obj)->file = ruby_sourcefile;
RANY(obj)->line = ruby_sourceline;
#endif
+
live_objects++;
+
allocated_objects++;
return obj;
}
@@ -1825,6 +1847,7 @@ gc_sweep()
add_heap();
}
during_gc = 0;
+
live_objects = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2790,6 +2813,35 @@ rb_obj_id(VALUE obj)
return (VALUE)((long)obj|FIXNUM_FLAG);
}
+/* call-seq:
+ * ObjectSpace.live_objects => number
+ *
+ * Returns the count of objects currently allocated in the system. This goes
+ * down after the garbage collector runs.
+ */
+static
+VALUE os_live_objects(VALUE self)
+{
+
return ULONG2NUM(live_objects);
+}
+
+/* call-seq:
+ * ObjectSpace.allocated_objects => number
+ *
+ * Returns the count of objects allocated since the Ruby interpreter has
+ * started. This number can only increase. To know how many objects are
+ * currently allocated, use ObjectSpace::live_objects
+ */
+static
+VALUE os_allocated_objects(VALUE self)
+{
+#if defined(HAVE_LONG_LONG)
+
return ULL2NUM(allocated_objects);
+#else
+
return ULONG2NUM(allocated_objects);
+#endif
+}
+
/*
* The <code>GC</code> module provides an interface to Ruby's mark and
* sweep garbage collection mechanism. Some of the underlying methods
@@ -2833,6 +2885,9 @@ Init_GC()
rb_define_module_function(rb_mObSpace, "finalizers", finals, 0);
rb_define_module_function(rb_mObSpace, "call_finalizer", call_final, 1);
+
+
+
rb_define_module_function(rb_mObSpace, "live_objects", os_live_objects, 0);
rb_define_module_function(rb_mObSpace, "allocated_objects", os_allocated_objects, 0);
rb_define_module_function(rb_mObSpace, "define_finalizer", define_final, -1);
rb_define_module_function(rb_mObSpace, "undefine_finalizer", undefine_final, 1);
diff --git a/intern.h b/intern.h
index 1117614..a87661d 100644
--- a/intern.h
+++ b/intern.h
@@ -274,6 +274,12 @@ void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
VALUE rb_gc_allocated_size _((void));
VALUE rb_gc_num_allocations _((void));
+unsigned long rb_os_live_objects _((void));
+#ifdef HAVE_LONG_LONG
+unsigned LONG_LONG rb_os_allocated_objects _((void));
+#else
+unsigned long rb_os_allocated_objects _((void));
+#endif
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.11.1.15. 02-sigvtalrm-fix.patch
diff --git a/eval.c b/eval.c
index 7886e17..6ff2560 100644
--- a/eval.c
+++ b/eval.c
@@ -12461,6 +12461,11 @@ rb_thread_start_0(fn, arg, th)
curr_thread->next = th;
th->priority = curr_thread->priority;
th->thgroup = curr_thread->thgroup;
+#if defined(HAVE_SETITIMER) || defined(_THREAD_SAFE)
+
if (!thread_init) {
+
rb_thread_start_timer();
+
}
+#endif
}
START_TIMER();
@@ -13189,7 +13194,9 @@ rb_thread_atfork()
main_thread = curr_thread;
curr_thread->next = curr_thread;
curr_thread->prev = curr_thread;
STOP_TIMER();
+#if defined(HAVE_SETITIMER) || defined(_THREAD_SAFE)
+
rb_thread_stop_timer();
+#endif
}
1.26.5.1.11.1.16. 10-expose-heap-slots.patch
diff --git a/gc.c b/gc.c
index 5b42b90..21b3f6b 100644
--- a/gc.c
+++ b/gc.c
@@ -690,6 +690,7 @@ static int heaps_used
= 0;
static int heap_min_slots = 10000;
static int heap_slots = 10000;
+static int heap_size = 0;
static int heap_free_min = 4096;
static int heap_slots_increment = 10000;
@@ -800,6 +801,21 @@ static void set_gc_parameters()
/*
* call-seq:
+ *
GC.heap_slots
=> Integer
+ *
+ * Returns the number of heap slots available for object allocations.
+ *
+ *
GC.heap_slots
#=> 10000
+ *
+ */
+VALUE
+rb_gc_heap_slots()
+{
+
return INT2NUM(heap_size);
+}
+
+/*
+ * call-seq:
*
GC.dump
=> nil
*
* dumps information about the current GC data structures to the GC log file
@@ -967,6 +983,7 @@ add_heap()
heaps[heaps_used].limit = heap_slots;
break;
}
+
heap_size += heap_slots;
pend = p + heap_slots;
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
@@ -1828,6 +1845,7 @@ gc_sweep()
if (n == heaps[i].limit && freed > free_min) {
RVALUE *pp;
+
heap_size -= n;
heaps[i].limit = 0;
for (pp = final_list; pp != final; pp = pp->as.free.next) {
pp->as.free.flags |= FL_SINGLETON; /* freeing page mark */
@@ -2866,6 +2884,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "clear_stats", rb_gc_clear_stats, 0);
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
+
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
diff --git a/intern.h b/intern.h
index a87661d..e8f3209 100644
--- a/intern.h
+++ b/intern.h
@@ -274,6 +274,7 @@ void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
VALUE rb_gc_allocated_size _((void));
VALUE rb_gc_num_allocations _((void));
+VALUE rb_gc_heap_slots _((void));
unsigned long rb_os_live_objects _((void));
#ifdef HAVE_LONG_LONG
unsigned LONG_LONG rb_os_allocated_objects _((void));
1.26.5.1.12. p334
1.26.5.1.12.1. railsexpress
1.26.5.1.12.1.1. 09-track-malloc-size.patch
diff --git a/gc.c b/gc.c
index a3cbe91..30a1219 100644
--- a/gc.c
+++ b/gc.c
@@ -79,6 +79,17 @@ void *alloca ();
static unsigned long malloc_increase = 0;
static unsigned long malloc_limit = GC_MALLOC_LIMIT;
+
+#ifdef HAVE_LONG_LONG
+static unsigned LONG_LONG gc_allocated_size = 0;
+static unsigned LONG_LONG gc_num_allocations = 0;
+#else
+static unsigned long gc_allocated_size = 0;
+static unsigned long gc_num_allocations = 0;
+#endif
+static int gc_statistics = 0;
+
+
static void run_final();
static VALUE nomem_error;
static void garbage_collect();
@@ -163,6 +174,11 @@ ruby_xmalloc(size)
}
malloc_increase += size;
+
if (gc_statistics) {
+
gc_allocated_size += size;
+gc_num_allocations += 1;
+
}
+
return mem;
}
@@ -220,7 +236,6 @@ ruby_xfree(x)
extern int ruby_in_compile;
static int dont_gc;
-static int gc_statistics = 0;
static GC_TIME_TYPE gc_time = 0;
static int gc_collections = 0;
static int verbose_gc_stats = Qfalse;
@@ -329,11 +344,55 @@ rb_gc_clear_stats()
{
gc_collections = 0;
gc_time = 0;
+
gc_allocated_size = 0;
+
gc_num_allocations = 0;
return Qnil;
}
/*
* call-seq:
+ *
GC.allocated_size
=> Integer
+ *
+ * Returns the size of memory (in bytes) allocated since GC statistics collection
+ * was enabled.
+ *
+ *
GC.allocated_size
#=> 35
+ *
+ */
+VALUE
+rb_gc_allocated_size()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_allocated_size);
+#else
+
return ULONG2NUM(gc_allocated_size);
+#endif
+}
+
+/*
+ * call-seq:
+ *
GC.num_allocations
=> Integer
+ *
+ * Returns the number of memory allocations since GC statistics collection
+ * was enabled.
+ *
+ *
GC.num_allocations
#=> 150
+ *
+ */
+VALUE
+rb_gc_num_allocations()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_num_allocations);
+#else
+
return ULONG2NUM(gc_num_allocations);
+#endif
+}
+
+/*
+
+/*
+ * call-seq:
*
GC.collections
=> Integer
*
* Returns the number of garbage collections performed while GC statistics collection
@@ -2753,6 +2812,8 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "enable_stats", rb_gc_enable_stats, 0);
rb_define_singleton_method(rb_mGC, "disable_stats", rb_gc_disable_stats, 0);
rb_define_singleton_method(rb_mGC, "clear_stats", rb_gc_clear_stats, 0);
+
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
+
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
diff --git a/intern.h b/intern.h
index 49e1827..78bf699 100644
--- a/intern.h
+++ b/intern.h
@@ -272,6 +272,8 @@ VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
+VALUE rb_gc_allocated_size _((void));
+VALUE rb_gc_num_allocations _((void));
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.12.1.2. 16-add-object-size-information-to-heap-dump.patch
diff --git a/gc.c b/gc.c
index 0ce7e68..53450bf 100644
--- a/gc.c
+++ b/gc.c
@@ -953,9 +953,21 @@ rb_gc_dump_file_and_line_info(int argc, VALUE *argv)
if (!p->as.basic.klass) {
fprintf(f, "__unknown__");
} else {
fprintf(f, rb_obj_classname((VALUE)p));
+
fprintf(f, "%s", rb_obj_classname((VALUE)p));
}
}
+
/* print object size for some known object types */
+
switch (TYPE(p)) {
+
case T_STRING:
+
fprintf(f, ":%lu", RSTRING(p)->len);
+
break;
+
case T_ARRAY:
+
fprintf(f, ":%lu", RARRAY(p)->len);
+
break;
+
case T_HASH:
+
fprintf(f, ":%d", RHASH(p)->tbl->num_entries);
+
break;
+
}
}
fprintf(f, "\n");
}
@@ -1924,10 +1936,10 @@ gc_sweep()
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7d\n", really_freed);
fprintf(gc_data_file, "objects processed: %.7lu\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7lu\n", live);
fprintf(gc_data_file, "freelist objects : %.7lu\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7lu\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0 || live_counts[i]>0) {
fprintf(gc_data_file,
@@ -2258,7 +2270,7 @@ garbage_collect()
gc_time += musecs_used;
+
+
+
+
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
fprintf(gc_data_file, "GC time: %ld msec\n", (long)(musecs_used / 1000));
fflush(gc_data_file);
}
+
}
1.26.5.1.12.1.3. 15-track-live-dataset-size.patch
diff --git a/gc.c b/gc.c
index 2c34932..0ce7e68 100644
--- a/gc.c
+++ b/gc.c
@@ -89,6 +89,7 @@ static unsigned long gc_num_allocations = 0;
#endif
static int gc_statistics = 0;
+static unsigned long heap_slots_live_after_last_gc = 0;
static void run_final();
static VALUE nomem_error;
@@ -465,6 +466,23 @@ rb_gc_time()
#endif
}
+/*
+ * call-seq:
+ *
GC.heap_slots_live_after_last_gc
=> Integer
+ *
+ * Returns the number of heap slots which were live after the last garbage collection.
+ *
+ *
GC.heap_slots_live_after_last_gc
#=> 231223
+ *
+ */
+VALUE
+rb_gc_heap_slots_live_after_last_gc()
+{
+
return ULONG2NUM(heap_slots_live_after_last_gc);
+}
+
+
+
VALUE rb_mGC;
/*
@@ -1903,6 +1921,7 @@ gc_sweep()
}
during_gc = 0;
live_objects = live;
+
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2924,6 +2943,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
+
rb_define_singleton_method(rb_mGC, "heap_slots_live_after_last_gc", rb_gc_heap_slots_live_after_last_gc, 0);
rb_define_const(rb_mGC, "HEAP_SLOT_SIZE", INT2FIX(sizeof(RVALUE)));
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
1.26.5.1.12.1.4. 14-add-trace-stats-enabled-methods.patch
diff --git a/gc.c b/gc.c
index 57740d2..2c34932 100644
--- a/gc.c
+++ b/gc.c
@@ -350,6 +350,22 @@ rb_gc_disable_stats()
/*
* call-seq:
+ *
GC.stats_enabled?
=> true or false
+ *
+ * Check whether GC stats have been enabled.
+ *
+ *
GC.stats_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_stats_enabled()
+{
+
return gc_statistics ? Qtrue : Qfalse;
+}
+
+/*
+ * call-seq:
*
GC.clear_stats
=> nil
*
* Clears garbage collection statistics, returning nil. This resets the number
@@ -491,6 +507,22 @@ rb_gc_disable_trace()
return old;
}
+/*
+ * call-seq:
+ *
GC.trace_enabled?
=> true or false
+ *
+ * Check whether GC tracing has been enabled.
+ *
+ *
GC.trace_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_trace_enabled()
+{
+
return verbose_gc_stats ? Qtrue : Qfalse;
+}
+
char* GC_LOGFILE_IVAR = "@gc_logfile_name";
/*
@@ -2887,6 +2919,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
@@ -2902,6 +2935,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"stats_enabled?", rb_gc_stats_enabled, 0);
"clear_stats", rb_gc_clear_stats, 0);
"allocated_size", rb_gc_allocated_size, 0);
"num_allocations", rb_gc_num_allocations, 0);
"log_file", rb_gc_log_file, -1);
"enable_trace", rb_gc_enable_trace, 0);
"disable_trace", rb_gc_disable_trace, 0);
"trace_enabled?", rb_gc_trace_enabled, 0);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
1.26.5.1.12.1.5. 10-track-object-allocation.patch
diff --git a/gc.c b/gc.c
index 30a1219..5b42b90 100644
--- a/gc.c
+++ b/gc.c
@@ -96,6 +96,26 @@ static void garbage_collect();
int ruby_gc_stress = 0;
+static unsigned long live_objects = 0;
+unsigned long rb_os_live_objects()
+{
+
return live_objects;
+}
+
+#if defined(HAVE_LONG_LONG)
+static unsigned LONG_LONG allocated_objects = 0;
+unsigned LONG_LONG rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#else
+static unsigned long allocated_objects = 0;
+unsigned long rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#endif
+
NORETURN(void rb_exc_jump _((VALUE)));
void
@@ -987,6 +1007,8 @@ rb_newobj()
RANY(obj)->file = ruby_sourcefile;
RANY(obj)->line = ruby_sourceline;
#endif
+
live_objects++;
+
allocated_objects++;
return obj;
}
@@ -1825,6 +1847,7 @@ gc_sweep()
add_heap();
}
during_gc = 0;
+
live_objects = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2790,6 +2813,35 @@ rb_obj_id(VALUE obj)
return (VALUE)((long)obj|FIXNUM_FLAG);
}
+/* call-seq:
+ * ObjectSpace.live_objects => number
+ *
+ * Returns the count of objects currently allocated in the system. This goes
+ * down after the garbage collector runs.
+ */
+static
+VALUE os_live_objects(VALUE self)
+{
+
return ULONG2NUM(live_objects);
+}
+
+/* call-seq:
+ * ObjectSpace.allocated_objects => number
+ *
+ * Returns the count of objects allocated since the Ruby interpreter has
+ * started. This number can only increase. To know how many objects are
+ * currently allocated, use ObjectSpace::live_objects
+ */
+static
+VALUE os_allocated_objects(VALUE self)
+{
+#if defined(HAVE_LONG_LONG)
+
return ULL2NUM(allocated_objects);
+#else
+
return ULONG2NUM(allocated_objects);
+#endif
+}
+
/*
* The <code>GC</code> module provides an interface to Ruby's mark and
* sweep garbage collection mechanism. Some of the underlying methods
@@ -2833,6 +2885,9 @@ Init_GC()
rb_define_module_function(rb_mObSpace, "finalizers", finals, 0);
rb_define_module_function(rb_mObSpace, "call_finalizer", call_final, 1);
+
+
+
rb_define_module_function(rb_mObSpace, "live_objects", os_live_objects, 0);
rb_define_module_function(rb_mObSpace, "allocated_objects", os_allocated_objects, 0);
rb_define_module_function(rb_mObSpace, "define_finalizer", define_final, -1);
rb_define_module_function(rb_mObSpace, "undefine_finalizer", undefine_final, 1);
diff --git a/intern.h b/intern.h
index 78bf699..86b4395 100644
--- a/intern.h
+++ b/intern.h
@@ -274,6 +274,12 @@ void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
VALUE rb_gc_allocated_size _((void));
VALUE rb_gc_num_allocations _((void));
+unsigned long rb_os_live_objects _((void));
+#ifdef HAVE_LONG_LONG
+unsigned LONG_LONG rb_os_allocated_objects _((void));
+#else
+unsigned long rb_os_allocated_objects _((void));
+#endif
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.12.1.6. 12-fix-heap-size-growth-logic.patch
diff --git a/gc.c b/gc.c
index 21b3f6b..7db1ef6 100644
--- a/gc.c
+++ b/gc.c
@@ -694,6 +694,7 @@ static int heap_size = 0;
static
static
+static
static
int heap_free_min = 4096;
int heap_slots_increment = 10000;
int initial_heap_slots_increment = 10000;
double heap_slots_growth_factor = 1.8;
static long initial_malloc_limit = GC_MALLOC_LIMIT;
@@ -771,14 +772,13 @@ static void set_gc_parameters()
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
}
if (heap_slots_incr_i > 0) {
heap_slots_increment = heap_slots_incr_i;
}
+
heap_slots_increment = heap_slots_incr_i;
+
initial_heap_slots_increment = heap_slots_increment;
}
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
if (heap_slots_growth_factor_ptr != NULL) {
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
double heap_slots_growth_factor_d = atof(heap_slots_growth_factor_ptr);
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
}
@@ -988,8 +988,13 @@ add_heap()
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots += heap_slots_increment;
heap_slots_increment *= heap_slots_growth_factor;
+
if (heaps_used == 1)
+
heap_slots = initial_heap_slots_increment;
+
else {
+
heap_slots_increment *= heap_slots_growth_factor;
+
heap_slots += heap_slots_increment;
+
}
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
@@ -1879,6 +1884,7 @@ gc_sweep()
live_counts[i], free_counts[i], obj_type(i));
}
}
+
rb_gc_dump();
fflush(gc_data_file);
}
1.26.5.1.12.1.7. 02-fix-rcs-keyword-idiom.patch
diff --git a/lib/logger.rb b/lib/logger.rb
index 15d95fc..69f0d7b 100644
--- a/lib/logger.rb
+++ b/lib/logger.rb
@@ -171,7 +171,13 @@ require 'monitor'
class Logger
VERSION = "1.2.6"
id, name, rev = %w$Id$
- ProgName = "#{name.chomp(",v")}/#{rev}"
+ if name
+
name = name.chomp(",v")
+ else
+
name = File.basename(__FILE__)
+ end
+ rev ||= "v#{VERSION}"
+ ProgName = "#{name}/#{rev}"
class Error < RuntimeError; end
class ShiftingError < Error; end
1.26.5.1.12.1.8. 01-ignore-generated-files.patch
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..00c347a
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,95 @@
+.ext
+.installed.list
+.rbconfig.time
+Makefile
+autom4te.cache/
+config.h
+config.status
+configure
+ext/Win32API/Makefile
+ext/bigdecimal/Makefile
+ext/curses/Makefile
+ext/dbm/Makefile
+ext/digest/Makefile
+ext/digest/bubblebabble/Makefile
+ext/digest/md5/Makefile
+ext/digest/rmd160/Makefile
+ext/digest/sha1/Makefile
+ext/digest/sha2/Makefile
+ext/dl/Makefile
+ext/dl/call.func
+ext/dl/callback.func
+ext/dl/cbtable.func
+ext/dl/dlconfig.h
+ext/dl/dlconfig.rb
+ext/enumerator/Makefile
+ext/etc/Makefile
+ext/fcntl/Makefile
+ext/gdbm/Makefile
+ext/iconv/Makefile
+ext/io/wait/Makefile
+ext/nkf/Makefile
+ext/openssl/Makefile
+ext/openssl/extconf.h
+ext/pty/Makefile
+ext/racc/cparse/Makefile
+ext/readline/Makefile
+ext/sdbm/Makefile
+ext/socket/Makefile
+ext/stringio/Makefile
+ext/strscan/Makefile
+ext/syck/Makefile
+ext/syslog/Makefile
+ext/thread/Makefile
+ext/tk/Makefile
+ext/tk/tkutil/Makefile
+ext/win32ole/Makefile
+ext/win32ole/.document
+ext/zlib/Makefile
+largefile.h
+miniruby
+parse.c
+rbconfig.rb
+ruby
+enc.mk
+ext/bigdecimal/extconf.h
+ext/continuation/
+ext/coverage/
+ext/curses/extconf.h
+ext/dbm/extconf.h
+ext/digest/bubblebabble/extconf.h
+ext/digest/extconf.h
+ext/digest/md5/extconf.h
+ext/digest/rmd160/extconf.h
+ext/digest/sha1/extconf.h
+ext/digest/sha2/extconf.h
+ext/dl/callback.h
+ext/dl/extconf.h
+ext/etc/extconf.h
+ext/fcntl/extconf.h
+ext/fiber/
+ext/iconv/extconf.h
+ext/io/wait/extconf.h
+ext/json/
+ext/nkf/extconf.h
+ext/pty/extconf.h
+ext/racc/cparse/extconf.h
+ext/readline/extconf.h
+ext/ripper/
+ext/sdbm/extconf.h
+ext/socket/constants.h
+ext/socket/extconf.h
+ext/stringio/extconf.h
+ext/strscan/extconf.h
+ext/syck/extconf.h
+ext/syslog/extconf.h
+ext/tk/extconf.h
+ext/tk/tkutil/extconf.h
+ext/zlib/extconf.h
+miniprelude.c
+prelude.c
+revision.h
+*.dylib
+*.log
+*.dSYM
+patches-ruby*
1.26.5.1.12.1.9. 04-railsbench-gc-patch.patch
diff --git a/gc.c b/gc.c
index fa45cd1..ab71d22 100644
--- a/gc.c
+++ b/gc.c
@@ -22,8 +22,16 @@
#include <setjmp.h>
#include <sys/types.h>
+#ifdef _WIN32
+#include <string.h>
+#else
+#include <strings.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
+#elif defined(_WIN32)
+#include <time.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H
@@ -42,7 +50,6 @@ void rb_io_fptr_finalize _((struct rb_io_t*));
#ifdef __CYGWIN__
int _setjmp(), _longjmp();
#endif
/* Make alloca work the best possible way. */
#ifdef __GNUC__
# ifndef atarist
@@ -86,12 +93,12 @@ rb_memerror()
rb_thread_t th = rb_curr_thread;
if (!nomem_error ||
-(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
-fprintf(stderr, "[FATAL] failed to allocate memory\n");
-exit(1);
+
(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
+
fprintf(stderr, "[FATAL] failed to allocate memory\n");
+
exit(1);
}
if (rb_thread_raised_p(th, RAISED_NOMEMORY)) {
-rb_exc_jump(nomem_error);
+
rb_exc_jump(nomem_error);
}
rb_thread_raised_set(th, RAISED_NOMEMORY);
rb_exc_raise(nomem_error);
@@ -139,7 +146,7 @@ ruby_xmalloc(size)
void *mem;
if (size < 0) {
-rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
+
rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
}
if (size == 0) size = 1;
@@ -148,11 +155,11 @@ ruby_xmalloc(size)
}
RUBY_CRITICAL(mem = malloc(size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = malloc(size));
-if (!mem) {
rb_memerror();
-}
+
garbage_collect();
+
RUBY_CRITICAL(mem = malloc(size));
+
if (!mem) {
+
rb_memerror();
+
}
}
malloc_increase += size;
@@ -179,17 +186,17 @@ ruby_xrealloc(ptr, size)
void *mem;
if (size < 0) {
-rb_raise(rb_eArgError, "negative re-allocation size");
+
rb_raise(rb_eArgError, "negative re-allocation size");
}
if (!ptr) return xmalloc(size);
if (size == 0) size = 1;
if (ruby_gc_stress) garbage_collect();
RUBY_CRITICAL(mem = realloc(ptr, size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = realloc(ptr, size));
-if (!mem) {
rb_memerror();
+
garbage_collect();
+
RUBY_CRITICAL(mem = realloc(ptr, size));
+
if (!mem) {
+
rb_memerror();
}
}
malloc_increase += size;
@@ -202,11 +209,20 @@ ruby_xfree(x)
void *x;
{
if (x)
-RUBY_CRITICAL(free(x));
+
RUBY_CRITICAL(free(x));
}
+#if HAVE_LONG_LONG
+#define GC_TIME_TYPE LONG_LONG
+#else
+#define GC_TIME_TYPE long
+#endif
+
extern int ruby_in_compile;
static int dont_gc;
+static int gc_statistics = 0;
+static GC_TIME_TYPE gc_time = 0;
+static int gc_collections = 0;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -241,7 +257,7 @@ rb_gc_enable()
* Disables garbage collection, returning <code>true</code> if garbage
* collection was already disabled.
*
- *
GC.disable
#=> false
+ *
GC.disable
#=> false or true
*
GC.disable
#=> true
*
*/
@@ -255,6 +271,104 @@ rb_gc_disable()
return old;
}
+/*
+ * call-seq:
+ *
GC.enable_stats
=> true or false
+ *
+ * Enables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already enabled.
+ *
+ *
GC.enable_stats
#=> false or true
+ *
GC.enable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_stats
=> true or false
+ *
+ * Disables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already disabled.
+ *
+ *
GC.disable_stats
#=> false or true
+ *
GC.disable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qfalse;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.clear_stats
=> nil
+ *
+ * Clears garbage collection statistics, returning nil. This resets the number
+ * of collections (GC.collections) and the time used (GC.time) to 0.
+ *
+ *
GC.clear_stats
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_clear_stats()
+{
+
gc_collections = 0;
+
gc_time = 0;
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.collections
=> Integer
+ *
+ * Returns the number of garbage collections performed while GC statistics collection
+ * was enabled.
+ *
+ *
GC.collections
#=> 35
+ *
+ */
+
+VALUE
+rb_gc_collections()
+{
+
return INT2NUM(gc_collections);
+}
+
+/*
+ * call-seq:
+ *
GC.time
=> Integer
+ *
+ * Returns the time spent during garbage collection while GC statistics collection
+ * was enabled (in micro seconds).
+ *
+ *
GC.time
#=> 20000
+ *
+ */
+
+VALUE
+rb_gc_time()
+{
+#if HAVE_LONG_LONG
+
return LL2NUM(gc_time);
+#else
+
return LONG2NUM(gc_time);
+#endif
+}
+
+
VALUE rb_mGC;
static struct gc_list {
@@ -281,19 +395,19 @@ rb_gc_unregister_address(addr)
struct gc_list *tmp = global_List;
if (tmp->varptr == addr) {
-global_List = tmp->next;
-RUBY_CRITICAL(free(tmp));
-return;
+
global_List = tmp->next;
+
RUBY_CRITICAL(free(tmp));
+
return;
}
while (tmp->next) {
-if (tmp->next->varptr == addr) {
struct gc_list *t = tmp->next;
+
if (tmp->next->varptr == addr) {
+
struct gc_list *t = tmp->next;
-}
-tmp
+
+
+
+
+
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
= tmp->next;
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
}
tmp = tmp->next;
}
}
@@ -312,26 +426,26 @@ rb_global_variable(var)
typedef struct RVALUE {
union {
-struct {
unsigned long flags;/* always 0 for freed obj */
struct RVALUE *next;
-} free;
-struct RBasic basic;
-struct RObject object;
-struct RClass klass;
-struct RFloat flonum;
-struct RString string;
-struct RArray array;
-struct RRegexp regexp;
-struct RHash
hash;
-struct RData
data;
-struct RStruct rstruct;
-struct RBignum bignum;
-struct RFile
file;
-struct RNode
node;
-struct RMatch match;
-struct RVarmap varmap;
-struct SCOPE
scope;
+
struct {
+
unsigned long flags;
/* always 0 for freed obj */
+
struct RVALUE *next;
+
} free;
+
struct RBasic basic;
+
struct RObject object;
+
struct RClass klass;
+
struct RFloat flonum;
+
struct RString string;
+
struct RArray array;
+
struct RRegexp regexp;
+
struct RHash
hash;
+
struct RData
data;
+
struct RStruct rstruct;
+
struct RBignum bignum;
+
struct RFile
file;
+
struct RNode
node;
+
struct RMatch match;
+
struct RVarmap varmap;
+
struct SCOPE
scope;
} as;
#ifdef GC_DEBUG
char *file;
@@ -346,7 +460,7 @@ typedef struct RVALUE {
static RVALUE *freelist = 0;
static RVALUE *deferred_final_list = 0;
-#define HEAPS_INCREMENT 10
+static int heaps_increment = 10;
static struct heaps_slot {
void *membase;
RVALUE *slot;
@@ -355,45 +469,197 @@ static struct heaps_slot {
static int heaps_length = 0;
static int heaps_used
= 0;
-#define HEAP_MIN_SLOTS 10000
-static int heap_slots = HEAP_MIN_SLOTS;
+static int heap_min_slots = 10000;
+static int heap_slots = 10000;
-#define FREE_MIN 4096
+static int heap_free_min = 4096;
+static int heap_slots_increment = 10000;
+static double heap_slots_growth_factor = 1.8;
+
+static long initial_malloc_limit = GC_MALLOC_LIMIT;
+
+static int verbose_gc_stats = Qfalse;
+
+static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
+static void set_gc_parameters()
+{
+
char *gc_stats_ptr, *min_slots_ptr, *free_min_ptr, *heap_slots_incr_ptr,
+
*heap_incr_ptr, *malloc_limit_ptr, *gc_heap_file_ptr, *heap_slots_growth_factor_ptr;
+
+
gc_data_file = stderr;
+
+
gc_stats_ptr = getenv("RUBY_GC_STATS");
+
if (gc_stats_ptr != NULL) {
+
int gc_stats_i = atoi(gc_stats_ptr);
+
if (gc_stats_i > 0) {
+
verbose_gc_stats = Qtrue;
+
}
+
}
+
+
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
+
if (gc_heap_file_ptr != NULL) {
+
FILE* data_file = fopen(gc_heap_file_ptr, "w");
+
if (data_file != NULL) {
+
gc_data_file = data_file;
+
}
+
else {
+
fprintf(stderr,
+
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
+
}
+
}
+
+
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
+
if (min_slots_ptr != NULL) {
+
int min_slots_i = atoi(min_slots_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_MIN_SLOTS=%s\n", min_slots_ptr);
+
}
+
if (min_slots_i > 0) {
+
heap_slots = min_slots_i;
+
heap_min_slots = min_slots_i;
+
}
+
}
+
+
free_min_ptr = getenv("RUBY_HEAP_FREE_MIN");
+
if (free_min_ptr != NULL) {
+
int free_min_i = atoi(free_min_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_FREE_MIN=%s\n", free_min_ptr);
+
}
+
if (free_min_i > 0) {
+
heap_free_min = free_min_i;
+
}
+
}
+
+
heap_incr_ptr = getenv("RUBY_HEAP_INCREMENT");
+
if (heap_incr_ptr != NULL) {
+
int heap_incr_i = atoi(heap_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_INCREMENT=%s\n", heap_incr_ptr);
+
}
+
if (heap_incr_i > 0) {
+
heaps_increment = heap_incr_i;
+
}
+
}
+
+
heap_slots_incr_ptr = getenv("RUBY_HEAP_SLOTS_INCREMENT");
+
if (heap_slots_incr_ptr != NULL) {
+
int heap_slots_incr_i = atoi(heap_slots_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
+
}
+
if (heap_slots_incr_i > 0) {
+
heap_slots_increment = heap_slots_incr_i;
+
}
+
}
+
+
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
+
if (heap_slots_growth_factor_ptr != NULL) {
+
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
+
}
+
if (heap_slots_growth_factor_d > 0) {
+
heap_slots_growth_factor = heap_slots_growth_factor_d;
+
}
+
}
+
+
malloc_limit_ptr = getenv("RUBY_GC_MALLOC_LIMIT");
+
if (malloc_limit_ptr != NULL) {
+
int malloc_limit_i = atol(malloc_limit_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_GC_MALLOC_LIMIT=%s\n", malloc_limit_ptr);
+
}
+
if (malloc_limit_i > 0) {
+
initial_malloc_limit = malloc_limit_i;
+
}
+
}
+}
+
+/*
+ * call-seq:
+ *
GC.dump
=> nil
+ *
+ * dumps information about the current GC data structures to the GC log file
+ *
+ *
GC.dump
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_dump()
+{
+
int i;
+
+
for (i = 0; i < heaps_used; i++) {
+
int heap_size = heaps[i].limit;
+
fprintf(gc_data_file, "HEAP[%2d]: size=%7d\n", i, heap_size);
+
}
+
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.log String => String
+ *
+ * Logs string to the GC data file and returns it.
+ *
+ *
GC.log "manual GC call"
#=> "manual GC call"
+ *
+ */
+
+VALUE
+rb_gc_log(self, original_str)
+
VALUE self, original_str;
+{
+
if (original_str == Qnil) {
+
fprintf(gc_data_file, "\n");
+
}
+
else {
+
VALUE str = StringValue(original_str);
+
char *p = RSTRING(str)->ptr;
+
fprintf(gc_data_file, "%s\n", p);
+
}
+
return original_str;
+}
+
+
static void
add_heap()
{
RVALUE *p, *pend;
if (heaps_used == heaps_length) {
-/* Realloc heaps */
-struct heaps_slot *p;
-int length;
-heaps_length += HEAPS_INCREMENT;
-length = heaps_length*sizeof(struct heaps_slot);
-RUBY_CRITICAL(
if (heaps_used > 0) {
-p = (struct heaps_slot *)realloc(heaps, length);
-if (p) heaps = p;
}
else {
-p = heaps = (struct heaps_slot *)malloc(length);
});
-if (p == 0) rb_memerror();
+
/* Realloc heaps */
+
struct heaps_slot *p;
+
int length;
+
+
heaps_length += heaps_increment;
+
length = heaps_length*sizeof(struct heaps_slot);
+
RUBY_CRITICAL(
+
if (heaps_used > 0) {
+
p = (struct heaps_slot *)realloc(heaps, length);
+
if (p) heaps = p;
+
}
+
else {
+
p = heaps = (struct heaps_slot *)malloc(length);
+
});
+
if (p == 0) rb_memerror();
}
for (;;) {
-RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
-if (p == 0) {
if (heap_slots == HEAP_MIN_SLOTS) {
-rb_memerror();
}
heap_slots = HEAP_MIN_SLOTS;
continue;
-}
+
RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
+
if (p == 0) {
+
if (heap_slots == heap_min_slots) {
+
rb_memerror();
+
}
+
heap_slots = heap_min_slots;
+
continue;
+
}
heaps[heaps_used].membase = p;
if ((VALUE)p % sizeof(RVALUE) == 0)
heap_slots += 1;
@@ -401,25 +667,26 @@ add_heap()
p = (RVALUE*)((VALUE)p + sizeof(RVALUE) - ((VALUE)p % sizeof(RVALUE)));
heaps[heaps_used].slot = p;
heaps[heaps_used].limit = heap_slots;
-break;
+
break;
}
pend = p + heap_slots;
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots *= 1.8;
if (heap_slots <= 0) heap_slots = HEAP_MIN_SLOTS;
+
heap_slots += heap_slots_increment;
+
heap_slots_increment *= heap_slots_growth_factor;
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
-p->as.free.flags = 0;
-p->as.free.next = freelist;
-freelist = p;
-p++;
+
p->as.free.flags = 0;
+
p->as.free.next = freelist;
+
freelist = p;
+
p++;
}
}
#define RANY(o) ((RVALUE*)(o))
-int
+int
rb_during_gc()
{
return during_gc;
@@ -431,7 +698,7 @@ rb_newobj()
VALUE obj;
if (during_gc)
-rb_bug("object allocation during garbage collection phase");
+
rb_bug("object allocation during garbage collection phase");
if (ruby_gc_stress || !freelist) garbage_collect();
@@ -580,13 +847,13 @@ rb_source_filename(f)
st_data_t name;
if (!st_lookup(source_filenames, (st_data_t)f, &name)) {
-long len = strlen(f) + 1;
-char *ptr = ALLOC_N(char, len + 1);
-name = (st_data_t)ptr;
-*ptr++ = 0;
-MEMCPY(ptr, f, char, len);
-st_add_direct(source_filenames, (st_data_t)ptr, name);
-return ptr;
+
long len = strlen(f) + 1;
+
char *ptr = ALLOC_N(char, len + 1);
+
name = (st_data_t)ptr;
+
*ptr++ = 0;
+
MEMCPY(ptr, f, char, len);
+
st_add_direct(source_filenames, (st_data_t)ptr, name);
+
return ptr;
}
return (char *)name + 1;
}
@@ -596,7 +863,7 @@ mark_source_filename(f)
char *f;
{
if (f) {
-f[-1] = 1;
+
f[-1] = 1;
}
}
@@ -605,12 +872,12 @@ sweep_source_filename(key, value)
char *key, *value;
{
if (*value) {
-*value = 0;
-return ST_CONTINUE;
+
*value = 0;
+
return ST_CONTINUE;
}
else {
-free(value);
-return ST_DELETE;
+
free(value);
+
return ST_DELETE;
}
}
@@ -625,14 +892,14 @@ gc_mark_all()
init_mark_stack();
for (i = 0; i < heaps_used; i++) {
-p = heaps[i].slot; pend = p + heaps[i].limit;
-while (p < pend) {
if ((p->as.basic.flags & FL_MARK) &&
-(p->as.basic.flags != FL_MARK)) {
-gc_mark_children((VALUE)p, 0);
}
p++;
-}
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
while (p < pend) {
+
if ((p->as.basic.flags & FL_MARK) &&
+
(p->as.basic.flags != FL_MARK)) {
+
gc_mark_children((VALUE)p, 0);
+
}
+
p++;
+
}
}
}
@@ -647,8 +914,8 @@ gc_mark_rest()
init_mark_stack();
while(p != tmp_arry){
-p--;
-gc_mark_children(*p, 0);
+
+
p--;
gc_mark_children(*p, 0);
}
}
@@ -665,9 +932,9 @@ is_pointer_to_heap(ptr)
/* check if p looks like a pointer */
for (i=0; i < heaps_used; i++) {
-heap_org = heaps[i].slot;
-if (heap_org <= p && p < heap_org + heaps[i].limit)
return Qtrue;
+
heap_org = heaps[i].slot;
+
if (heap_org <= p && p < heap_org + heaps[i].limit)
+
return Qtrue;
}
return Qfalse;
}
@@ -680,10 +947,10 @@ mark_locations_array(x, n)
VALUE v;
while (n--) {
v = *x;
-if (is_pointer_to_heap((void *)v)) {
gc_mark(v, 0);
-}
-x++;
+
if (is_pointer_to_heap((void *)v)) {
+
gc_mark(v, 0);
+
}
+
x++;
}
}
@@ -780,7 +1047,7 @@ rb_gc_mark_maybe(obj)
VALUE obj;
{
if (is_pointer_to_heap((void *)obj)) {
-gc_mark(obj, 0);
+
gc_mark(obj, 0);
}
}
@@ -828,7 +1095,7 @@ gc_mark_children(ptr, lev)
{
register RVALUE *obj = RANY(ptr);
+
goto marking;/* skip */
goto marking;
/* skip */
again:
obj = RANY(ptr);
@@ -839,148 +1106,148 @@ gc_mark_children(ptr, lev)
marking:
if (FL_TEST(obj, FL_EXIVAR)) {
-rb_mark_generic_ivar(ptr);
+
rb_mark_generic_ivar(ptr);
}
switch (obj->as.basic.flags & T_MASK) {
case T_NIL:
case T_FIXNUM:
-rb_bug("rb_gc_mark() called for broken object");
-break;
+
rb_bug("rb_gc_mark() called for broken object");
+
break;
case T_NODE:
-mark_source_filename(obj->as.node.nd_file);
-switch (nd_type(obj)) {
- case NODE_IF:/* 1,2,3 */
- case NODE_FOR:
- case NODE_ITER:
- case NODE_CREF:
- case NODE_WHEN:
- case NODE_MASGN:
- case NODE_RESCUE:
- case NODE_RESBODY:
- case NODE_CLASS:
gc_mark((VALUE)obj->as.node.u2.node, lev);
/* fall through */
- case NODE_BLOCK:/* 1,3 */
- case NODE_ARRAY:
- case NODE_DSTR:
- case NODE_DXSTR:
- case NODE_DREGX:
- case NODE_DREGX_ONCE:
- case NODE_FBODY:
- case NODE_ENSURE:
- case NODE_CALL:
- case NODE_DEFS:
- case NODE_OP_ASGN1:
gc_mark((VALUE)obj->as.node.u1.node, lev);
/* fall through */
- case NODE_SUPER:/* 3 */
- case NODE_FCALL:
- case NODE_DEFN:
- case NODE_NEWLINE:
ptr = (VALUE)obj->as.node.u3.node;
goto again;
- case NODE_WHILE:/* 1,2 */
- case NODE_UNTIL:
- case NODE_AND:
- case NODE_OR:
- case NODE_CASE:
- case NODE_SCLASS:
- case NODE_DOT2:
- case NODE_DOT3:
- case NODE_FLIP2:
- case NODE_FLIP3:
- case NODE_MATCH2:
- case NODE_MATCH3:
- case NODE_OP_ASGN_OR:
- case NODE_OP_ASGN_AND:
- case NODE_MODULE:
- case NODE_ALIAS:
- case NODE_VALIAS:
- case NODE_ARGS:
gc_mark((VALUE)obj->as.node.u1.node, lev);
/* fall through */
- case NODE_METHOD:/* 2 */
- case NODE_NOT:
- case NODE_GASGN:
- case NODE_LASGN:
- case NODE_DASGN:
- case NODE_DASGN_CURR:
- case NODE_IASGN:
- case NODE_CVDECL:
- case NODE_CVASGN:
- case NODE_COLON3:
- case NODE_OPT_N:
- case NODE_EVSTR:
- case NODE_UNDEF:
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- case NODE_HASH:/* 1 */
- case NODE_LIT:
- case NODE_STR:
- case NODE_XSTR:
- case NODE_DEFINED:
- case NODE_MATCH:
- case NODE_RETURN:
- case NODE_BREAK:
- case NODE_NEXT:
- case NODE_YIELD:
- case NODE_COLON2:
- case NODE_SPLAT:
- case NODE_TO_ARY:
- case NODE_SVALUE:
ptr = (VALUE)obj->as.node.u1.node;
goto again;
- case NODE_SCOPE:/* 2,3 */
- case NODE_BLOCK_PASS:
- case NODE_CDECL:
gc_mark((VALUE)obj->as.node.u3.node, lev);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- case NODE_ZARRAY:/* - */
- case NODE_ZSUPER:
- case NODE_CFUNC:
- case NODE_VCALL:
- case NODE_GVAR:
- case NODE_LVAR:
- case NODE_DVAR:
- case NODE_IVAR:
- case NODE_CVAR:
- case NODE_NTH_REF:
- case NODE_BACK_REF:
- case NODE_REDO:
- case NODE_RETRY:
- case NODE_SELF:
- case NODE_NIL:
- case NODE_TRUE:
- case NODE_FALSE:
- case NODE_ATTRSET:
- case NODE_BLOCK_ARG:
- case NODE_POSTEXE:
break;
- case NODE_ALLOCA:
mark_locations_array((VALUE*)obj->as.node.u1.value,
- obj->as.node.u3.cnt);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
- default:/* unlisted NODE */
if (is_pointer_to_heap(obj->as.node.u1.node)) {
-gc_mark((VALUE)obj->as.node.u1.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u2.node)) {
-gc_mark((VALUE)obj->as.node.u2.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u3.node)) {
-gc_mark((VALUE)obj->as.node.u3.node, lev);
}
-}
-return;/* no need to mark class. */
+
mark_source_filename(obj->as.node.nd_file);
+
switch (nd_type(obj)) {
+
case NODE_IF:
/* 1,2,3 */
+
case NODE_FOR:
+
case NODE_ITER:
+
case NODE_CREF:
+
case NODE_WHEN:
+
case NODE_MASGN:
+
case NODE_RESCUE:
+
case NODE_RESBODY:
+
case NODE_CLASS:
+
gc_mark((VALUE)obj->as.node.u2.node, lev);
+
/* fall through */
+
case NODE_BLOCK:
/* 1,3 */
+
case NODE_ARRAY:
+
case NODE_DSTR:
+
case NODE_DXSTR:
+
case NODE_DREGX:
+
case NODE_DREGX_ONCE:
+
case NODE_FBODY:
+
case NODE_ENSURE:
+
case NODE_CALL:
+
case NODE_DEFS:
+
case NODE_OP_ASGN1:
+
gc_mark((VALUE)obj->as.node.u1.node, lev);
+
/* fall through */
+
case NODE_SUPER:
/* 3 */
+
case NODE_FCALL:
+
case NODE_DEFN:
+
case NODE_NEWLINE:
+
ptr = (VALUE)obj->as.node.u3.node;
+
goto again;
+
+
case NODE_WHILE:
/* 1,2 */
+
case NODE_UNTIL:
+
case NODE_AND:
+
case NODE_OR:
+
case NODE_CASE:
+
case NODE_SCLASS:
+
case NODE_DOT2:
+
case NODE_DOT3:
+
case NODE_FLIP2:
+
case NODE_FLIP3:
+
case NODE_MATCH2:
+
case NODE_MATCH3:
+
case NODE_OP_ASGN_OR:
+
case NODE_OP_ASGN_AND:
+
case NODE_MODULE:
+
case NODE_ALIAS:
+
case NODE_VALIAS:
+
case NODE_ARGS:
+
gc_mark((VALUE)obj->as.node.u1.node, lev);
+
/* fall through */
+
case NODE_METHOD:
/* 2 */
+
case NODE_NOT:
+
case NODE_GASGN:
+
case NODE_LASGN:
+
case NODE_DASGN:
+
case NODE_DASGN_CURR:
+
case NODE_IASGN:
+
case NODE_CVDECL:
+
case NODE_CVASGN:
+
case NODE_COLON3:
+
case NODE_OPT_N:
+
case NODE_EVSTR:
+
case NODE_UNDEF:
+
ptr = (VALUE)obj->as.node.u2.node;
+
goto again;
+
+
case NODE_HASH:
/* 1 */
+
case NODE_LIT:
+
case NODE_STR:
+
case NODE_XSTR:
+
case NODE_DEFINED:
+
case NODE_MATCH:
+
case NODE_RETURN:
+
case NODE_BREAK:
+
case NODE_NEXT:
+
case NODE_YIELD:
+
case NODE_COLON2:
+
case NODE_SPLAT:
+
case NODE_TO_ARY:
+
case NODE_SVALUE:
+
ptr = (VALUE)obj->as.node.u1.node;
+
goto again;
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
case NODE_SCOPE:
/* 2,3 */
case NODE_BLOCK_PASS:
case NODE_CDECL:
gc_mark((VALUE)obj->as.node.u3.node, lev);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
case NODE_ZARRAY:
/* - */
case NODE_ZSUPER:
case NODE_CFUNC:
case NODE_VCALL:
case NODE_GVAR:
case NODE_LVAR:
case NODE_DVAR:
case NODE_IVAR:
case NODE_CVAR:
case NODE_NTH_REF:
case NODE_BACK_REF:
case NODE_REDO:
case NODE_RETRY:
case NODE_SELF:
case NODE_NIL:
case NODE_TRUE:
case NODE_FALSE:
case NODE_ATTRSET:
case NODE_BLOCK_ARG:
case NODE_POSTEXE:
break;
case NODE_ALLOCA:
mark_locations_array((VALUE*)obj->as.node.u1.value,
obj->as.node.u3.cnt);
ptr = (VALUE)obj->as.node.u2.node;
goto again;
default:
/* unlisted NODE */
if (is_pointer_to_heap(obj->as.node.u1.node)) {
gc_mark((VALUE)obj->as.node.u1.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u2.node)) {
gc_mark((VALUE)obj->as.node.u2.node, lev);
}
if (is_pointer_to_heap(obj->as.node.u3.node)) {
gc_mark((VALUE)obj->as.node.u3.node, lev);
}
}
return;
/* no need to mark class. */
}
gc_mark(obj->as.basic.klass, lev);
@@ -988,92 +1255,92 @@ gc_mark_children(ptr, lev)
case T_ICLASS:
case T_CLASS:
case T_MODULE:
-mark_tbl(obj->as.klass.m_tbl, lev);
-mark_tbl(obj->as.klass.iv_tbl, lev);
-ptr = obj->as.klass.super;
-goto again;
+
mark_tbl(obj->as.klass.m_tbl, lev);
+
mark_tbl(obj->as.klass.iv_tbl, lev);
+
ptr = obj->as.klass.super;
+
goto again;
case T_ARRAY:
-if (FL_TEST(obj, ELTS_SHARED)) {
ptr = obj->as.array.aux.shared;
goto again;
-}
-else {
long i, len = obj->as.array.len;
VALUE *ptr = obj->as.array.ptr;
+
if (FL_TEST(obj, ELTS_SHARED)) {
+
ptr = obj->as.array.aux.shared;
+
goto again;
+
}
+
else {
+
long i, len = obj->as.array.len;
+
VALUE *ptr = obj->as.array.ptr;
for (i=0; i
-gc_mark(*ptr++,
}
-}
-break;
+
for
+
+
}
+
}
+
break;
< len; i++) {
lev);
(i=0; i < len; i++) {
gc_mark(*ptr++, lev);
case T_HASH:
-mark_hash(obj->as.hash.tbl, lev);
-ptr = obj->as.hash.ifnone;
-goto again;
+
mark_hash(obj->as.hash.tbl, lev);
+
+
ptr = obj->as.hash.ifnone;
goto again;
case T_STRING:
#define STR_ASSOC FL_USER3
/* copied from string.c */
-if (FL_TEST(obj, ELTS_SHARED|STR_ASSOC)) {
ptr = obj->as.string.aux.shared;
goto again;
-}
-break;
+
if (FL_TEST(obj, ELTS_SHARED|STR_ASSOC)) {
+
ptr = obj->as.string.aux.shared;
+
goto again;
+
}
+
break;
case T_DATA:
-if (obj->as.data.dmark) (*obj->as.data.dmark)(DATA_PTR(obj));
-break;
+
if (obj->as.data.dmark) (*obj->as.data.dmark)(DATA_PTR(obj));
+
break;
case T_OBJECT:
-mark_tbl(obj->as.object.iv_tbl, lev);
-break;
+
mark_tbl(obj->as.object.iv_tbl, lev);
+
break;
case
case
case
case
case
-break;
+
T_FILE:
T_REGEXP:
T_FLOAT:
T_BIGNUM:
T_BLKTAG:
break;
case T_MATCH:
-if (obj->as.match.str) {
ptr = obj->as.match.str;
goto again;
-}
-break;
+
if (obj->as.match.str) {
+
ptr = obj->as.match.str;
+
goto again;
+
}
+
break;
case T_VARMAP:
-gc_mark(obj->as.varmap.val, lev);
-ptr = (VALUE)obj->as.varmap.next;
-goto again;
+
gc_mark(obj->as.varmap.val, lev);
+
ptr = (VALUE)obj->as.varmap.next;
+
goto again;
case T_SCOPE:
-if (obj->as.scope.local_vars && (obj->as.scope.flags & SCOPE_MALLOC)) {
int n = obj->as.scope.local_tbl[0]+1;
VALUE *vars = &obj->as.scope.local_vars[-1];
+
if (obj->as.scope.local_vars && (obj->as.scope.flags & SCOPE_MALLOC)) {
+
int n = obj->as.scope.local_tbl[0]+1;
+
VALUE *vars = &obj->as.scope.local_vars[-1];
while (n--) {
-gc_mark(*vars++, lev);
}
-}
-break;
+
while (n--) {
+
gc_mark(*vars++, lev);
+
}
+
}
+
break;
case T_STRUCT:
-{
+
+
+
long len = obj->as.rstruct.len;
VALUE *ptr = obj->as.rstruct.ptr;
{
long len = obj->as.rstruct.len;
VALUE *ptr = obj->as.rstruct.ptr;
while (len--) {
-gc_mark(*ptr++, lev);
}
-}
-break;
+
while (len--) {
+
gc_mark(*ptr++, lev);
+
}
+
}
+
break;
default:
-rb_bug("rb_gc_mark(): unknown data type 0x%lx(0x%lx) %s",
obj->as.basic.flags & T_MASK, obj,
is_pointer_to_heap(obj) ? "corrupted object" : "non object");
+
rb_bug("rb_gc_mark(): unknown data type 0x%lx(0x%lx) %s",
+
obj->as.basic.flags & T_MASK, obj,
+
is_pointer_to_heap(obj) ? "corrupted object" : "non object");
}
}
@@ -1102,22 +1369,55 @@ finalize_list(p)
}
}
+static char* obj_type(int tp)
+{
+
switch (tp) {
+
case T_NIL
: return "NIL";
+
case T_OBJECT : return "OBJECT";
+
case T_CLASS : return "CLASS";
+
case T_ICLASS : return "ICLASS";
+
case T_MODULE : return "MODULE";
+
case T_FLOAT : return "FLOAT";
+
case T_STRING : return "STRING";
+
case T_REGEXP : return "REGEXP";
+
case T_ARRAY : return "ARRAY";
+
case T_FIXNUM : return "FIXNUM";
+
case T_HASH
: return "HASH";
+
case T_STRUCT : return "STRUCT";
+
case T_BIGNUM : return "BIGNUM";
+
case T_FILE
: return "FILE";
+
+
case T_TRUE
: return "TRUE";
+
case T_FALSE : return "FALSE";
+
case T_DATA
: return "DATA";
+
case T_MATCH : return "MATCH";
+
case T_SYMBOL : return "SYMBOL";
+
+
case T_BLKTAG : return "BLKTAG";
+
case T_UNDEF : return "UNDEF";
+
case T_VARMAP : return "VARMAP";
+
case T_SCOPE : return "SCOPE";
+
case T_NODE
: return "NODE";
+
default: return "____";
+
}
+}
+
static void
free_unused_heaps()
{
int i, j;
for (i = j = 1; j < heaps_used; i++) {
-if (heaps[i].limit == 0) {
free(heaps[i].membase);
heaps_used--;
-}
-else {
if (i != j) {
-heaps[j] = heaps[i];
}
j++;
-}
+
if (heaps[i].limit == 0) {
+
free(heaps[i].membase);
+
heaps_used--;
+
}
+
else {
+
if (i != j) {
+
heaps[j] = heaps[i];
+
}
+
j++;
+
}
}
}
@@ -1134,24 +1434,33 @@ gc_sweep()
unsigned long live = 0;
unsigned long free_min = 0;
+
+
+
+
+
+
+
+
+
+
unsigned long really_freed = 0;
int free_counts[256];
int live_counts[256];
int do_gc_stats = gc_statistics & verbose_gc_stats;
for (i = 0; i < heaps_used; i++) {
free_min += heaps[i].limit;
}
free_min = free_min * 0.2;
if (free_min < FREE_MIN)
free_min = FREE_MIN;
if (free_min < heap_free_min)
free_min = heap_free_min;
if (do_gc_stats) {
for (i = 0 ; i< 256; i++) { free_counts[i] = live_counts[i] = 0; }
+
}
if (ruby_in_compile && ruby_parser_stack_on_heap()) {
-/* should not reclaim nodes during compilation
+
/* should not reclaim nodes during compilation
if yacc's semantic stack is not allocated on machine stack */
-for (i = 0; i < heaps_used; i++) {
p = heaps[i].slot; pend = p + heaps[i].limit;
while (p < pend) {
-if (!(p->as.basic.flags&FL_MARK) && BUILTIN_TYPE(p) == T_NODE)
gc_mark((VALUE)p, 0);
-p++;
}
-}
+
for (i = 0; i < heaps_used; i++) {
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
while (p < pend) {
+
if (!(p->as.basic.flags&FL_MARK) && BUILTIN_TYPE(p) == T_NODE)
+
gc_mark((VALUE)p, 0);
+
p++;
+
}
+
}
}
mark_source_filename(ruby_sourcefile);
@@ -1172,7 +1481,7 @@ gc_sweep()
while (p < pend) {
if (!(p->as.basic.flags & FL_MARK)) {
if (p->as.basic.flags &&
((deferred = obj_free((VALUE)p)) ||
+
(((do_gc_stats && really_freed++), deferred = obj_free((VALUE)p)) ||
((FL_TEST(p, FL_FINALIZE)) && need_call_final))) {
if (!deferred) {
p->as.free.flags = T_DEFERRED;
@@ -1183,6 +1492,12 @@ gc_sweep()
final_list = p;
}
else {
+
if (do_gc_stats) {
+
int obt = p->as.basic.flags & T_MASK;
+
if (obt) {
+
free_counts[obt]++;
+
}
+
}
add_freelist(p);
}
n++;
@@ -1194,6 +1509,9 @@ gc_sweep()
else {
RBASIC(p)->flags &= ~FL_MARK;
live++;
+
if (do_gc_stats) {
+
live_counts[RANY((VALUE)p)->as.basic.flags & T_MASK]++;
+
}
}
p++;
}
@@ -1211,15 +1529,29 @@ gc_sweep()
}
}
if (malloc_increase > malloc_limit) {
-malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
-if (malloc_limit < GC_MALLOC_LIMIT) malloc_limit = GC_MALLOC_LIMIT;
+
malloc_limit += (malloc_increase - malloc_limit) * (double)live / (live + freed);
+
if (malloc_limit < initial_malloc_limit) malloc_limit = initial_malloc_limit;
}
malloc_increase = 0;
if (freed < free_min) {
-add_heap();
+
add_heap();
}
during_gc = 0;
+
+
+
+
+
+
+
+
+
+
+
+
+
+
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7d\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0 || live_counts[i]>0) {
fprintf(gc_data_file,
"kept %.7d / freed %.7d objects of type %s\n",
live_counts[i], free_counts[i], obj_type(i));
}
}
}
/* clear finalization list */
if (final_list) {
deferred_final_list = final_list;
@@ -1260,51 +1592,51 @@ obj_free(obj)
case T_FIXNUM:
case T_TRUE:
case T_FALSE:
-rb_bug("obj_free() called for broken object");
-break;
+
+
}
rb_bug("obj_free() called for broken object");
break;
if (FL_TEST(obj, FL_EXIVAR)) {
-rb_free_generic_ivar((VALUE)obj);
+
rb_free_generic_ivar((VALUE)obj);
}
switch (BUILTIN_TYPE(obj)) {
case T_OBJECT:
-if (RANY(obj)->as.object.iv_tbl) {
st_free_table(RANY(obj)->as.object.iv_tbl);
-}
-break;
+
if (RANY(obj)->as.object.iv_tbl) {
+
st_free_table(RANY(obj)->as.object.iv_tbl);
+
}
+
break;
case T_MODULE:
case T_CLASS:
-rb_clear_cache_by_class((VALUE)obj);
-st_free_table(RANY(obj)->as.klass.m_tbl);
-if (RANY(obj)->as.object.iv_tbl) {
st_free_table(RANY(obj)->as.object.iv_tbl);
-}
-break;
+
rb_clear_cache_by_class((VALUE)obj);
+
st_free_table(RANY(obj)->as.klass.m_tbl);
+
if (RANY(obj)->as.object.iv_tbl) {
+
st_free_table(RANY(obj)->as.object.iv_tbl);
+
}
+
break;
case T_STRING:
-if (RANY(obj)->as.string.ptr && !FL_TEST(obj, ELTS_SHARED)) {
RUBY_CRITICAL(free(RANY(obj)->as.string.ptr));
-}
-break;
+
if (RANY(obj)->as.string.ptr && !FL_TEST(obj, ELTS_SHARED)) {
+
RUBY_CRITICAL(free(RANY(obj)->as.string.ptr));
+
}
+
break;
case T_ARRAY:
-if (RANY(obj)->as.array.ptr && !FL_TEST(obj, ELTS_SHARED)) {
RUBY_CRITICAL(free(RANY(obj)->as.array.ptr));
-}
-break;
+
if (RANY(obj)->as.array.ptr && !FL_TEST(obj, ELTS_SHARED)) {
+
RUBY_CRITICAL(free(RANY(obj)->as.array.ptr));
+
}
+
break;
case T_HASH:
-if (RANY(obj)->as.hash.tbl) {
st_free_table(RANY(obj)->as.hash.tbl);
-}
-break;
+
if (RANY(obj)->as.hash.tbl) {
+
st_free_table(RANY(obj)->as.hash.tbl);
+
}
+
break;
case T_REGEXP:
-if (RANY(obj)->as.regexp.ptr) {
re_free_pattern(RANY(obj)->as.regexp.ptr);
-}
-if (RANY(obj)->as.regexp.str) {
RUBY_CRITICAL(free(RANY(obj)->as.regexp.str));
-}
-break;
+
if (RANY(obj)->as.regexp.ptr) {
+
re_free_pattern(RANY(obj)->as.regexp.ptr);
+
}
+
if (RANY(obj)->as.regexp.str) {
+
RUBY_CRITICAL(free(RANY(obj)->as.regexp.str));
+
}
+
break;
case T_DATA:
if (DATA_PTR(obj)) {
if ((long)RANY(obj)->as.data.dfree == -1) {
@@ -1317,11 +1649,11 @@ obj_free(obj)
}
break;
case T_MATCH:
-if (RANY(obj)->as.match.regs) {
re_free_registers(RANY(obj)->as.match.regs);
RUBY_CRITICAL(free(RANY(obj)->as.match.regs));
-}
-break;
+
if (RANY(obj)->as.match.regs) {
+
re_free_registers(RANY(obj)->as.match.regs);
+
RUBY_CRITICAL(free(RANY(obj)->as.match.regs));
+
}
+
break;
case T_FILE:
if (RANY(obj)->as.file.fptr) {
struct rb_io_t *fptr = RANY(obj)->as.file.fptr;
@@ -1332,19 +1664,19 @@ obj_free(obj)
}
break;
case T_ICLASS:
-/* iClass shares table with the module */
-break;
+
/* iClass shares table with the module */
+
break;
case T_FLOAT:
case T_VARMAP:
case T_BLKTAG:
-break;
+
break;
case T_BIGNUM:
-if (RANY(obj)->as.bignum.digits) {
RUBY_CRITICAL(free(RANY(obj)->as.bignum.digits));
-}
-break;
+
if (RANY(obj)->as.bignum.digits) {
+
RUBY_CRITICAL(free(RANY(obj)->as.bignum.digits));
+
}
+
break;
case T_NODE:
switch (nd_type(obj)) {
case NODE_SCOPE:
@@ -1359,7 +1691,7 @@ obj_free(obj)
break;/* no need to free iv_tbl */
case T_SCOPE:
-if (RANY(obj)->as.scope.local_vars &&
+
if (RANY(obj)->as.scope.local_vars &&
RANY(obj)->as.scope.flags != SCOPE_ALLOCA) {
VALUE *vars = RANY(obj)->as.scope.local_vars-1;
if (!(RANY(obj)->as.scope.flags & SCOPE_CLONE) && vars[0] == 0)
@@ -1370,14 +1702,14 @@ obj_free(obj)
break;
case T_STRUCT:
-if (RANY(obj)->as.rstruct.ptr) {
RUBY_CRITICAL(free(RANY(obj)->as.rstruct.ptr));
-}
-break;
+
if (RANY(obj)->as.rstruct.ptr) {
+
RUBY_CRITICAL(free(RANY(obj)->as.rstruct.ptr));
+
}
+
break;
default:
-rb_bug("gc_sweep(): unknown data type 0x%lx(0x%lx)",
RANY(obj)->as.basic.flags & T_MASK, obj);
+
rb_bug("gc_sweep(): unknown data type 0x%lx(0x%lx)",
+
RANY(obj)->as.basic.flags & T_MASK, obj);
}
return 0;
@@ -1407,18 +1739,18 @@ _rb_setjmp:\n\
typedef unsigned long rb_jmp_buf[6];
__asm__ (".align 4\n\
_rb_setjmp:\n\
-pushl%ebp\n\
-movl%esp,%ebp\n\
-movl8(%ebp),%ebp\n\
-movl%eax,(%ebp)\n\
-movl%ebx,4(%ebp)\n\
-movl%ecx,8(%ebp)\n\
-movl%edx,12(%ebp)\n\
-movl%esi,16(%ebp)\n\
-movl%edi,20(%ebp)\n\
-popl%ebp\n\
-xorl%eax,%eax\n\
-ret");
+
pushl
%ebp\n\
+
movl
%esp,%ebp\n\
+
movl
8(%ebp),%ebp\n\
+
movl
%eax,(%ebp)\n\
+
movl
%ebx,4(%ebp)\n\
+
movl
%ecx,8(%ebp)\n\
+
movl
%edx,12(%ebp)\n\
+
movl
%esi,16(%ebp)\n\
+
movl
%edi,20(%ebp)\n\
+
popl
%ebp\n\
+
xorl
%eax,%eax\n\
+
ret");
#endif
#endif
int rb_setjmp (rb_jmp_buf);
@@ -1431,41 +1763,50 @@ garbage_collect()
struct gc_list *list;
struct FRAME * volatile frame; /* gcc 2.7.2.3 -O2 bug??
jmp_buf save_regs_gc_mark;
+
struct timeval gctv1, gctv2;
SET_STACK_END;
*/
#ifdef HAVE_NATIVETHREAD
if (!is_ruby_native_thread()) {
-rb_bug("cross-thread violation on rb_gc()");
+
rb_bug("cross-thread violation on rb_gc()");
}
#endif
if (dont_gc || during_gc) {
-if (!freelist) {
add_heap();
-}
-return;
+
if (!freelist) {
+
add_heap();
+
}
+
return;
}
if (during_gc) return;
during_gc++;
+
+
+
+
+
+
+
+
if (gc_statistics) {
gc_collections++;
gettimeofday(&gctv1, NULL);
if (verbose_gc_stats) {
fprintf(gc_data_file, "Garbage collection started\n");
}
}
init_mark_stack();
gc_mark((VALUE)ruby_current_node, 0);
/* mark frame stack */
for (frame = ruby_frame; frame; frame = frame->prev) {
-rb_gc_mark_frame(frame);
-if (frame->tmp) {
struct FRAME *tmp = frame->tmp;
while (tmp) {
-rb_gc_mark_frame(tmp);
-tmp = tmp->prev;
}
-}
+
rb_gc_mark_frame(frame);
+
if (frame->tmp) {
+
struct FRAME *tmp = frame->tmp;
+
while (tmp) {
+
rb_gc_mark_frame(tmp);
+
tmp = tmp->prev;
+
}
+
}
}
gc_mark((VALUE)ruby_scope, 0);
gc_mark((VALUE)ruby_dyna_vars, 0);
if (finalizer_table) {
-mark_tbl(finalizer_table, 0);
+
mark_tbl(finalizer_table, 0);
}
FLUSH_REGISTER_WINDOWS;
@@ -1478,9 +1819,9 @@ garbage_collect()
rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
#else
if ((VALUE*)STACK_END < rb_gc_stack_start)
-rb_gc_mark_locations((VALUE*)STACK_END, rb_gc_stack_start);
+
rb_gc_mark_locations((VALUE*)STACK_END, rb_gc_stack_start);
else
-rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
+
rb_gc_mark_locations(rb_gc_stack_start, (VALUE*)STACK_END + 1);
#endif
#ifdef __ia64
/* mark backing store (flushed register window on the stack) */
@@ -1489,13 +1830,13 @@ garbage_collect()
#endif
#if defined(__human68k__) || defined(__mc68000__)
rb_gc_mark_locations((VALUE*)((char*)STACK_END + 2),
- (VALUE*)((char*)rb_gc_stack_start + 2));
+
(VALUE*)((char*)rb_gc_stack_start + 2));
#endif
rb_gc_mark_threads();
/* mark protected global variables */
for (list = global_List; list; list = list->next) {
-rb_gc_mark_maybe(*list->varptr);
+
rb_gc_mark_maybe(*list->varptr);
}
rb_mark_end_proc();
rb_gc_mark_global_tbl();
@@ -1510,18 +1851,30 @@ garbage_collect()
/* gc_mark objects whose marking are not completed*/
do {
-while (!MARK_STACK_EMPTY) {
if (mark_stack_overflow){
-gc_mark_all();
}
else {
-gc_mark_rest();
}
-}
-rb_gc_abort_threads();
+
while (!MARK_STACK_EMPTY) {
+
if (mark_stack_overflow){
+
gc_mark_all();
+
}
+
else {
+
gc_mark_rest();
+
}
+
}
+
rb_gc_abort_threads();
} while (!MARK_STACK_EMPTY);
gc_sweep();
+
+
+
+
+
+
+
+
+
+
+
+
if (gc_statistics) {
GC_TIME_TYPE musecs_used;
gettimeofday(&gctv2, NULL);
musecs_used = ((GC_TIME_TYPE)(gctv2.tv_sec - gctv1.tv_sec) * 1000000) + (gctv2.tv_usec - gctv1.tv_usec);
gc_time += musecs_used;
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
fflush(gc_data_file);
}
}
}
void
@@ -1588,8 +1941,8 @@ Init_stack(addr)
memset(&m, 0, sizeof(m));
VirtualQuery(&m, &m, sizeof(m));
rb_gc_stack_start =
-STACK_UPPER((VALUE *)&m, (VALUE *)m.BaseAddress,
(VALUE *)((char *)m.BaseAddress + m.RegionSize) - 1);
+
STACK_UPPER((VALUE *)&m, (VALUE *)m.BaseAddress,
+
(VALUE *)((char *)m.BaseAddress + m.RegionSize) - 1);
#elif defined(STACK_END_ADDRESS)
{
extern void *STACK_END_ADDRESS;
@@ -1599,24 +1952,24 @@ Init_stack(addr)
if (!addr) addr = (void *)&addr;
STACK_UPPER(&addr, addr, ++addr);
if (rb_gc_stack_start) {
-if (STACK_UPPER(&addr,
-rb_gc_stack_start > addr,
-rb_gc_stack_start < addr))
rb_gc_stack_start = addr;
-return;
+
if (STACK_UPPER(&addr,
+
rb_gc_stack_start > addr,
+
rb_gc_stack_start < addr))
+
rb_gc_stack_start = addr;
+
return;
}
rb_gc_stack_start = addr;
#endif
#ifdef HAVE_GETRLIMIT
{
-struct rlimit rlim;
+
struct rlimit rlim;
-if (getrlimit(RLIMIT_STACK, &rlim) == 0) {
unsigned int space = rlim.rlim_cur/5;
+
if (getrlimit(RLIMIT_STACK, &rlim) == 0) {
+
unsigned int space = rlim.rlim_cur/5;
-}
+
+
+
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (rlim.rlim_cur - space) / sizeof(VALUE);
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (rlim.rlim_cur - space) / sizeof(VALUE);
}
}
#endif
}
@@ -1652,16 +2005,16 @@ void ruby_init_stack(VALUE *addr
}
#elif defined _WIN32
{
-MEMORY_BASIC_INFORMATION mi;
-DWORD size;
-DWORD space;
-if (VirtualQuery(&mi, &mi, sizeof(mi))) {
size = (char *)mi.BaseAddress - (char *)mi.AllocationBase;
space = size / 5;
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (size - space) / sizeof(VALUE);
-}
+
MEMORY_BASIC_INFORMATION mi;
+
DWORD size;
+
+
+
+
+
+
+
+
DWORD space;
if (VirtualQuery(&mi, &mi, sizeof(mi))) {
size = (char *)mi.BaseAddress - (char *)mi.AllocationBase;
space = size / 5;
if (space > 1024*1024) space = 1024*1024;
STACK_LEVEL_MAX = (size - space) / sizeof(VALUE);
}
}
#endif
}
@@ -1701,8 +2054,9 @@ void
Init_heap()
{
if (!rb_gc_stack_start) {
-Init_stack(0);
+
Init_stack(0);
}
+
set_gc_parameters();
add_heap();
}
@@ -1715,7 +2069,7 @@ os_obj_of(of)
volatile VALUE v;
for (i = 0; i < heaps_used; i++) {
-RVALUE *p, *pend;
+
RVALUE *p, *pend;
p = heaps[i].slot; pend = p + heaps[i].limit;
for (;p < pend; p++) {
@@ -1808,8 +2162,8 @@ add_final(os, block)
{
rb_warn("ObjectSpace::add_finalizer is deprecated; use define_finalizer");
if (!rb_respond_to(block, rb_intern("call"))) {
-rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
- rb_obj_classname(block));
+
rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
+
rb_obj_classname(block));
}
rb_ary_push(finalizers, block);
return block;
@@ -1864,7 +2218,7 @@ undefine_final(os, obj)
VALUE os, obj;
{
if (finalizer_table) {
-st_delete(finalizer_table, (st_data_t*)&obj, 0);
+
st_delete(finalizer_table, (st_data_t*)&obj, 0);
}
return obj;
}
@@ -1888,11 +2242,11 @@ define_final(argc, argv, os)
rb_scan_args(argc, argv, "11", &obj, &block);
if (argc == 1) {
-block = rb_block_proc();
+
block = rb_block_proc();
}
else if (!rb_respond_to(block, rb_intern("call"))) {
-rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
- rb_obj_classname(block));
+
rb_raise(rb_eArgError, "wrong type argument %s (should be callable)",
+
rb_obj_classname(block));
}
need_call_final = 1;
if (!FL_ABLE(obj)) {
@@ -1905,10 +2259,10 @@ define_final(argc, argv, os)
OBJ_FREEZE(block);
if (!finalizer_table) {
-finalizer_table = st_init_numtable();
+
finalizer_table = st_init_numtable();
}
if (st_lookup(finalizer_table, obj, &table)) {
-rb_ary_push(table, block);
+
rb_ary_push(table, block);
}
else {
table = rb_ary_new3(1, block);
@@ -1927,7 +2281,7 @@ rb_gc_copy_finalizer(dest, obj)
if (!finalizer_table) return;
if (!FL_TEST(obj, FL_FINALIZE)) return;
if (st_lookup(finalizer_table, obj, &table)) {
-st_insert(finalizer_table, dest, table);
+
st_insert(finalizer_table, dest, table);
}
RBASIC(dest)->flags |= FL_FINALIZE;
}
@@ -1957,18 +2311,18 @@ run_final(obj)
args[1] = 0;
args[2] = (VALUE)ruby_safe_level;
for (i=0; i<RARRAY(finalizers)->len; i++) {
-args[0] = RARRAY(finalizers)->ptr[i];
-if (!args[1]) args[1] = rb_ary_new3(1, objid);
-rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
+
+
+
args[0] = RARRAY(finalizers)->ptr[i];
if (!args[1]) args[1] = rb_ary_new3(1, objid);
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
}
if (finalizer_table && st_delete(finalizer_table, (st_data_t*)&obj, &table)) {
-for (i=0; i<RARRAY(table)->len; i++) {
VALUE final = RARRAY(table)->ptr[i];
args[0] = RARRAY(final)->ptr[1];
if (!args[1]) args[1] = rb_ary_new3(1, objid);
args[2] = FIX2INT(RARRAY(final)->ptr[0]);
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
-}
+
for (i=0; i<RARRAY(table)->len; i++) {
+
VALUE final = RARRAY(table)->ptr[i];
+
args[0] = RARRAY(final)->ptr[1];
+
if (!args[1]) args[1] = rb_ary_new3(1, objid);
+
args[2] = FIX2INT(RARRAY(final)->ptr[0]);
+
rb_protect((VALUE(*)_((VALUE)))run_single_final, (VALUE)args, &status);
+
}
}
rb_thread_critical = critical_save;
}
@@ -1980,8 +2334,8 @@ rb_gc_finalize_deferred()
deferred_final_list = 0;
if (p) {
-finalize_list(p);
-free_unused_heaps();
+
finalize_list(p);
+
free_unused_heaps();
}
}
@@ -2061,7 +2415,7 @@ id2ref(obj, objid)
if (ptr == Qfalse) return Qfalse;
if (ptr == Qnil) return Qnil;
if (FIXNUM_P(ptr)) return (VALUE)ptr;
ptr = objid ^ FIXNUM_FLAG;/* unset FIXNUM_FLAG */
+
ptr = objid ^ FIXNUM_FLAG; /* unset FIXNUM_FLAG */
if ((ptr % sizeof(RVALUE)) == (4 << 2)) {
ID symid = ptr / sizeof(RVALUE);
@@ -2075,7 +2429,7 @@ id2ref(obj, objid)
rb_raise(rb_eRangeError, "0x%lx is not id value", p0);
}
if (BUILTIN_TYPE(ptr) == 0 || RBASIC(ptr)->klass == 0) {
-rb_raise(rb_eRangeError, "0x%lx is recycled object", p0);
+
rb_raise(rb_eRangeError, "0x%lx is recycled object", p0);
}
return (VALUE)ptr;
}
@@ -2166,6 +2520,14 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "stress=", gc_stress_set, 1);
rb_define_method(rb_mGC, "garbage_collect", rb_gc_start, 0);
+
+
+
+
+
+
+
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"clear_stats", rb_gc_clear_stats, 0);
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
rb_define_module_function(rb_mObSpace, "garbage_collect", rb_gc_start, 0);
@@ -2188,7 +2550,7 @@ Init_GC()
+
rb_global_variable(&nomem_error);
nomem_error = rb_exc_new3(rb_eNoMemError,
rb_obj_freeze(rb_str_new2("failed to allocate memory")));
rb_obj_freeze(rb_str_new2("failed to allocate memory")));
OBJ_TAINT(nomem_error);
OBJ_FREEZE(nomem_error);
1.26.5.1.12.1.10. 08-fork-support-for-gc-logging.patch
diff --git a/gc.c b/gc.c
index 9ad716f..a3cbe91 100644
--- a/gc.c
+++ b/gc.c
@@ -223,6 +223,8 @@ static int dont_gc;
static int gc_statistics = 0;
static GC_TIME_TYPE gc_time = 0;
static int gc_collections = 0;
+static int verbose_gc_stats = Qfalse;
+static FILE* gc_data_file = NULL;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -368,9 +370,148 @@ rb_gc_time()
#endif
}
VALUE rb_mGC;
+/*
+ * call-seq:
+ *
GC.enable_trace
=> true or false
+ *
+ * Enables garbage collection tracing, returning <code>true</code> if garbage
+ * collection tracing was already enabled.
+ *
+ *
GC.enable_trace
#=> false or true
+ *
GC.enable_trace
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_trace()
+{
+
int old = verbose_gc_stats;
+
verbose_gc_stats = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_trace
=> true or false
+ *
+ * Disables garbage collection tracing, returning <code>true</code> if garbage
+ * collection tracing was already disabled.
+ *
+ *
GC.disable_trace
#=> false or true
+ *
GC.disable_trace
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_trace()
+{
+
int old = verbose_gc_stats;
+
verbose_gc_stats = Qfalse;
+
return old;
+}
+
+char* GC_LOGFILE_IVAR = "@gc_logfile_name";
+
+/*
+ * call-seq:
+ *
GC.log_file(filename=nil, mode="w")
=> boolean
+ *
+ * Changes the GC data log file. Closes the currently open logfile.
+ * Returns true if the file was successfully opened for
+ * writing. Returns false if the file could not be opened for
+ * writing. Returns the name of the current logfile (or nil) if no
+ * parameter is given. Restores logging to stderr when given nil as
+ * an argument.
+ *
+ *
GC.log_file
#=> nil
+ *
GC.log_file "/tmp/gc.log"
#=> true
+ *
GC.log_file
#=> "/tmp/gc.log"
+ *
GC.log_file nil
#=> true
+ *
+ */
+
+VALUE
+rb_gc_log_file(int argc, VALUE *argv, VALUE self)
+{
+
VALUE filename = Qnil;
+
VALUE mode_str = Qnil;
+
FILE* f = NULL;
+
char* mode = "w";
+
+
VALUE current_logfile_name = rb_iv_get(rb_mGC, GC_LOGFILE_IVAR);
+
+
if (argc==0)
+
return current_logfile_name;
+
+
rb_scan_args(argc, argv, "02", &filename, &mode_str);
+
+
if (filename == Qnil) {
+
/* close current logfile and reset logfile to stderr */
+
if (gc_data_file != stderr) {
+
fclose(gc_data_file);
+
gc_data_file = stderr;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, Qnil);
+
}
+
return Qtrue;
+
}
+
+
/* we have a real logfile name */
+
filename = StringValue(filename);
+
+
if (rb_equal(current_logfile_name, filename) == Qtrue) {
+
/* do nothing if we get the file name we're already logging to */
+
return Qtrue;
+
}
+
+
/* get mode for file opening */
+
if (mode_str != Qnil)
+
{
+
mode = RSTRING(StringValue(mode_str))->ptr;
+
}
+
+
/* try to open file in given mode */
+
if (f = fopen(RSTRING(filename)->ptr, mode)) {
+
if (gc_data_file != stderr) {
+
fclose(gc_data_file);
+
}
+
gc_data_file = f;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, filename);
+
} else {
+
return Qfalse;
+
}
+
return Qtrue;
+}
+
+
+/*
+ * Called from process.c before a fork. Flushes the gc log file to
+ * avoid writing the buffered output twice (once in the parent, and
+ * once in the child).
+ */
+void
+rb_gc_before_fork()
+{
+ /* flush gc log file */
+ fflush(gc_data_file);
+}
+
+/*
+ * Called from process.c after a fork in the child process. Turns off
+ * logging, disables GC stats and resets all gc counters and timing
+ * information.
+ */
+void
+rb_gc_after_fork()
+{
+
rb_gc_disable_stats();
+
rb_gc_clear_stats();
+
rb_gc_disable_trace();
+
gc_data_file = stderr;
+
rb_iv_set(rb_mGC, GC_LOGFILE_IVAR, Qnil);
+}
+
static struct gc_list {
VALUE *varptr;
struct gc_list *next;
@@ -477,10 +618,6 @@ static double heap_slots_growth_factor = 1.8;
static long initial_malloc_limit = GC_MALLOC_LIMIT;
-static int verbose_gc_stats = Qfalse;
-static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
static void set_gc_parameters()
@@ -496,6 +633,8 @@ static void set_gc_parameters()
if (gc_stats_i > 0) {
verbose_gc_stats = Qtrue;
}
+
/* child processes should not inherit RUBY_GC_STATS */
+
unsetenv("RUBY_GC_STATS");
}
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
@@ -508,6 +647,8 @@ static void set_gc_parameters()
fprintf(stderr,
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
}
/* child processes should not inherit RUBY_GC_DATA_FILE to avoid clobbering */
unsetenv("RUBY_GC_DATA_FILE");
+
+
}
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
@@ -2619,6 +2760,9 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "dump_file_and_line_info", rb_gc_dump_file_and_line_info, -1);
#endif
rb_define_singleton_method(rb_mGC, "log", rb_gc_log, 1);
+
rb_define_singleton_method(rb_mGC, "log_file", rb_gc_log_file, -1);
+
rb_define_singleton_method(rb_mGC, "enable_trace", rb_gc_enable_trace, 0);
+
rb_define_singleton_method(rb_mGC, "disable_trace", rb_gc_disable_trace, 0);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
diff --git a/intern.h b/intern.h
index acae58d..49e1827 100644
--- a/intern.h
+++ b/intern.h
@@ -270,6 +270,8 @@ void rb_gc_call_finalizer_at_exit _((void));
VALUE rb_gc_enable _((void));
VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
+void rb_gc_before_fork _((void));
+void rb_gc_after_fork _((void));
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
diff --git a/process.c b/process.c
index 8f6285d..ea28cb8 100644
--- a/process.c
+++ b/process.c
@@ -1330,6 +1330,8 @@ rb_f_fork(obj)
fflush(stderr);
#endif
+
+
rb_gc_before_fork();
before_exec();
pid = fork();
after_exec();
@@ -1339,6 +1341,7 @@ rb_f_fork(obj)
#ifdef linux
after_exec();
#endif
+
rb_gc_after_fork();
rb_thread_atfork();
if (rb_block_given_p()) {
int status;
@@ -1574,10 +1577,12 @@ rb_f_system(argc, argv)
chfunc = signal(SIGCHLD, SIG_DFL);
retry:
+
rb_gc_before_fork();
before_exec();
pid = fork();
if (pid == 0) {
/* child process */
+
rb_gc_after_fork();
rb_thread_atfork();
rb_protect(proc_exec_args, (VALUE)&earg, NULL);
_exit(127);
1.26.5.1.12.1.11. 17-caller-for-all-threads.patch
diff --git a/eval.c b/eval.c
index 8a2f492..b34b60d 100644
--- a/eval.c
+++ b/eval.c
@@ -8199,6 +8199,17 @@ rb_f_method_name()
}
}
+/* Hash (Thread => Backtrace) used to collect backtrace for each threads. */
+static VALUE backtrace_for_each_thread;
+
+static int backtrace_level_for_each_thread;
+
+static VALUE
+switch_thread_context_to_collect_backtrace(rb_thread_t next);
+
+static VALUE
+rb_f_caller_for_all_threads();
+
void
Init_eval()
{
@@ -8244,6 +8255,7 @@ Init_eval()
rb_define_global_function("fail", rb_f_raise, -1);
+
rb_define_global_function("caller", rb_f_caller, -1);
rb_define_global_function("caller_for_all_threads", rb_f_caller_for_all_threads, -1);
rb_define_global_function("exit", rb_f_exit, -1);
rb_define_global_function("abort", rb_f_abort, -1);
@@ -10599,6 +10611,7 @@ static int
th_sig, th_safe;
#define RESTORE_RAISE5
#define RESTORE_SIGNAL6
#define RESTORE_EXIT7
+#define RESTORE_BACKTRACE8
extern VALUE *rb_gc_stack_start;
#ifdef __ia64
@@ -10705,6 +10718,15 @@ rb_thread_switch(n)
}
rb_exc_raise(th_raise_exception);
break;
+
case RESTORE_BACKTRACE:
+
rb_hash_aset(backtrace_for_each_thread, curr_thread->thread,
+
backtrace(backtrace_level_for_each_thread));
+
if (curr_thread != main_thread) {
+
switch_thread_context_to_collect_backtrace(curr_thread->next);
+
} else {
+
/* Circled back to main thread, cycle is complete. */
+
}
+
break;
case RESTORE_NORMAL:
default:
break;
@@ -13874,3 +13896,74 @@ rb_throw(tag, val)
argv[1] = val;
rb_f_throw(2, argv);
}
+
+static VALUE
+switch_thread_context_to_collect_backtrace(rb_thread_t next)
+{
+
if (THREAD_SAVE_CONTEXT(curr_thread)) {
+
return Qnil;
+
}
+
curr_thread = next;
+
rb_thread_restore_context(next, RESTORE_BACKTRACE);
+
return Qnil;
+}
+
+
+/*
+ * call-seq:
+ *
caller_for_all_threads(start=1)
=> array
+ *
+ * Returns the current execution stack for all threads
+ * ---a hash whose keys are thread instances and values
+ * the thread caller backtrace.
+ *
+ * Backtraces are array of hashes indicating location on the
+ * stack. Hash keys include ``<em>:line</em>'' or ``<em>:file</em>''
+ * and ``<em>:method'</em>''.
+ *
+ * The optional _start_ parameter
+ * determines the number of initial stack entries to omit from the
+ * result.
+ *
+ *
def a(skip)
+ *
caller_for_all_threads(skip)
+ *
end
+ *
def b(skip)
+ *
a(skip)
+ *
end
+ *
def c(skip)
+ *
b(skip)
+ *
end
+ *
c(0)
#=> ["prog:2:in `a'", "prog:5:in `b'", "prog:8:in `c'", "prog:10"]
+ *
c(1)
#=> ["prog:5:in `b'", "prog:8:in `c'", "prog:11"]
+ *
c(2)
#=> ["prog:8:in `c'", "prog:12"]
+ *
c(3)
#=> ["prog:13"]
+ */
+static VALUE
+rb_f_caller_for_all_threads(argc, argv)
+
int argc;
+
VALUE *argv;
+{
+
volatile int critical;
+
VALUE level;
+VALUE result;
+
+
rb_scan_args(argc, argv, "01", &level);
+
backtrace_level_for_each_thread = NIL_P(level) ? 0 : NUM2INT(level);
+if (backtrace_level_for_each_thread < 0) {
+rb_raise(rb_eArgError, "negative level (%d)", backtrace_level_for_each_thread);
+}
+
+critical = rb_thread_critical;
+rb_thread_critical = Qtrue;
+
+
backtrace_for_each_thread = rb_hash_new();
+
switch_thread_context_to_collect_backtrace(main_thread->next);
+
+result = backtrace_for_each_thread;
+backtrace_for_each_thread = Qnil;
+backtrace_for_each_thread = 0;
+
+rb_thread_critical = critical;
+
return result;
+}
diff --git a/test/callerforallthreads/test_caller_for_each_thread.rb
b/test/callerforallthreads/test_caller_for_each_thread.rb
new file mode 100644
index 0000000..6aebaed
--- /dev/null
+++ b/test/callerforallthreads/test_caller_for_each_thread.rb
@@ -0,0 +1,95 @@
+# -*- ruby-indent-level: 4 -*+require 'thread'
+require 'test/unit'
+
+class AClassWithNestedmethods
+
+ def an_ultra_nested_method(skip)
+
caller_for_all_threads skip
+ end
+
+ def a_nested_method(skip)
+
an_ultra_nested_method skip
+ end
+
+ def a_method(skip=0)
+
a_nested_method skip
+ end
+
+end
+
+class CallerForEachThreadTest < Test::Unit::TestCase
+
+ def testCollectMeaningfulBacktraceForASingleThread
+
backtraces = AClassWithNestedmethods.new.a_method
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":8:in `an_ultra_nested_method'", backtrace[0]
+
assert_equal __FILE__ + ":12:in `a_nested_method'", backtrace[1]
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[2]
+
assert_equal __FILE__ + ":24:in `testCollectMeaningfulBacktraceForASingleThread'",
+
backtrace[3]
+ end
+
+ def testCanSkipFirstStackEntries
+
backtraces = AClassWithNestedmethods.new.a_method 2
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[0]
+
assert_equal __FILE__ + ":35:in `testCanSkipFirstStackEntries'",
+
backtrace[1]
+ end
+
+ def testCollectMeaningfulBacktraceForMultipleThreads
+
first_thread = Thread.new do
+
loop do
+
Thread.pass
+
sleep 1
+
end
+
end
+
+
second_thread = Thread.new do
+
loop do
+
Thread.pass
+
sleep 1
+
end
+
end
+
+
backtraces = AClassWithNestedmethods.new.a_method
+
+
backtrace = backtraces[Thread.current]
+
assert_not_nil backtrace
+
assert_match __FILE__ + ":8:in `an_ultra_nested_method'", backtrace[0]
+
assert_match __FILE__ + ":12:in `a_nested_method'", backtrace[1]
+
assert_equal __FILE__ + ":16:in `a_method'", backtrace[2]
+
assert_equal __FILE__ + ":58:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[3]
+
+
backtrace = backtraces[first_thread]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":47:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[0]
+
assert_equal __FILE__ + ":45:in `loop'",
+
backtrace[1]
+
assert_equal __FILE__ + ":45:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[2]
+
assert_equal __FILE__ + ":44:in `initialize'",backtrace[3]
+
assert_equal __FILE__ + ":44:in `new'", backtrace[4]
+
assert_equal __FILE__ + ":44:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[5]
+
+
backtrace = backtraces[second_thread]
+
assert_not_nil backtrace
+
assert_equal __FILE__ + ":53:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[0]
+
assert_equal __FILE__ + ":52:in `loop'", backtrace[1]
+
assert_equal __FILE__ + ":52:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[2]
+
assert_equal __FILE__ + ":51:in `initialize'",backtrace[3]
+
assert_equal __FILE__ + ":51:in `new'", backtrace[4]
+
assert_equal __FILE__ + ":51:in `testCollectMeaningfulBacktraceForMultipleThreads'",
+
backtrace[5]
+ end
+
+end
+
1.26.5.1.12.1.12. 11-expose-heap-slots.patch
diff --git a/gc.c b/gc.c
index 5b42b90..21b3f6b 100644
--- a/gc.c
+++ b/gc.c
@@ -690,6 +690,7 @@ static int heaps_used
= 0;
static int heap_min_slots = 10000;
static int heap_slots = 10000;
+static int heap_size = 0;
static int heap_free_min = 4096;
static int heap_slots_increment = 10000;
@@ -800,6 +801,21 @@ static void set_gc_parameters()
/*
* call-seq:
+ *
GC.heap_slots
=> Integer
+ *
+ * Returns the number of heap slots available for object allocations.
+ *
+ *
GC.heap_slots
#=> 10000
+ *
+ */
+VALUE
+rb_gc_heap_slots()
+{
+
return INT2NUM(heap_size);
+}
+
+/*
+ * call-seq:
*
GC.dump
=> nil
*
* dumps information about the current GC data structures to the GC log file
@@ -967,6 +983,7 @@ add_heap()
heaps[heaps_used].limit = heap_slots;
break;
}
+
heap_size += heap_slots;
pend = p + heap_slots;
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
@@ -1828,6 +1845,7 @@ gc_sweep()
if (n == heaps[i].limit && freed > free_min) {
RVALUE *pp;
+
heap_size -= n;
heaps[i].limit = 0;
for (pp = final_list; pp != final; pp = pp->as.free.next) {
pp->as.free.flags |= FL_SINGLETON; /* freeing page mark */
@@ -2866,6 +2884,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "clear_stats", rb_gc_clear_stats, 0);
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
+
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
diff --git a/intern.h b/intern.h
index 86b4395..e23d2d7 100644
--- a/intern.h
+++ b/intern.h
@@ -274,6 +274,7 @@ void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
VALUE rb_gc_allocated_size _((void));
VALUE rb_gc_num_allocations _((void));
+VALUE rb_gc_heap_slots _((void));
unsigned long rb_os_live_objects _((void));
#ifdef HAVE_LONG_LONG
unsigned LONG_LONG rb_os_allocated_objects _((void));
1.26.5.1.12.1.13. 03-sigvtalrm-fix.patch
diff --git a/eval.c b/eval.c
index 284e486..00bcd36 100644
--- a/eval.c
+++ b/eval.c
@@ -12461,6 +12461,11 @@ rb_thread_start_0(fn, arg, th)
curr_thread->next = th;
th->priority = curr_thread->priority;
th->thgroup = curr_thread->thgroup;
+#if defined(HAVE_SETITIMER) || defined(_THREAD_SAFE)
+
if (!thread_init) {
+
rb_thread_start_timer();
+
}
+#endif
}
START_TIMER();
@@ -13188,7 +13193,9 @@ rb_thread_atfork()
main_thread = curr_thread;
curr_thread->next = curr_thread;
curr_thread->prev = curr_thread;
STOP_TIMER();
+#if defined(HAVE_SETITIMER) || defined(_THREAD_SAFE)
+
rb_thread_stop_timer();
+#endif
}
1.26.5.1.12.1.14. 07-heap-dump-support.patch
diff --git a/configure.in b/configure.in
index 7368808..ffe0649 100644
--- a/configure.in
+++ b/configure.in
@@ -1609,6 +1609,14 @@ fi
LDFLAGS="-L. $LDFLAGS"
AC_SUBST(ARCHFILE)
+dnl enable gc debugging
+AC_ARG_ENABLE(gcdebug,
+
[ --enable-gcdebug
build garbage collector with debugging enabled. ],
+
[enable_gcdebug=$enableval])
+if test "$enable_gcdebug" = 'yes'; then
+
AC_DEFINE(GC_DEBUG, 1)
+fi
+
dnl build rdoc index if requested
RDOCTARGET=""
AC_ARG_ENABLE(install-doc,
diff --git a/gc.c b/gc.c
index ab71d22..9ad716f 100644
--- a/gc.c
+++ b/gc.c
@@ -411,7 +411,6 @@ rb_gc_unregister_address(addr)
}
}
-#undef GC_DEBUG
void
rb_global_variable(var)
@@ -602,6 +601,85 @@ rb_gc_dump()
return Qnil;
}
+
+static char* obj_type(int tp);
+
+#ifdef GC_DEBUG
+/*
+ * call-seq:
+ *
GC.dump_file_and_line_info(String, boolean)
=> nil
+ *
+ * dumps information on which currently allocated object was created by which file and on which line
+ *
+ *
GC.dump_file_and_line_info(String, boolean)
#=> nil
+ *
+ * The second parameter specifies whether class names should be included in the dump.
+ * Note that including class names will allocate additional string objects on the heap.
+ *
+ */
+
+VALUE
+rb_gc_dump_file_and_line_info(int argc, VALUE *argv)
+{
+ VALUE filename, str, include_classnames = Qnil;
+ char *fname = NULL;
+ char *klass = NULL;
+ FILE* f = NULL;
+ int i,n = 0;
+
+ rb_scan_args(argc, argv, "11", &filename, &include_classnames);
+
+ str = StringValue(filename);
+ fname = RSTRING(str)->ptr;
+ f = fopen(fname, "w");
+
+ for (i = 0; i < heaps_used; i++) {
+
RVALUE *p, *pend;
+
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
for (;p < pend; p++) {
+
if (p->as.basic.flags) {
+
fprintf(f, "%s:%s:%d", obj_type(p->as.basic.flags & T_MASK), p->file, p->line);
+
// rb_obj_classname will create objects on the heap, we need a better solution
+
if (include_classnames == Qtrue) {
+
/* write the class */
+
fprintf(f, ":");
+
switch (TYPE(p)) {
+
case T_NONE:
+
fprintf(f, "__none__");
+
break;
+
case T_BLKTAG:
+
fprintf(f, "__blktag__");
+
break;
+
case T_UNDEF:
+
fprintf(f, "__undef__");
+
break;
+
case T_VARMAP:
+
fprintf(f, "__varmap__");
+
break;
+
case T_SCOPE:
+
fprintf(f, "__scope__");
+
break;
+
case T_NODE:
+
fprintf(f, "__node__");
+
break;
+
default:
+
if (!p->as.basic.klass) {
+
fprintf(f, "__unknown__");
+
} else {
+
fprintf(f, rb_obj_classname((VALUE)p));
+
}
+
}
+
}
+
fprintf(f, "\n");
+
}
+
}
+ }
+ fclose(f);
+ return Qnil;
+}
+#endif
+
/*
* call-seq:
*
GC.log String => String
@@ -1066,6 +1144,11 @@ gc_mark(ptr, lev)
if (obj->as.basic.flags & FL_MARK) return; /* already marked */
obj->as.basic.flags |= FL_MARK;
+#ifdef GC_DEBUG
+
/* mark our new reference point for sourcefile objects */
+
mark_source_filename(RANY(obj)->file);
+#endif
+
if (lev > GC_LEVEL_MAX || (lev == 0 && ruby_stack_check())) {
if (!mark_stack_overflow) {
if (mark_stack_ptr - mark_stack < MARK_STACK_MAX) {
@@ -1104,6 +1187,11 @@ gc_mark_children(ptr, lev)
if (obj->as.basic.flags & FL_MARK) return; /* already marked */
obj->as.basic.flags |= FL_MARK;
+#ifdef GC_DEBUG
+
/* mark our new reference point for sourcefile objects */
+
mark_source_filename(RANY(obj)->file);
+#endif
+
marking:
if (FL_TEST(obj, FL_EXIVAR)) {
rb_mark_generic_ivar(ptr);
@@ -1550,6 +1638,7 @@ gc_sweep()
live_counts[i], free_counts[i], obj_type(i));
}
}
+
fflush(gc_data_file);
}
/* clear finalization list */
@@ -2526,6 +2615,9 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+#ifdef GC_DEBUG
+
rb_define_singleton_method(rb_mGC,
+#endif
rb_define_singleton_method(rb_mGC,
"collections", rb_gc_collections, 0);
"time", rb_gc_time, 0);
"dump", rb_gc_dump, 0);
"dump_file_and_line_info", rb_gc_dump_file_and_line_info, -1);
"log", rb_gc_log, 1);
rb_mObSpace = rb_define_module("ObjectSpace");
1.26.5.1.12.1.15. 05-display-full-stack-trace.patch
diff --git a/eval.c b/eval.c
index 00bcd36..5ee11a0 100644
--- a/eval.c
+++ b/eval.c
@@ -1325,8 +1325,8 @@ error_print()
int truncate = eclass == rb_eSysStackError;
#define
-#define
-#define
+#define
+#define
TRACE_MAX (TRACE_HEAD+TRACE_TAIL+5)
TRACE_HEAD 8
TRACE_TAIL 5
TRACE_HEAD 100
TRACE_TAIL 100
ep = RARRAY(errat);
for (i=1; i<ep->len; i++) {
1.26.5.1.12.1.16. 06-better-source-file-tracing.patch
diff --git a/eval.c b/eval.c
index 5ee11a0..8a2f492 100644
--- a/eval.c
+++ b/eval.c
@@ -1161,7 +1161,7 @@ static VALUE trace_func = 0;
static int tracing = 0;
static void call_trace_func _((rb_event_t,NODE*,VALUE,ID,VALUE));
-#if 0
+#if 1
#define SET_CURRENT_SOURCE() (ruby_sourcefile = ruby_current_node->nd_file, \
ruby_sourceline = nd_line(ruby_current_node))
#else
1.26.5.1.12.1.17. 13-heap-slot-size.patch
diff --git a/gc.c b/gc.c
index 7db1ef6..57740d2 100644
--- a/gc.c
+++ b/gc.c
@@ -2891,6 +2891,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
+
rb_define_const(rb_mGC, "HEAP_SLOT_SIZE", INT2FIX(sizeof(RVALUE)));
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
1.26.5.1.13. head
1.26.5.1.13.1. railsexpress
1.26.5.1.13.1.1. 09-track-malloc-size.patch
diff --git a/gc.c b/gc.c
index a3cbe91..30a1219 100644
--- a/gc.c
+++ b/gc.c
@@ -79,6 +79,17 @@ void *alloca ();
static unsigned long malloc_increase = 0;
static unsigned long malloc_limit = GC_MALLOC_LIMIT;
+
+#ifdef HAVE_LONG_LONG
+static unsigned LONG_LONG gc_allocated_size = 0;
+static unsigned LONG_LONG gc_num_allocations = 0;
+#else
+static unsigned long gc_allocated_size = 0;
+static unsigned long gc_num_allocations = 0;
+#endif
+static int gc_statistics = 0;
+
+
static void run_final();
static VALUE nomem_error;
static void garbage_collect();
@@ -163,6 +174,11 @@ ruby_xmalloc(size)
}
malloc_increase += size;
+
if (gc_statistics) {
+
gc_allocated_size += size;
+gc_num_allocations += 1;
+
}
+
return mem;
}
@@ -220,7 +236,6 @@ ruby_xfree(x)
extern int ruby_in_compile;
static int dont_gc;
-static int gc_statistics = 0;
static GC_TIME_TYPE gc_time = 0;
static int gc_collections = 0;
static int verbose_gc_stats = Qfalse;
@@ -329,11 +344,55 @@ rb_gc_clear_stats()
{
gc_collections = 0;
gc_time = 0;
+
gc_allocated_size = 0;
+
gc_num_allocations = 0;
return Qnil;
}
/*
* call-seq:
+ *
GC.allocated_size
=> Integer
+ *
+ * Returns the size of memory (in bytes) allocated since GC statistics collection
+ * was enabled.
+ *
+ *
GC.allocated_size
#=> 35
+ *
+ */
+VALUE
+rb_gc_allocated_size()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_allocated_size);
+#else
+
return ULONG2NUM(gc_allocated_size);
+#endif
+}
+
+/*
+ * call-seq:
+ *
GC.num_allocations
=> Integer
+ *
+ * Returns the number of memory allocations since GC statistics collection
+ * was enabled.
+ *
+ *
GC.num_allocations
#=> 150
+ *
+ */
+VALUE
+rb_gc_num_allocations()
+{
+#if HAVE_LONG_LONG
+
return ULL2NUM(gc_num_allocations);
+#else
+
return ULONG2NUM(gc_num_allocations);
+#endif
+}
+
+/*
+
+/*
+ * call-seq:
*
GC.collections
=> Integer
*
* Returns the number of garbage collections performed while GC statistics collection
@@ -2753,6 +2812,8 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "enable_stats", rb_gc_enable_stats, 0);
rb_define_singleton_method(rb_mGC, "disable_stats", rb_gc_disable_stats, 0);
rb_define_singleton_method(rb_mGC, "clear_stats", rb_gc_clear_stats, 0);
+
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
+
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
rb_define_singleton_method(rb_mGC, "dump", rb_gc_dump, 0);
diff --git a/intern.h b/intern.h
index 99696f1..1117614 100644
--- a/intern.h
+++ b/intern.h
@@ -272,6 +272,8 @@ VALUE rb_gc_disable _((void));
VALUE rb_gc_start _((void));
void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
+VALUE rb_gc_allocated_size _((void));
+VALUE rb_gc_num_allocations _((void));
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.13.1.2. 16-add-object-size-information-to-heap-dump.patch
diff --git a/gc.c b/gc.c
index 0ce7e68..53450bf 100644
--- a/gc.c
+++ b/gc.c
@@ -953,9 +953,21 @@ rb_gc_dump_file_and_line_info(int argc, VALUE *argv)
if (!p->as.basic.klass) {
fprintf(f, "__unknown__");
} else {
fprintf(f, rb_obj_classname((VALUE)p));
+
fprintf(f, "%s", rb_obj_classname((VALUE)p));
}
}
+
/* print object size for some known object types */
+
switch (TYPE(p)) {
+
case T_STRING:
+
fprintf(f, ":%lu", RSTRING(p)->len);
+
break;
+
case T_ARRAY:
+
fprintf(f, ":%lu", RARRAY(p)->len);
+
break;
+
case T_HASH:
+
fprintf(f, ":%d", RHASH(p)->tbl->num_entries);
+
break;
+
}
}
fprintf(f, "\n");
}
@@ -1924,10 +1936,10 @@ gc_sweep()
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7d\n", live);
fprintf(gc_data_file, "freelist objects : %.7d\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7d\n", really_freed);
fprintf(gc_data_file, "objects processed: %.7lu\n", live+freed);
fprintf(gc_data_file, "live objects
: %.7lu\n", live);
fprintf(gc_data_file, "freelist objects : %.7lu\n", freed - really_freed);
fprintf(gc_data_file, "freed objects
: %.7lu\n", really_freed);
for(i=0; i<256; i++) {
if (free_counts[i]>0 || live_counts[i]>0) {
fprintf(gc_data_file,
@@ -2258,7 +2270,7 @@ garbage_collect()
gc_time += musecs_used;
+
+
+
+
if (verbose_gc_stats) {
fprintf(gc_data_file, "GC time: %d msec\n", musecs_used / 1000);
fprintf(gc_data_file, "GC time: %ld msec\n", (long)(musecs_used / 1000));
fflush(gc_data_file);
}
+
}
1.26.5.1.13.1.3. 15-track-live-dataset-size.patch
diff --git a/gc.c b/gc.c
index 2c34932..0ce7e68 100644
--- a/gc.c
+++ b/gc.c
@@ -89,6 +89,7 @@ static unsigned long gc_num_allocations = 0;
#endif
static int gc_statistics = 0;
+static unsigned long heap_slots_live_after_last_gc = 0;
static void run_final();
static VALUE nomem_error;
@@ -465,6 +466,23 @@ rb_gc_time()
#endif
}
+/*
+ * call-seq:
+ *
GC.heap_slots_live_after_last_gc
=> Integer
+ *
+ * Returns the number of heap slots which were live after the last garbage collection.
+ *
+ *
GC.heap_slots_live_after_last_gc
#=> 231223
+ *
+ */
+VALUE
+rb_gc_heap_slots_live_after_last_gc()
+{
+
return ULONG2NUM(heap_slots_live_after_last_gc);
+}
+
+
+
VALUE rb_mGC;
/*
@@ -1903,6 +1921,7 @@ gc_sweep()
}
during_gc = 0;
live_objects = live;
+
heap_slots_live_after_last_gc = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2924,6 +2943,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC, "allocated_size", rb_gc_allocated_size, 0);
rb_define_singleton_method(rb_mGC, "num_allocations", rb_gc_num_allocations, 0);
rb_define_singleton_method(rb_mGC, "heap_slots", rb_gc_heap_slots, 0);
+
rb_define_singleton_method(rb_mGC, "heap_slots_live_after_last_gc", rb_gc_heap_slots_live_after_last_gc, 0);
rb_define_const(rb_mGC, "HEAP_SLOT_SIZE", INT2FIX(sizeof(RVALUE)));
rb_define_singleton_method(rb_mGC, "collections", rb_gc_collections, 0);
rb_define_singleton_method(rb_mGC, "time", rb_gc_time, 0);
1.26.5.1.13.1.4. 14-add-trace-stats-enabled-methods.patch
diff --git a/gc.c b/gc.c
index 57740d2..2c34932 100644
--- a/gc.c
+++ b/gc.c
@@ -350,6 +350,22 @@ rb_gc_disable_stats()
/*
* call-seq:
+ *
GC.stats_enabled?
=> true or false
+ *
+ * Check whether GC stats have been enabled.
+ *
+ *
GC.stats_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_stats_enabled()
+{
+
return gc_statistics ? Qtrue : Qfalse;
+}
+
+/*
+ * call-seq:
*
GC.clear_stats
=> nil
*
* Clears garbage collection statistics, returning nil. This resets the number
@@ -491,6 +507,22 @@ rb_gc_disable_trace()
return old;
}
+/*
+ * call-seq:
+ *
GC.trace_enabled?
=> true or false
+ *
+ * Check whether GC tracing has been enabled.
+ *
+ *
GC.trace_enabled?
#=> false or true
+ *
+ */
+
+VALUE
+rb_gc_trace_enabled()
+{
+
return verbose_gc_stats ? Qtrue : Qfalse;
+}
+
char* GC_LOGFILE_IVAR = "@gc_logfile_name";
/*
@@ -2887,6 +2919,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
@@ -2902,6 +2935,7 @@ Init_GC()
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
rb_define_singleton_method(rb_mGC,
+
rb_define_singleton_method(rb_mGC,
"enable_stats", rb_gc_enable_stats, 0);
"disable_stats", rb_gc_disable_stats, 0);
"stats_enabled?", rb_gc_stats_enabled, 0);
"clear_stats", rb_gc_clear_stats, 0);
"allocated_size", rb_gc_allocated_size, 0);
"num_allocations", rb_gc_num_allocations, 0);
"log_file", rb_gc_log_file, -1);
"enable_trace", rb_gc_enable_trace, 0);
"disable_trace", rb_gc_disable_trace, 0);
"trace_enabled?", rb_gc_trace_enabled, 0);
rb_mObSpace = rb_define_module("ObjectSpace");
rb_define_module_function(rb_mObSpace, "each_object", os_each_obj, -1);
1.26.5.1.13.1.5. 02-fix-tests-for-osx.patch
diff --git a/test/drb/drbtest.rb b/test/drb/drbtest.rb
index bc16ab1..c12b168 100644
--- a/test/drb/drbtest.rb
+++ b/test/drb/drbtest.rb
@@ -22,7 +22,7 @@ class DRbService
%w(ut_drb.rb ut_array.rb ut_port.rb ut_large.rb ut_safe1.rb ut_eval.rb).each do |nm|
add_service_command(nm)
end
- @server = @@server = DRb::DRbServer.new('druby://localhost:0', @@manager, {})
+ @server = @@server = DRb::DRbServer.new('druby://127.0.0.1:0', @@manager, {})
@@manager.uri = @@server.uri
def self.manager
@@manager
@@ -79,16 +79,16 @@ module DRbCore
end
+
+
+
+
+
+
def test_00_DRbObject
ro = DRbObject.new(nil, 'druby://localhost:12345')
assert_equal('druby://localhost:12345', ro.__drburi)
ro = DRbObject.new(nil, 'druby://127.0.0.1:12345')
assert_equal('druby://127.0.0.1:12345', ro.__drburi)
assert_equal(nil, ro.__drbref)
ro = DRbObject.new_with_uri('druby://localhost:12345')
assert_equal('druby://localhost:12345', ro.__drburi)
ro = DRbObject.new_with_uri('druby://127.0.0.1:12345')
assert_equal('druby://127.0.0.1:12345', ro.__drburi)
assert_equal(nil, ro.__drbref)
ro = DRbObject.new_with_uri('druby://localhost:12345?foobar')
assert_equal('druby://localhost:12345', ro.__drburi)
ro = DRbObject.new_with_uri('druby://127.0.0.1:12345?foobar')
assert_equal('druby://127.0.0.1:12345', ro.__drburi)
assert_equal(DRb::DRbURIOption.new('foobar'), ro.__drbref)
end
diff --git a/test/drb/ut_drb.rb b/test/drb/ut_drb.rb
index f5720cf..265713d 100644
--- a/test/drb/ut_drb.rb
+++ b/test/drb/ut_drb.rb
@@ -154,7 +154,7 @@ if __FILE__ == $0
DRb::DRbServer.default_argc_limit(8)
DRb::DRbServer.default_load_limit(4096)
- DRb.start_service('druby://localhost:0', DRbEx.new)
+ DRb.start_service('druby://127.0.0.1:0', DRbEx.new)
es = DRb::ExtServ.new(ARGV.shift, ARGV.shift)
DRb.thread.join
end
diff --git a/test/drb/ut_drb_drbssl.rb b/test/drb/ut_drb_drbssl.rb
index 0a2191e..bca3012 100644
--- a/test/drb/ut_drb_drbssl.rb
+++ b/test/drb/ut_drb_drbssl.rb
@@ -18,7 +18,7 @@ if __FILE__ == $0
DRb::DRbServer.default_argc_limit(8)
DRb::DRbServer.default_load_limit(4096)
- DRb.start_service('drbssl://localhost:0', DRbEx.new, config)
+ DRb.start_service('drbssl://127.0.0.1:0', DRbEx.new, config)
es = DRb::ExtServ.new(ARGV.shift, ARGV.shift)
DRb.thread.join
end
diff --git a/test/drb/ut_eval.rb b/test/drb/ut_eval.rb
index 4df963e..9127939 100644
--- a/test/drb/ut_eval.rb
+++ b/test/drb/ut_eval.rb
@@ -3,7 +3,7 @@ require 'drb/extserv'
class EvalAttack
def initialize
@four = DRb::DRbServer.new('druby://localhost:0', self, {:safe_level => 4})
+
@four = DRb::DRbServer.new('druby://127.0.0.1:0', self, {:safe_level => 4})
end
def four
@@ -25,7 +25,7 @@ if __FILE__ == $0
$SAFE = 1
+
DRb.start_service('druby://localhost:0', EvalAttack.new, {:safe_level => 2})
DRb.start_service('druby://127.0.0.1:0', EvalAttack.new, {:safe_level => 2})
es = DRb::ExtServ.new(ARGV.shift, ARGV.shift)
DRb.thread.join
end
diff --git a/test/drb/ut_large.rb b/test/drb/ut_large.rb
index d6717c5..0aefd1b 100644
--- a/test/drb/ut_large.rb
+++ b/test/drb/ut_large.rb
@@ -31,7 +31,7 @@ if __FILE__ == $0
DRb::DRbServer.default_argc_limit(3)
DRb::DRbServer.default_load_limit(100000)
DRb.start_service('druby://localhost:0', DRbLarge.new)
DRb.start_service('druby://127.0.0.1:0', DRbLarge.new)
es = DRb::ExtServ.new(ARGV.shift, ARGV.shift)
DRb.thread.join
end
diff --git a/test/drb/ut_safe1.rb b/test/drb/ut_safe1.rb
index 4df8e1e..ee097f6 100644
--- a/test/drb/ut_safe1.rb
+++ b/test/drb/ut_safe1.rb
@@ -8,7 +8,7 @@ if __FILE__ == $0
it
end
+
+
DRb.start_service('druby://localhost:0', [1, 2, 'III', 4, "five", 6],
DRb.start_service('druby://127.0.0.1:0', [1, 2, 'III', 4, "five", 6],
{:safe_level => 1})
es = DRb::ExtServ.new(ARGV.shift, ARGV.shift)
DRb.thread.join
diff --git a/test/net/pop/test_pop.rb b/test/net/pop/test_pop.rb
index c8aa9a8..129ca08 100644
--- a/test/net/pop/test_pop.rb
+++ b/test/net/pop/test_pop.rb
@@ -3,10 +3,14 @@ require 'test/unit'
require 'digest/md5'
class TestPOP < Test::Unit::TestCase
def localhost
'127.0.0.1'
end
+
+
+
+
+
def setup
@users = {'user' => 'pass' }
@ok_user = 'user'
@stamp_base = "#{$$}.#{Time.now.to_i}@localhost"
@stamp_base = "#{$$}.#{Time.now.to_i}@#{localhost}"
end
def test_pop_auth_ok
@@ -64,7 +68,7 @@ class TestPOP < Test::Unit::TestCase
end
+
def pop_test(apop=false)
host = 'localhost'
host = localhost
server = TCPServer.new(host, 0)
port = server.addr[1]
thread = Thread.start do
1.26.5.1.13.1.6. 10-track-object-allocation.patch
diff --git a/gc.c b/gc.c
index 30a1219..5b42b90 100644
--- a/gc.c
+++ b/gc.c
@@ -96,6 +96,26 @@ static void garbage_collect();
int ruby_gc_stress = 0;
+static unsigned long live_objects = 0;
+unsigned long rb_os_live_objects()
+{
+
return live_objects;
+}
+
+#if defined(HAVE_LONG_LONG)
+static unsigned LONG_LONG allocated_objects = 0;
+unsigned LONG_LONG rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#else
+static unsigned long allocated_objects = 0;
+unsigned long rb_os_allocated_objects()
+{
+
return allocated_objects;
+}
+#endif
+
NORETURN(void rb_exc_jump _((VALUE)));
void
@@ -987,6 +1007,8 @@ rb_newobj()
RANY(obj)->file = ruby_sourcefile;
RANY(obj)->line = ruby_sourceline;
#endif
+
live_objects++;
+
allocated_objects++;
return obj;
}
@@ -1825,6 +1847,7 @@ gc_sweep()
add_heap();
}
during_gc = 0;
+
live_objects = live;
if (do_gc_stats) {
fprintf(gc_data_file, "objects processed: %.7d\n", live+freed);
@@ -2790,6 +2813,35 @@ rb_obj_id(VALUE obj)
return (VALUE)((long)obj|FIXNUM_FLAG);
}
+/* call-seq:
+ * ObjectSpace.live_objects => number
+ *
+ * Returns the count of objects currently allocated in the system. This goes
+ * down after the garbage collector runs.
+ */
+static
+VALUE os_live_objects(VALUE self)
+{
+
return ULONG2NUM(live_objects);
+}
+
+/* call-seq:
+ * ObjectSpace.allocated_objects => number
+ *
+ * Returns the count of objects allocated since the Ruby interpreter has
+ * started. This number can only increase. To know how many objects are
+ * currently allocated, use ObjectSpace::live_objects
+ */
+static
+VALUE os_allocated_objects(VALUE self)
+{
+#if defined(HAVE_LONG_LONG)
+
return ULL2NUM(allocated_objects);
+#else
+
return ULONG2NUM(allocated_objects);
+#endif
+}
+
/*
* The <code>GC</code> module provides an interface to Ruby's mark and
* sweep garbage collection mechanism. Some of the underlying methods
@@ -2833,6 +2885,9 @@ Init_GC()
rb_define_module_function(rb_mObSpace, "finalizers", finals, 0);
rb_define_module_function(rb_mObSpace, "call_finalizer", call_final, 1);
+
+
+
rb_define_module_function(rb_mObSpace, "live_objects", os_live_objects, 0);
rb_define_module_function(rb_mObSpace, "allocated_objects", os_allocated_objects, 0);
rb_define_module_function(rb_mObSpace, "define_finalizer", define_final, -1);
rb_define_module_function(rb_mObSpace, "undefine_finalizer", undefine_final, 1);
diff --git a/intern.h b/intern.h
index 1117614..a87661d 100644
--- a/intern.h
+++ b/intern.h
@@ -274,6 +274,12 @@ void rb_gc_before_fork _((void));
void rb_gc_after_fork _((void));
VALUE rb_gc_allocated_size _((void));
VALUE rb_gc_num_allocations _((void));
+unsigned long rb_os_live_objects _((void));
+#ifdef HAVE_LONG_LONG
+unsigned LONG_LONG rb_os_allocated_objects _((void));
+#else
+unsigned long rb_os_allocated_objects _((void));
+#endif
/* hash.c */
void st_foreach_safe _((struct st_table *, int (*)(ANYARGS), unsigned long));
void rb_hash_foreach _((VALUE, int (*)(ANYARGS), VALUE));
1.26.5.1.13.1.7. 12-fix-heap-size-growth-logic.patch
diff --git a/gc.c b/gc.c
index 21b3f6b..7db1ef6 100644
--- a/gc.c
+++ b/gc.c
@@ -694,6 +694,7 @@ static int heap_size = 0;
static
static
+static
static
int heap_free_min = 4096;
int heap_slots_increment = 10000;
int initial_heap_slots_increment = 10000;
double heap_slots_growth_factor = 1.8;
static long initial_malloc_limit = GC_MALLOC_LIMIT;
@@ -771,14 +772,13 @@ static void set_gc_parameters()
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
}
if (heap_slots_incr_i > 0) {
heap_slots_increment = heap_slots_incr_i;
}
+
heap_slots_increment = heap_slots_incr_i;
+
initial_heap_slots_increment = heap_slots_increment;
}
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
if (heap_slots_growth_factor_ptr != NULL) {
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
double heap_slots_growth_factor_d = atof(heap_slots_growth_factor_ptr);
if (verbose_gc_stats) {
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
}
@@ -988,8 +988,13 @@ add_heap()
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots += heap_slots_increment;
heap_slots_increment *= heap_slots_growth_factor;
+
if (heaps_used == 1)
+
heap_slots = initial_heap_slots_increment;
+
else {
+
heap_slots_increment *= heap_slots_growth_factor;
+
heap_slots += heap_slots_increment;
+
}
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
@@ -1879,6 +1884,7 @@ gc_sweep()
live_counts[i], free_counts[i], obj_type(i));
}
}
+
rb_gc_dump();
fflush(gc_data_file);
}
1.26.5.1.13.1.8. 01-ignore-generated-files.patch
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..00c347a
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,95 @@
+.ext
+.installed.list
+.rbconfig.time
+Makefile
+autom4te.cache/
+config.h
+config.status
+configure
+ext/Win32API/Makefile
+ext/bigdecimal/Makefile
+ext/curses/Makefile
+ext/dbm/Makefile
+ext/digest/Makefile
+ext/digest/bubblebabble/Makefile
+ext/digest/md5/Makefile
+ext/digest/rmd160/Makefile
+ext/digest/sha1/Makefile
+ext/digest/sha2/Makefile
+ext/dl/Makefile
+ext/dl/call.func
+ext/dl/callback.func
+ext/dl/cbtable.func
+ext/dl/dlconfig.h
+ext/dl/dlconfig.rb
+ext/enumerator/Makefile
+ext/etc/Makefile
+ext/fcntl/Makefile
+ext/gdbm/Makefile
+ext/iconv/Makefile
+ext/io/wait/Makefile
+ext/nkf/Makefile
+ext/openssl/Makefile
+ext/openssl/extconf.h
+ext/pty/Makefile
+ext/racc/cparse/Makefile
+ext/readline/Makefile
+ext/sdbm/Makefile
+ext/socket/Makefile
+ext/stringio/Makefile
+ext/strscan/Makefile
+ext/syck/Makefile
+ext/syslog/Makefile
+ext/thread/Makefile
+ext/tk/Makefile
+ext/tk/tkutil/Makefile
+ext/win32ole/Makefile
+ext/win32ole/.document
+ext/zlib/Makefile
+largefile.h
+miniruby
+parse.c
+rbconfig.rb
+ruby
+enc.mk
+ext/bigdecimal/extconf.h
+ext/continuation/
+ext/coverage/
+ext/curses/extconf.h
+ext/dbm/extconf.h
+ext/digest/bubblebabble/extconf.h
+ext/digest/extconf.h
+ext/digest/md5/extconf.h
+ext/digest/rmd160/extconf.h
+ext/digest/sha1/extconf.h
+ext/digest/sha2/extconf.h
+ext/dl/callback.h
+ext/dl/extconf.h
+ext/etc/extconf.h
+ext/fcntl/extconf.h
+ext/fiber/
+ext/iconv/extconf.h
+ext/io/wait/extconf.h
+ext/json/
+ext/nkf/extconf.h
+ext/pty/extconf.h
+ext/racc/cparse/extconf.h
+ext/readline/extconf.h
+ext/ripper/
+ext/sdbm/extconf.h
+ext/socket/constants.h
+ext/socket/extconf.h
+ext/stringio/extconf.h
+ext/strscan/extconf.h
+ext/syck/extconf.h
+ext/syslog/extconf.h
+ext/tk/extconf.h
+ext/tk/tkutil/extconf.h
+ext/zlib/extconf.h
+miniprelude.c
+prelude.c
+revision.h
+*.dylib
+*.log
+*.dSYM
+patches-ruby*
1.26.5.1.13.1.9. 04-railsbench-gc-patch.patch
diff --git a/gc.c b/gc.c
index fa45cd1..ab71d22 100644
--- a/gc.c
+++ b/gc.c
@@ -22,8 +22,16 @@
#include <setjmp.h>
#include <sys/types.h>
+#ifdef _WIN32
+#include <string.h>
+#else
+#include <strings.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
+#elif defined(_WIN32)
+#include <time.h>
#endif
#ifdef HAVE_SYS_RESOURCE_H
@@ -42,7 +50,6 @@ void rb_io_fptr_finalize _((struct rb_io_t*));
#ifdef __CYGWIN__
int _setjmp(), _longjmp();
#endif
/* Make alloca work the best possible way. */
#ifdef __GNUC__
# ifndef atarist
@@ -86,12 +93,12 @@ rb_memerror()
rb_thread_t th = rb_curr_thread;
if (!nomem_error ||
-(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
-fprintf(stderr, "[FATAL] failed to allocate memory\n");
-exit(1);
+
(rb_thread_raised_p(th, RAISED_NOMEMORY) && rb_safe_level() < 4)) {
+
fprintf(stderr, "[FATAL] failed to allocate memory\n");
+
exit(1);
}
if (rb_thread_raised_p(th, RAISED_NOMEMORY)) {
-rb_exc_jump(nomem_error);
+
rb_exc_jump(nomem_error);
}
rb_thread_raised_set(th, RAISED_NOMEMORY);
rb_exc_raise(nomem_error);
@@ -139,7 +146,7 @@ ruby_xmalloc(size)
void *mem;
if (size < 0) {
-rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
+
rb_raise(rb_eNoMemError, "negative allocation size (or too big)");
}
if (size == 0) size = 1;
@@ -148,11 +155,11 @@ ruby_xmalloc(size)
}
RUBY_CRITICAL(mem = malloc(size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = malloc(size));
-if (!mem) {
rb_memerror();
-}
+
garbage_collect();
+
RUBY_CRITICAL(mem = malloc(size));
+
if (!mem) {
+
rb_memerror();
+
}
}
malloc_increase += size;
@@ -179,17 +186,17 @@ ruby_xrealloc(ptr, size)
void *mem;
if (size < 0) {
-rb_raise(rb_eArgError, "negative re-allocation size");
+
rb_raise(rb_eArgError, "negative re-allocation size");
}
if (!ptr) return xmalloc(size);
if (size == 0) size = 1;
if (ruby_gc_stress) garbage_collect();
RUBY_CRITICAL(mem = realloc(ptr, size));
if (!mem) {
-garbage_collect();
-RUBY_CRITICAL(mem = realloc(ptr, size));
-if (!mem) {
rb_memerror();
+
garbage_collect();
+
RUBY_CRITICAL(mem = realloc(ptr, size));
+
if (!mem) {
+
rb_memerror();
}
}
malloc_increase += size;
@@ -202,11 +209,20 @@ ruby_xfree(x)
void *x;
{
if (x)
-RUBY_CRITICAL(free(x));
+
RUBY_CRITICAL(free(x));
}
+#if HAVE_LONG_LONG
+#define GC_TIME_TYPE LONG_LONG
+#else
+#define GC_TIME_TYPE long
+#endif
+
extern int ruby_in_compile;
static int dont_gc;
+static int gc_statistics = 0;
+static GC_TIME_TYPE gc_time = 0;
+static int gc_collections = 0;
static int during_gc;
static int need_call_final = 0;
static st_table *finalizer_table = 0;
@@ -241,7 +257,7 @@ rb_gc_enable()
* Disables garbage collection, returning <code>true</code> if garbage
* collection was already disabled.
*
- *
GC.disable
#=> false
+ *
GC.disable
#=> false or true
*
GC.disable
#=> true
*
*/
@@ -255,6 +271,104 @@ rb_gc_disable()
return old;
}
+/*
+ * call-seq:
+ *
GC.enable_stats
=> true or false
+ *
+ * Enables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already enabled.
+ *
+ *
GC.enable_stats
#=> false or true
+ *
GC.enable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_enable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qtrue;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.disable_stats
=> true or false
+ *
+ * Disables garbage collection statistics, returning <code>true</code> if garbage
+ * collection statistics was already disabled.
+ *
+ *
GC.disable_stats
#=> false or true
+ *
GC.disable_stats
#=> true
+ *
+ */
+
+VALUE
+rb_gc_disable_stats()
+{
+
int old = gc_statistics;
+
gc_statistics = Qfalse;
+
return old;
+}
+
+/*
+ * call-seq:
+ *
GC.clear_stats
=> nil
+ *
+ * Clears garbage collection statistics, returning nil. This resets the number
+ * of collections (GC.collections) and the time used (GC.time) to 0.
+ *
+ *
GC.clear_stats
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_clear_stats()
+{
+
gc_collections = 0;
+
gc_time = 0;
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.collections
=> Integer
+ *
+ * Returns the number of garbage collections performed while GC statistics collection
+ * was enabled.
+ *
+ *
GC.collections
#=> 35
+ *
+ */
+
+VALUE
+rb_gc_collections()
+{
+
return INT2NUM(gc_collections);
+}
+
+/*
+ * call-seq:
+ *
GC.time
=> Integer
+ *
+ * Returns the time spent during garbage collection while GC statistics collection
+ * was enabled (in micro seconds).
+ *
+ *
GC.time
#=> 20000
+ *
+ */
+
+VALUE
+rb_gc_time()
+{
+#if HAVE_LONG_LONG
+
return LL2NUM(gc_time);
+#else
+
return LONG2NUM(gc_time);
+#endif
+}
+
+
VALUE rb_mGC;
static struct gc_list {
@@ -281,19 +395,19 @@ rb_gc_unregister_address(addr)
struct gc_list *tmp = global_List;
if (tmp->varptr == addr) {
-global_List = tmp->next;
-RUBY_CRITICAL(free(tmp));
-return;
+
global_List = tmp->next;
+
RUBY_CRITICAL(free(tmp));
+
return;
}
while (tmp->next) {
-if (tmp->next->varptr == addr) {
struct gc_list *t = tmp->next;
+
if (tmp->next->varptr == addr) {
+
struct gc_list *t = tmp->next;
-}
-tmp
+
+
+
+
+
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
= tmp->next;
tmp->next = tmp->next->next;
RUBY_CRITICAL(free(t));
break;
}
tmp = tmp->next;
}
}
@@ -312,26 +426,26 @@ rb_global_variable(var)
typedef struct RVALUE {
union {
-struct {
unsigned long flags;/* always 0 for freed obj */
struct RVALUE *next;
-} free;
-struct RBasic basic;
-struct RObject object;
-struct RClass klass;
-struct RFloat flonum;
-struct RString string;
-struct RArray array;
-struct RRegexp regexp;
-struct RHash
hash;
-struct RData
data;
-struct RStruct rstruct;
-struct RBignum bignum;
-struct RFile
file;
-struct RNode
node;
-struct RMatch match;
-struct RVarmap varmap;
-struct SCOPE
scope;
+
struct {
+
unsigned long flags;
/* always 0 for freed obj */
+
struct RVALUE *next;
+
} free;
+
struct RBasic basic;
+
struct RObject object;
+
struct RClass klass;
+
struct RFloat flonum;
+
struct RString string;
+
struct RArray array;
+
struct RRegexp regexp;
+
struct RHash
hash;
+
struct RData
data;
+
struct RStruct rstruct;
+
struct RBignum bignum;
+
struct RFile
file;
+
struct RNode
node;
+
struct RMatch match;
+
struct RVarmap varmap;
+
struct SCOPE
scope;
} as;
#ifdef GC_DEBUG
char *file;
@@ -346,7 +460,7 @@ typedef struct RVALUE {
static RVALUE *freelist = 0;
static RVALUE *deferred_final_list = 0;
-#define HEAPS_INCREMENT 10
+static int heaps_increment = 10;
static struct heaps_slot {
void *membase;
RVALUE *slot;
@@ -355,45 +469,197 @@ static struct heaps_slot {
static int heaps_length = 0;
static int heaps_used
= 0;
-#define HEAP_MIN_SLOTS 10000
-static int heap_slots = HEAP_MIN_SLOTS;
+static int heap_min_slots = 10000;
+static int heap_slots = 10000;
-#define FREE_MIN 4096
+static int heap_free_min = 4096;
+static int heap_slots_increment = 10000;
+static double heap_slots_growth_factor = 1.8;
+
+static long initial_malloc_limit = GC_MALLOC_LIMIT;
+
+static int verbose_gc_stats = Qfalse;
+
+static FILE* gc_data_file = NULL;
static RVALUE *himem, *lomem;
+static void set_gc_parameters()
+{
+
char *gc_stats_ptr, *min_slots_ptr, *free_min_ptr, *heap_slots_incr_ptr,
+
*heap_incr_ptr, *malloc_limit_ptr, *gc_heap_file_ptr, *heap_slots_growth_factor_ptr;
+
+
gc_data_file = stderr;
+
+
gc_stats_ptr = getenv("RUBY_GC_STATS");
+
if (gc_stats_ptr != NULL) {
+
int gc_stats_i = atoi(gc_stats_ptr);
+
if (gc_stats_i > 0) {
+
verbose_gc_stats = Qtrue;
+
}
+
}
+
+
gc_heap_file_ptr = getenv("RUBY_GC_DATA_FILE");
+
if (gc_heap_file_ptr != NULL) {
+
FILE* data_file = fopen(gc_heap_file_ptr, "w");
+
if (data_file != NULL) {
+
gc_data_file = data_file;
+
}
+
else {
+
fprintf(stderr,
+
"can't open gc log file %s for writing, using default\n", gc_heap_file_ptr);
+
}
+
}
+
+
min_slots_ptr = getenv("RUBY_HEAP_MIN_SLOTS");
+
if (min_slots_ptr != NULL) {
+
int min_slots_i = atoi(min_slots_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_MIN_SLOTS=%s\n", min_slots_ptr);
+
}
+
if (min_slots_i > 0) {
+
heap_slots = min_slots_i;
+
heap_min_slots = min_slots_i;
+
}
+
}
+
+
free_min_ptr = getenv("RUBY_HEAP_FREE_MIN");
+
if (free_min_ptr != NULL) {
+
int free_min_i = atoi(free_min_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_FREE_MIN=%s\n", free_min_ptr);
+
}
+
if (free_min_i > 0) {
+
heap_free_min = free_min_i;
+
}
+
}
+
+
heap_incr_ptr = getenv("RUBY_HEAP_INCREMENT");
+
if (heap_incr_ptr != NULL) {
+
int heap_incr_i = atoi(heap_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_INCREMENT=%s\n", heap_incr_ptr);
+
}
+
if (heap_incr_i > 0) {
+
heaps_increment = heap_incr_i;
+
}
+
}
+
+
heap_slots_incr_ptr = getenv("RUBY_HEAP_SLOTS_INCREMENT");
+
if (heap_slots_incr_ptr != NULL) {
+
int heap_slots_incr_i = atoi(heap_slots_incr_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_INCREMENT=%s\n", heap_slots_incr_ptr);
+
}
+
if (heap_slots_incr_i > 0) {
+
heap_slots_increment = heap_slots_incr_i;
+
}
+
}
+
+
heap_slots_growth_factor_ptr = getenv("RUBY_HEAP_SLOTS_GROWTH_FACTOR");
+
if (heap_slots_growth_factor_ptr != NULL) {
+
double heap_slots_growth_factor_d = atoi(heap_slots_growth_factor_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_HEAP_SLOTS_GROWTH_FACTOR=%s\n", heap_slots_growth_factor_ptr);
+
}
+
if (heap_slots_growth_factor_d > 0) {
+
heap_slots_growth_factor = heap_slots_growth_factor_d;
+
}
+
}
+
+
malloc_limit_ptr = getenv("RUBY_GC_MALLOC_LIMIT");
+
if (malloc_limit_ptr != NULL) {
+
int malloc_limit_i = atol(malloc_limit_ptr);
+
if (verbose_gc_stats) {
+
fprintf(gc_data_file, "RUBY_GC_MALLOC_LIMIT=%s\n", malloc_limit_ptr);
+
}
+
if (malloc_limit_i > 0) {
+
initial_malloc_limit = malloc_limit_i;
+
}
+
}
+}
+
+/*
+ * call-seq:
+ *
GC.dump
=> nil
+ *
+ * dumps information about the current GC data structures to the GC log file
+ *
+ *
GC.dump
#=> nil
+ *
+ */
+
+VALUE
+rb_gc_dump()
+{
+
int i;
+
+
for (i = 0; i < heaps_used; i++) {
+
int heap_size = heaps[i].limit;
+
fprintf(gc_data_file, "HEAP[%2d]: size=%7d\n", i, heap_size);
+
}
+
+
return Qnil;
+}
+
+/*
+ * call-seq:
+ *
GC.log String => String
+ *
+ * Logs string to the GC data file and returns it.
+ *
+ *
GC.log "manual GC call"
#=> "manual GC call"
+ *
+ */
+
+VALUE
+rb_gc_log(self, original_str)
+
VALUE self, original_str;
+{
+
if (original_str == Qnil) {
+
fprintf(gc_data_file, "\n");
+
}
+
else {
+
VALUE str = StringValue(original_str);
+
char *p = RSTRING(str)->ptr;
+
fprintf(gc_data_file, "%s\n", p);
+
}
+
return original_str;
+}
+
+
static void
add_heap()
{
RVALUE *p, *pend;
if (heaps_used == heaps_length) {
-/* Realloc heaps */
-struct heaps_slot *p;
-int length;
-heaps_length += HEAPS_INCREMENT;
-length = heaps_length*sizeof(struct heaps_slot);
-RUBY_CRITICAL(
if (heaps_used > 0) {
-p = (struct heaps_slot *)realloc(heaps, length);
-if (p) heaps = p;
}
else {
-p = heaps = (struct heaps_slot *)malloc(length);
});
-if (p == 0) rb_memerror();
+
/* Realloc heaps */
+
struct heaps_slot *p;
+
int length;
+
+
heaps_length += heaps_increment;
+
length = heaps_length*sizeof(struct heaps_slot);
+
RUBY_CRITICAL(
+
if (heaps_used > 0) {
+
p = (struct heaps_slot *)realloc(heaps, length);
+
if (p) heaps = p;
+
}
+
else {
+
p = heaps = (struct heaps_slot *)malloc(length);
+
});
+
if (p == 0) rb_memerror();
}
for (;;) {
-RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
-if (p == 0) {
if (heap_slots == HEAP_MIN_SLOTS) {
-rb_memerror();
}
heap_slots = HEAP_MIN_SLOTS;
continue;
-}
+
RUBY_CRITICAL(p = (RVALUE*)malloc(sizeof(RVALUE)*(heap_slots+1)));
+
if (p == 0) {
+
if (heap_slots == heap_min_slots) {
+
rb_memerror();
+
}
+
heap_slots = heap_min_slots;
+
continue;
+
}
heaps[heaps_used].membase = p;
if ((VALUE)p % sizeof(RVALUE) == 0)
heap_slots += 1;
@@ -401,25 +667,26 @@ add_heap()
p = (RVALUE*)((VALUE)p + sizeof(RVALUE) - ((VALUE)p % sizeof(RVALUE)));
heaps[heaps_used].slot = p;
heaps[heaps_used].limit = heap_slots;
-break;
+
break;
}
pend = p + heap_slots;
if (lomem == 0 || lomem > p) lomem = p;
if (himem < pend) himem = pend;
heaps_used++;
heap_slots *= 1.8;
if (heap_slots <= 0) heap_slots = HEAP_MIN_SLOTS;
+
heap_slots += heap_slots_increment;
+
heap_slots_increment *= heap_slots_growth_factor;
+
if (heap_slots <= 0) heap_slots = heap_min_slots;
while (p < pend) {
-p->as.free.flags = 0;
-p->as.free.next = freelist;
-freelist = p;
-p++;
+
p->as.free.flags = 0;
+
p->as.free.next = freelist;
+
freelist = p;
+
p++;
}
}
#define RANY(o) ((RVALUE*)(o))
-int
+int
rb_during_gc()
{
return during_gc;
@@ -431,7 +698,7 @@ rb_newobj()
VALUE obj;
if (during_gc)
-rb_bug("object allocation during garbage collection phase");
+
rb_bug("object allocation during garbage collection phase");
if (ruby_gc_stress || !freelist) garbage_collect();
@@ -580,13 +847,13 @@ rb_source_filename(f)
st_data_t name;
if (!st_lookup(source_filenames, (st_data_t)f, &name)) {
-long len = strlen(f) + 1;
-char *ptr = ALLOC_N(char, len + 1);
-name = (st_data_t)ptr;
-*ptr++ = 0;
-MEMCPY(ptr, f, char, len);
-st_add_direct(source_filenames, (st_data_t)ptr, name);
-return ptr;
+
long len = strlen(f) + 1;
+
char *ptr = ALLOC_N(char, len + 1);
+
name = (st_data_t)ptr;
+
*ptr++ = 0;
+
MEMCPY(ptr, f, char, len);
+
st_add_direct(source_filenames, (st_data_t)ptr, name);
+
return ptr;
}
return (char *)name + 1;
}
@@ -596,7 +863,7 @@ mark_source_filename(f)
char *f;
{
if (f) {
-f[-1] = 1;
+
f[-1] = 1;
}
}
@@ -605,12 +872,12 @@ sweep_source_filename(key, value)
char *key, *value;
{
if (*value) {
-*value = 0;
-return ST_CONTINUE;
+
*value = 0;
+
return ST_CONTINUE;
}
else {
-free(value);
-return ST_DELETE;
+
free(value);
+
return ST_DELETE;
}
}
@@ -625,14 +892,14 @@ gc_mark_all()
init_mark_stack();
for (i = 0; i < heaps_used; i++) {
-p = heaps[i].slot; pend = p + heaps[i].limit;
-while (p < pend) {
if ((p->as.basic.flags & FL_MARK) &&
-(p->as.basic.flags != FL_MARK)) {
-gc_mark_children((VALUE)p, 0);
}
p++;
-}
+
p = heaps[i].slot; pend = p + heaps[i].limit;
+
while (p < pend) {
+
if ((p->as.basic.flags & FL_MARK) &&
+
(p->as.basic.flags != FL_MARK)) {
+
gc_mark_children((VALUE)p, 0);
+
}
+
p++;
+
}
}
}
@@ -647,8 +914,8 @@ gc_mark_rest()
init_mark_stack();
while(p != tmp_arry){
-p--;
-gc_mark_children(*p, 0);
+
+
p--;
gc_mark_children(*p, 0);
}
}
@@ -665,9 +932,9 @@ is_pointer_to_heap(ptr)
/* check if p looks like a pointer */
for (i=0; i < heaps_used; i++) {
-heap_org = heaps[i].slot;
-if (heap_org <= p && p < heap_org + heaps[i].limit)
return Qtrue;
+
heap_org = heaps[i].slot;
+
if (heap_org <= p && p < heap_org + heaps[i].limit)
+
return Qtrue;
}
return Qfalse;
}
@@ -680,10 +947,10 @@ mark_locations_array(x, n)
VALUE v;
while (n--) {
v = *x;
-if (is_pointer_to_heap((void *)v)) {
gc_mark(v, 0);
-}
-x++;
+
if (is_pointer_to_heap((void *)v)) {
+
gc_mark(v, 0);
+
}
+
x++;
}
}
@@ -780,7 +1047,7 @@ rb_gc_mark_maybe(obj)
VALUE obj;
{
if (is_pointer_to_heap((void *)obj)) {
-gc_mark(obj, 0);
+
gc_mark(obj, 0);
}
}
@@ -828,7 +1095,7 @@ gc_mark_children(ptr, lev)
{
register RVALUE *obj = RANY(ptr);
+
goto marking;/* skip */
goto marking;
/* skip */
again:
obj = RANY(ptr);
@@ -839,148 +1106,148 @@ gc_mark_children(ptr, lev)
marking:
if (FL_TEST(obj, FL_EXIVAR)) {
-rb_mark_generic_ivar(ptr);
+
rb_mark_generi