Class: Omnizip::Formats::Rpm::Header

Inherits:
Object
  • Object
show all
Includes:
Constants
Defined in:
lib/omnizip/formats/rpm/header.rb

Overview

RPM header parser

Parses RPM header structure including the 16-byte header header, tag entries, and data blob. Used for both signature and main headers.

Constant Summary

Constants included from Constants

Constants::FILE_CONFIG, Constants::FILE_DOC, Constants::FILE_LICENSE, Constants::FILE_README, Constants::FLAG_EQUAL, Constants::FLAG_GREATER, Constants::FLAG_LESS, Constants::HEADER_HEADER_SIZE, Constants::HEADER_MAGIC, Constants::HEADER_SIGNED_TYPE, Constants::LEAD_MAGIC, Constants::LEAD_SIZE, Constants::PACKAGE_BINARY, Constants::PACKAGE_SOURCE, Constants::TAG_ENTRY_SIZE, Constants::TYPE_BINARY, Constants::TYPE_CHAR, Constants::TYPE_I18NSTRING, Constants::TYPE_INT16, Constants::TYPE_INT32, Constants::TYPE_INT64, Constants::TYPE_INT8, Constants::TYPE_NULL, Constants::TYPE_STRING, Constants::TYPE_STRING_ARRAY

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#data_lengthInteger (readonly)

Returns Data blob length.

Returns:

  • (Integer)

    Data blob length



20
21
22
# File 'lib/omnizip/formats/rpm/header.rb', line 20

def data_length
  @data_length
end

#entry_countInteger (readonly)

Returns Number of tag entries.

Returns:

  • (Integer)

    Number of tag entries



17
18
19
# File 'lib/omnizip/formats/rpm/header.rb', line 17

def entry_count
  @entry_count
end

#lengthInteger (readonly)

Returns Total header length.

Returns:

  • (Integer)

    Total header length



26
27
28
# File 'lib/omnizip/formats/rpm/header.rb', line 26

def length
  @length
end

#magicString (readonly)

Returns 8-byte header magic.

Returns:

  • (String)

    8-byte header magic



14
15
16
# File 'lib/omnizip/formats/rpm/header.rb', line 14

def magic
  @magic
end

#tagsArray<Tag> (readonly)

Returns Parsed tags.

Returns:

  • (Array<Tag>)

    Parsed tags



23
24
25
# File 'lib/omnizip/formats/rpm/header.rb', line 23

def tags
  @tags
end

Class Method Details

.parse(io) ⇒ Header

Parse header from IO

Parameters:

  • io (IO)

    Input stream positioned at header

Returns:

  • (Header)

    Parsed header object

Raises:

  • (ArgumentError)

    If magic is invalid



33
34
35
# File 'lib/omnizip/formats/rpm/header.rb', line 33

def self.parse(io)
  new.tap { |header| header.parse!(io) }
end

Instance Method Details

#[](name) ⇒ Object?

Get tag value by name

Parameters:

  • name (Symbol)

    Tag name

Returns:

  • (Object, nil)

    Tag value or nil if not found



41
42
43
44
# File 'lib/omnizip/formats/rpm/header.rb', line 41

def [](name)
  tag = find_tag(name)
  tag&.value
end

#find_tag(name) ⇒ Tag?

Find tag by name

Parameters:

  • name (Symbol)

    Tag name

Returns:

  • (Tag, nil)

    Tag object or nil



50
51
52
# File 'lib/omnizip/formats/rpm/header.rb', line 50

def find_tag(name)
  @tags.find { |t| t.name == name }
end

#parse!(io) ⇒ Object

Raises:

  • (ArgumentError)


73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
# File 'lib/omnizip/formats/rpm/header.rb', line 73

def parse!(io)
  # Read header header (16 bytes)
  header_data = io.read(HEADER_HEADER_SIZE)
  raise ArgumentError, "Failed to read RPM header" unless header_data

  @magic = header_data[0, 8]
  @entry_count = header_data[8, 4].unpack1("N")
  @data_length = header_data[12, 4].unpack1("N")

  validate!

  # Read tag entries
  tag_data_size = @entry_count * TAG_ENTRY_SIZE
  tag_entries_data = io.read(tag_data_size)

  # Read data blob
  data_blob = io.read(@data_length)

  # Parse tags
  @tags = []
  @entry_count.times do |i|
    offset = i * TAG_ENTRY_SIZE
    entry = tag_entries_data[offset, TAG_ENTRY_SIZE].unpack("NNNN")

    tag = Tag.new(entry[0], entry[1], entry[2], entry[3], data_blob)
    @tags << tag
  end

  @length = HEADER_HEADER_SIZE + tag_data_size + @data_length
end

#to_hHash

Get all tags as hash

Returns:

  • (Hash)

    Tag names to values



57
58
59
60
61
# File 'lib/omnizip/formats/rpm/header.rb', line 57

def to_h
  @tags.to_h do |tag|
    [tag.name, tag.value]
  end
end

#validate!Object

Validate header

Raises:

  • (ArgumentError)

    If validation fails



66
67
68
69
70
71
# File 'lib/omnizip/formats/rpm/header.rb', line 66

def validate!
  unless @magic == HEADER_MAGIC
    raise ArgumentError,
          "Invalid header magic: #{@magic.inspect}"
  end
end