minilab 2.0.0-x86-mingw32

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (42) hide show
  1. data/.document +2 -0
  2. data/.gitignore +2 -0
  3. data/CHANGES +22 -0
  4. data/Gemfile +3 -0
  5. data/LICENSE +19 -0
  6. data/README.rdoc +101 -0
  7. data/Rakefile +25 -0
  8. data/doc/UniLib.chm +0 -0
  9. data/doc/minilab-1008.pdf +0 -0
  10. data/doc/minilab_systest_setup.txt +38 -0
  11. data/doc/port_mapping.txt +2 -0
  12. data/lib/minilab/analog_io.rb +25 -0
  13. data/lib/minilab/connection_state.rb +15 -0
  14. data/lib/minilab/digital_auxport_io.rb +36 -0
  15. data/lib/minilab/digital_configuration.rb +55 -0
  16. data/lib/minilab/digital_port_io.rb +41 -0
  17. data/lib/minilab/library_translator.rb +48 -0
  18. data/lib/minilab/minilab.rb +130 -0
  19. data/lib/minilab/minilab_constants.rb +22 -0
  20. data/lib/minilab/minilab_context.rb +18 -0
  21. data/lib/minilab/minilab_hardware.rb +118 -0
  22. data/lib/minilab/minilab_wrapper.rb +14 -0
  23. data/lib/minilab/objects.yml +24 -0
  24. data/lib/minilab/version.rb +3 -0
  25. data/lib/minilab.rb +14 -0
  26. data/minilab.gemspec +32 -0
  27. data/spec/acceptance/analog_spec.rb +35 -0
  28. data/spec/acceptance/digital_port_spec.rb +81 -0
  29. data/spec/acceptance/digital_screw_terminal_spec.rb +22 -0
  30. data/spec/spec_helper.rb +102 -0
  31. data/spec/unit/analog_io_spec.rb +55 -0
  32. data/spec/unit/connection_state_spec.rb +14 -0
  33. data/spec/unit/digital_auxport_io_spec.rb +98 -0
  34. data/spec/unit/digital_configuration_spec.rb +96 -0
  35. data/spec/unit/digital_port_io_spec.rb +65 -0
  36. data/spec/unit/library_translator_spec.rb +86 -0
  37. data/spec/unit/minilab_context_spec.rb +17 -0
  38. data/spec/unit/minilab_hardware_spec.rb +17 -0
  39. data/spec/unit/minilab_spec.rb +104 -0
  40. data/spec/unit/minilab_wrapper_spec.rb +20 -0
  41. data/vendor/mcc/cbw32.dll +0 -0
  42. metadata +192 -0
@@ -0,0 +1,118 @@
1
+ require "ffi"
2
+ require "pathname"
3
+
4
+ module Minilab
5
+ class MinilabHardware
6
+ include MinilabConstants
7
+
8
+ def setup_error_handling(reporting, handling)
9
+ create_error_hash cbErrHandling(reporting, handling)
10
+ end
11
+
12
+ def declare_revision(revision)
13
+ memory = FFI::MemoryPointer.new :float
14
+ memory.write_float(revision)
15
+ create_error_hash cbDeclareRevision(memory)
16
+ end
17
+
18
+ def get_revision
19
+ dll_revision_number = FFI::MemoryPointer.new :float
20
+ vxd_revision_number = FFI::MemoryPointer.new :float
21
+ error = cbGetRevision(dll_revision_number, vxd_revision_number)
22
+ create_error_or_value_hash(error, dll_revision_number.read_float)
23
+ end
24
+
25
+ def get_error_string(error)
26
+ message = FFI::MemoryPointer.new :char, ERRSTRLEN
27
+ new_error = cbGetErrMsg(error, message)
28
+ if new_error != 0
29
+ create_error_hash(new_error)
30
+ else
31
+ message.read_string
32
+ end
33
+ end
34
+
35
+ def configure_auxport(optz)
36
+ raise ":pin is a required parameter" if optz[:pin].nil?
37
+ raise ":direction is a required parameter" if optz[:direction].nil?
38
+ create_error_hash cbDConfigBit(BOARDNUM, AUXPORT, optz[:pin], optz[:direction])
39
+ end
40
+
41
+ def configure_port(optz)
42
+ raise ":port is a required parameter" if optz[:port].nil?
43
+ raise ":direction is a required parameter" if optz[:direction].nil?
44
+ create_error_hash cbDConfigPort(BOARDNUM, optz[:port], optz[:direction])
45
+ end
46
+
47
+ def read_analog(channel)
48
+ raw_data = FFI::MemoryPointer.new :ushort
49
+ error = cbAIn(BOARDNUM, channel, BIP10VOLTS, raw_data)
50
+ return create_error_hash(error) if error != 0
51
+
52
+ voltage = FFI::MemoryPointer.new :float
53
+ error = cbToEngUnits(BOARDNUM, BIP10VOLTS, raw_data.get_ushort(0), voltage)
54
+ create_error_or_value_hash(error, voltage.read_float)
55
+ end
56
+
57
+ def read_digital_pin(pin)
58
+ data = FFI::MemoryPointer.new :ushort
59
+ error = cbDBitIn(BOARDNUM, FIRSTPORTA, pin, data)
60
+ create_error_or_value_hash(error, data.get_ushort(0))
61
+ end
62
+
63
+ def read_auxport(pin)
64
+ data = FFI::MemoryPointer.new :ushort
65
+ error = cbDBitIn(BOARDNUM, AUXPORT, pin, data)
66
+ create_error_or_value_hash(error, data.get_ushort(0))
67
+ end
68
+
69
+ def read_port(port)
70
+ data = FFI::MemoryPointer.new :ushort
71
+ error = cbDIn(BOARDNUM, port, data)
72
+ create_error_or_value_hash(error, data.get_ushort(0))
73
+ end
74
+
75
+ def write_analog(channel, volts)
76
+ raw_data = FFI::MemoryPointer.new :ushort
77
+ error = cbFromEngUnits(BOARDNUM, UNI5VOLTS, volts, raw_data)
78
+ return create_error_hash(error) if error != 0
79
+ error = cbAOut(BOARDNUM, channel, UNI5VOLTS, raw_data.get_ushort(0))
80
+ create_error_hash(error)
81
+ end
82
+
83
+ def write_digital_pin(pin, data)
84
+ create_error_hash cbDBitOut(BOARDNUM, FIRSTPORTA, pin, data)
85
+ end
86
+
87
+ def write_auxport(pin, data)
88
+ create_error_hash cbDBitOut(BOARDNUM, AUXPORT, pin, data)
89
+ end
90
+
91
+ private
92
+ def create_error_or_value_hash(error, value)
93
+ error != 0 ? { :error => error } : { :value => value }
94
+ end
95
+
96
+ def create_error_hash(error)
97
+ create_error_or_value_hash(error, true)
98
+ end
99
+
100
+ MCC_LIBRARY = Pathname.new(__FILE__).dirname.join("..", "..", "vendor", "mcc", "cbw32.dll")
101
+ extend FFI::Library
102
+ ffi_lib MCC_LIBRARY
103
+
104
+ attach_function "cbErrHandling", [:int, :int], :int
105
+ attach_function "cbDeclareRevision", [:pointer], :int
106
+ attach_function "cbGetRevision", [:pointer, :pointer], :int
107
+ attach_function "cbGetErrMsg", [:int, :pointer], :int
108
+ attach_function "cbDConfigBit", [:int, :int, :int, :int], :int
109
+ attach_function "cbDConfigPort", [:int, :int, :int], :int
110
+ attach_function "cbAIn", [:int, :int, :int, :pointer], :int
111
+ attach_function "cbToEngUnits", [:int, :int, :ushort, :pointer], :int
112
+ attach_function "cbFromEngUnits", [:int, :int, :float, :pointer], :int
113
+ attach_function "cbDBitIn", [:int, :int, :int, :pointer], :int
114
+ attach_function "cbDIn", [:int, :int, :pointer], :int
115
+ attach_function "cbAOut", [:int, :int, :int, :ushort], :int
116
+ attach_function "cbDBitOut", [:int, :int, :int, :ushort], :int
117
+ end
118
+ end
@@ -0,0 +1,14 @@
1
+ module Minilab
2
+ class MinilabWrapper #:nodoc:
3
+ constructor :minilab_hardware
4
+
5
+ def method_missing(method, *argz)
6
+ result = @minilab_hardware.send(method, *argz)
7
+ if result[:error]
8
+ message = @minilab_hardware.get_error_string(result[:error])
9
+ raise "Command [#{method}(#{argz.inspect})] caused a hardware error: #{message}"
10
+ end
11
+ result[:value]
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,24 @@
1
+ using_namespace Minilab:
2
+ minilab:
3
+ compose: minilab_wrapper, analog_io, digital_auxport_io, digital_port_io, connection_state
4
+
5
+ connection_state:
6
+
7
+ minilab_wrapper:
8
+ compose: minilab_hardware
9
+
10
+ minilab_hardware:
11
+
12
+ analog_io:
13
+ compose: minilab_wrapper
14
+
15
+ digital_auxport_io:
16
+ compose: minilab_wrapper
17
+
18
+ digital_port_io:
19
+ compose: minilab_wrapper, digital_configuration, library_translator
20
+
21
+ library_translator:
22
+
23
+ digital_configuration:
24
+ compose: minilab_wrapper
@@ -0,0 +1,3 @@
1
+ module Minilab
2
+ VERSION = "2.0.0"
3
+ end
data/lib/minilab.rb ADDED
@@ -0,0 +1,14 @@
1
+ require "constructor"
2
+
3
+ require_relative "minilab/minilab_constants"
4
+ require_relative "minilab/minilab_context"
5
+
6
+ require_relative "minilab/analog_io"
7
+ require_relative "minilab/connection_state"
8
+ require_relative "minilab/digital_auxport_io"
9
+ require_relative "minilab/digital_configuration"
10
+ require_relative "minilab/digital_port_io"
11
+ require_relative "minilab/library_translator"
12
+ require_relative "minilab/minilab"
13
+ require_relative "minilab/minilab_hardware"
14
+ require_relative "minilab/minilab_wrapper"
data/minilab.gemspec ADDED
@@ -0,0 +1,32 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "minilab/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "minilab"
7
+ s.version = Minilab::VERSION
8
+ s.platform = Gem::Platform::CURRENT
9
+ s.authors = ["Matt Fletcher"]
10
+ s.email = ["fletcher@atomicobject.com"]
11
+ s.homepage = "http://atomicobject.github.com/minilab"
12
+ s.summary = %q{Ruby interface to Measurement Computing's miniLAB 1008}
13
+ s.description = "#{s.summary} "
14
+
15
+ s.add_dependency "constructor", "~>2.0"
16
+ s.add_dependency "diy", "~>1.1"
17
+ s.add_dependency "ffi", "~>1.0"
18
+
19
+ s.add_development_dependency "steak", "~>1.0"
20
+ s.add_development_dependency "rr", "~>1.0"
21
+
22
+ s.rubyforge_project = "minilab"
23
+
24
+ s.has_rdoc = true
25
+ s.extra_rdoc_files = %w[ README.rdoc CHANGES LICENSE ]
26
+ s.rdoc_options = %w[ --main README.rdoc --title minilab ]
27
+
28
+ s.files = `git ls-files`.split("\n")
29
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
30
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
31
+ s.require_paths = ["lib"]
32
+ end
@@ -0,0 +1,35 @@
1
+ require_relative "../spec_helper"
2
+
3
+ feature "Analog" do
4
+ scenario "inputs" do
5
+ analog_input_4_should_be_about 5.0
6
+
7
+ analog_input_1_should_be_about 0.0
8
+ end
9
+
10
+ scenario "outputs" do
11
+ write_analog_1 5.0
12
+ analog_input_0_should_be_about 5.0
13
+
14
+ write_analog_1 0.0
15
+ analog_input_0_should_be_about 0.0
16
+
17
+ write_analog_1 2.77
18
+ analog_input_0_should_be_about 2.77
19
+
20
+ write_analog_1 3.19
21
+ analog_input_0_should_be_about 3.19
22
+
23
+ write_analog_0 5.0
24
+ analog_input_6_should_be_about 5.0
25
+
26
+ write_analog_0 0.0
27
+ analog_input_6_should_be_about 0.0
28
+
29
+ write_analog_0 3.75
30
+ analog_input_6_should_be_about 3.75
31
+
32
+ write_analog_0 1.88
33
+ analog_input_6_should_be_about 1.88
34
+ end
35
+ end
@@ -0,0 +1,81 @@
1
+ require_relative "../spec_helper"
2
+
3
+ feature "Digital ports" do
4
+ scenario "reading bits" do
5
+ configure_portb_for_input
6
+ digital_pin_10_should_be 1
7
+
8
+ configure_porta_for_input
9
+ digital_pin_30_should_be 0
10
+ end
11
+
12
+ scenario "writing bits" do
13
+ # Port A --> Port B
14
+ configure_porta_for_output
15
+ configure_portb_for_input
16
+
17
+ write_digital_pin_36 1
18
+ digital_pin_7_should_be 1
19
+
20
+ write_digital_pin_36 0
21
+ digital_pin_7_should_be 0
22
+
23
+ # Port B --> Port CL
24
+ configure_portb_for_output
25
+ configure_portcl_for_input
26
+
27
+ write_digital_pin_5 0
28
+ digital_pin_28_should_be 0
29
+
30
+ write_digital_pin_5 1
31
+ digital_pin_28_should_be 1
32
+
33
+ # Port CL -> Port CH
34
+ configure_portcl_for_output
35
+ configure_portch_for_input
36
+
37
+ write_digital_pin_27 1
38
+ digital_pin_22_should_be 1
39
+
40
+ write_digital_pin_27 0
41
+ digital_pin_22_should_be 0
42
+
43
+ # Port CH -> Port A
44
+ configure_portch_for_output
45
+ configure_porta_for_input
46
+
47
+ write_digital_pin_24 0
48
+ digital_pin_34_should_be 0
49
+
50
+ write_digital_pin_24 1
51
+ digital_pin_34_should_be 1
52
+ end
53
+
54
+ scenario "reading bytes" do
55
+ configure_porta_for_output
56
+ configure_portcl_for_output
57
+ configure_portb_for_input
58
+
59
+ # GND to pin 3 (portb bit 7)
60
+ # GND to pin 4 (portb bit 6)
61
+ write_digital_pin_28 1 # map to pin 5 (portb bit 5)
62
+ # GND to pin 6 (portb bit 4)
63
+ write_digital_pin_36 1 # map to pin 7 (portb bit 3)
64
+ # GND to pin 8 (portb bit 2)
65
+ # GND to pin 9 (portb bit 1)
66
+ # +5v to pin 10 (portb bit 0)
67
+ digital_portb_should_be 0x29
68
+
69
+
70
+
71
+ configure_porta_for_output
72
+ configure_portcl_for_output
73
+ configure_portch_for_input
74
+
75
+ write_digital_pin_27 1 # map to pin 22 (portch bit 3)
76
+ # GND to pin 23 (portch bit 2)
77
+ write_digital_pin_32 1 # map to pin 24 (portch bit 1)
78
+ # GND to pin 22 (portch bit 0)
79
+ digital_portch_should_be 0x0A
80
+ end
81
+ end
@@ -0,0 +1,22 @@
1
+ require_relative "../spec_helper"
2
+
3
+ feature "Digital screw terminals" do
4
+ scenario "input" do
5
+ dio1_should_be 1
6
+ dio2_should_be 0
7
+ end
8
+
9
+ scenario "output" do
10
+ write_dio0 1
11
+ dio3_should_be 1
12
+
13
+ write_dio0 0
14
+ dio3_should_be 0
15
+
16
+ write_dio0 0
17
+ analog_input_2_should_be_about 0.0
18
+
19
+ write_dio0 1
20
+ analog_input_2_should_be_greater_than 0.0
21
+ end
22
+ end
@@ -0,0 +1,102 @@
1
+ require_relative "../lib/minilab"
2
+ require "steak"
3
+
4
+ module MinilabUnitSpecHelpers
5
+ def create_mocks(*mox)
6
+ mox.inject({}) do |bag, name|
7
+ the_mock = Object.new
8
+ self.instance_variable_set("@#{name}", mock(the_mock))
9
+ bag[name] = the_mock
10
+ bag
11
+ end
12
+ end
13
+ end
14
+
15
+ module MinilabAcceptanceSpecHelpers
16
+ GOOD_DELTA = 0.12
17
+ VALID_PORTS = [:porta, :portb, :portcl, :portch]
18
+ VALID_PINS = (30..37).to_a + (3..10).to_a + (26..29).to_a + (22..25).to_a
19
+
20
+ # Analog input methods
21
+ 0.upto(7) do |channel|
22
+ define_method("analog_input_#{channel}_should_be_about") do |value|
23
+ input = @minilab.read_analog(channel)
24
+ assert_in_delta(value, input, GOOD_DELTA, "Input voltage was not ~#{value} volts")
25
+ end
26
+
27
+ define_method("analog_input_#{channel}_should_be_greater_than") do |value|
28
+ volts = @minilab.read_analog(channel)
29
+ assert volts > (value + GOOD_DELTA)
30
+ end
31
+ end
32
+
33
+ # Analog output methods
34
+ [0, 1].each do |channel|
35
+ define_method("write_analog_#{channel}") do |value|
36
+ @minilab.write_analog(channel, value)
37
+ sleep 0.1
38
+ end
39
+ end
40
+
41
+ # Digital pin input and output methods
42
+ VALID_PINS.each do |pin|
43
+ define_method("digital_pin_#{pin}_should_be") do |value|
44
+ assert_equal value, @minilab.read_digital(pin)
45
+ end
46
+
47
+ define_method("write_digital_pin_#{pin}") do |value|
48
+ @minilab.write_digital(pin, value)
49
+ end
50
+ end
51
+
52
+ # Digital port read (entire bytes) methods
53
+ VALID_PORTS.each do |port|
54
+ define_method("digital_#{port}_should_be") do |value|
55
+ assert_equal value, @minilab.read_digital_byte(port)
56
+ end
57
+ end
58
+
59
+ # DIOx input and output methods
60
+ 0.upto(3) do |pin|
61
+ define_method("dio#{pin}_should_be") do |value|
62
+ assert_equal value, @minilab.read_digital("dio#{pin}")
63
+ end
64
+
65
+ define_method("write_dio#{pin}") do |value|
66
+ @minilab.write_digital("dio#{pin}", value)
67
+ end
68
+ end
69
+
70
+ # Configuration methods
71
+ VALID_PORTS.each do |port|
72
+ define_method("configure_#{port}_for_input") do
73
+ @minilab.configure_input_port(port)
74
+ end
75
+
76
+ define_method("configure_#{port}_for_output") do
77
+ @minilab.configure_output_port(port)
78
+ end
79
+ end
80
+
81
+ # Other
82
+ def minilab_revision_should_be(revision)
83
+ assert_equal revision, @minilab.get_revision
84
+ end
85
+ end
86
+
87
+ RSpec.configure do |config|
88
+ # Using both to minimize the amount of porting work.
89
+ # most assertions are still test:unit based, but some
90
+ # (like exceptions) us rspec
91
+ config.expect_with :stdlib, :rspec
92
+ config.mock_framework = :rr
93
+
94
+ config.include Minilab::MinilabConstants
95
+
96
+ config.include MinilabUnitSpecHelpers
97
+ config.include MinilabAcceptanceSpecHelpers, :type => :acceptance
98
+ config.before(:all, :type => :acceptance) do
99
+ @minilab = Minilab.build
100
+ @minilab.connect
101
+ end
102
+ end
@@ -0,0 +1,55 @@
1
+ require_relative "../spec_helper"
2
+
3
+ describe Minilab::AnalogIo do
4
+ before { @mox = create_mocks(:minilab_wrapper) }
5
+ subject { described_class.new(@mox) }
6
+
7
+ it "read analog data" do
8
+ @minilab_wrapper.read_analog(2).returns 5.7
9
+ assert_equal 5.7, subject.read_analog(2)
10
+ end
11
+
12
+ it "raise an exception when analog input channel is out of range" do
13
+ # The minilab device has 8 analog inputs (when used in straight
14
+ # input mode, not differential). We expect that exceptions
15
+ # it be thrown for channels that are out of bounds.
16
+ -> { subject.read_analog(-1) }.should raise_error
17
+ 0.upto(7) do |channel|
18
+ @minilab_wrapper.read_analog(channel).returns(1.0)
19
+ -> { subject.read_analog(channel) }.should_not raise_error
20
+ end
21
+ -> { subject.read_analog(8) }.should raise_error
22
+ end
23
+
24
+ it "write analog data" do
25
+ @minilab_wrapper.write_analog(1, 4.5)
26
+ subject.write_analog(1, 4.5)
27
+ end
28
+
29
+ it "raise an error when analog output voltage is out of range" do
30
+ -> { subject.write_analog(0, -0.1) }.should raise_error
31
+
32
+ @minilab_wrapper.write_analog(0, 0.0)
33
+ -> { subject.write_analog(0, 0.0) }.should_not raise_error
34
+
35
+ @minilab_wrapper.write_analog(0, 2.1)
36
+ -> { subject.write_analog(0, 2.1) }.should_not raise_error
37
+
38
+ @minilab_wrapper.write_analog(0, 5.0)
39
+ -> { subject.write_analog(0, 5.0) }.should_not raise_error
40
+
41
+ -> { subject.write_analog(0, 5.1) }.should raise_error
42
+ end
43
+
44
+ it "raise an error when analog output channel is out of range" do
45
+ -> { subject.write_analog(-1, 0.0) }.should raise_error
46
+
47
+ @minilab_wrapper.write_analog(0, 0.0)
48
+ -> { subject.write_analog(0, 0.0) }.should_not raise_error
49
+
50
+ @minilab_wrapper.write_analog(1, 0.0)
51
+ -> { subject.write_analog(1, 0.0) }.should_not raise_error
52
+
53
+ -> { subject.write_analog(2, 0.0) }.should raise_error
54
+ end
55
+ end
@@ -0,0 +1,14 @@
1
+ require_relative "../spec_helper.rb"
2
+
3
+ describe Minilab::ConnectionState do
4
+ it "default to an unconnected state" do
5
+ assert_equal false, subject.connected?
6
+ end
7
+
8
+ it "allow the connection state to be changed" do
9
+ subject.connected = true
10
+ assert_equal true, subject.connected?
11
+ subject.connected = false
12
+ assert_equal false, subject.connected?
13
+ end
14
+ end
@@ -0,0 +1,98 @@
1
+ require_relative "../spec_helper"
2
+
3
+ describe Minilab::DigitalAuxportIo do
4
+ before { @mox = create_mocks(:minilab_wrapper) }
5
+ subject { described_class.new(@mox) }
6
+
7
+ it "read digital data from the screw terminals" do
8
+ expected_configuration = { :direction => DIGITALIN, :pin => get_pin_number("DIO1") }
9
+ @minilab_wrapper.configure_auxport(expected_configuration)
10
+ @minilab_wrapper.read_auxport(get_pin_number("DIO1")).returns 1
11
+
12
+ assert_equal 1, subject.read_digital('DIO1')
13
+ end
14
+
15
+ it "raise an error when digital input pin is not valid" do
16
+ make_sure_bad_pins_blow_up
17
+
18
+ good_pins.each do |pin|
19
+ expected_configuration = { :direction => DIGITALIN, :pin => get_pin_number(pin) }
20
+ @minilab_wrapper.configure_auxport(expected_configuration)
21
+ @minilab_wrapper.read_auxport(get_pin_number(pin)).returns 0
22
+ -> { subject.read_digital(pin) }.should_not raise_error
23
+ end
24
+ end
25
+
26
+ # Output tests
27
+ it "write digital data to the screw terminals" do
28
+ expected_configuration = { :direction => DIGITALOUT, :pin => get_pin_number("DIO1") }
29
+ @minilab_wrapper.configure_auxport(expected_configuration)
30
+ @minilab_wrapper.write_auxport(get_pin_number("DIO1"), 1)
31
+
32
+ subject.write_digital("DIO1", 1)
33
+ end
34
+
35
+ it "write 1 to a digital output when the commanded value is anything not 0" do
36
+ expected_configuration = { :direction => DIGITALOUT, :pin => get_pin_number("DIO1") }
37
+ @minilab_wrapper.configure_auxport(expected_configuration)
38
+ @minilab_wrapper.write_auxport(get_pin_number("DIO1"), 1)
39
+ subject.write_digital("DIO1", 173)
40
+
41
+ @minilab_wrapper.configure_auxport(expected_configuration)
42
+ @minilab_wrapper.write_auxport(get_pin_number("DIO1"), 1)
43
+ subject.write_digital("DIO1", 872)
44
+ end
45
+
46
+ it "raise an exception if someone tries to command a negative value" do
47
+ -> { subject.write_digital("DIO2", -1) }.should raise_error
48
+ -> { subject.write_digital("DIO2", -80) }.should raise_error
49
+ end
50
+
51
+ it "raise an exception when digital output pin is out of range" do
52
+ make_sure_bad_pins_blow_up
53
+
54
+ good_pins.each do |pin|
55
+ expected_configuration = { :direction => DIGITALOUT, :pin => get_pin_number(pin) }
56
+ @minilab_wrapper.configure_auxport(expected_configuration)
57
+ @minilab_wrapper.write_auxport(get_pin_number(pin), 1)
58
+ -> { subject.write_digital(pin, 1) }.should_not raise_error
59
+ end
60
+ end
61
+
62
+ it "accept case-insensitive DIO strings as pins" do
63
+ expected_configuration = { :direction => DIGITALOUT, :pin => get_pin_number("DIO1") }
64
+ @minilab_wrapper.configure_auxport(expected_configuration)
65
+ @minilab_wrapper.write_auxport(get_pin_number("DIO1"), 1)
66
+ subject.write_digital('dio1', 1)
67
+
68
+ expected_configuration = { :direction => DIGITALOUT, :pin => get_pin_number("DIO2") }
69
+ @minilab_wrapper.configure_auxport(expected_configuration)
70
+ @minilab_wrapper.write_auxport(get_pin_number("DIO2"), 1)
71
+ subject.write_digital('dIo2', 1)
72
+
73
+ expected_configuration = { :direction => DIGITALIN, :pin => get_pin_number("DIO0") }
74
+ @minilab_wrapper.configure_auxport(expected_configuration)
75
+ @minilab_wrapper.read_auxport(get_pin_number("DIO0")).returns 1
76
+ subject.read_digital('DiO0')
77
+
78
+ expected_configuration = { :direction => DIGITALIN, :pin => get_pin_number("DIO3") }
79
+ @minilab_wrapper.configure_auxport(expected_configuration)
80
+ @minilab_wrapper.read_auxport(get_pin_number("DIO3")).returns 1
81
+ subject.read_digital('diO3')
82
+ end
83
+
84
+ private
85
+ def get_pin_number(pin)
86
+ pin.match(/(\d)$/)[0].to_i
87
+ end
88
+
89
+ def good_pins
90
+ %w[ DIO0 DIO1 DIO2 DIO3 ]
91
+ end
92
+
93
+ def make_sure_bad_pins_blow_up
94
+ [ 'yourmom', 'bill', nil, false, 55, 'DIO4', -1, 38 ].each do |pin|
95
+ -> { subject.read_digital(pin) }.should raise_error
96
+ end
97
+ end
98
+ end