Guest User

Untitled

a guest
Apr 26th, 2018
64
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 1.74 KB | None | 0 0
  1. #!/usr/bin/env ruby -wKU
  2.  
  3. require "rubygems"
  4. require "ffi"
  5.  
  6. # map the C interface
  7. module Lib
  8. extend FFI::Library
  9. ffi_lib(
  10. *Array(
  11. ENV.fetch(
  12. "TOKYO_CABINET_LIB",
  13. Dir["/{opt,usr}/{,local/}lib{,64}/libtokyocabinet.{dylib,so*}"]
  14. )
  15. )
  16. )
  17.  
  18. attach_function :free, [ :pointer ], :void
  19.  
  20. attach_function :tchdbnew, [ ], :pointer
  21. attach_function :tchdbopen, [:pointer, :string, :int], :bool
  22. attach_function :tchdbput, [:pointer, :pointer, :int, :pointer,
  23. :int], :bool
  24. attach_function :tchdbget, [:pointer, :pointer, :int, :pointer], :pointer
  25. attach_function :tchdbclose, [:pointer], :bool
  26. end
  27.  
  28. # translate the interface to Ruby
  29. class TokyoCabinet
  30. def self.open(*args)
  31. db = new(*args)
  32. yield db
  33. ensure
  34. db.close if db
  35. end
  36.  
  37. def initialize(path)
  38. @db = Lib.tchdbnew
  39. Lib.tchdbopen(@db, path, (1 << 1) | (1 << 2)) # write create mode
  40. end
  41.  
  42. def []=(key, value)
  43. k, v = key.to_s, value.to_s
  44. Lib.tchdbput(@db, k, k.size, v, v.size)
  45. end
  46.  
  47. def [](key)
  48. k = key.to_s
  49. size = FFI::MemoryPointer.new(:int)
  50. value = Lib.tchdbget(@db, k, k.size, size)
  51. value.address.zero? ? nil : value.get_bytes(0, size.get_int(0))
  52. ensure
  53. size.free if size
  54. # FIXME: How do I free value here?
  55. Lib.free(value)
  56. end
  57.  
  58. def close
  59. Lib.tchdbclose(@db)
  60. end
  61. end
  62.  
  63. # show the problem
  64. def show_memory
  65. 3.times { GC.start } # try to clean up
  66. mem = `ps -o rss -p #{Process.pid}`[/\d+/]
  67. puts "Current memory: #{mem}"
  68. end
  69.  
  70. TokyoCabinet.open("leak.tch") do |db|
  71. db[:some_key] = "X" * 1024
  72. 10.times do
  73. 5000.times do
  74. db[:some_key] # reading causes the memory leak
  75. end
  76. show_memory
  77. end
  78. end
Add Comment
Please, Sign In to add comment