LuaJIT FFI

From FxCodeBaseWiki
Jump to: navigation, search

What Is It

The FFI library allows calling external C functions and using C data structures from the pure Lua code. The FFI library is a part of LuaJIT so it may only be used in this mode. You can find more information about FFI at LuaJIT FFI Library

How It Works

LuaJIT hastens executions of the pure Lua code. Execution speed is comparable with native code (C++) execution. However, execution speed will fall if Indicore functions are called because LuaJIT switches to working in the Lua virtual machine. If a lot of Indicore functions are called, all advantages of using LuaJIT will be lost. To solve this problem, use FFI API for indicators with high performance requirements.

The FFI library allows calling native Indicore functions directly from Lua. This does not require switching to the Lua virtual machine. Moreover, this type of call does not require executing the intermediate layer code between Lua and Indicore which significantly hastens execution. However, there are some disadvantages to this method. In standard mode, when an indicator passes wrong parameters to any Indicore function, execution is stopped by the Indicore core. When using FFI, this may crash the whole application.

What Is It For

Indicore FFI API is intended for indicators with high performance requirements that are executed in the LuaJIT mode. For example standard indicators. Since they are used by multiple custom indicators and strategies, these indicators should provide maximum performance. That is why all standard FXTS indicators use FFI in the LuaJIT mode. In other modes FFI is not used.

For custom indicators, we suggest using FFI carefully and only for indicators intended to be used in the LuaJIT mode because of high performance requirements. We also suggest optimizing the indicator code before using FFI. See Indicator Optimization.

Please note that by default custom strategies and indicators are prohibited to use FFI. The user should either select the Allow FFI option in the Extension Permissions options category prior to installing a strategy/indicator which will allow FFI for all extensions that will be installed later or allow FFI for a particular extension using dialog Manage Extensions after installing a strategy/indicator (recommended).

How To Use It

Indicore defines ffi global boolean variable that has true value if an indicator/strategy works in the FFI mode. In this case Lua functions of the indicore3_ffi table are allowed to be used.

Depending on how often FFI will be used, one of the following patterns may be used.

If there are a lot of FFI calls, the FFI check may done from out of the function. This way there will be two functions with the same names and parameters. One of them will work in the FFI mode, the other one will work in standard:

if ffi then

function Update(period, mode)
  -- implementation used in FFI mode
end

else

function Update(period, mode)
  -- implementation used in non-FFI mode
end

end

If there are not so many FFI calls, the FFI check may be done within the function by calling either FFI or a standard Indicore function:

function Update(period, mode)
  -- some code here

  if ffi then
    -- implementation used in FFI mode
  else
    -- implementation used in non-FFI mode
  end

  -- some code here
end

When in the FFI mode, Indicore provides the indicore3_ffi table that contains a lot of static functions. Each of these functions has a counterpart among standard (non-FFI) Indicore functions. In Help, functions are described as declarations of called C++ functions. Most functions with complicated argument type (such as streams) have call examples.

You can also study code of standard FXTS indicators.

Recommendations on Using FFI

  • FFI can be used in the LuaJIT mode only.
  • Use FFI only when it is really necessary.
  • Use FFI for frequently executed calls. For example the code within Update and Draw functions.
  • Make sure the indicator can work both in FFI and standard modes.
  • Executing native calls using the FFI is still slower than executing pure Lua code in the LuaJIT mode. That is why if Indicore data is not planned to be frequently used (price streams for example) and what is needed is to just process some numbers, Lua code may be more effective. This relates to creating custom Lua extensions on C++.
  • FFI usage for custom extensions should be explicitly allowed by the user.

This Article in Other Languages

Language: English