Skip to content

Fix string memory leaks in Ruby 1.8.6

by Topper on September 4th, 2009

UPDATE: This is rails-incompatible... which sucks.

Ruby 1.8.6 leaks memory in some surprising places. Even gsub and split on the String class cause some bad headaches. If you're using Haml and 1.8.6 - you are probably in a bit of trouble.
Read more: http://blog.edhickey.com/2008/12/03/memory-leak-in-ruby-186-string-class/

However, simply overwriting the offending methods fixes this memory leak at least. With a weird caveat that you may not use $ variables (eg $1) in any blocks passed to gsub.

Re-read that last sentence... "boom".gsub(/b(.)/) {|m| $1.upcase} will NO LONGER work. Unfortunately... rails uses that syntax, making this blog post probably moot

RUBY:
  1. class ::String
  2.   # This below fixes a bad memory leak in ruby 1.8.6
  3.   # http://blog.edhickey.com/2008/12/03/memory-leak-in-ruby-186-string-class/
  4.   alias :non_garbage_split :split
  5.   alias :non_garbage_gsub :gsub
  6.   alias :non_garbage_gsub! :gsub!
  7.  
  8.   def split(char)
  9.     holder = char
  10.     non_garbage_split(holder)
  11.   end
  12.  
  13.   def gsub(*args, &block)
  14.     if args.size == 1
  15.       non_garbage_gsub(args[0], &block)
  16.     else
  17.       non_garbage_gsub(args[0], args[1], &block)
  18.     end
  19.   end
  20.  
  21.   def gsub!(*args, &block)
  22.     holder = args[0]
  23.     args[0] = holder
  24.     non_garbage_gsub!(*args, &block)
  25.   end
  26.   #end memory leak fixes
  27. end

2 Comments
  1. MarkusQ permalink

    Try something like:

    alias mri_gsub gsub
    def gsub(*args,&block)
    mri_gsub(*args,&block)
    end

    It handles $1 et al fine. Also, you should do the same trick with sub, sub!, etc.

    – MarkusQ

  2. MarkusQ permalink

    My bad, I failed to test it thoroughly. It works for special cases, but what is needed is a “works always.”

    – Markus

    P.S. After looking at the C code (and this time testing before I post) I see that File#gets & $_ have the same problem.

Leave a Reply

Note: XHTML is allowed. Your email address will never be published.

Subscribe to this comment feed via RSS