diff options
author | Chris Seaton <chris@chrisseaton.com> | 2020-05-19 00:12:47 +0100 |
---|---|---|
committer | Nobuyoshi Nakada <nobu@ruby-lang.org> | 2020-05-23 14:34:07 +0900 |
commit | 3015a7aae7ddc9b63149df34b1f12366e07a9563 (patch) | |
tree | d8717bceae57a47f2257f8701c02423d51dab62f /ext/fiddle | |
parent | 24b615e82ee327a9ac583937de746ba12dde2d6a (diff) |
[ruby/fiddle] Improve documentation on how to correctly free memory and free memory in tests (#33)
https://github.com/ruby/fiddle/commit/e59cfd708a
Diffstat (limited to 'ext/fiddle')
-rw-r--r-- | ext/fiddle/lib/fiddle/struct.rb | 11 | ||||
-rw-r--r-- | ext/fiddle/pointer.c | 26 |
2 files changed, 31 insertions, 6 deletions
diff --git a/ext/fiddle/lib/fiddle/struct.rb b/ext/fiddle/lib/fiddle/struct.rb index 8a48a1cb8b..259903d25c 100644 --- a/ext/fiddle/lib/fiddle/struct.rb +++ b/ext/fiddle/lib/fiddle/struct.rb @@ -73,7 +73,12 @@ module Fiddle # # MyStruct = Fiddle::CStructBuilder.create(Fiddle::CUnion, types, members) # - # obj = MyStruct.allocate + # obj = MyStruct.malloc + # begin + # ... + # ensure + # Fiddle.free obj.to_ptr + # end # def create(klass, types, members) new_class = Class.new(klass){ @@ -112,7 +117,7 @@ module Fiddle # Allocates a C struct with the +types+ provided. # - # When the instance is garbage collected, the C function +func+ is called. + # See Fiddle::Pointer.malloc for memory management issues. def CStructEntity.malloc(types, func = nil) addr = Fiddle.malloc(CStructEntity.size(types)) CStructEntity.new(addr, types, func) @@ -267,7 +272,7 @@ module Fiddle # Allocates a C union the +types+ provided. # - # When the instance is garbage collected, the C function +func+ is called. + # See Fiddle::Pointer.malloc for memory management issues. def CUnionEntity.malloc(types, func=nil) addr = Fiddle.malloc(CUnionEntity.size(types)) CUnionEntity.new(addr, types, func) diff --git a/ext/fiddle/pointer.c b/ext/fiddle/pointer.c index 117cc9b826..7c60da477a 100644 --- a/ext/fiddle/pointer.c +++ b/ext/fiddle/pointer.c @@ -193,14 +193,34 @@ rb_fiddle_ptr_initialize(int argc, VALUE argv[], VALUE self) /* * call-seq: - * * Fiddle::Pointer.malloc(size, freefunc = nil) => fiddle pointer instance * + * == Examples + * + * # Relying on the garbage collector - may lead to unlimited memory allocated before freeing any, but safe + * pointer = Fiddle::Pointer.malloc(size, Fiddle::RUBY_FREE) + * ... + * + * # Manual freeing + * pointer = Fiddle::Pointer.malloc(size) + * begin + * ... + * ensure + * Fiddle.free pointer + * end + * + * # No free function and no call to free - the native memory will leak if the pointer is garbage collected + * pointer = Fiddle::Pointer.malloc(size) + * ... + * * Allocate +size+ bytes of memory and associate it with an optional * +freefunc+ that will be called when the pointer is garbage collected. - * * +freefunc+ must be an address pointing to a function or an instance of - * Fiddle::Function + * +Fiddle::Function+. Using +freefunc+ may lead to unlimited memory being + * allocated before any is freed as the native memory the pointer references + * does not contribute to triggering the Ruby garbage collector. Consider + * manually freeing the memory as illustrated above. You cannot combine + * the techniques as this may lead to a double-free. */ static VALUE rb_fiddle_ptr_s_malloc(int argc, VALUE argv[], VALUE klass) |