Skip to main content
summaryrefslogblamecommitdiffstats
blob: 11e9b1bc06aeaa8b8e2d2ecec0ebd615c07c4cff (plain) (tree)
1
2
3
4
5
6
7
8
9
10
11
                                                                                
                                                        








                                                                                


                                                        


                                     
                                            
                                         
                               


                                









                                                  





                                             




































































































                                                                 








                                                             











                                                             
 











                                                              



                                                    
         
 
                                                         


























                                                                 
                                                                    




                                                                 

                                                                                                                      





                                                                 
                                               




                                                                     

                                                                                                                                   










                                                                                                           
                                                                     




                                                                    

                                                                                                                      





                                                                  
                                                

                                                 
                                                                        

                                                                 

                                                                                                                                   












                                                                                                            



                                                                                             

                           

                          


                                                                 

                                                                                                                                



                                                                                            
                                                                                
                                                                        

                                                 

                           

                          











                                                                       



                                                                                                          





                                                                        



                                                                                                                                            





                                                       
                                                                                                     




                                                                                                              


                                                                                               










                                                                          



                                                                                                 




                                                                                                             




                                                                           
                                 
                                                      



                         
                                             


                                                     



                                                  
                                                                               


         
/*******************************************************************************
 * Copyright (c) 2009, 2010 Oracle. All rights reserved.
 * This program and the accompanying materials are made available under the
 * terms of the Eclipse Public License v1.0, which accompanies this distribution
 * and is available at http://www.eclipse.org/legal/epl-v10.html.
 * 
 * Contributors:
 *     Oracle - initial API and implementation
 ******************************************************************************/
package org.eclipse.jpt.utility.tests.internal;

import org.eclipse.jpt.utility.internal.SynchronizedInt;

@SuppressWarnings("nls")
public class SynchronizedIntTests
	extends MultiThreadedTestCase
{
	private volatile SynchronizedInt si;
	volatile boolean timeoutOccurred;
	volatile int value = 7;
	volatile long startTime;
	volatile long endTime;
	volatile int sIntValue;


	public SynchronizedIntTests(String name) {
		super(name);
	}

	@Override
	protected void setUp() throws Exception {
		super.setUp();
		this.si = new SynchronizedInt();
		this.timeoutOccurred = false;
		this.startTime = 0;
		this.endTime = 0;
		this.sIntValue = 0;
	}

	public void testGetValue() throws Exception {
		assertEquals(0, this.si.getValue());
	}

	public void testEqualsInt() throws Exception {
		assertTrue(this.si.equals(0));
		this.si.setValue(this.value);
		assertTrue(this.si.equals(7));
	}

	public void testNotEqualsInt() throws Exception {
		assertTrue(this.si.notEquals(7));
		this.si.setValue(this.value);
		assertTrue(this.si.notEquals(0));
	}

	public void testIsZero() throws Exception {
		assertTrue(this.si.isZero());
		this.si.setValue(this.value);
		assertFalse(this.si.isZero());
	}

	public void testIsNotZero() throws Exception {
		assertFalse(this.si.isNotZero());
		this.si.setValue(this.value);
		assertTrue(this.si.isNotZero());
	}

	public void testIsGreaterThan() throws Exception {
		assertTrue(this.si.isGreaterThan(-1));
		assertFalse(this.si.isGreaterThan(0));
		assertFalse(this.si.isGreaterThan(1));
		this.si.setValue(this.value);
		assertTrue(this.si.isGreaterThan(-1));
		assertFalse(this.si.isGreaterThan(7));
		assertFalse(this.si.isGreaterThan(8));
	}

	public void testIsGreaterThanOrEqual() throws Exception {
		assertTrue(this.si.isGreaterThanOrEqual(-1));
		assertTrue(this.si.isGreaterThanOrEqual(0));
		assertFalse(this.si.isGreaterThanOrEqual(1));
		this.si.setValue(this.value);
		assertTrue(this.si.isGreaterThanOrEqual(-1));
		assertTrue(this.si.isGreaterThanOrEqual(7));
		assertFalse(this.si.isGreaterThanOrEqual(8));
	}

	public void testIsLessThan() throws Exception {
		assertFalse(this.si.isLessThan(-1));
		assertFalse(this.si.isLessThan(0));
		assertTrue(this.si.isLessThan(1));
		this.si.setValue(this.value);
		assertFalse(this.si.isLessThan(-1));
		assertFalse(this.si.isLessThan(7));
		assertTrue(this.si.isLessThan(8));
	}

	public void testIsLessThanOrEqual() throws Exception {
		assertFalse(this.si.isLessThanOrEqual(-1));
		assertTrue(this.si.isLessThanOrEqual(0));
		assertTrue(this.si.isLessThanOrEqual(1));
		this.si.setValue(this.value);
		assertFalse(this.si.isLessThanOrEqual(-1));
		assertTrue(this.si.isLessThanOrEqual(7));
		assertTrue(this.si.isLessThanOrEqual(8));
	}

	public void testIsPositive() throws Exception {
		assertFalse(this.si.isPositive());
		this.si.setValue(this.value);
		assertTrue(this.si.isPositive());
		this.si.setValue(-3);
		assertFalse(this.si.isPositive());
	}

	public void testIsNotPositive() throws Exception {
		assertTrue(this.si.isNotPositive());
		this.si.setValue(this.value);
		assertFalse(this.si.isNotPositive());
		this.si.setValue(-3);
		assertTrue(this.si.isNotPositive());
	}

	public void testIsNegative() throws Exception {
		assertFalse(this.si.isNegative());
		this.si.setValue(this.value);
		assertFalse(this.si.isNegative());
		this.si.setValue(-3);
		assertTrue(this.si.isNegative());
	}

	public void testIsNotNegative() throws Exception {
		assertTrue(this.si.isNotNegative());
		this.si.setValue(this.value);
		assertTrue(this.si.isNotNegative());
		this.si.setValue(-3);
		assertFalse(this.si.isNotNegative());
	}

	public void testSetValue() throws Exception {
		this.si.setValue(0);
		assertEquals(0, this.si.getValue());
		assertFalse(this.si.isNotZero());
		assertTrue(this.si.isZero());

		this.si.setValue(this.value);
		assertEquals(this.value, this.si.getValue());
		assertTrue(this.si.isNotZero());
		assertFalse(this.si.isZero());
	}

	public void testAbs() throws Exception {
		assertEquals(0, this.si.abs());
		assertEquals(0, this.si.getValue());
		this.si.setValue(this.value);
		assertEquals(this.value, this.si.abs());
		assertEquals(this.value, this.si.getValue());
		this.si.setValue(-this.value);
		assertEquals(this.value, this.si.abs());
		assertEquals(this.value, this.si.getValue());
	}

	public void testNeg() throws Exception {
		assertEquals(0, this.si.neg());
		assertEquals(0, this.si.getValue());
		this.si.setValue(this.value);
		assertEquals(-this.value, this.si.neg());
		assertEquals(-this.value, this.si.getValue());
		this.si.setValue(-this.value);
		assertEquals(this.value, this.si.neg());
		assertEquals(this.value, this.si.getValue());
	}

	public void testSetZero() throws Exception {
		this.si.setZero();
		assertEquals(0, this.si.getValue());
		assertFalse(this.si.isNotZero());
		assertTrue(this.si.isZero());
	}

	public void testGetMutexThis() throws Exception {
		assertSame(this.si, this.si.getMutex());
	}

	public void testEquals() throws Exception {
		this.si.setValue(0);
		SynchronizedInt so2 = new SynchronizedInt(0);
		assertEquals(this.si, so2);

		this.si.setValue(this.value);
		assertFalse(this.si.equals(so2));

		so2.setValue(this.value);
		assertEquals(this.si, so2);
	}

	public void testHashCode() {
		this.si.setValue(this.value);
		assertEquals(this.value, this.si.hashCode());

		this.si.setValue(0);
		assertEquals(0, this.si.hashCode());
	}

	/**
	 * t2 will wait indefinitely until t1 sets the value to 0
	 */
	public void testWaitUntilZero() throws Exception {
		this.verifyWaitUntilZero(0);  // 0 = indefinite wait
		// no timeout occurs...
		assertFalse(this.timeoutOccurred);
		// ...and the value should be set to 0 by t2
		assertEquals(0, this.si.getValue());
		// make a reasonable guess about how long t2 took
		long time = this.calculateElapsedTime();
		assertTrue("t2 finished a bit early (expected value should be > " + TICK + "): " + time, time > TICK);
	}

	/**
	 * t2 will time out waiting for t1 to set the value to 0
	 */
	public void testWaitUntilZeroTimeout() throws Exception {
		this.verifyWaitUntilZero(TICK);
		// timeout occurs...
		assertTrue(this.timeoutOccurred);
		// ...and the value will eventually be set to 0 by t1
		assertEquals(0, this.si.getValue());
		// make a reasonable guess about how long t2 took
		long time = this.calculateElapsedTime();
		assertTrue("t2 finished a bit late (expected value should be < " + THREE_TICKS + "): " + time, time < THREE_TICKS);
	}

	private void verifyWaitUntilZero(long t2Timeout) throws Exception {
		this.executeThreads(this.buildSetZeroCommand(), this.buildWaitUntilZeroCommand(t2Timeout));
	}

	/**
	 * t2 will wait indefinitely until t1 sets the value to 0;
	 * then t2 will set the value to 7
	 */
	public void testWaitToSetValue() throws Exception {
		this.verifyWaitToSetValue(0);  // 0 = indefinite wait
		// no timeout occurs...
		assertFalse(this.timeoutOccurred);
		// ...and the value should be set to an object by t2
		assertTrue(this.si.isNotZero());
		// make a reasonable guess about how long t2 took
		long time = this.calculateElapsedTime();
		assertTrue("t2 finished a bit early (expected value should be > " + TICK + "): " + time, time > TICK);
	}

	/**
	 * t2 will time out waiting for t1 to set the value to 0
	 */
	public void testWaitToSetValueTimeout() throws Exception {
		this.verifyWaitToSetValue(TICK);
		// timeout occurs...
		assertTrue(this.timeoutOccurred);
		// ...and the value will eventually be set to zero by t1
		assertTrue(this.si.isZero());
		// make a reasonable guess about how long t2 took
		long time = this.calculateElapsedTime();
		assertTrue("t2 finished a bit late (expected value should be < " + THREE_TICKS + "): " + time, time < THREE_TICKS);
	}

	private void verifyWaitToSetValue(long t2Timeout) throws Exception {
		this.executeThreads(this.buildSetZeroCommand(), this.buildWaitToSetValueCommand(t2Timeout));
	}

	/**
	 * t2 will wait until t1 is finished "initializing" the value;
	 * then t2 will get the newly-initialized value (42)
	 */
	public void testExecute() throws Exception {
		this.si.setValue(0);
		Runnable r1 = this.buildRunnable(this.buildInitializeValueCommand(), this.si, 0);
		// give t1 a head start
		Runnable r2 = this.buildRunnable(this.buildGetValueCommand(), this.si, TICK);
		Thread t1 = this.buildThread(r1);
		Thread t2 = this.buildThread(r2);
		t1.start();
		t2.start();
		t1.join();
		t2.join();
		assertEquals(42, this.si.getValue());
		assertEquals(42, this.sIntValue);
		// make a reasonable guess about how long t2 took
		long time = this.calculateElapsedTime();
		assertTrue("t2 finished a bit early (expected value should be > " + TWO_TICKS + "): " + time, time > TWO_TICKS);
	}

	private void executeThreads(Command t1Command, Command t2Command) throws Exception {
		this.si.setValue(this.value);
		Runnable r1 = this.buildRunnable(t1Command, this.si, TWO_TICKS);
		Runnable r2 = this.buildRunnable(t2Command, this.si, 0);
		Thread t1 = this.buildThread(r1);
		Thread t2 = this.buildThread(r2);
		t1.start();
		t2.start();
		t1.join();
		t2.join();
	}

	private Command buildSetZeroCommand() {
		return new Command() {
			public void execute(SynchronizedInt sInt) {
				sInt.setZero();
			}
		};
	}

	private Command buildWaitUntilZeroCommand(final long timeout) {
		return new Command() {
			public void execute(SynchronizedInt sInt) throws InterruptedException {
				SynchronizedIntTests.this.startTime = System.currentTimeMillis();
				SynchronizedIntTests.this.timeoutOccurred = ! sInt.waitUntilZero(timeout);
				SynchronizedIntTests.this.endTime = System.currentTimeMillis();
			}
		};
	}

	private Command buildWaitToSetValueCommand(final long timeout) {
		return new Command() {
			public void execute(SynchronizedInt sInt) throws InterruptedException {
				SynchronizedIntTests.this.startTime = System.currentTimeMillis();
				SynchronizedIntTests.this.timeoutOccurred = ! sInt.waitToSetValue(SynchronizedIntTests.this.value, timeout);
				SynchronizedIntTests.this.endTime = System.currentTimeMillis();
			}
		};
	}

	private Command buildInitializeValueCommand() {
		return new Command() {
			public void execute(final SynchronizedInt sInt) throws InterruptedException {
				sInt.execute(
					new org.eclipse.jpt.utility.Command() {
						public void execute() {
							// pretend to perform some long initialization process
							try {
								Thread.sleep(5 * TICK);
							} catch (InterruptedException ex) {
								throw new RuntimeException(ex);
							}
							sInt.setValue(42);
						}
					}
				);
			}
		};
	}

	private Command buildGetValueCommand() {
		return new Command() {
			public void execute(SynchronizedInt sInt) throws InterruptedException {
				SynchronizedIntTests.this.startTime = System.currentTimeMillis();
				SynchronizedIntTests.this.sIntValue = sInt.getValue();
				SynchronizedIntTests.this.endTime = System.currentTimeMillis();
			}
		};
	}

	private Runnable buildRunnable(final Command command, final SynchronizedInt sInt, final long sleep) {
		return new TestRunnable() {
			@Override
			protected void run_() throws InterruptedException {
				if (sleep != 0) {
					Thread.sleep(sleep);
				}
				command.execute(sInt);
			}
		};
	}

	private long calculateElapsedTime() {
		return this.endTime - this.startTime;
	}


	// ********** Command interface **********

	private interface Command {
		void execute(SynchronizedInt sInt) throws InterruptedException;
	}

}

Back to the top