Class: LGPIO::SPIBitBang
- Inherits:
-
Object
- Object
- LGPIO::SPIBitBang
- Defined in:
- lib/lgpio/spi_bitbang.rb
Instance Attribute Summary collapse
-
#clock_handle ⇒ Object
readonly
Returns the value of attribute clock_handle.
-
#clock_line ⇒ Object
readonly
Returns the value of attribute clock_line.
-
#input_handle ⇒ Object
readonly
Returns the value of attribute input_handle.
-
#input_line ⇒ Object
readonly
Returns the value of attribute input_line.
-
#output_handle ⇒ Object
readonly
Returns the value of attribute output_handle.
-
#output_line ⇒ Object
readonly
Returns the value of attribute output_line.
Instance Method Summary collapse
- #config ⇒ Object
-
#initialize(options = {}) ⇒ SPIBitBang
constructor
A new instance of SPIBitBang.
- #initialize_pins ⇒ Object
- #set_output(level) ⇒ Object
- #transfer(write: [], read: 0, select: nil, order: :msbfirst, mode: 0) ⇒ Object
- #transfer_bit(write_bit, reading: false, mode: 0) ⇒ Object
- #transfer_byte(byte, reading: false, order: :msbfirst, mode: 0) ⇒ Object
Constructor Details
#initialize(options = {}) ⇒ SPIBitBang
Returns a new instance of SPIBitBang.
6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
# File 'lib/lgpio/spi_bitbang.rb', line 6 def initialize(={}) clock = [:clock] input = [:input] output = [:output] @clock_handle = clock[:handle] if clock @clock_line = clock[:line] if clock raise ArgumentError, ":clock pin required as Hash, with :handle and :line required" unless (@clock_handle && @clock_line) @input_handle = input[:handle] if input @input_line = input[:line] if input @output_handle = output[:handle] if output @output_line = output[:line] if output unless ((@input_handle && @input_line) || (@output_handle && @output_line)) raise ArgumentError, "either :input or :output pin required as Hash, with :handle and :line required" end @output_state = nil initialize_pins end |
Instance Attribute Details
#clock_handle ⇒ Object (readonly)
Returns the value of attribute clock_handle.
3 4 5 |
# File 'lib/lgpio/spi_bitbang.rb', line 3 def clock_handle @clock_handle end |
#clock_line ⇒ Object (readonly)
Returns the value of attribute clock_line.
4 5 6 |
# File 'lib/lgpio/spi_bitbang.rb', line 4 def clock_line @clock_line end |
#input_handle ⇒ Object (readonly)
Returns the value of attribute input_handle.
3 4 5 |
# File 'lib/lgpio/spi_bitbang.rb', line 3 def input_handle @input_handle end |
#input_line ⇒ Object (readonly)
Returns the value of attribute input_line.
4 5 6 |
# File 'lib/lgpio/spi_bitbang.rb', line 4 def input_line @input_line end |
#output_handle ⇒ Object (readonly)
Returns the value of attribute output_handle.
3 4 5 |
# File 'lib/lgpio/spi_bitbang.rb', line 3 def output_handle @output_handle end |
#output_line ⇒ Object (readonly)
Returns the value of attribute output_line.
4 5 6 |
# File 'lib/lgpio/spi_bitbang.rb', line 4 def output_line @output_line end |
Instance Method Details
#config ⇒ Object
27 28 29 |
# File 'lib/lgpio/spi_bitbang.rb', line 27 def config @config ||= [clock_handle, clock_line, input_handle, input_line, output_handle, output_line] end |
#initialize_pins ⇒ Object
31 32 33 34 35 |
# File 'lib/lgpio/spi_bitbang.rb', line 31 def initialize_pins LGPIO.gpio_claim_output(clock_handle, clock_line, LGPIO::SET_PULL_NONE, LGPIO::LOW) LGPIO.gpio_claim_input(input_handle, input_line, LGPIO::SET_PULL_NONE) if input_line LGPIO.gpio_claim_output(output_handle, output_line, LGPIO::SET_PULL_NONE, LGPIO::LOW) if output_line end |
#set_output(level) ⇒ Object
37 38 39 40 |
# File 'lib/lgpio/spi_bitbang.rb', line 37 def set_output(level) return if (level == @output_state) LGPIO.gpio_write(output_handle, output_line, @output_state = level) end |
#transfer(write: [], read: 0, select: nil, order: :msbfirst, mode: 0) ⇒ Object
94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 |
# File 'lib/lgpio/spi_bitbang.rb', line 94 def transfer(write: [], read: 0, select: nil, order: :msbfirst, mode: 0) # Idle clock state depends on SPI mode. case mode when 0..1 LGPIO.gpio_write(clock_handle, clock_line, 0) when 2..3 LGPIO.gpio_write(clock_handle, clock_line, 1) else raise ArgumentError, "invalid SPI mode: #{mode} given" end raise ArgumentError, "invalid Array for write: #{write}" unless write.kind_of?(Array) raise ArgumentError, "invalid Integer for read: #{read}" unless read.kind_of?(Integer) read_bytes = (read > 0) ? [] : nil LGPIO.gpio_write(select[:handle], select[:line], 0) if select i = 0 while (i < read) || (i < write.length) read_byte = transfer_byte(write[i], reading: (i < read), order: order, mode: mode) read_bytes << read_byte if read_byte i = i + 1 end LGPIO.gpio_write(select[:handle], select[:line], 1) if select read_bytes end |
#transfer_bit(write_bit, reading: false, mode: 0) ⇒ Object
42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 |
# File 'lib/lgpio/spi_bitbang.rb', line 42 def transfer_bit(write_bit, reading: false, mode: 0) case mode when 0 set_output(write_bit) if write_bit LGPIO.gpio_write(clock_handle, clock_line, 1) read_bit = LGPIO.gpio_read(input_handle, input_line) if reading LGPIO.gpio_write(clock_handle, clock_line, 0) when 1 LGPIO.gpio_write(clock_handle, clock_line, 1) set_output(write_bit) if write_bit LGPIO.gpio_write(clock_handle, clock_line, 0) read_bit = LGPIO.gpio_read(input_handle, input_line) if reading when 2 set_output(write_bit) if write_bit LGPIO.gpio_write(clock_handle, clock_line, 0) read_bit = LGPIO.gpio_read(input_handle, input_line) if reading LGPIO.gpio_write(clock_handle, clock_line, 1) when 3 LGPIO.gpio_write(clock_handle, clock_line, 0) set_output(write_bit) if write_bit LGPIO.gpio_write(clock_handle, clock_line, 1) read_bit = LGPIO.gpio_read(input_handle, input_line) if reading else raise ArgumentError, "invalid SPI mode: #{mode} given" end return reading ? read_bit : nil end |
#transfer_byte(byte, reading: false, order: :msbfirst, mode: 0) ⇒ Object
70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 |
# File 'lib/lgpio/spi_bitbang.rb', line 70 def transfer_byte(byte, reading: false, order: :msbfirst, mode: 0) read_byte = reading ? 0 : nil if (order == :msbfirst) i = 7 while i >= 0 write_bit = byte ? (byte >> i) & 0b1 : nil read_bit = transfer_bit(write_bit, mode: mode, reading: reading) read_byte = (read_byte << 1) | read_bit if reading i = i - 1 end else i = 0 while i < 8 write_bit = byte ? (byte >> i) : nil read_bit = transfer_bit(write_bit, mode: mode, reading: reading) read_byte = read_byte | (read_bit << i) if reading i = i + 1 end end read_byte end |