module GDAL::InternalHelpers::ClassMethods

Public Instance Methods

_buffer_from_data_type(data_type, size = nil) click to toggle source

@param data_type [FFI::GDAL::GDAL::DataType] @param size [Integer] Size of the pointer to allocate. @return [FFI::Buffer]

# File lib/gdal/internal_helpers.rb, line 55
def _buffer_from_data_type(data_type, size = nil)
  pointer_type = _gdal_data_type_to_ffi(data_type)

  if size
    FFI::Buffer.alloc_inout(pointer_type, size)
  else
    FFI::Buffer.alloc_inout(pointer_type)
  end
end
_cpl_read_and_free_string() { |result_ptr_ptr| ... } click to toggle source

Convenience function for allocating a pointer to a string (**char), yielding the pointer so it can written to (i.e. passed to a GDAL/OGR function to be written to), then reads the string out of the buffer, then calls FFI::CPL::VSI.VSIFree (which is an alias for FFI::CPL::Conv.CPLFree).

@yield [FFI::MemoryPointer] @return [String]

# File lib/gdal/internal_helpers.rb, line 120
def _cpl_read_and_free_string
  result_ptr_ptr = GDAL._pointer_pointer(:string)
  result_ptr_ptr.autorelease = false

  yield result_ptr_ptr

  result = if result_ptr_ptr.null?
             ""
           else
             GDAL._read_pointer_pointer_safely(result_ptr_ptr, :string)
           end

  FFI::CPL::VSI.VSIFree(result_ptr_ptr)

  result
end
_gdal_access_flag(char) click to toggle source

@param char [String] ‘r’ or ‘w’ @return [Symbol] :GF_Read if ‘r’ or :GF_Write if ‘w’. @raise [GDAL::InvalidAccessFlag] If char is not ‘r’ or ‘w’.

# File lib/gdal/internal_helpers.rb, line 245
def _gdal_access_flag(char)
  case char
  when "r" then :GF_Read
  when "w" then :GF_Write
  else raise GDAL::InvalidAccessFlag, "Invalid access flag: #{char}"
  end
end
_gdal_data_type_to_ffi(data_type) click to toggle source

Maps GDAL DataTypes to FFI types.

@param data_type [FFI::GDAL::GDAL::DataType] @return [Symbol]

# File lib/gdal/internal_helpers.rb, line 141
def _gdal_data_type_to_ffi(data_type)
  case data_type
  when :GDT_Byte                    then :uchar
  when :GDT_Int8                    then :int8
  when :GDT_UInt16                  then :uint16
  when :GDT_Int16, :GDT_CInt16      then :int16
  when :GDT_UInt32                  then :uint32
  when :GDT_Int32, :GDT_CInt32      then :int32
  when :GDT_UInt64                  then :uint64
  when :GDT_Int64                   then :int64
  when :GDT_Float32, :GDT_CFloat32  then :float
  when :GDT_Float64, :GDT_CFloat64  then :double
  else
    raise GDAL::InvalidDataType, "Unknown data type: #{data_type}"
  end
end
_gdal_data_type_to_narray(data_type) click to toggle source

Maps GDAL DataTypes to NArray types.

@param data_type [FFI::GDAL::GDAL::DataType] @return [Symbol]

# File lib/gdal/internal_helpers.rb, line 162
def _gdal_data_type_to_narray(data_type)
  case data_type
  when :GDT_Byte                                then :byte
  when :GDT_Int16                               then :sint
  when :GDT_UInt16, :GDT_Int32, :GDT_UInt32     then :int
  when :GDT_Float32                             then :float
  when :GDT_Float64                             then :dfloat
  when :GDT_CInt16, :GDT_CInt32                 then :scomplex
  when :GDT_CFloat32                            then :complex
  when :GDT_CFloat64                            then :dcomplex
  else
    raise GDAL::InvalidDataType, "Unknown data type: #{data_type}"
  end
end
_gdal_data_type_to_narray_type_constant(data_type) click to toggle source

Maps GDAL DataTypes to NArray type constants.

@param data_type [FFI::GDAL::GDAL::DataType] @return [Symbol]

# File lib/gdal/internal_helpers.rb, line 181
def _gdal_data_type_to_narray_type_constant(data_type)
  case data_type
  when :GDT_Byte                            then NArray::BYTE
  when :GDT_Int16                           then NArray::SINT
  when :GDT_UInt16, :GDT_Int32, :GDT_UInt32 then NArray::INT
  when :GDT_Float32                         then NArray::FLOAT
  when :GDT_Float64                         then NArray::DFLOAT
  when :GDT_CInt16, :GDT_CInt32             then NArray::SCOMPLEX
  when :GDT_CFloat32                        then NArray::COMPLEX
  when :GDT_CFloat64                        then NArray::DCOMPLEX
  else
    raise GDAL::InvalidDataType, "Unknown data type: #{data_type}"
  end
end
_narray_from_data_type(data_type, *narray_args) click to toggle source

@param data_type [FFI::GDAL::GDAL::DataType] @param narray_args Args to pass to the NArray initializer. @return [NArray]

# File lib/gdal/internal_helpers.rb, line 68
def _narray_from_data_type(data_type, *narray_args)
  init_meth = _gdal_data_type_to_narray(data_type)
  narray_args = 0 if narray_args.empty?

  NArray.send(init_meth, *narray_args)
end
_pointer(klass, variable, warn_on_nil: true, autorelease: true) click to toggle source

Internal factory method for returning a pointer from variable, which could be either of klass class or a type of FFI::Pointer.

@param klass [Class] @param variable [Object] @param warn_on_nil [Boolean] If true, print out warning that the method

couldn't do what it's supposed to do.

@param autorelease [Boolean] Pass this on to the pointer. @return [FFI::Pointer, nil]

# File lib/gdal/internal_helpers.rb, line 20
def _pointer(klass, variable, warn_on_nil: true, autorelease: true)
  case variable
  when klass
    variable.c_pointer.autorelease = autorelease
    variable.c_pointer
  when FFI::MemoryPointer
    variable.autorelease = autorelease
    variable
  when FFI::Pointer
    # This is a C-allocated pointer and needs to be freed using a C method,
    # and thus shouldn't be autorelease-freed.
    variable
  else
    if warn_on_nil && Logger.logging_enabled
      Logger.logger.debug "<#{name}._pointer> #{variable.inspect} is not a valid #{klass} or FFI::Pointer."
      Logger.logger.debug "<#{name}._pointer> Called at:"
      caller(1, 2).each { |line| Logger.logger.debug "<#{name}._pointer>\t#{line}" }
    end

    nil
  end
end
_pointer_from_data_type(data_type, size = nil) click to toggle source

@param data_type [FFI::GDAL::GDAL::DataType] @param size [Integer] Size of the pointer to allocate. @return [FFI::MemoryPointer]

# File lib/gdal/internal_helpers.rb, line 46
def _pointer_from_data_type(data_type, size = nil)
  pointer_type = _gdal_data_type_to_ffi(data_type)

  size ? FFI::MemoryPointer.new(pointer_type, size) : FFI::MemoryPointer.new(pointer_type)
end
_pointer_pointer(type) click to toggle source

@param type [Symbol] FFI type of pointer to make a pointer to. @return [FFI::MemoryPointer] Pointer to a pointer.

# File lib/gdal/internal_helpers.rb, line 97
def _pointer_pointer(type)
  pointer = FFI::MemoryPointer.new(type)
  pointer_ptr = FFI::MemoryPointer.new(:pointer)
  pointer_ptr.write_pointer(pointer)

  pointer_ptr
end
_read_pointer(pointer, data_type, length = 1) click to toggle source

Helper method for reading an FFI pointer based on the GDAL DataType of the pointer.

@param pointer [FFI::Pointer] The pointer to read from. @param data_type [FFI::GDAL::GDAL::DataType] The GDAL data type that

determines what FFI type to use when reading.

@param length [Integer] The amount of data to read from the pointer. If

> 1, the "read_array_of_" method will be called.

@return [Number, Array<Number>]

# File lib/gdal/internal_helpers.rb, line 205
def _read_pointer(pointer, data_type, length = 1)
  if length == 1
    pointer.send(:"read_#{_gdal_data_type_to_ffi(data_type)}")
  else
    pointer.send(:"read_array_of_#{_gdal_data_type_to_ffi(data_type)}", length)
  end
end
_read_pointer_pointer_safely(pointer_ptr, type) click to toggle source

@return [String, nil]

# File lib/gdal/internal_helpers.rb, line 106
def _read_pointer_pointer_safely(pointer_ptr, type)
  return if pointer_ptr.read_pointer.null?

  pointer_ptr.read_pointer.send(:"read_#{type}")
end
_string_array_to_pointer(strings) click to toggle source

Takes an array of strings (or things that should be converted to strings) and creates a char**.

@param strings [Array<String>] @return [FFI::MemoryPointer]

# File lib/gdal/internal_helpers.rb, line 80
def _string_array_to_pointer(strings)
  string_pointers = strings.map { |string| FFI::MemoryPointer.from_string(string.to_s) }
  string_pointers << nil
  array_pointer = FFI::MemoryPointer.new(:pointer, strings.size + 1)
  i = 0

  # fast-ruby says while is faster than each_with_index
  while i < string_pointers.length
    array_pointer[i].put_pointer(0, string_pointers[i])
    i += 1
  end

  array_pointer
end
_supported?(function_name) click to toggle source

Check to see if the function is supported in the version of GDAL that we’re using.

@param function_name [Symbol] @return [Boolean] TODO: Should the respond_to? check all FFI::GDAL::* classes? What about

OGR?
# File lib/gdal/internal_helpers.rb, line 237
def _supported?(function_name)
  !FFI::GDAL.unsupported_gdal_functions.include?(function_name) &&
    FFI::GDAL::GDAL.respond_to?(function_name)
end
_write_pointer(pointer, data_type, data) click to toggle source

Helper method for writing data to an FFI pointer based on the GDAL DataType of the pointer.

@param pointer [FFI::Pointer] The pointer to write to. @param data_type [FFI::GDAL::GDAL::DataType] The GDAL data type that

determines what FFI type to use when writing.

@param data [Integer] The data to write to the pointer. If it’s an Array

with size > 1, the "write_array_of_" method will be called.
# File lib/gdal/internal_helpers.rb, line 221
def _write_pointer(pointer, data_type, data)
  if data.is_a?(Array) && data.size > 1
    pointer.send(:"write_array_of_#{_gdal_data_type_to_ffi(data_type)}", data)
  else
    data = data.first if data.is_a?(Array)
    pointer.send(:"write_#{_gdal_data_type_to_ffi(data_type)}", data)
  end
end