/* * To change this template, choose Tools | Templates * and open the template in the editor. */ package org.mobicents.media.server.impl.resource.audio; import java.io.IOException; import java.util.ArrayList; import java.util.concurrent.Semaphore; import java.util.concurrent.TimeUnit; import org.junit.After; import org.junit.AfterClass; import org.junit.Before; import org.junit.BeforeClass; import org.junit.Test; import static org.junit.Assert.*; import org.mobicents.media.Buffer; import org.mobicents.media.Format; import org.mobicents.media.server.impl.AbstractSink; import org.mobicents.media.server.impl.clock.TimerImpl; import org.mobicents.media.server.impl.resource.test.SineGenerator; import org.mobicents.media.server.spi.Endpoint; import org.mobicents.media.server.spi.Timer; import org.mobicents.media.server.spi.dsp.Codec; /** * * @author kulikov */ public class EndpointTransmittorTest { private final static int F = 50; private Timer timer; private EndpointTransmittor filler; private SineGenerator gen; private ExtSineGenerator extgen; private TestSink sink; private Semaphore semaphore = new Semaphore(0); private ArrayList<double[]> s = new ArrayList(); private long maxDiff; private boolean signalDetected = true; private boolean outOfSeq; private int count = 0; private long wrongSeq; private long maxDifNo; private boolean silenceExpected = false; public EndpointTransmittorTest() { } @BeforeClass public static void setUpClass() throws Exception { } @AfterClass public static void tearDownClass() throws Exception { } @Before public void setUp() { timer = new TimerImpl(); timer.start(); gen = new SineGenerator("test.sine", timer); gen.setAmplitude(Short.MAX_VALUE); gen.setFrequency(F); extgen = new ExtSineGenerator("test.sine", timer); extgen.setAmplitude(Short.MAX_VALUE); extgen.setFrequency(F); extgen.setGenerationTime(3000); sink = new TestSink("test.sink"); filler = new EndpointTransmittor("test.filler", timer); } @After public void tearDown() { timer.stop(); } /** * Test of getInput method, of class NoiseFiller. */ @Test public void testTransmission() throws Exception { gen.connect(filler.getInput()); sink.connect(filler.getOutput()); filler.getInput().start(); filler.getOutput().start(); gen.start(); sink.start(); semaphore.tryAcquire(5, TimeUnit.SECONDS); gen.stop(); assertTrue("Interarrival interval to long", maxDiff < 60); assertTrue("Signal not detected", signalDetected); assertFalse("Out of sequence", outOfSeq); assertTrue("Signal too short", count > 200); signalDetected = false; count = 0; this.silenceExpected = true; semaphore.tryAcquire(5, TimeUnit.SECONDS); assertTrue("Interarrival interval to long", maxDiff < 60); assertFalse("Signal detected", signalDetected); assertFalse("Out of sequence", outOfSeq); assertTrue("Signal too short", count > 200); } /** * Test of getInput method, of class NoiseFiller. */ @Test public void testTransmission2() throws Exception { extgen.connect(filler.getInput()); sink.connect(filler.getOutput()); filler.getInput().start(); filler.getOutput().start(); extgen.start(); sink.start(); semaphore.tryAcquire(3, TimeUnit.SECONDS); extgen.stop(); assertTrue("Interarrival interval to long", maxDiff < 60); assertTrue("Signal not detected", signalDetected); assertFalse("Out of sequence", outOfSeq); assertTrue("Signal too short", count > 140); signalDetected = false; count = 0; this.silenceExpected = true; semaphore.tryAcquire(5, TimeUnit.SECONDS); assertTrue("Interarrival interval to long", maxDiff < 60); assertFalse("Signal detected", signalDetected); assertFalse("Out of sequence", outOfSeq); assertTrue("Signal too short", count > 200); } private class TestSink extends AbstractSink { private long timestamp; private long seq; public TestSink(String name) { super(name); } @Override public void onMediaTransfer(Buffer buffer) throws IOException { count++; long next = buffer.getTimeStamp(); long seqNext = buffer.getSequenceNumber(); if (count == 1) { timestamp = next; seq = seqNext; return; } long diff = Math.abs(next - timestamp); if (diff > maxDiff && !silenceExpected) { maxDiff = diff; maxDifNo = seqNext; } if (silenceExpected) { silenceExpected = false; } if (seqNext - seq != 1) { outOfSeq = true; wrongSeq = seq; } timestamp = next; seq = seqNext; byte[] data = (byte[]) buffer.getData(); short[] signal = new short[buffer.getLength() / 2]; int k = buffer.getOffset(); for (int i = 0; i < signal.length; i++) { signal[i] = (short) ((data[k++] & 0xff) | (data[k++] << 8)); } for (int i = 0; i < signal.length; i++) { if (signal[i] > 320) { signalDetected = true; return; } } } public Format[] getFormats() { return new Format[] { Codec.LINEAR_AUDIO }; } public boolean isAcceptable(Format format) { return Codec.LINEAR_AUDIO.matches(format); } } private class ExtSineGenerator extends SineGenerator { private double time; private double generationTime; public ExtSineGenerator(String name, Timer timer) { super(name, timer); } public void setGenerationTime(double generationTime) { this.generationTime = generationTime; } @Override public void evolve(Buffer buffer, long timestamp, long seq) { super.evolve(buffer, timestamp, seq); time += ((double) getDuration()) / 1000.0; if (time >= (this.generationTime / 1000.0)) { buffer.setEOM(true); } } } }