# File lib/innodb/page/index.rb, line 281
  def record_header(cursor)
    origin = cursor.position
    header = {}
    cursor.backward.name("header") do |c|
      case page_header[:format]
      when :compact
        # The "next" pointer is a relative offset from the current record.
        header[:next] = c.name("next") { origin + c.get_sint16 }

        # Fields packed in a 16-bit integer (LSB first):
        #   3 bits for type
        #   13 bits for heap_number
        bits1 = c.name("bits1") { c.get_uint16 }
        header[:type] = RECORD_TYPES[bits1 & 0x07]
        header[:heap_number] = (bits1 & 0xfff8) >> 3
      when :redundant
        # The "next" pointer is an absolute offset within the page.
        header[:next] = c.name("next") { c.get_uint16 }

        # Fields packed in a 24-bit integer (LSB first):
        #   1 bit for offset_size (0 = 2 bytes, 1 = 1 byte)
        #   10 bits for n_fields
        #   13 bits for heap_number
        bits1 = c.name("bits1") { c.get_uint24 }
        header[:offset_size]  = (bits1 & 1) == 0 ? 2 : 1
        header[:n_fields]     = (bits1 & (((1 << 10) - 1) <<  1)) >>  1
        header[:heap_number]  = (bits1 & (((1 << 13) - 1) << 11)) >> 11
      end

      # Fields packed in an 8-bit integer (LSB first):
      #   4 bits for n_owned
      #   4 bits for flags
      bits2 = c.name("bits2") { c.get_uint8 }
      header[:n_owned] = bits2 & 0x0f
      info = (bits2 & 0xf0) >> 4
      header[:min_rec] = (info & RECORD_INFO_MIN_REC_FLAG) != 0
      header[:deleted] = (info & RECORD_INFO_DELETED_FLAG) != 0

      case page_header[:format]
      when :compact
        record_header_compact_additional(header, cursor)
      when :redundant
        record_header_redundant_additional(header, cursor)
      end

      header[:length] = origin - cursor.position
    end

    header
  end