class HexData

@author Marek K. <m.k@mk16.de, mk16.de> @example

require "hexdata"
hex = HexData.new [":04001000746573742C", ":0D00000048656C6C6F20576F726C642100B6", ":10004000404142434445464748494A4B4C4D4E4F38", ":00000001FF"] # Open to read
hex.interpret # Interpret data
p hex.ascii # return string result of the interpret
p hex.checksum # return checksum from the first data
p hex.checksum 1 # return checksum from the second data

hex = HexData.new # Open to write/read
hex.push "test" # Write "test"
hex.push_end # Write End of File
hex.interpret # Interpret data
p hex.ascii 0 # return string result of the interpret of the first data

@attr [Integer] push_address The address of the next record in the (Intel) hex file @attr [String] enddef The “end of file” mark @note The file hexdata.rb is available under the {www.gnu.org/licenses/gpl.txt GNU GPL v3}.

Attributes

enddef[RW]
push_address[RW]

Public Class Methods

new(sets=[]) click to toggle source

Initalies the cash register hexdata @param sets [Array] The (Intel) hex data to be read or edited. Default: []

# File lib/hexdata.rb, line 57
def initialize sets=[]
  @sets = sets
  @push_address = 16
  @enddef = ":00000001FF"
end

Public Instance Methods

ascii(index=nil) click to toggle source

Reads the result, the ASCII / ANSI text, the evaluation (interpretation). @param index [Integer] The index of the record to be read. If all is to be read out, nil can be transferred. Default: nil @return The result of all records, if no index was specified, otherwise only the result of the record from which the index was specified.

# File lib/hexdata.rb, line 167
def ascii index=nil
  return (index ? @ascii[index] : @ascii.join(""))
end
checksum?(index=0) click to toggle source

Reads the checksum of a record. @param index [Integer] The index of the record from which the checksum is to be read. Default: 0 @return [Integer] The read checksum

# File lib/hexdata.rb, line 160
def checksum? index=0
  return @sums[index]
end
clear!() click to toggle source

Resets the hex data. All saved hex data will be deleted. Then HexData is ready to write. @return [NilClass] nil

# File lib/hexdata.rb, line 136
def clear!
  @sets = nil.to_a
  @sums = nil.to_a
  @push_address = 16
  nil
end
data() click to toggle source

Returns the records @note No copy of the array is created. If you edit the arrays, this affects the HexData class. If you want a copy of the array, you can, for example, use the .clone method. @return [Array] The records returned as an array

# File lib/hexdata.rb, line 66
def data
  @sets
end
data_end?() click to toggle source

Returns the index of the first record that detected an “End of File” markup. @return [Integer] The index of the first element where an “End of file”-mark was detected.

# File lib/hexdata.rb, line 151
def data_end?
  for i in 0...@sets.length
    return i if @sets[i] == @enddef
  end
end
delete_data!(index) click to toggle source

The string to be written. @param index [Integer] The index of the record to be deleted. @return [NilClass] nil

# File lib/hexdata.rb, line 129
def delete_data! index
  @sets.delete_at index
  nil
end
interpret() click to toggle source

Evaluate the (Intel) Hex data (interpretation) and make it available for reading. @return [NilClass] nil

# File lib/hexdata.rb, line 72
def interpret
  @ascii = nil.to_a
  @sums = nil.to_a
  @sets.each { |data|
    if data[0] != ":"
      raise "Invalid data! Data: #{data}"
    end
  
    len = data[1 .. 2].to_i 16
    address = data[3 .. 6]
    type = data[7 .. 8]
    field = data[9 .. len * 2 + 8]
    sum = data[-2 .. -1].to_i 16
    str = ""

    csum = len + address.to_i(16) + type.to_i(16)
    #p field
    for i in (0..field.length-1).step(2)
      v = field[i .. i + 1].to_i 16
      csum += v
      str += v.chr
    end
  
    csum &= 255
    bsum = ""
    csum.to_s(2).each_char { |c| bsum += (c=="0"?"1":"0") }
    while bsum.length < 8
      bsum = "1" + bsum
    end

    if bsum.to_i(2) + 1 != sum
      raise "Invalid checksum! Data: #{data}"
    end
    @ascii << str if type == "00"
    @sums << sum
  }
  nil
end
max_index?() click to toggle source

Returns the number of records. @return [Integer] The number of records.

# File lib/hexdata.rb, line 145
def max_index?
  @sets.length
end
push(str) click to toggle source

Write a user-entered text to the records as (Intel) Hex. @param str [String] The text to be written to the records. @return [NilClass] nil

# File lib/hexdata.rb, line 181
def push str

  if @push_address > 65535
    raise "To many data!"
  end

  sum = str.length + @push_address
  res = "#{str.length.to_s 16}"
  while res.length < 2
    res = "0" + res
  end
  
  res = ":" + res
  
  tmp = @push_address.to_s 16
  while tmp.length < 4
    tmp = "0" + tmp
  end
  res += tmp + "00"
  
  str.each_char { |c|
    sum += c.ord
    tmp = c.ord.to_s 16
    while tmp.length < 2
      tmp = "0" + tmp
    end
    res += tmp
  }
  
  sum &= 255
  bsum = ""
  sum.to_s(2).each_char { |c| bsum += (c=="0"?"1":"0") }
  while bsum.length < 8
    bsum = "1" + bsum
  end

  res += bsum.to_i(2).+(1).to_s 16
  @sets << res
  @push_address += 1
end
push_end() click to toggle source

Writes the “End of file” mark. This is appended to the end of the records. @return [NilClass] nil

# File lib/hexdata.rb, line 173
def push_end
  @sets << @enddef
  nil
end
push_user(str) click to toggle source

Writes a string passed by the user to the data. @param str [String] The user data to be written as a record. @return [NilClass] nil

# File lib/hexdata.rb, line 121
def push_user str
  @sets << str
  nil
end
reset_address!() click to toggle source

Resets the write address to the default value (16). @return [NilClass] nil

# File lib/hexdata.rb, line 113
def reset_address!
  @push_address = 16
  nil
end