From 8b5e81ed867ed8b3788696c4b82018e4fd130091 Mon Sep 17 00:00:00 2001 From: Francois Best Date: Tue, 4 Oct 2016 18:56:18 -0700 Subject: [PATCH] Added MIDI IO tests. --- .../unit-tests/tests/unit-tests_MidiInput.cpp | 55 +++++++ .../tests/unit-tests_MidiOutput.cpp | 146 ++++++++++++++++++ 2 files changed, 201 insertions(+) diff --git a/test/unit-tests/tests/unit-tests_MidiInput.cpp b/test/unit-tests/tests/unit-tests_MidiInput.cpp index 1c271f0..9ff755f 100644 --- a/test/unit-tests/tests/unit-tests_MidiInput.cpp +++ b/test/unit-tests/tests/unit-tests_MidiInput.cpp @@ -48,6 +48,39 @@ TEST(MidiInput, getTypeFromStatusByte) EXPECT_EQ(MidiInterface::getTypeFromStatusByte(0xfd), midi::InvalidType); } +TEST(MidiInput, getChannelFromStatusByte) +{ + EXPECT_EQ(MidiInterface::getChannelFromStatusByte(0x00), 1); + EXPECT_EQ(MidiInterface::getChannelFromStatusByte(0x80), 1); + EXPECT_EQ(MidiInterface::getChannelFromStatusByte(0x94), 5); + EXPECT_EQ(MidiInterface::getChannelFromStatusByte(0xaf), 16); +} + +TEST(MidiInput, isChannelMessage) +{ + EXPECT_EQ(MidiInterface::isChannelMessage(midi::InvalidType), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::NoteOff), true); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::NoteOn), true); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::AfterTouchPoly), true); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::ControlChange), true); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::ProgramChange), true); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::AfterTouchChannel), true); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::PitchBend), true); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::SystemExclusive), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::TimeCodeQuarterFrame), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::SongPosition), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::SongSelect), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::TuneRequest), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::Clock), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::Start), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::Continue), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::Stop), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::ActiveSensing), false); + EXPECT_EQ(MidiInterface::isChannelMessage(midi::SystemReset), false); +} + +// -- + TEST(MidiInput, begin) { SerialMock serial; @@ -64,4 +97,26 @@ TEST(MidiInput, begin) EXPECT_EQ(midi.getInputChannel(), 12); } +TEST(MidiInput, initInputChannel) +{ + SerialMock serial; + MidiInterface midi(serial); + + EXPECT_EQ(midi.getInputChannel(), 0); + midi.setInputChannel(12); + EXPECT_EQ(midi.getInputChannel(), 12); +} + +TEST(MidiInput, initMessage) +{ + SerialMock serial; + MidiInterface midi(serial); + EXPECT_EQ(midi.getType(), midi::InvalidType); + EXPECT_EQ(midi.getChannel(), 0); + EXPECT_EQ(midi.getData1(), 0); + EXPECT_EQ(midi.getData2(), 0); + EXPECT_EQ(midi.getSysExArrayLength(), 0); + EXPECT_EQ(midi.check(), false); +} + END_UNNAMED_NAMESPACE diff --git a/test/unit-tests/tests/unit-tests_MidiOutput.cpp b/test/unit-tests/tests/unit-tests_MidiOutput.cpp index e69de29..a03685a 100644 --- a/test/unit-tests/tests/unit-tests_MidiOutput.cpp +++ b/test/unit-tests/tests/unit-tests_MidiOutput.cpp @@ -0,0 +1,146 @@ +#include "unit-tests.h" +#include +#include + +BEGIN_MIDI_NAMESPACE + +END_MIDI_NAMESPACE + +// ----------------------------------------------------------------------------- + +BEGIN_UNNAMED_NAMESPACE + +template +struct VariableSettings : public midi::DefaultSettings +{ + static const bool UseRunningStatus = RunningStatus; + static const bool Use1ByteParsing = OneByteParsing; +}; + +template +const bool VariableSettings::UseRunningStatus; +template +const bool VariableSettings::Use1ByteParsing; + +using namespace testing; +typedef test_mocks::SerialMock<32> SerialMock; +typedef midi::MidiInterface MidiInterface; + +// -- + +TEST(MidiOutput, sendSingle) +{ + SerialMock serial; + MidiInterface midi(serial); + test_mocks::uint8 buffer[3] = { 0 }; + + midi.begin(); + midi.send(midi::NoteOn, 47, 42, 12); + EXPECT_EQ(serial.mTxBuffer.getLength(), 3); + serial.mTxBuffer.read(buffer, 3); + EXPECT_THAT(buffer, ElementsAre(0x9b, 47, 42)); +} + +TEST(MidiOutput, sendWithRunningStatus) +{ + SerialMock serial; + MidiInterface midi(serial); + test_mocks::uint8 buffer[5] = { 0 }; + + midi.begin(); + EXPECT_EQ(MidiInterface::Settings::UseRunningStatus, true); + EXPECT_EQ(serial.mTxBuffer.isEmpty(), true); + midi.send(midi::NoteOn, 47, 42, 12); + midi.send(midi::NoteOn, 42, 47, 12); + EXPECT_EQ(serial.mTxBuffer.getLength(), 5); + serial.mTxBuffer.read(buffer, 5); + EXPECT_THAT(buffer, ElementsAre(0x9b, 47, 42, 42, 47)); +} + +TEST(MidiOutput, sendWithoutRunningStatus) +{ + typedef VariableSettings Settings; // No running status + typedef midi::MidiInterface MidiInterface; + + SerialMock serial; + MidiInterface midi(serial); + test_mocks::uint8 buffer[6] = { 0 }; + + // Same status byte + midi.begin(); + EXPECT_EQ(MidiInterface::Settings::UseRunningStatus, false); + EXPECT_EQ(serial.mTxBuffer.isEmpty(), true); + midi.send(midi::NoteOn, 47, 42, 12); + midi.send(midi::NoteOn, 42, 47, 12); + EXPECT_EQ(serial.mTxBuffer.getLength(), 6); + serial.mTxBuffer.read(buffer, 6); + EXPECT_THAT(buffer, ElementsAre(0x9b, 47, 42, 0x9b, 42, 47)); + + // Different status byte + midi.begin(); + midi.send(midi::NoteOn, 47, 42, 12); + midi.send(midi::NoteOff, 47, 42, 12); + EXPECT_EQ(serial.mTxBuffer.getLength(), 6); + serial.mTxBuffer.read(buffer, 6); + EXPECT_THAT(buffer, ElementsAre(0x9b, 47, 42, 0x8b, 47, 42)); +} + +TEST(MidiOutput, sendBreakingRunningStatus) +{ + SerialMock serial; + MidiInterface midi(serial); + test_mocks::uint8 buffer[6] = { 0 }; + + midi.begin(); + midi.send(midi::NoteOn, 47, 42, 12); + midi.send(midi::NoteOff, 47, 42, 12); + EXPECT_EQ(serial.mTxBuffer.getLength(), 6); + serial.mTxBuffer.read(buffer, 6); + EXPECT_THAT(buffer, ElementsAre(0x9b, 47, 42, 0x8b, 47, 42)); +} + +TEST(MidiOutput, sendMultipleNoteOff) +{ + SerialMock serial; + MidiInterface midi(serial); + test_mocks::uint8 buffer[5] = { 0 }; + + midi.begin(); + midi.send(midi::NoteOff, 10, 11, 12); + midi.send(midi::NoteOff, 12, 13, 12); + EXPECT_EQ(serial.mTxBuffer.getLength(), 5); + serial.mTxBuffer.read(buffer, 5); + EXPECT_THAT(buffer, ElementsAre(0x8b, 10, 11, 12, 13)); +} + +/* TEST(MidiOutput, Issue41) +{ + typedef VariableSettings Settings; // Running status, multibyte parsing + typedef midi::MidiInterface MidiInterface; + + // #41: issue with sending series of ControlChange + SerialMock serial; + MidiInterface midi(serial); + test_mocks::uint8 buffer[9] = { 0 }; + + midi.begin(MIDI_CHANNEL_OMNI); + midi.turnThruOff(); + + // Simulate some pitch bend messages + serial.mRxBuffer.write(0xe0); + serial.mRxBuffer.write(0); + serial.mRxBuffer.write(12); + serial.mRxBuffer.write(0); + serial.mRxBuffer.write(42); + serial.mRxBuffer.write(0); + serial.mRxBuffer.write(47); + midi.read(); + + EXPECT_EQ(serial.mTxBuffer.getLength(), 9); + serial.mTxBuffer.read(buffer, 9); + EXPECT_THAT(buffer, ElementsAre(0xbb, 80, 42, 80, 47, 80, 42, 80, 47)); +} */ + +// -- + +END_UNNAMED_NAMESPACE