/*
 * Copyright 2007 Russell Harmon
 *
 *    Licensed under the Apache License, Version 2.0 (the "License");
 *    you may not use this file except in compliance with the License.
 *    You may obtain a copy of the License at
 *
 *        http://www.apache.org/licenses/LICENSE-2.0
 *
 *    Unless required by applicable law or agreed to in writing, software
 *    distributed under the License is distributed on an "AS IS" BASIS,
 *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *    See the License for the specific language governing permissions and
 *    limitations under the License.
 */

package com.eatnumber1.util.cglib;

import com.eatnumber1.util.concurrent.lock.LockProvider;
import com.eatnumber1.util.facade.Facade;
import java.util.concurrent.locks.Lock;
import junit.framework.TestCase;

/**
 * @author Russell Harmon
 * @since Jul 13, 2007
 */
public class EnhancerUtilsTest extends TestCase {
    private static final int ITERATIONS = 1000000;

    private static class Reference<T> {
        private volatile T referent;

        private Reference( T referent ) {
            this.referent = referent;
        }

        public T getReferent() {
            return referent;
        }

        public void setReferent( T referent ) {
            this.referent = referent;
        }
    }

    public static class IncrementableInteger {
        private Reference<Integer> num = new Reference<Integer>(0);

        public int increment() {
            num.setReferent(num.getReferent() + 1);
            return num.getReferent();
        }

        public Reference<Integer> getNum() {
            return num;
        }

        public void setNum( Reference<Integer> num ) {
            this.num = num;
        }
    }

    public void testSynchronizeIsLockProvider() {
        IncrementableInteger str = EnhancerUtils.synchronize(new IncrementableInteger());
        try {
            //noinspection UnusedDeclaration
            LockProvider provider = (LockProvider) str;
        } catch( ClassCastException e ) {
            fail();
        }
    }

    public void testSynchronizeIsFacade() {
        IncrementableInteger str = EnhancerUtils.synchronize(new IncrementableInteger());
        try {
            //noinspection UnusedDeclaration,unchecked
            Facade<IncrementableInteger> provider = (Facade<IncrementableInteger>) str;
        } catch( ClassCastException e ) {
            fail();
        }
    }

    public void testSynchronizeIsSynchronized() throws InterruptedException {
        final IncrementableInteger integer = EnhancerUtils.synchronize(new IncrementableInteger());

        Thread[] threads = {
                new Thread() {
                    @Override
                    public void run() {
                        for( int i = 0; i < ITERATIONS; i++ ) {
                            integer.increment();
                        }
                    }
                },
                new Thread() {
                    @Override
                    public void run() {
                        for( int i = 0; i < ITERATIONS; i++ ) {
                            integer.increment();
                        }
                    }
                },
                new Thread() {
                    @Override
                    public void run() {
                        Lock lock = ( (LockProvider) integer ).getLock();
                        for( int i = 0; i < ITERATIONS; i++ ) {
                            lock.lock();
                            try {
                                Reference<Integer> ref = integer.getNum();
                                ref.setReferent(ref.getReferent() + 1);
                            } finally {
                                lock.unlock();
                            }
                        }
                    }
                }
        };

        for( Thread thread : threads ) {
            thread.start();
        }
        for( Thread thread : threads ) {
            thread.join();
        }

        // Prevents ambiguous method call.
        //noinspection RedundantCast
        assertEquals(threads.length * ITERATIONS, (long) integer.getNum().getReferent());
    }
}

@@ -805,32 +805,47 @@
 ort 
+org.
 junit.
-framework
+Assert;%0Aimport org.junit
 .Test
-Case
 ;%0A%0A/
@@ -935,25 +935,8 @@
 est 
-extends TestCase 
 %7B%0A  
@@ -1752,32 +1752,42 @@
        %7D%0A    %7D%0A%0A
+    @Test%0A
     public void 
@@ -1778,37 +1778,33 @@
     public void 
-testS
+s
 ynchronizeIsLock
@@ -2067,32 +2067,39 @@
 ) %7B%0A            
+Assert.
 fail();%0A        
@@ -2099,32 +2099,42 @@
        %7D%0A    %7D%0A%0A
+    @Test%0A
     public void 
@@ -2462,16 +2462,23 @@
         
+Assert.
 fail();%0A
@@ -2486,32 +2486,42 @@
        %7D%0A    %7D%0A%0A
+    @Test%0A
     public void 
@@ -4168,24 +4168,24 @@
 antCast%0A
-
         
 assertEq
@@ -4176,16 +4176,23 @@
         
+Assert.
 assertEq

Convert back to JUnit4 test