Brincando com FFI no
Ruby
1º Floripa on Rails - 2015
@wevtimoteo
O que é FFI?
FFI (Foreign Function Interface) é um mecanismo
pela qual, um programa escrito em determinada
linguagem, pode realizar chamadas, funções e
comunicar-se outros programas e serviços de
linguagens distintas.
http://www.c2.com/cgi/wiki?ForeignFunctionInterface
Método spawn
Executa um comando e retorna o pid
RubyInline
Automaticamente determina se o código em questão
mudou e só roda build quando necessário.
As extensões são automaticamente carregadas na
classe/módulo que a definiu.
Por padrão suporta apenas C/C++
https://github.com/seattlerb/rubyinline
Exemplo usando RubyInline
Mais rápido?
JavaInline
Plugin para RubyInline que adiciona suporte a
linguagens da JVM (Java, Scala e Mirah)
https://github.com/jruby/java_inline
Exemplo usando JavaInline
RubyFFI
"FFI is a fantastic tool for easily interfacing your Ruby
code with native libraries.
Using FFI, you can use native libraries from Ruby
without writing a single line of native code."
https://github.com/ffi/ffi/wiki/Core-Concepts
Exemplo usando FFI
Vantagens de utilizar FFI
• Não, necessariamente, escrever código da linguagem
que está integrando
• Mesmo código em qualquer interpretador Ruby (MRI,
JRuby, Rubinius)
• Melhor para outros membros do time, principalmente
se tratando de uma gem
• Instalar apenas libs de runtime
• Não quebra por mudanças na API interna do Ruby
Componentes do Ruby FFI
FFI::Library - utilizada ao chamar `require 'ffi'`
FFI::Pointer - segura memória alocada pela
biblioteca terceira.
FFI::MemoryPointer - permite o Ruby alocar
memória nativa e passá-la para bibliotecas não-
Ruby. Também controla ciclo de vida de objetos em
memória
FFI::Struct e FFI::Union
Gerenciamento de Memória
• Biblioteca/Linguagem utilizada
• Interpretador Ruby utilizado
• Dois tipos de pilha de memória: Ruby e nativa.
Pilha de memória Ruby é gerenciado pelo GC do
interpretador.
Tipos
• :char and :uchar - 8 bit signed and unsigned values
• :short and :ushort - 16 bit signed and unsigned values
• :int and :uint - 32 bit signed and unsigned values
• :long_long and :ulong_long - 64 bit signed and unsigned values
• :long and :ulong - native cpu word (32 bit or 64bit) signed and unsigned values.
Equivalent to C 'long' type.
• :float and :double
• :string - C string, NULL terminated.
• :pointer - a C pointer
https://github.com/ffi/ffi/wiki/Types
NULL ou nil?
Quando usar FFI pode não
ser uma boa ideia?
• Cada milisegundo conta
• Tempo alto de compilação
• Uso intenso de callbacks
Obrigado!
http://www.slideshare.net/wevtimoteo/brincando-com-ffi-no-ruby
ou
http://goo.gl/TsP1Ei
https://github.com/wevtimoteo/ruby-ffi-examples
Referências
• https://github.com/ffi/ffi/wiki/Core-Concepts
• http://apidock.com/ruby/Kernel/spawn
• http://www.slideshare.net/delagoya/ruby-ffi
• http://www.sitepoint.com/detecting-faces-with-ruby-
ffi-in-a-nutshell/
• http://www.akitaonrails.com/2015/06/05/primeiros-
passos-brincando-de-rust-ruby-ffi#.VY7zPhNViko