// ----------------------------------------- // SoundScribe (TM) and related software. // // Copyright (C) 2007-2011 Vannatech // http://www.vannatech.com // All rights reserved. // // This source code is subject to the MIT License. // http://www.opensource.org/licenses/mit-license.php // // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN // THE SOFTWARE. // ----------------------------------------- using System; using System.Linq; using CoreAudioTests.Common; using Microsoft.VisualStudio.TestTools.UnitTesting; using Vannatech.CoreAudio.Interfaces; using Vannatech.CoreAudio.Constants; using System.Collections.Generic; using Vannatech.CoreAudio.Enumerations; namespace CoreAudioTests.DeviceTopologyApi { // TODO: Create a custom test manager for IConnector tests, and properly dispose of COM interfaces. /// /// Tests all methods of the IConnector interface. /// [TestClass] public class IConnectorTest { /// /// Tests that each available connector in the system may be connectors to other connectors. /// [TestMethod] public void IConnector_ConnectTo() { int result = 0; IEnumerable inputConnectors, outputConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out inputConnectors, out outputConnectors); foreach (var cIn in inputConnectors) { bool isConnected; IConnector inOrig = null; cIn.IsConnected(out isConnected); if (isConnected) cIn.GetConnectedTo(out inOrig); // New try connection to each output connector foreach (var cOut in outputConnectors) { IConnector outOrig; cOut.GetConnectedTo(out outOrig); // Start by disconnecting the connectors cIn.Disconnect(); cOut.Disconnect(); // Connect the input and output result = cIn.ConnectTo(cOut); AssertCoreAudio.IsHResultOk(result); // Verify the connection was made. string cInId, idVerify; ((IPart)cIn).GetGlobalId(out cInId); cOut.GetConnectorIdConnectedTo(out idVerify); Assert.AreEqual(cInId, idVerify, "The connector IDs do not match."); // Return the output connector to original state. cOut.Disconnect(); cOut.ConnectTo(outOrig); } // Return the input connector to original state. cIn.Disconnect(); if (inOrig != null) cIn.ConnectTo(inOrig); } } /// /// Tests that each available connector in the system may be disconnected. /// [TestMethod] public void IConnector_Disconnect() { int result = 0; IEnumerable allConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out allConnectors); foreach (var con in allConnectors) { bool isConnected; IConnector conOrig = null; con.IsConnected(out isConnected); if (isConnected) con.GetConnectedTo(out conOrig); result = con.Disconnect(); // HRESULT should either be S_OK, or E_NOTFOUND // E_NOTFOUND is returned when Disconnect method is called on a connector that is already disconnected. if (isConnected) AssertCoreAudio.IsHResultOk(result); else Assert.AreEqual(TestUtilities.HRESULTS.E_NOTFOUND, (uint)result, "A disconnected connector did not return E_NOTFOUND HRESULT."); // Verify connected state is now false. con.IsConnected(out isConnected); Assert.IsFalse(isConnected, "The connector was not properly disconnected."); // Return connector to original state. if (conOrig != null) con.ConnectTo(conOrig); } } /// /// Tests that the global ID may be received, for each available connector in the system. /// [TestMethod] public void IConnector_GetConnectorIdConnectedTo() { int result = 0; IEnumerable allConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out allConnectors); foreach (var con in allConnectors) { bool isConnected; con.IsConnected(out isConnected); if (isConnected) { IConnector cTo; con.GetConnectedTo(out cTo); string expectedId, idConTo; ((IPart)cTo).GetGlobalId(out expectedId); result = con.GetConnectorIdConnectedTo(out idConTo); AssertCoreAudio.IsHResultOk(result); Assert.AreEqual(expectedId, idConTo, "The connected to ID does not match the actual ID of the part."); } } } /// /// Tests that the other connector may be received, for each applicable connector in the system. /// [TestMethod] public void IConnector_GetConnectedTo() { int result = 0; IEnumerable allConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out allConnectors); foreach (var con in allConnectors) { IConnector cTo; result = con.GetConnectedTo(out cTo); // A result of E_NOTFOUND is valid in this context. if ((uint)result == TestUtilities.HRESULTS.E_NOTFOUND) continue; // Otherwise the result should be S_OK AssertCoreAudio.IsHResultOk(result); } } /// /// Tests that the data flow may be received, for each available connector in the system. /// [TestMethod] public void IConnector_GetDataFlow() { int result = 0; IEnumerable allConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out allConnectors); foreach (var con in allConnectors) { var valOne = DataFlow.In; var valTwo = DataFlow.Out; result = con.GetDataFlow(out valOne); AssertCoreAudio.IsHResultOk(result); result = con.GetDataFlow(out valTwo); AssertCoreAudio.IsHResultOk(result); Assert.AreEqual(valOne, valTwo, "The data flow was not received."); } } /// /// Tests that the local device ID may be received, for each available connector in the system. /// [TestMethod] public void IConnector_GetDeviceIdConnectedTo() { int result = 0; IEnumerable allConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out allConnectors); foreach (var con in allConnectors) { bool isConnected; con.IsConnected(out isConnected); if (isConnected) { IConnector cTo; con.GetConnectedTo(out cTo); IDeviceTopology topology; ((IPart)cTo).GetTopologyObject(out topology); string expectedId, devIdConTo; topology.GetDeviceId(out expectedId); result = con.GetDeviceIdConnectedTo(out devIdConTo); AssertCoreAudio.IsHResultOk(result); Assert.AreEqual(expectedId, devIdConTo, "The connected to device ID does not match the actual device ID."); } } } /// /// Tests that the connector type may be received, for each available connector in the system. /// [TestMethod] public void IConnector_GetType() { int result = 0; IEnumerable allConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out allConnectors); foreach (var con in allConnectors) { // Try confiming that the type is changed from unknown. var cType = ConnectorType.Unknown_Connector; result = con.GetType(out cType); AssertCoreAudio.IsHResultOk(result); if (cType == ConnectorType.Unknown_Connector) { // If it's still unknown, verify that this is correct. var cType2 = ConnectorType.Network; con.GetType(out cType2); AssertCoreAudio.IsHResultOk(result); Assert.AreEqual(ConnectorType.Unknown_Connector, cType2, "The connector type was not received."); } else { // The value being changed is enough to verify correctness of the method. } } } /// /// Tests that the connected state may be received, for each available connector in the system. /// [TestMethod] public void IConnector_IsConnected() { int result = 0; IEnumerable allConnectors; ToConnectors(TestUtilities.CreateIPartCollection(), out allConnectors); foreach (var con in allConnectors) { var valOne = true; var valTwo = false; result = con.IsConnected(out valOne); AssertCoreAudio.IsHResultOk(result); result = con.IsConnected(out valTwo); AssertCoreAudio.IsHResultOk(result); Assert.AreEqual(valOne, valTwo, "The connected state was not received."); } } #region Helper Methods /// /// Takes a collection of IPart objects and returns the subset of the collection that are IConnector objects. /// /// A collection that may contain both subunits and connectors. /// A collection of connectors contained within the part collection. private static void ToConnectors(IEnumerable allParts, out IEnumerable allConnectors) { var cList = new List(); IEnumerable cIns, cOuts; ToConnectors(allParts, out cIns, out cOuts); cList.AddRange(cIns); cList.AddRange(cIns); allConnectors = cList; } /// /// Takes a collection of IPart objects and returns the subset of the collection that are separated input and output IConnector objects. /// /// A collection that may contain both subunits and connectors. /// A collection of input connectors contained within the part collection. /// A collection of output connectors contained within the part collection. private static void ToConnectors(IEnumerable allParts, out IEnumerable inputConnectors, out IEnumerable outputConnectors) { var inList = new List(); var outList = new List(); foreach (IPart part in allParts) { PartType pType; part.GetPartType(out pType); if (pType == PartType.Connector) { DataFlow flow; var connector = (IConnector)part; connector.GetDataFlow(out flow); switch (flow) { case DataFlow.In: inList.Add(connector); break; case DataFlow.Out: outList.Add(connector); break; } } } if (!inList.Any()) Assert.Inconclusive("The test cannot be run properly. No connectors were found."); if (!outList.Any()) Assert.Inconclusive("The test cannot be run properly. No connectors were found."); inputConnectors = inList; outputConnectors = outList; } #endregion } }