2014年4月30日星期三

Glassfish_005:安装时谎报4848端口被占用问题

环境:CentOS6.0 + Glassfish 4.0

关于安装,请参考《在CentOS6.5上安装GlassFish4.0》。
在我自己的机器上安装没有出现此问题,但是在客户的机器上出现了。

安装过程一切正常,就是无法正常启动,会报出4848端口已经占用的错误。
但是使用nestat -anp |grep 4848,发现并没有其它进程占用此端口。
好奇怪啊。
经过参考文献提示,检查了hostname,果然有问题。
解决方法如下:
(1)vi /etc/sysconfig/network,查看hostname,如果不对,修改一下。
NETWORKING=yes
HOSTNAME=eventownjiankong51
(2)vi /etc/hosts,内容要有对应的hostname,如果没有,加上。
127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4 eventownjiankong51
::1         localhost localhost.localdomain localhost6 localhost6.localdomain6 eventownjiankong51

参考文献:
1. http://lztang1964.blog.163.com/blog/static/187545985201111124654414/


Java_016:死锁线程例子(摘录+整理)

1. DeadThread.java

public class DeadThread implements Runnable{

private Object monitor_A = new Object();

private Object monitor_B = new Object();

public void  method_A(){
synchronized(monitor_A) {
      synchronized(monitor_B) {
              System.out.println(Thread.currentThread().getName()+" invoke method A");
          }              
      }  
}

public void  method_B(){
synchronized(monitor_B) {
      synchronized(monitor_A) {
      System.out.println(Thread.currentThread().getName()+" invoke method B");
          }              
      }  
}

public void run() {
for(int i=0;i<1 class="Apple-tab-span" i--="" span="" style="white-space: pre;">
  method_A();
method_B();
}  
}

  public static void main(String[] args) {
 DeadThread t1 = new DeadThread();
       Thread ta = new Thread(t1, "A");
       Thread tb = new Thread(t1, "B");

       ta.start();
       tb.start();
  }
}

2. 线程A和线程B的thread dump
"B" prio=5 tid=0x00007fefa8886800 nid=0x5903 waiting for monitor entry [0x000000011daa6000]
   java.lang.Thread.State: BLOCKED (on object monitor)
at DeadThread.method_A(DeadThread.java:10)
- waiting to lock <0x00000007aab2c0b0> (a java.lang.Object)
- locked <0x00000007aab2c0a0> (a java.lang.Object)
at DeadThread.run(DeadThread.java:25)
at java.lang.Thread.run(Thread.java:744)

"A" prio=5 tid=0x00007fefa8885800 nid=0x5703 waiting for monitor entry [0x000000011d9a3000]
   java.lang.Thread.State: BLOCKED (on object monitor)
at DeadThread.method_B(DeadThread.java:18)
- waiting to lock <0x00000007aab2c0a0> (a java.lang.Object)
- locked <0x00000007aab2c0b0> (a java.lang.Object)
at DeadThread.run(DeadThread.java:26)
at java.lang.Thread.run(Thread.java:744)

3. 直接报告死锁的thread dump
Found one Java-level deadlock:
=============================
"B":
  waiting to lock monitor 0x00007fefa8850cb8 (object 0x00000007aab2c0b0, a java.lang.Object),
  which is held by "A"
"A":
  waiting to lock monitor 0x00007fefa88522b8 (object 0x00000007aab2c0a0, a java.lang.Object),
  which is held by "B"

Java stack information for the threads listed above:
===================================================
"B":
at DeadThread.method_A(DeadThread.java:10)
- waiting to lock <0x00000007aab2c0b0> (a java.lang.Object)
- locked <0x00000007aab2c0a0> (a java.lang.Object)
at DeadThread.run(DeadThread.java:25)
at java.lang.Thread.run(Thread.java:744)
"A":
at DeadThread.method_B(DeadThread.java:18)
- waiting to lock <0x00000007aab2c0a0> (a java.lang.Object)
- locked <0x00000007aab2c0b0> (a java.lang.Object)
at DeadThread.run(DeadThread.java:26)
at java.lang.Thread.run(Thread.java:744)

Found 1 deadlock.

参考文献:
1. http://blog.csdn.net/jackie_xiaonan/article/details/8546541
2. http://www.cnblogs.com/tomsheep/archive/2010/06/10/1755840.html

Java_015:TIMED_WAITING (on object monitor)线程例子 (摘录+整理)

1. WaitThread.java

public class WaitThread implements Runnable{
public void run() {
        synchronized(this) {
                try {
                                this.wait(200000L);
                        } catch (InterruptedException e) {
                                // TODO Auto-generated catch block
                                e.printStackTrace();
                        }
        }
   }
   public static void main(String[] args) {
        WaitThread t1 = new WaitThread();
        Thread ta = new Thread(t1, "A");
        Thread tb = new Thread(t1, "B");
        ta.start();
        tb.start();
   }

}

2. 线程A和线程B的thread dump
(1)线程A的状态是in Object.wait():TIMED_WAITING (on object monitor)。
(2)线程B的状态也是in Object.wait():TIMED_WAITING (on object monitor)。

"B" prio=5 tid=0x00007fc52c8bf000 nid=0x5903 in Object.wait() [0x000000011af67000]
   java.lang.Thread.State: TIMED_WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x00000007aab2bc98> (a WaitThread)
at WaitThread.run(WaitThread.java:5)
- locked <0x00000007aab2bc98> (a WaitThread)
at java.lang.Thread.run(Thread.java:744)

"A" prio=5 tid=0x00007fc52c039000 nid=0x5703 in Object.wait() [0x000000011ae64000]
   java.lang.Thread.State: TIMED_WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x00000007aab2bc98> (a WaitThread)
at WaitThread.run(WaitThread.java:5)
- locked <0x00000007aab2bc98> (a WaitThread)
at java.lang.Thread.run(Thread.java:744)

原因解释:
与上一个例子代码基本相同,只是在wait()方法上增加了一个时间参数,因此具体状态由WAITING 变为TIMED_WAITING,即等待一定的时间。
如果在这段时间内,其它线程调用锁对象的notify()或notifyall()方法,则再次试图获取该对象的锁。
当过了指定时间后,也会再次试图获取该对象的锁。
线程A获取Monitor后:locked <0x00000007aab2bc80>,又调用wait(),释放了锁:waiting on <0x00000007aab2bc80>。
因为线程A释放了锁<0x00000007aab2bc80>,线程B得以获取该锁,然后线程B也调用wait(),释放了该锁。

Java_014:WAITING线程例子 (摘录+整理)

1.  WaitThread.java

public class WaitThread implements Runnable{
public void run() {
        synchronized(this) {
                try {
                                this.wait();
                      } catch (InterruptedException e) {
                                // TODO Auto-generated catch block
                                e.printStackTrace();
                      }
        }
   }
   public static void main(String[] args) {
        WaitThread t1 = new WaitThread();
        Thread ta = new Thread(t1, "A");
        Thread tb = new Thread(t1, "B");
        ta.start();
        tb.start();
   }

}

2. 线程A和线程B的thread dump
(1)线程A的状态是in Object.wait():WAITING (on object monitor)。
(2)线程B的状态也是in Object.wait():WAITING (on object monitor)。

"B" prio=5 tid=0x00007fc16d83d000 nid=0x5903 in Object.wait() [0x00000001215cb000]
   java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x00000007aab2bc80> (a WaitThread)
at java.lang.Object.wait(Object.java:503)
at WaitThread.run(WaitThread.java:5)
- locked <0x00000007aab2bc80> (a WaitThread)
at java.lang.Thread.run(Thread.java:744)

"A" prio=5 tid=0x00007fc16d83c000 nid=0x5703 in Object.wait() [0x00000001214c8000]
   java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x00000007aab2bc80> (a WaitThread)
at java.lang.Object.wait(Object.java:503)
at WaitThread.run(WaitThread.java:5)
- locked <0x00000007aab2bc80> (a WaitThread)
at java.lang.Thread.run(Thread.java:744)

原因解释:
线程A获取Monitor后:locked <0x00000007aab2bc80>,又调用wait(),释放了锁:waiting on <0x00000007aab2bc80>。
因为线程A释放了锁<0x00000007aab2bc80>,线程B得以获取该锁,然后线程B也调用wait(),释放了该锁。
现在,线程A和线程B都在等待其它线程调用锁对象的notify()或notifyall()方法,将它们再次“唤醒”。

Java_013:TIMED_WAITING (sleeping)线程例子 (摘录+整理)

1. 代码
public class SleepThread {
    public static void main(final String[] args) throws Exception {
        Thread.sleep(200000L);
    }

}

2. 线程main的thread dump
线程main的状态是wait on condiction:TIMED_WAITING(sleeping)
"main" prio=5 tid=0x00007fddfb800000 nid=0x1903 waiting on condition [0x00000001063e8000]
   java.lang.Thread.State: TIMED_WAITING (sleeping)
at java.lang.Thread.sleep(Native Method)
at SleepThread.main(SleepThread.java:3)

原因解释:
因为main线程一直在睡大觉,所以睡醒之前,状态一直是TIMED_WAITING(sleeping)。

Java_012:BLOCKED线程例子 (摘录+整理)

1. MyThread.java

public class MyThread implements Runnable {

    public void run() {
        synchronized (this) {
            for (int i = 0; i < 1; i--) {
                System.out.println(Thread.currentThread().getName() + " synchronized loop " + i);
            }
        }
    }

    public static void main(String[] args) {
        MyThread t1 = new MyThread();
        Thread ta = new Thread(t1, "A");
        Thread tb = new Thread(t1, "B");
        ta.start();
        tb.start();
    }
}

2. 线程A与线程B的thread dump
(1)线程A的状态是runnable:RUNNABE。
(2)线程B 的状态是waiting for monitor entry:BLOCKED。

"B" prio=5 tid=0x00007fb683944000 nid=0x6103 waiting for monitor entry [0x00000001127fb000]
   java.lang.Thread.State: BLOCKED (on object monitor)
at MyThread.run(MyThread.java:18)
- waiting to lock <0x00000007247b6220> (a MyThread)
at java.lang.Thread.run(Thread.java:744)

"A" prio=5 tid=0x00007fb6838be800 nid=0x5f03 runnable [0x00000001126f8000]
   java.lang.Thread.State: RUNNABLE
at java.io.FileOutputStream.writeBytes(Native Method)
at java.io.FileOutputStream.write(FileOutputStream.java:345)
at java.io.BufferedOutputStream.flushBuffer(BufferedOutputStream.java:82)
at java.io.BufferedOutputStream.flush(BufferedOutputStream.java:140)
- locked <0x000000072482bd48> (a java.io.BufferedOutputStream)
at java.io.PrintStream.write(PrintStream.java:482)
- locked <0x00000007247b59a0> (a java.io.PrintStream)
at sun.nio.cs.StreamEncoder.writeBytes(StreamEncoder.java:221)
at sun.nio.cs.StreamEncoder.implFlushBuffer(StreamEncoder.java:291)
at sun.nio.cs.StreamEncoder.flushBuffer(StreamEncoder.java:104)
- locked <0x0000000724821340> (a java.io.OutputStreamWriter)
at java.io.OutputStreamWriter.flushBuffer(OutputStreamWriter.java:185)
at java.io.PrintStream.newLine(PrintStream.java:546)
- eliminated <0x00000007247b59a0> (a java.io.PrintStream)
at java.io.PrintStream.println(PrintStream.java:807)
- locked <0x00000007247b59a0> (a java.io.PrintStream)
at MyThread.run(MyThread.java:19)
- locked <0x00000007247b6220> (a MyThread)
at java.lang.Thread.run(Thread.java:744)

原因解释:
线程阻塞是指当前线程执行过程中,所需要的资源长时间等待却一直未能获取到,被容器的线程管理器标识为阻塞状态,可以理解为等待资源超时的线程。
这里线程B苦苦等待获取Monitor,企图lock对象<0x00000007247b6220>,但该对象一直被线程A牢牢locked <0x00000007247b6220>,因此经过一定时间,线程B被容器的线程管理器标识为BLOCKED。

2014年4月29日星期二

Java_011:如何找到导致CPU100%的代码?

基本思路如下:

1. 找到导致CPU100%的进程号
Linux下可以使用命令:top,然后按照CPU利用率排序。
Windows下可以使用Task Manager。

2. 打印该进程的线程信息
Linux下可以使用命令:top -Hp [pid],找到CPU利用率最高的线程号。
Windows下可以使用第三方工具:pslist,找到State=Running的线程号。
关于pslist,可以参考《WebLogic 常见故障之七:High CPU》。

3. 获取当前Java进程的thread dump
把第2步得到的线程号(10进制),转换成16进制。
然后在thead dump中搜索转换后的16进制字符串。
找到后,看StackTrace,锁定问题代码。

以此类推,应该也可以找到导致Memory和IO问题的代码。

参考文献:
1. http://blog.csdn.net/gobitan/article/details/5474062

Java_010:JVM内部线程功能说明(摘录+整理)

JDK 版本:Java HotSpot(TM) 64-Bit Server VM (build 24.51-b03, mixed mode)

下面的输出是一个典型的HotSpot JVM的thread dump,以此为例,来说明一下JVM的内部线程功能。

2014-04-29 17:59:54
Full thread dump Java HotSpot(TM) 64-Bit Server VM (24.51-b03 mixed mode):

"Attach Listener" daemon prio=5 tid=0x00007fc6b6800800 nid=0x3b07 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"DestroyJavaVM" prio=5 tid=0x00007fc6b3001000 nid=0x1903 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Service Thread" daemon prio=5 tid=0x00007fc6b3840000 nid=0x5303 runnable [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"C2 CompilerThread1" daemon prio=5 tid=0x00007fc6b280f800 nid=0x5103 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"C2 CompilerThread0" daemon prio=5 tid=0x00007fc6b5035800 nid=0x4f03 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Signal Dispatcher" daemon prio=5 tid=0x00007fc6b502e000 nid=0x4d03 runnable [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Finalizer" daemon prio=5 tid=0x00007fc6b2818800 nid=0x3903 in Object.wait() [0x000000011fda0000]
   java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x00000007000049a0> (a java.lang.ref.ReferenceQueue$Lock)
at java.lang.ref.ReferenceQueue.remove(ReferenceQueue.java:135)
- locked <0x00000007000049a0> (a java.lang.ref.ReferenceQueue$Lock)
at java.lang.ref.ReferenceQueue.remove(ReferenceQueue.java:151)
at java.lang.ref.Finalizer$FinalizerThread.run(Finalizer.java:189)

"Reference Handler" daemon prio=5 tid=0x00007fc6b2815800 nid=0x3703 in Object.wait() [0x000000011fc9d000]
   java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x0000000700006b00> (a java.lang.ref.Reference$Lock)
at java.lang.Object.wait(Object.java:503)
at java.lang.ref.Reference$ReferenceHandler.run(Reference.java:133)
- locked <0x0000000700006b00> (a java.lang.ref.Reference$Lock)

"VM Thread" prio=5 tid=0x00007fc6b383e800 nid=0x3503 runnable

"GC task thread#0 (ParallelGC)" prio=5 tid=0x00007fc6b480d000 nid=0x2503 runnable

"GC task thread#1 (ParallelGC)" prio=5 tid=0x00007fc6b2812000 nid=0x2703 runnable

"GC task thread#2 (ParallelGC)" prio=5 tid=0x00007fc6b2812800 nid=0x2903 runnable

"GC task thread#3 (ParallelGC)" prio=5 tid=0x00007fc6b2813000 nid=0x2b03 runnable

"GC task thread#4 (ParallelGC)" prio=5 tid=0x00007fc6b2813800 nid=0x2d03 runnable

"GC task thread#5 (ParallelGC)" prio=5 tid=0x00007fc6b2814800 nid=0x2f03 runnable

"GC task thread#6 (ParallelGC)" prio=5 tid=0x00007fc6b2815000 nid=0x3103 runnable

"GC task thread#7 (ParallelGC)" prio=5 tid=0x00007fc6b3801000 nid=0x3303 runnable

"VM Periodic Task Thread" prio=5 tid=0x00007fc6b502f000 nid=0x5503 waiting on condition

JNI global references: 159


1. Attach Listener 
负责接收到外部的命令,而对该命令进行执行的并且吧结果返回给发送者。
通常我们会用一些命令去要求jvm给我们一些反馈信息,如:java -version、jmap、jstack等等。 如果该线程在jvm启动的时候没有初始化,那么,则会在用户第一次执行jvm命令时,得到启动。

2. DestroyJavaVM
执行main()的线程在main执行完后调用JNI中的 jni_DestroyJavaVM() 方法唤起DestroyJavaVM 线程。
JVM在 Jboss 服务器启动之后,就会唤起DestroyJavaVM线程,处于等待状态,等待其它线程(java线程和native线程)退出时通知它卸载JVM。线程退出时,都会判断自己当前是否是整个JVM中最后一个非deamon线程,如果是,则通知DestroyJavaVM 线程卸载JVM。
(1)如果线程退出时判断自己不为最后一个非deamon线程,那么调用thread->exit(false) ,并在其中抛出thread_end事件,jvm不退出。
(2)如果线程退出时判断自己为最后一个非deamon线程,那么调用before_exit() 方法,抛出两个事件:thread_end 线程结束事件和VM的death事件。
然后调用thread->exit(true) 方法,接下来把线程从active list卸下,删除线程等等一系列工作执行完成后,则通知正在等待的DestroyJavaVM 线程执行卸载JVM操作。

3. Service Thread

4. CompilerThread0
用来调用JITing,实时编译装卸CLASS。
通常JVM会启动多个线程来处理这部分工作,线程名称后面的数字也会累加,比如CompilerThread1。

5. Signal Dispatcher
Attach Listener线程的职责是接收外部jvm命令,当命令接收成功后,会交给signal dispather 线程去进行分发到各个不同的模块处理命令,并且返回处理结果。
signal dispather线程也是在第一次接收外部jvm命令时,进行初始化工作。

6. Finalizer
这个线程也是在main线程之后创建的,其优先级为10,主要用于在垃圾收集前,调用对象的finalize()方法;关于Finalizer线程的几点:
(1)只有当开始一轮垃圾收集时,才会开始调用finalize()方法;因此并不是所有对象的finalize()方法都会被执行;
(2)该线程也是daemon线程,因此如果虚拟机中没有其他非daemon线程,不管该线程有没有执行完finalize()方法,JVM也会退出;
(3)JVM在垃圾收集时会将失去引用的对象包装成Finalizer对象(Reference的实现),并放入ReferenceQueue,由Finalizer线程来处理;最后将该Finalizer对象的引用置为null,由垃圾收集器来回收;
(4)JVM为什么要单独用一个线程来执行finalize()方法呢?
如果JVM的垃圾收集线程自己来做,很有可能由于在finalize()方法中误操作导致GC线程停止或不可控,这对GC线程来说是一种灾难。

7. Reference Handler
JVM在创建main线程后就创建Reference Handler线程,其优先级最高,为10,它主要用于处理引用对象本身(软引用、弱引用、虚引用)的垃圾回收问题 。

8. VM Thread
这个线程比较牛,是JVM里面的线程母体,根据hotspot源码:vmThread.hpp里面的注释,它是一个单例的对象(最原始的线程)会产生或触发所有其他的线程,这个单个的VM线程是会被其他线程所使用来做一些VM操作(如清扫垃圾等)。
在 VM Thread 的结构体里有一个VMOperationQueue列队,所有的VM线程操作(vm_operation)都会被保存到这个列队当中,VMThread 本身就是一个线程,它的线程负责执行一个自轮询的loop函数(具体可以参考:VMThread.cpp里面的void VMThread::loop()) ,该loop函数从VMOperationQueue列队中按照优先级取出当前需要执行的操作对象(VM_Operation),并且调用VM_Operation->evaluate函数去执行该操作类型本身的业务逻辑。
VM操作类型被定义在vm_operations.hpp文件内,列举几个:ThreadStop、ThreadDump、PrintThreads、GenCollectFull、GenCollectFullConcurrent、CMS_Initial_Mark、CMS_Final_Remark….. 有兴趣的同学,可以自己去查看源文件。

9. GC task thread#0 (ParallelGC)
垃圾回收线程,负责垃圾回收。
通常JVM会启动多个线程来处理这部分工作,线程名称中#后面的数字也会累加,比如GC task thread#1 (ParallelGC)。

10. VM Periodic Task Thread
该线程是JVM周期性任务调度的线程,它由WatcherThread创建,是一个单例对象。
该线程在JVM内使用得比较频繁,比如:定期的内存监控、JVM运行状况监控。
可以使用jstat 命令查看GC的情况,比如查看某个进程没有存活必要的引用:
jstat -gcutil 23483 250 7
让JVM在控制台输出pid=23483的没有存活必要的引用情况,间隔250毫秒打印一次,一共打印7次。
这对于防止因为应用代码中直接使用native库或者第三方的一些监控工具的内存泄漏有非常大的帮助。

11.  JNI (Java Native Interface) global reference count
全局引用也是受垃圾回收器管理。
它的作用是防止回收到那些在native代码上还是被引用的,但是在java代码中却没有存活必要的引用。
对于防止因为应用代码中直接使用native库或者第三方的一些监控工具的内存泄漏有非常大的帮助。

如果启动Java程序时,增加了参数:-XX:+UseConcMarkSweepGC,表明将启用CMS (Concurrent Mark-Sweep)GC Thread,下面就是设置CMS GC后的thread dump:

2014-04-30 11:52:02
Full thread dump Java HotSpot(TM) 64-Bit Server VM (24.51-b03 mixed mode):

"Attach Listener" daemon prio=5 tid=0x00007fb6838bf000 nid=0x4a0b waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"DestroyJavaVM" prio=5 tid=0x00007fb683945000 nid=0x1903 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Service Thread" daemon prio=5 tid=0x00007fb682821000 nid=0x5b03 runnable [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"C2 CompilerThread1" daemon prio=5 tid=0x00007fb682834800 nid=0x5903 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"C2 CompilerThread0" daemon prio=5 tid=0x00007fb6838c7000 nid=0x5703 waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Signal Dispatcher" daemon prio=5 tid=0x00007fb683001000 nid=0x5503 runnable [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Surrogate Locker Thread (Concurrent GC)" daemon prio=5 tid=0x00007fb6838bd000 nid=0x521f waiting on condition [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

"Finalizer" daemon prio=5 tid=0x00007fb6838bc800 nid=0x3f03 in Object.wait() [0x0000000111e4c000]
   java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x00000007247b8780> (a java.lang.ref.ReferenceQueue$Lock)
at java.lang.ref.ReferenceQueue.remove(ReferenceQueue.java:135)
- locked <0x00000007247b8780> (a java.lang.ref.ReferenceQueue$Lock)
at java.lang.ref.ReferenceQueue.remove(ReferenceQueue.java:151)
at java.lang.ref.Finalizer$FinalizerThread.run(Finalizer.java:189)

"Reference Handler" daemon prio=5 tid=0x00007fb68300f000 nid=0x3d03 in Object.wait() [0x0000000111d49000]
   java.lang.Thread.State: WAITING (on object monitor)
at java.lang.Object.wait(Native Method)
- waiting on <0x00000007247b0830> (a java.lang.ref.Reference$Lock)
at java.lang.Object.wait(Object.java:503)
at java.lang.ref.Reference$ReferenceHandler.run(Reference.java:133)
- locked <0x00000007247b0830> (a java.lang.ref.Reference$Lock)

"VM Thread" prio=5 tid=0x00007fb68403c800 nid=0x3b03 runnable

"Gang worker#0 (Parallel GC Threads)" prio=5 tid=0x00007fb683800000 nid=0x2503 runnable

"Gang worker#1 (Parallel GC Threads)" prio=5 tid=0x00007fb683801000 nid=0x2703 runnable

"Gang worker#2 (Parallel GC Threads)" prio=5 tid=0x00007fb68281e800 nid=0x2903 runnable

"Gang worker#3 (Parallel GC Threads)" prio=5 tid=0x00007fb683801800 nid=0x2b03 runnable

"Gang worker#4 (Parallel GC Threads)" prio=5 tid=0x00007fb683002000 nid=0x2d03 runnable

"Gang worker#5 (Parallel GC Threads)" prio=5 tid=0x00007fb683003000 nid=0x2f03 runnable

"Gang worker#6 (Parallel GC Threads)" prio=5 tid=0x00007fb683003800 nid=0x3103 runnable

"Gang worker#7 (Parallel GC Threads)" prio=5 tid=0x00007fb683802000 nid=0x3303 runnable

"Concurrent Mark-Sweep GC Thread" prio=5 tid=0x00007fb6838ba000 nid=0x3903 runnable
"Gang worker#0 (Parallel CMS Threads)" prio=5 tid=0x00007fb6838b8800 nid=0x3503 runnable

"Gang worker#1 (Parallel CMS Threads)" prio=5 tid=0x00007fb6838b9000 nid=0x3703 runnable

"VM Periodic Task Thread" prio=5 tid=0x00007fb682820000 nid=0x5d03 waiting on condition

JNI global references: 159

可以看出,多了以下线程:

12. Concurrent Mark-Sweep GC Thread
并发标记清除垃圾回收器(就是通常所说的CMS GC)线程, 该线程主要针对于年老代垃圾回收。

13. Surrogate Locker Thread (Concurrent GC)
这个线程主要用于配合CMS垃圾回收器使用,它是一个守护线程,其主要负责处理GC过程中,Java层的Reference(指软引用、弱引用等等)与jvm 内部层面的对象状态同步。 这里对它们的实现稍微做一下介绍:这里拿 WeakHashMap做例子,将一些关键点先列出来(我们后面会将这些关键点全部串起来):
(1)我们知道HashMap用Entry[]数组来存储数据的,WeakHashMap也不例外, 内部有一个Entry[]数组。
(2)WeakHashMap的Entry比较特殊,它的继承体系结构为Entry->WeakReference->Reference 。
(3)Reference 里面有一个全局锁对象:Lock,它也被称为pending_lock.    注意:它是静态对象。
(4)Reference  里面有一个静态变量:pending。
(5)Reference  里面有一个静态内部类:ReferenceHandler的线程,它在static块里面被初始化并且启动,启动完成后处于wait状态,它在一个Lock同步锁模块中等待。
(6)另外,WeakHashMap里面还实例化了一个ReferenceQueue列队,这个列队的作用,后面会提到。
(7)上面关键点就介绍完毕了,下面我们把他们串起来。
假设,WeakHashMap对象里面已经保存了很多对象的引用。 JVM 在进行CMS GC的时候,会创建一个ConcurrentMarkSweepThread(简称CMST)线程去进行GC,ConcurrentMarkSweepThread线程被创建的同时会创建一个SurrogateLockerThread(简称SLT)线程并且启动它,SLT启动之后,处于等待阶段。CMST开始GC时,会发一个消息给SLT让它去获取Java层Reference对象的全局锁:Lock。 直到CMS GC完毕之后,JVM 会将WeakHashMap中所有被回收的对象所属的WeakReference容器对象放入到Reference 的pending属性当中(每次GC完毕之后,pending属性基本上都不会为null了),然后通知SLT释放并且notify全局锁:Lock。此时激活了ReferenceHandler线程的run方法,使其脱离wait状态,开始工作了。ReferenceHandler这个线程会将pending中的所有WeakReference对象都移动到它们各自的列队当中,比如当前这个WeakReference属于某个WeakHashMap对象,那么它就会被放入相应的ReferenceQueue列队里面(该列队是链表结构)。 当我们下次从WeakHashMap对象里面get、put数据或者调用size方法的时候,WeakHashMap就会将ReferenceQueue列队中的WeakReference依依poll出来去和Entry[]数据做比较,如果发现相同的,则说明这个Entry所保存的对象已经被GC掉了,那么将Entry[]内的Entry对象剔除掉。

14. 原来的垃圾回收线程GC task thread#0 (ParallelGC) 被替换为 Gang worker#0 (Parallel GC Threads)
垃圾回收线程,负责垃圾回收。
通常JVM会启动多个线程来处理这部分工作,线程名称中#后面的数字也会累加,比如GC task thread#1 (Parallel GC Threads)
Gang worker 是JVM用于做年轻代垃圾回收(minor gc)的线程。

参考文献:
1. http://blog.csdn.net/a43350860/article/details/8134234

Java_009:Thread Dump 中线程状态的含义(摘录+整理)

Thread Dump 是当前Java进程的一个快照,打印出所有线程的状态和调用堆栈,以及 Monitor的状态。
在不同的操作系统下,产生thread dump的方式是不同的。
(1)Windows 环境
在启动程序的控制台里输入:Ctrl + Break,thread dump会产生在标准输出中。
(2)Linux 环境
在启动程序的控制台里输入:Ctrl + \,thread dump会产生在标准输出中。
或者在另外一个终端中输入:kill -3 [pid],thread dump会产生在启动程序的标准输出中。
(3)在终端输入:jstack [pid],jstack是JDK5.0以后增加的查看某个java进程的线程信息命令。

以JBoss EAP 6.2为例,我们来看看一个Java thread dump的基本样子:

2014-04-29 14:28:08
Full thread dump Java HotSpot(TM) 64-Bit Server VM (24.51-b03 mixed mode):

说明:这部分可以看到thread dump的时间,JVM的信息

"Attach Listener" daemon prio=5 tid=0x00007f907901b000 nid=0x5c07 runnable [0x0000000000000000]
   java.lang.Thread.State: RUNNABLE

说明:"Attach Listener"是一个JVM内部的后台线程。

"Thread-71" prio=5 tid=0x00007f9074cfe800 nid=0x10403 runnable [0x00000001194f9000]
   java.lang.Thread.State: RUNNABLE
at sun.nio.ch.KQueueArrayWrapper.kevent0(Native Method)
at sun.nio.ch.KQueueArrayWrapper.poll(KQueueArrayWrapper.java:200)
at sun.nio.ch.KQueueSelectorImpl.doSelect(KQueueSelectorImpl.java:103)
at sun.nio.ch.SelectorImpl.lockAndDoSelect(SelectorImpl.java:87)
- locked <0x00000007ed189fd8> (a sun.nio.ch.Util$2)
- locked <0x00000007ed189fc8> (a java.util.Collections$UnmodifiableSet)
- locked <0x00000007ed189ea8> (a sun.nio.ch.KQueueSelectorImpl)
at sun.nio.ch.SelectorImpl.select(SelectorImpl.java:98)
at org.jboss.sun.net.httpserver.ServerImpl$Dispatcher.run(ServerImpl.java:382)
at java.lang.Thread.run(Thread.java:744)

说明:这是一个用户进程,是我们最需要关心的进程。
(1)线程 name: "Thread-71"
(2)线程优先级: prio=5
(3)java线程的标识:tid=0x00007f9074cfe800
(4)native线程的标识: nid= 0x10403
(5)线程的状态:runnable
(6)线程栈起始地址:[0x00000001194f9000] 

那么,Java thread dump中的线程状态都有哪些,它们的含义各是什么呢?

1.  runnable:执行中
一般指该线程正在执行状态中,该线程占用了资源,正在处理某个请求,有可能正在传递SQL到数据库执行,有可能在对某个文件操作,有可能进行数据类型等转换。

2. waiting on condition:等待资源(需重点关注) 
等待某个资源或等待某个条件的发生,可能情况有:
(1)读取某资源,且该资源采用了资源锁的情况下,线程进入等待状态,等待资源的读取。
比如,如果发现大量线程都在处在 wait on condition,并且从线程 stack看,发现都在等待网络读写,则这是一个网络瓶颈,因为网络阻塞导致线程无法执行,具体原因还要进一步分析。
一种可能情况是网络非常忙,几乎消耗了所有的带宽,仍然有大量数据等待网络读写;
另一种可能情况是网络空闲,但由于路由等问题,导致包无法正常的到达。
(2)正在等待其他线程的执行。
(3)线程正在sleep。

3. waiting on monitor entry:等待获取Monitor(需重点关注)
在dump中找到等待获取Monitor对应的对象地址,比如0x00000000acf4d0c0,如果发现有大量线程都在等待给这个地址上锁,那么这个对象就是引起性能瓶颈的原因。
继续在dump中寻找,看看线程获得了这个对象能在日志里找到谁获得了这个锁,如发现locked 0x00000000acf4d0c0 字样,就可以进一步分析了。

4. in Object.wait() :对象等待中 

关于Monitor的含义
Monitor是 Java中用以实现线程之间的互斥与协作的主要手段,它可以看成是对象或者 Class的锁。每一个对象都有,也仅有一个 Monitor。
从下图可以看出,每个 Monitor在某个时刻,只能被一个线程拥有,该线程就是“Active Thread”,而其它线程都是“Waiting Thread”,分别在两个队列“ Entry Set”和“Wait Set”里面等候。在“Entry Set”中等待的线程状态是“Waiting for monitor entry”;在“Wait Set”中等待的线程状态是“in Object.wait()”。
在“ Entry Set”里面的线程都等待拿到Monitor,拿到了线程就成为了Runnable线程,否则就会一直处于处于“waiting for monitor entry”。
在 “Wait Set”里面的线程都如饥似渴地等待拿到Monitor。那么它们他是怎么进入到“Wait Set”的呢?
当一个线程拿到了Monitor,但是在其他资源没有到位的情况下,调用同步锁对象(一般是synchronized()内的对象)的 wait() 方法,放弃了 Monitor,它就进入到了 “Wait Set”队列。只有当其他线程通过notify() 或者 notifyAll(),释放了同步锁后,这个线程才会有机会重新去竞争Monitor。在stack中,它表现的状态是in Object.wait()。


参考文献:
1. http://www.blogjava.net/jzone/articles/303979.html
2. http://go-on.iteye.com/blog/1673894
3. http://www.cnblogs.com/zhengyun_ustc/archive/2013/01/06/dumpanalysis.html
4. http://www.cnblogs.com/tomsheep/archive/2010/06/09/1754419.html
5. http://www.blogjava.net/jzone/articles/303979.html

2014年4月27日星期日

Tools_028:使用goagent为电脑翻墙

2008年,GFW开始封住了blogspot,为此,我每次更新博客都要翻墙。
虽然有公司的VPN,但VPN等于是给了一个国外的IP,对于经常做本地开发的我来说,时常要来回切换,VPN的每一次的断开与连接都是一次虐心的感受。
多少个朋友劝我把博客搬到墙内,但是我就是不愿意,因为我已经割舍不下blogspot。
我不知道,他们究竟在怕什么;我不知道,我能坚持写博客到什么时候;我不知道,GFW什么时候能够轰然倒塌。
我只是一名IT工程师,我唯一能做的就是坚持,因为我“热爱Java,热爱生活”,因为我需要经常翻墙去寻找一些问题的解决思路。

如果你像我一样,一直希望看看墙外的世界。
如果你像我一样,一直希望能够有一个好用又免费的翻墙软件。
那么,请选择goagent吧。
我第一次发现,PAAS平台不再是高不可攀的技术,而是切切实实地带给你自由愉悦的体验。
让每个炎黄子孙骄傲的雄伟的万里长城作为历史遗存留在那里就够了,不需要再筑起这道烦人的防火墙。更何况“万里长城今犹在,不见当年秦始皇。”
“外面的世界精彩,外面的世界很无奈。”
精彩也好,无奈也罢,请把看与不看的权利交给每个人自己,以自由的名义。

附1:关于goagent使用方法。
请参考这个最权威、最详细、最傻瓜的教程《goagent GAE平台部署教程》。
遇到问题,请耐心查看错误提示,我刚刚部署成功,预祝你也成功!

附2:关于"无法连接到真正的 www.youtube.com"问题的解决。
按照教程设置好之后,发现我的博客虽然可以直接访问了,但是访问youtube,会报告下图错误:

解决方法如下:
(1)先说明一下我的系统是MAC OS X 10.9.2,为了使用上更加灵活,我没有在“系统偏好设置”中设置网络代理,而是使SwitchySharp(一个Chrome插件)为Chrome浏览器设置代理。
也就是说,我的机器上只有Chrome浏览器可以翻墙,其它浏览器还在墙内,这样就彻底免除了切换的痛苦。
(2)确认你安装了GoAgent CA 证书:CA.crt,这个文件在local目录下,双击即可安装。
(3)打开“钥匙串访问”应用,修改设置:使用此证书时:总是信任。


现在,你可以畅游youtube啦!

如果要查看你的应用使用的流量的情况,可以访问:https://appengine.google.com/,统计的信息非常全面。

2014年4月22日星期二

Linux_038:常用命令之九:ps

环境:RHEL 7

ps 是 Process Status 的缩写。

1. 语法格式 
ps 命令支持三种使用的语法格式
(1)UNIX 风格,选项可以组合在一起,并且选项前必须有“-”连字符。
(2)BSD 风格,选项可以组合在一起,但是选项前不能有“-”连字符。
(3)GNU 风格,选项前有两个“-”连字符。
能够混用这几种风格,但是可能会发生冲突,因此建议不要混用。

2. BSD 风格常用命令

2.1 ps
输出默认显示 4 列信息:
(1)PID:进程号
(2)TTY:命令所运行的终端  
(3)TIME:运行着的该命令所占用的 CPU 处理时间  
(4)CMD:进程所运行的命令

2.2 ps aux
参数说明:
(1)a:当前终端下的所有程序,包括其他用户的程序。
(2)u:以用户为主的格式来显示程序状况。
(3)x:显示所有程序,不以终端来区分。
输出如下:
USER        PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
root          1  0.0  0.3 128100  6736 ?        Ss   22:27   0:01 /usr/lib/systemd/systemd --switched-root --system --deserialize 21
root          2  0.0  0.0      0     0 ?        S    22:27   0:00 [kthreadd]
root          3  0.0  0.0      0     0 ?        S    22:27   0:00 [ksoftirqd/0]
root          7  0.0  0.0      0     0 ?        S    22:27   0:00 [migration/0]
root          8  0.0  0.0      0     0 ?        S    22:27   0:00 [rcu_bh]
root          9  0.0  0.0      0     0 ?        S    22:27   0:01 [rcu_sched]
root         10  0.0  0.0      0     0 ?        S    22:27   0:00 [watchdog/0]

2.4 其它参数
(1)c:显示每个程序真正的指令名称,不包含路径,参数或常驻服务的标识。
(2)e:显示每个程序所使用的环境变量。
(3)r:显示正在运行的进程。
(4)l:长格式输出。
(5)j:用任务格式来显示进程。
(6)f:用树形格式来显示进程。
(7)s:采用程序信号的格式显示程序状况。

MAC_011:NetBeans十大快捷键

OS X 版本:10.9.2。
NetBeans 版本:8.0。

MAC中使用NetBeans时,快捷键与Windows下有所不同,这里特地总结常用十大快捷键:

1. 查找与替换
(1)当前文件中查找:command + F
(2)当前文件中替换:command + R
(3)在项目中查找:shift + command + F
(4)在项目中替换:shift + command + H
(5)重命名:control + R (根据上下文不同,可能是重命名类、方法名、参数名、变量名)
(6)在项目窗口中定位类文件的位置:shift + command + 1
(7)在文件窗口中定位类文件的位置:shift + command + 2

2. 新建与打开
(1)新建文件:command + N
(2)新建项目:command + shift + N
(3)打开文件:control + shift + O
(4)打开类:command + O
(5)打开项目:shift + command + O

3. 取消/增加注释:command + /

4. 最大化/最小化编辑窗口:shift + esc

5. 插入代码:control + I

6. 修复导入:shift + command + I

7. 打开不同的窗口
(1)返回编辑窗口:command + 0
(2)打开项目窗口:command + 1
(3)打开文件窗口:command + 2
(4)打开收藏夹窗口:command + 3
(5)打开输出窗口:command + 4
(6)打开服务窗口:command + 5
(7)打开操作项窗口:command + 6
(8)打开导航器窗口:command + 7
(9)关闭某个窗口:command + W

8. 格式化代码:control + shift + F

9. 查找用例:command + F7
这个快捷键与MAC默认的快捷键冲突,我不想改动MAC的默认快捷键,所以还是希望下个NetBeans版本能修复吧。

10. 代码提示:command + \

11. 上一个/下一个编辑处
这个快捷键我觉得还是挺有用的,但是我没找到,也没试出来。
原来Windows下NetBeans的此快捷键是Alt + 左/右箭头。
但是在MAC下,似乎所有带alt键的快捷方式都不起作用了。

现在,让NetBeans在你的指尖飞起来吧。

参考文献:
1. http://poplaryy.iteye.com/blog/620574
2. https://netbeans.org/kb/articles/mac.html?print=yes

2014年4月21日星期一

MAC_010:启用MAC自带的Apache

OS X 版本:10.9.2。

Apache的安装目录位于/etc/apache2/,httpd.conf文件就在这个目录下。
Apache的module库位于/usr/libexec/apache2/目录下。

1. 查看版本:sudo apachectl -v

2. 启动:sudo apachectl start

3. 重启:sudo apachectl restart

4. 停止:sudo apachectl stop

5. 查看状态:sudo apachectl status

启动后,打开浏览器,访问:http://localhost,显示"It Works!",即说明启动成功!

参考文献:
1. http://www.cnblogs.com/snandy/archive/2012/11/13/2765381.html
2. http://smartwebdeveloper.com/mac/httpd-conf-location-mac
3. http://stackoverflow.com/questions/2306337/wheres-the-module-files-for-the-build-in-apache-in-snow-leopard
4. http://stackoverflow.com/questions/12395639/mac-os-mountain-lion-apache-running-but-localhost-not-working
5. http://down.chinaz.com/server/201108/942_1.htm
6. http://blog.csdn.net/u012945598/article/details/17162039

Linux_037:常用命令之八:ln

1. 目录软连接
ln -s maven-3.2.1 maven
这里 maven-3.2.1 是源文件,maven 是目标文件。
这样做的好处是,以后 Maven升级后,比如升到了3.2.2版本,只需执行如下命令,而环境脚本无需修改:
rm maven
ln -s maven-3.2.2 maven

也可以省略目标文件,如果不指定目标文件,ln 命令会在当前目录中创建一个和源文件一样的文件名。

考虑如下场景:
/root 所在分区很大,而 /opt 所在分区空间不够了,而环境变量等是设置在 /opt 目录下的。

可以通过 ln -s 解决这个问题,进行如下操作:

# cd /root
# mkdir ose
# cd /opt
# ln -s /root/ose
# ll
输出如下:
lrwxrwxrwx.  1 root root     9 2月   3 11:50 ose -> /root/ose
会看到在 /opt 目录下创建了一个 ose 目录,并指向 /root/ose。

参考文献:
1. http://www.9usb.net/200812/linux-ln.html
2. http://www.cnblogs.com/peida/archive/2012/12/11/2812294.html

2014年4月20日星期日

Linux_036:常用命令之七:netstat

我们知道,计算机与网络上的其他计算机建立连接是通过开放端口的方式来实现的。
而查看本机开放的端口就要用到netstat命令。
netstat命令用来显示本机网络连接、运行端口和路由表等信息。
netstat是在内核中访问网络及相关信息的程序,它能提供TCP连接,TCP和UDP监听,进程内存管理的相关报告。

其格式如下:netstat [参数选项]

(1)-a:显示本机所有连接和监听端口。
(2)-n:以网络IP地址的形式显示当前建立的有效连接和端口。
(3)-r:显示路由表信息。
(4)-s:显示按协议的统计信息。默认显示IP、IPv6、ICMP、ICMPv6、TCP、TCPv6、UDP和UDPv6的统计信息。
(5)-v:显示当前的有效连接,与“-n”选项类似。
(6)-t:显示所有的TCP连接情况。
(7)-u:显示所有的UDP连接情况。
(8)-c[秒数]:后面跟的秒数表示每隔几秒就刷新显示一次。
(9)-i:显示自动配置接口的状态。
(10)-l:仅显示连接状态为“LISTEN”的服务的网络状态。
(11)-p:显示连接对应的PID与Program name。

运行netstat需要root权限,下面列举一些常用的命令参数。

1. 列出本机所有连接和监听端口以及对应的PID和Program name:netstat -anp

Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address               Foreign Address             State       PID/Program name
tcp        0      0 127.0.0.1:9999              0.0.0.0:*                   LISTEN      4849/java        
tcp        0      0 0.0.0.0:111                 0.0.0.0:*                   LISTEN      1244/rpcbind      
tcp        0      0 127.0.0.1:8080              0.0.0.0:*                   LISTEN      4849/java        
tcp        0      0 0.0.0.0:22                  0.0.0.0:*                   LISTEN      1664/sshd        
tcp        0      0 127.0.0.1:631               0.0.0.0:*                   LISTEN      1407/cupsd        
tcp        0      0 127.0.0.1:25                0.0.0.0:*                   LISTEN      1744/master      
tcp        0      0 127.0.0.1:4447              0.0.0.0:*                   LISTEN      4849/java        
tcp        0      0 127.0.0.1:9990              0.0.0.0:*                   LISTEN      4849/java        
tcp        0      0 0.0.0.0:38310               0.0.0.0:*                   LISTEN      1374/rpc.statd    
tcp        0      0 10.0.2.15:54360             173.194.127.73:80           ESTABLISHED 3265/firefox      
tcp        0      0 10.0.2.15:41326             74.125.235.206:80           ESTABLISHED 3265/firefox      
tcp        1      0 10.0.2.15:38472             23.61.250.43:80             CLOSE_WAIT  2258/clock-applet
tcp        0      0 :::111                      :::*                        LISTEN      1244/rpcbind      
tcp        0      0 :::22                       :::*                        LISTEN      1664/sshd        
tcp        0      0 ::1:631                     :::*                        LISTEN      1407/cupsd        
tcp        0      0 ::1:25                      :::*                        LISTEN      1744/master      
tcp        0      0 :::59594                    :::*                        LISTEN      1374/rpc.statd    
udp        0      0 0.0.0.0:48238               0.0.0.0:*                               1374/rpc.statd    
udp        0      0 0.0.0.0:111                 0.0.0.0:*                               1244/rpcbind      
udp        0      0 0.0.0.0:631                 0.0.0.0:*                               1407/cupsd        
udp        0      0 0.0.0.0:702                 0.0.0.0:*                               1374/rpc.statd    
udp        0      0 0.0.0.0:68                  0.0.0.0:*                               5167/dhclient    
udp        0      0 0.0.0.0:995                 0.0.0.0:*                               1244/rpcbind      
udp        0      0 :::111                      :::*                                    1244/rpcbind      
udp        0      0 :::41636                    :::*                                    1374/rpc.statd    
udp        0      0 :::995                      :::*                                    1244/rpcbind  

1.1 以 tcp        0      0 0.0.0.0:22                  0.0.0.0:*                   LISTEN      1664/sshd 这行数据为例说明
(1)tcp 表示使用的传输层协议是TCP。
(2)0.0.0.0:22 表示本机上的任意IP地址,端口是22。
(3)0.0.0.0:* 表示接受任意IP地址的连接,端口任意。
(4)LISTENING 表示处于监听状态。
(5)1664/sshd 表示PID是524,运行的程序是sshd。
这条数据告诉我们:本机运行的程序sshd,其PID是1664,正在本机绑定的任意IP地址的端口22上监听来自任意IP地址任意端口的访问。

1.2 以 tcp        0      0 10.0.2.15:54360             173.194.127.73:80           ESTABLISHED 3265/firefox 这行数据为例说明  
这条数据告诉我们:本机中的firefox(PID=3265)进程使用54360与远程web服务器(173.194.127.73)的80端口建立了一个TCP连接,ESTABLISHED表示已经建立了连接。

2. 端口状态的含义
(1)LISTEN 表示服务器端口正在开放,等待客户端连接。
(2)ESTABLISHED 表示已经建立了连接,数据处于正常传输状态。
(3)CLOSE_WAIT 表示正在关闭的端口。
(4)TIME_WAIT 表示本地连接(客户端)已经正常关闭,此时服务器端状态为TIME_WAIT。
(5)CLOSED 表示没有活动的连接。

要想清楚知道这些状态的含义,就要了解TCP协议的工作过程。






查看本机各个状态的连接有多少个:netstat -an|awk '/tcp/ {print $6}'|sort|uniq -c

3. 查看本机路由信息:netstat -nr
Kernel IP routing table
Destination     Gateway         Genmask         Flags   MSS Window  irtt Iface
10.0.2.0        0.0.0.0         255.255.255.0   U         0 0          0 eth0
0.0.0.0         10.0.2.2        0.0.0.0         UG        0 0          0 eth0
(1)第1行数据:10.0.2.0 表示主机所在网络的地址。
如果数据传送目标是在本局域网内通信,则可直接通过eth0转发数据包。
(2)第2行数据:0.0.0.0 表示默认路由的目标。
默认路由的意思是当一个数据包的目的网段(比如访问Internet)不在当前的路由表中时,将会把这个数据包通过eth0这个接口发送到10.0.2.2这个地址,这个地址是下一个路由器的接口。

4. 查看JVM都在监听哪些进程:netstat -naoputl | grep java


参考文献:
1. http://hi.baidu.com/senya/item/c9031d0f6cd1f511acdc706e
2. http://www.cnblogs.com/peida/archive/2013/03/08/2949194.html
3. http://www.itokit.com/2012/0516/73950.html
4. http://xcily1.blog.163.com/blog/static/2871691620096911313479/
5. http://www.blogjava.net/spray/archive/2008/06/19/209158.html?opt=admin

Linux_035:常用命令之六:top

top 命令能够实时显示系统中各个进程的资源占用状况。

# top

top - 16:20:18 up 82 days,  2:07,  2 users,  load average: 0.00, 0.00, 0.00
Tasks: 269 total,   1 running, 268 sleeping,   0 stopped,   0 zombie
Cpu(s):  0.0%us,  0.0%sy,  0.0%ni,100.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st
Mem:  16457696k total,  2580412k used, 13877284k free,   296768k buffers
Swap: 20479992k total,        0k used, 20479992k free,   688564k cached

  PID USER      PR  NI  VIRT  RES  SHR S %CPU %MEM    TIME+  COMMAND                                            
13898 root      20   0 15064 1404  956 R  0.3  0.0   0:00.10 top                                                
18130 root      20   0 9403m 705m  19m S  0.3  4.4 109:35.46 java                                                
    1 root      20   0 19112 1424 1176 S  0.0  0.0   0:15.75 init                                            
    2 root      20   0     0    0    0 S  0.0  0.0   0:00.02 kthreadd                                            
    3 root      RT   0     0    0    0 S  0.0  0.0   0:00.00 migration/0                                        
    4 root      20   0     0    0    0 S  0.0  0.0   0:00.13 ksoftirqd/0                                        
    5 root      RT   0     0    0    0 S  0.0  0.0   0:00.00 watchdog/0                                          
    6 root      RT   0     0    0    0 S  0.0  0.0   0:00.00 migration/1                                        
    7 root      20   0     0    0    0 S  0.0  0.0   0:00.11 ksoftirqd/1                                        
    8 root      RT   0     0    0    0 S  0.0  0.0   0:00.00 watchdog/1                                          
    9 root      RT   0     0    0    0 S  0.0  0.0   0:00.00 migration/2                                        
   10 root      20   0     0    0    0 S  0.0  0.0   0:00.01 ksoftirqd/2                                        
   11 root      RT   0     0    0    0 S  0.0  0.0   0:00.00 watchdog/2                                          
   12 root      RT   0     0    0    0 S  0.0  0.0   0:00.07 migration/3                                        
   13 root      20   0     0    0    0 S  0.0  0.0   0:00.00 ksoftirqd/3                                        
   14 root      RT   0     0    0    0 S  0.0  0.0   0:00.00 watchdog/3                                          
   15 root      RT   0     0    0    0 S  0.0  0.0   0:00.01 migration/4    

说明:

1. 第 1-5 行是当前系统情况整体的统计信息区

1.1 第 1 行是任务队列信息,包括:
(1)当前系统时间。
(2)系统持续运行的时间。
(3)当前登录用户数。
(4)load average后面的三个数分别是1分钟、5分钟、15分钟前到现在的负载平均值。
load average 数据是每隔 5 秒钟检查一次活跃的进程数,然后按特定算法计算出的数值。
如果这个数除以逻辑 CPU 的数量,结果高于 1 的时候就表明系统在超负荷运转了。

1.2 第 2 行是任务信息,包括:
(1)total - 当前系统中的进程总数量。
(2)running - 处于运行状态的进程数量。
(3)sleeping - 处于休眠状态的进程数量。
(4)stopped - 处于停止状态的进程数量。
(5)zombie - 处于僵尸状态的进程数量。

1.3 第 3 行是CPU状态信息,包括:
(1)us - 用户空间占用CPU的百分比。
(2)sy - 内核空间占用CPU的百分比。
(3)ni - 改变过优先级的进程占用CPU的百分比。
(4)id - 空闲CPU百分比。
(5)wa - IO等待占用CPU的百分比。
(6)hi - 硬中断(Hardware IRQ)占用CPU的百分比。
(7)si - 软中断(Software Interrupts)占用CPU的百分比。

1.4 第 4 行是内存状态信心,包括:
(1)total - 物理内存总量。
(2)used - 已经使用的内存总量,是内核可“控制”的内存数量。
注意,被“控制”的内存不见得都在实际使用中,内核有自己的考虑:比如内核并不会把对象已经释放的内存交还给free。
(3)free - 空闲的内存总量,还未被内核纳入“控制”的内存数量。
(4)buffers - 存的内存总量。

1.5 第5行是swap交换分区信息,包括:
(1)total - 交换区总量。
(2)used - 使用的交换区总量。
注意,要特别关注used数值,如果它在不断的变化,说明内核在不断进行内存和swap的数据交换,即内存不够用了。
(3)free - 空闲交换区总量。
(4)cached - 缓冲的交换区总量。

2. 第 7 行以下是各进程(任务)的状态监控,项目列信息说明如下:
(1)PID - 进程id。
(2)USER - 进程所有者。
(3)PR - 进程优先级。
(4)NI - nice值,负值表示高优先级,正值表示低优先级。
(5)VIRT - 进程使用的虚拟内存总量,单位kb,VIRT=SWAP+RES。
(6)RES - 进程使用的、未被换出的物理内存大小,单位kb,RES=CODE+DATA。
(7)SHR - 共享内存大小,单位kb。
(8)S - 进程状态,D=不可中断的睡眠状态、R=运行、S=睡眠、T=跟踪/停止、Z=僵尸进程。
(9)%CPU - 上次更新到现在的CPU时间占用百分比。
注意,这里%CPU指的是逻辑CPU百分比,如果你有8个逻辑CPU,理论上该值最大可达800%。
也就是说,该值是每个逻辑CPU百分比的总和,是可以超过100%的。
(10)%MEM - 进程使用的物理内存百分比。
(11)TIME+ - 进程使用的CPU时间总计,单位1/100秒。
(12)COMMAND - 进程名称(命令名/命令行)。

3. 高级操作
(1)按下 L 键,打开或关闭显示 load(第 1 行)内容。
(2)按下 T 键,打开或关闭显示 thread(第 2、3 行)行内容。
(3)按下 M 键,打开或关闭显示 memory(第 4、5 行)行内容。
(4)加重显示当前运行(S=R)的进程
默认进入 top 时,(S=R)的进程字体是被加重显示的,按下 Y 键可以关闭/打开加重显示效果。
(5)整行加重反显当前运行(S=R)的进程
在加重显示当前运行(S=R)的进程情况下,按下 B 键(Bold)可以关闭/打开整行加重反显效果。
(6)加重显示显示排序列
默认进入 top 时,进程是按照 CPU% 来排序的,按下 X 键可以打开/关闭加重显示效果。
(7)整列加重反显排序列
在加重显示排序列的情况下,按下 B 键(Bold)可以关闭/打开整列加重反显效果。
(8)通过“shift + >”或“shift + <”可以向右或左改变排序列。
通过“shift + > + R”或“shift + < + R ”可以向右或左改变排序列,并倒序排列。
(9)top -c 可以显示 COMMAND 列完整的命令行。
(10)top -p [PID] 显示指定进程的信息。
(11)监控每个逻辑CPU的状态
敲击键盘“1”键可以打开/关闭逻辑CPU的状态信息。
关于逻辑CPU的概念,请参考《如何查看机器的CPU信息?》。
(12)top -Hp [pid] 显示指定进程的线程信息。
(13)按下 K 键,输入 PID,输入信号,回车确认给该 PID 发送信号。
(14)按下 R 键,输入 PID,输入 nice 值,回车确认给该 PID 设置 nice 值。

参考文献:
1. http://www.cnblogs.com/peida/archive/2012/12/24/2831353.html
2. http://www.cnblogs.com/caosiyang/archive/2012/10/15/2724585.html
3. http://www.cnblogs.com/wangkangluo1/archive/2012/04/18/2454993.html
4. http://wenku.baidu.com/view/1cb3338683d049649b6658a3.html
5. http://edsionte.com/techblog/archives/4297                      

MAC_009:唤醒后无声的解决办法

OS X 版本:10.9.2。

情况是这样的:一开始我插着耳机听音乐,然后中间去做其它事情,回来时,MAC休眠了。
唤醒后,拔掉耳机后开始工作,发现没有声音了,而声音提示显示一切正常。
来来回回折腾了一下,还是不行,因为还有其它程序在运行,我不想重启。

经过百度,发现这是MAC的一个BUG,解决办法如下:

切换到root用户,然后先卸载音频驱动,再重新加载音频驱动:
# kextunload /System/Library/Extensions/AppleHDA.kext
# kextload /System/Library/Extensions/AppleHDA.kext

为了方便,参考文献1还写成了脚本,贴在下面,我不懂Apple Script,贴出来留待以后参考吧:

on run {input, parameters}
do shell script "" with administrator privileges
set the rootPwd to text returned of (display dialog "请输入您的管理员密码:" default answer "" with hidden answer)
try
do shell script "echo " & rootPwd & "|sudo -S killall coreaudiod"
do shell script "echo " & rootPwd & "|sudo -S kextunload /System/Library/Extensions/AppleHDA.kext"
do shell script "echo " & rootPwd & "|sudo -S kextload /System/Library/Extensions/AppleHDA.kext"
do shell script "sudo -k" --logout root
display dialog "操作已经成功完成,您的系统应该能够恢复声音。如果问题依旧,请直接重启系统。" buttons {"好"} with icon 1 with title "成功"
on error
display dialog "由于您输入错误的密码,操作无法进行。请再次运行这个服务,并重新输入正确的当前管理员密码。" buttons {"好"} with icon caution with title "错误"
end try
return input
end run

参考文献:
1. http://tieba.baidu.com/p/2865826102

2014年4月19日星期六

Linux_034:终端类型介绍

1. tty
tty 一词源于 teletypes,或者 teletypewriters,原指电传打字机,是通过串行线用打印机键盘通过阅读和发送信息的东西,后被键盘与显示器取代,即终端设备。
终端是一种字符型设备,它有多种类型,通常使用 tty 来简称各种类型的终端设备。

2. pty
虚拟终端(pseudo-tty),远程使用 telnet 或 xterm 连接到到主机时的终端。

3. pts/ptmx
pts(pseudo-terminal slave)是 pty 的实现方法,与 ptmx(pseudo-terminal master)配合使用实现pty。

参考文献:
1. http://blog.chinaunix.net/uid-24227137-id-3440106.html 如何区分Linux下的几种终端类型:tty、pty和pts

Linux_033:常用命令之五:uname

uname命令用来查看系统信息。

1. 显示操作系统的名称:uname
# uname
Linux

2. 显示CPU类型:uname -m (联想记忆:machine)
# uname -m
x86_64

3. 显示主机名:uname -n (联想记忆:nodename)
# uname -n
localhost.localdomain

4. 显示系统的内核版本信息:uname -r (联想记忆:release)
# uname -r
2.6.32-431.el6.x86_64

5. 显示操作系统是第几个版本:uname -v (联想记忆:version)
# uname -v
#1 SMP Sun Nov 10 22:19:54 EST

6. 显示硬件平台类型:uname -i 
# uname -i
x86_64

7. 显示所有系统信息:uname -a (联想记忆:all)
# uname -a
Linux localhost.localdomain 2.6.32-431.el6.x86_64 #1 SMP Sun Nov 10 22:19:54 EST 2013 x86_64 x86_64 x86_64 GNU/Linux 

Linux_032:如何查看Linux版本信息?

1. 安装时的版本信息
在/etc/issue和/etc/redhat-release文件中保存了系统安装时默认的发行版本信息,通常安装好这两个文件内容不会发生变化。
# cat /etc/issue
Red Hat Enterprise Linux Server release 6.5 (Santiago)
Kernel \r on an \m

# cat /etc/redhat-release
Red Hat Enterprise Linux Server release 6.5 (Santiago)

2. 当前系统的版本信息
# lsb_release -a
LSB Version: :base-4.0-amd64:base-4.0-noarch:core-4.0-amd64:core-4.0-noarch:graphics-4.0-amd64:graphics-4.0-noarch:printing-4.0-amd64:printing-4.0-noarch
Distributor ID: RedHatEnterpriseServer
Description: Red Hat Enterprise Linux Server release 6.5 (Santiago)
Release: 6.5
Codename: Santiago
[root@localhost 桌面]# cat /etc/issue
Red Hat Enterprise Linux Server release 6.5 (Santiago)
Kernel \r on an \m

如果报告:lsb_release command not found,可以用 yum install redhat-lsb -y 来安装。
如果发现lsb_release -a和/etc/issue显示的发行版本号不同,原因可能是内核升级了。

3. 当前系统的内核版本信息
# cat /proc/version
Linux version 2.6.32-431.el6.x86_64 (mockbuild@x86-023.build.eng.bos.redhat.com) (gcc version 4.4.7 20120313 (Red Hat 4.4.7-4) (GCC) ) #1 SMP Sun Nov 10 22:19:54 EST 2013

Linux_031:如何查看机器的CPU信息?


在/proc/cpuinfo这个文件中存储了CPU信息。
信息内容分别列出了processor 0 – n 的规格,注意,这里的n并不是物理CPU的数量,而是逻辑CPU的数量。
以下是其中一个逻辑CPU的信息:

processor : 15
vendor_id : GenuineIntel
cpu family : 6
model : 26
model name : Intel(R) Xeon(R) CPU           E5520  @ 2.27GHz
stepping : 5
cpu MHz : 2266.779
cache size : 8192 KB
physical id : 1
siblings : 8
core id : 3
cpu cores : 4
apicid : 23
initial apicid : 23
fpu : yes
fpu_exception : yes
cpuid level : 11
wp : yes
flags : fpu vme de pse tsc msr pae mce cx8 apic mtrr pge mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe syscall nx rdtscp lm constant_tsc arch_perfmon pebs bts rep_good xtopology nonstop_tsc aperfmperf pni dtes64 monitor ds_cpl vmx est tm2 ssse3 cx16 xtpr pdcm dca sse4_1 sse4_2 popcnt lahf_lm tpr_shadow vnmi flexpriority ept vpid
bogomips : 4532.68
clflush size : 64
cache_alignment : 64
address sizes : 40 bits physical, 48 bits virtual
power management:

1. 物理CPU
指的是物理机器中CPU插槽上的实际CPU个数。
查看方法:查看/proc/cpuinfo文件中不重复的physical id 有几个,因为具有相同physical id的CPU是同一个CPU封装的Core。
查看命令:cat /proc/cpuinfo |grep "physical id"|sort |uniq|wc -l
我这里是2。

2. 逻辑CPU 
指的是物理机器的CPU Core的总数量。
一般情况下,一颗CPU可能有多核(CPU Core),如果使用了Intel的超线程(Hyper-Threading), CPU Core的数量还要乘以2。
所以,逻辑CPU数量=物理CPU数量 x CPU Core数量 x 2(如果支持并开启HT)。
proc/cpuinfo文件中具有相同core id的CPU是同一个Core的超线程。
查看方法:查看/proc/cpuinfo文件中不重复的processor有几个。
查看命令:cat /proc/cpuinfo |grep "processor"|wc -l
我这里是16。

3. CPU Core
查看方法:查看/proc/cpuinfo文件中不重复的cores有几个。
查看命令:cat /proc/cpuinfo |grep "cores"|uniq 
我这里是4。

结论:我这里应该是2个物理CPU,每个物理CPU有4个Core,并且使用了Intel的超线程,所以显示16个逻辑CPU=2 x 4 x 2。

参考文献:
1. http://baike.baidu.com/link?url=oTAtRWVj2vpIFCgr9B9EFa7ccHMV7_iGBQVzVF-ON3FEKHKuDAZdWSXej9_97UIg
2. http://blog.csdn.net/dba_waterbin/article/details/8644626

2014年4月18日星期五

MAC_008:VirtualBox 虚机的快捷键

OS X 版本:10.9.2。

使用MAC后,开始习惯和掌握MAC快捷键。
关于MAC快捷键,请参考《MAC 快捷键》。
使用VirtualBox安装了其它虚机后,比如Windows和Linux,出现了一个现实的问题:
因为MAC键盘以及快捷键与Windows和Linux都不太一样,导致操作VirtualBox中的客机非常不方便。

为此,总结以下常用的MAC键盘和Windows键盘的映射关系:

1. Windows键:右command键,注意是右边的command键,左边的command键是MAC自己用的,用来在虚机和主机之间切换。经过实验,control + esc 组合键也相当于Windows键。
找到了Windows键,所有的与Windows键有关的快捷键,比如Win + D、Win + E,都可以继续使用啦!

2. 所有 F功能键(比如F1,F2...F12):fn + F功能键,比如fn+ F1相当于Windows的F1键。

3. 复制:control + C,这和Windows系统一样。注意,MAC键盘只有一个control键,在左边,而且MAC的复制快捷键是 command + C。

4. 粘贴:control + V,这和Windows系统一样。注意,MAC键盘只有一个control键,在左边,而且MAC的复制快捷键是 command + V。

5. 关闭窗口:alt + fn + F4。根据第2条,fn + F4 相当于Windows的F4,所以alt + fn + F4,就相当于Windows下的alt + F4。注意,MAC键盘中alt和option是一个键,且左右各有一个。

6. 任务管理器:control + alt + esc
 

2014年4月17日星期四

EAP_002:HornetQ集群fail over失败问题

JBoss版本:JBoss EAP 6.2.0。

1. 测试环境
一台机器上部署2个JBoss:server1和server2。

2. 修改server1的standalone-full-ha.xml文件内容如下:
主要是替换了hornetq-server部分内容:

<?xml version='1.0' encoding='UTF-8'?>
<server xmlns="urn:jboss:domain:1.5">
    <extensions>
        <extension module="org.jboss.as.clustering.infinispan"/>
        <extension module="org.jboss.as.clustering.jgroups"/>
        <extension module="org.jboss.as.cmp"/>
        <extension module="org.jboss.as.connector"/>
        <extension module="org.jboss.as.deployment-scanner"/>
        <extension module="org.jboss.as.ee"/>
        <extension module="org.jboss.as.ejb3"/>
        <extension module="org.jboss.as.jacorb"/>
        <extension module="org.jboss.as.jaxr"/>
        <extension module="org.jboss.as.jaxrs"/>
        <extension module="org.jboss.as.jdr"/>
        <extension module="org.jboss.as.jmx"/>
        <extension module="org.jboss.as.jpa"/>
        <extension module="org.jboss.as.jsf"/>
        <extension module="org.jboss.as.jsr77"/>
        <extension module="org.jboss.as.logging"/>
        <extension module="org.jboss.as.mail"/>
        <extension module="org.jboss.as.messaging"/>
        <extension module="org.jboss.as.modcluster"/>
        <extension module="org.jboss.as.naming"/>
        <extension module="org.jboss.as.pojo"/>
        <extension module="org.jboss.as.remoting"/>
        <extension module="org.jboss.as.sar"/>
        <extension module="org.jboss.as.security"/>
        <extension module="org.jboss.as.threads"/>
        <extension module="org.jboss.as.transactions"/>
        <extension module="org.jboss.as.web"/>
        <extension module="org.jboss.as.webservices"/>
        <extension module="org.jboss.as.weld"/>
    </extensions>


    <management>
        <security-realms>
            <security-realm name="ManagementRealm">
                <authentication>
                    <local default-user="$local"/>
                    <properties path="mgmt-users.properties" relative-to="jboss.server.config.dir"/>
                </authentication>
                <authorization map-groups-to-roles="false">
                    <properties path="mgmt-groups.properties" relative-to="jboss.server.config.dir"/>
                </authorization>
            </security-realm>
            <security-realm name="ApplicationRealm">
                <authentication>
                    <local default-user="$local" allowed-users="*"/>
                    <properties path="application-users.properties" relative-to="jboss.server.config.dir"/>
                </authentication>
                <authorization>
                    <properties path="application-roles.properties" relative-to="jboss.server.config.dir"/>
                </authorization>
            </security-realm>
        </security-realms>
        <audit-log>
            <formatters>
                <json-formatter name="json-formatter"/>
            </formatters>
            <handlers>
                <file-handler name="file" formatter="json-formatter" path="audit-log.log" relative-to="jboss.server.data.dir"/>
            </handlers>
            <logger log-boot="true" log-read-only="false" enabled="false">
                <handlers>
                    <handler name="file"/>
                </handlers>
            </logger>
        </audit-log>
        <management-interfaces>
            <native-interface security-realm="ManagementRealm">
                <socket-binding native="management-native"/>
            </native-interface>
            <http-interface security-realm="ManagementRealm">
                <socket-binding http="management-http"/>
            </http-interface>
        </management-interfaces>
        <access-control provider="simple">
            <role-mapping>
                <role name="SuperUser">
                    <include>
                        <user name="$local"/>
                    </include>
                </role>
            </role-mapping>
        </access-control>
    </management>

    <profile>
        <subsystem xmlns="urn:jboss:domain:logging:1.3">
            <console-handler name="CONSOLE">
                <level name="INFO"/>
                <formatter>
                    <pattern-formatter pattern="%K{level}%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
                </formatter>
            </console-handler>
            <periodic-rotating-file-handler name="FILE" autoflush="true">
                <formatter>
                    <pattern-formatter pattern="%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
                </formatter>
                <file relative-to="jboss.server.log.dir" path="server.log"/>
                <suffix value=".yyyy-MM-dd"/>
                <append value="true"/>
            </periodic-rotating-file-handler>
            <logger category="com.arjuna">
                <level name="WARN"/>
            </logger>
            <logger category="org.apache.tomcat.util.modeler">
                <level name="WARN"/>
            </logger>
            <logger category="org.jboss.as.config">
                <level name="DEBUG"/>
            </logger>
            <logger category="sun.rmi">
                <level name="WARN"/>
            </logger>
            <logger category="jacorb">
                <level name="WARN"/>
            </logger>
            <logger category="jacorb.config">
                <level name="ERROR"/>
            </logger>
            <root-logger>
                <level name="INFO"/>
                <handlers>
                    <handler name="CONSOLE"/>
                    <handler name="FILE"/>
                </handlers>
            </root-logger>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:cmp:1.1"/>
        <subsystem xmlns="urn:jboss:domain:datasources:1.1">
            <datasources>
                <datasource jndi-name="java:jboss/datasources/ExampleDS" pool-name="ExampleDS" enabled="true" use-java-context="true">
                    <connection-url>jdbc:h2:mem:test;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE</connection-url>
                    <driver>h2</driver>
                    <security>
                        <user-name>sa</user-name>
                        <password>sa</password>
                    </security>
                </datasource>
                <drivers>
                    <driver name="h2" module="com.h2database.h2">
                        <xa-datasource-class>org.h2.jdbcx.JdbcDataSource</xa-datasource-class>
                    </driver>
                </drivers>
            </datasources>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:deployment-scanner:1.1">
            <deployment-scanner path="deployments" relative-to="jboss.server.base.dir" scan-interval="0"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:ee:1.1">
            <spec-descriptor-property-replacement>false</spec-descriptor-property-replacement>
            <jboss-descriptor-property-replacement>true</jboss-descriptor-property-replacement>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:ejb3:1.4">
            <session-bean>
                <stateless>
                    <bean-instance-pool-ref pool-name="slsb-strict-max-pool"/>
                </stateless>
                <stateful default-access-timeout="5000" cache-ref="simple" clustered-cache-ref="clustered"/>
                <singleton default-access-timeout="5000"/>
            </session-bean>
            <mdb>
                <resource-adapter-ref resource-adapter-name="${ejb.resource-adapter-name:hornetq-ra}"/>
                <bean-instance-pool-ref pool-name="mdb-strict-max-pool"/>
            </mdb>
            <pools>
                <bean-instance-pools>
                    <strict-max-pool name="slsb-strict-max-pool" max-pool-size="20" instance-acquisition-timeout="5" instance-acquisition-timeout-unit="MINUTES"/>
                    <strict-max-pool name="mdb-strict-max-pool" max-pool-size="20" instance-acquisition-timeout="5" instance-acquisition-timeout-unit="MINUTES"/>
                </bean-instance-pools>
            </pools>
            <caches>
                <cache name="simple" aliases="NoPassivationCache"/>
                <cache name="passivating" passivation-store-ref="file" aliases="SimpleStatefulCache"/>
                <cache name="clustered" passivation-store-ref="infinispan" aliases="StatefulTreeCache"/>
            </caches>
            <passivation-stores>
                <file-passivation-store name="file"/>
                <cluster-passivation-store name="infinispan" cache-container="ejb"/>
            </passivation-stores>
            <async thread-pool-name="default"/>
            <timer-service thread-pool-name="default">
                <data-store path="timer-service-data" relative-to="jboss.server.data.dir"/>
            </timer-service>
            <remote connector-ref="remoting-connector" thread-pool-name="default"/>
            <thread-pools>
                <thread-pool name="default">
                    <max-threads count="10"/>
                    <keepalive-time time="100" unit="milliseconds"/>
                </thread-pool>
            </thread-pools>
            <iiop enable-by-default="false" use-qualified-name="false"/>
            <default-security-domain value="other"/>
            <default-missing-method-permissions-deny-access value="true"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:infinispan:1.4">
            <cache-container name="singleton" aliases="cluster ha-partition" default-cache="default">
                <transport lock-timeout="60000"/>
                <replicated-cache name="default" mode="SYNC" batching="true">
                    <locking isolation="REPEATABLE_READ"/>
                </replicated-cache>
            </cache-container>
            <cache-container name="web" aliases="standard-session-cache" default-cache="repl" module="org.jboss.as.clustering.web.infinispan">
                <transport lock-timeout="60000"/>
                <replicated-cache name="repl" mode="ASYNC" batching="true">
                    <file-store/>
                </replicated-cache>
                <replicated-cache name="sso" mode="SYNC" batching="true"/>
                <distributed-cache name="dist" l1-lifespan="0" mode="ASYNC" batching="true">
                    <file-store/>
                </distributed-cache>
            </cache-container>
            <cache-container name="ejb" aliases="sfsb sfsb-cache" default-cache="repl" module="org.jboss.as.clustering.ejb3.infinispan">
                <transport lock-timeout="60000"/>
                <replicated-cache name="repl" mode="ASYNC" batching="true">
                    <eviction strategy="LRU" max-entries="10000"/>
                    <file-store/>
                </replicated-cache>
                <replicated-cache name="remote-connector-client-mappings" mode="SYNC" batching="true"/>
                <distributed-cache name="dist" l1-lifespan="0" mode="ASYNC" batching="true">
                    <eviction strategy="LRU" max-entries="10000"/>
                    <file-store/>
                </distributed-cache>
            </cache-container>
            <cache-container name="hibernate" default-cache="local-query" module="org.jboss.as.jpa.hibernate:4">
                <transport lock-timeout="60000"/>
                <local-cache name="local-query">
                    <transaction mode="NONE"/>
                    <eviction strategy="LRU" max-entries="10000"/>
                    <expiration max-idle="100000"/>
                </local-cache>
                <invalidation-cache name="entity" mode="SYNC">
                    <transaction mode="NON_XA"/>
                    <eviction strategy="LRU" max-entries="10000"/>
                    <expiration max-idle="100000"/>
                </invalidation-cache>
                <replicated-cache name="timestamps" mode="ASYNC">
                    <transaction mode="NONE"/>
                    <eviction strategy="NONE"/>
                </replicated-cache>
            </cache-container>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jacorb:1.3">
            <orb socket-binding="jacorb" ssl-socket-binding="jacorb-ssl">
                <initializers security="identity" transactions="spec"/>
            </orb>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jaxr:1.1">
            <connection-factory jndi-name="java:jboss/jaxr/ConnectionFactory"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jaxrs:1.0"/>
        <subsystem xmlns="urn:jboss:domain:jca:1.1">
            <archive-validation enabled="true" fail-on-error="true" fail-on-warn="false"/>
            <bean-validation enabled="true"/>
            <default-workmanager>
                <short-running-threads>
                    <core-threads count="50"/>
                    <queue-length count="50"/>
                    <max-threads count="50"/>
                    <keepalive-time time="10" unit="seconds"/>
                </short-running-threads>
                <long-running-threads>
                    <core-threads count="50"/>
                    <queue-length count="50"/>
                    <max-threads count="50"/>
                    <keepalive-time time="10" unit="seconds"/>
                </long-running-threads>
            </default-workmanager>
            <cached-connection-manager/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jdr:1.0"/>
        <subsystem xmlns="urn:jboss:domain:jgroups:1.1" default-stack="udp">
            <stack name="udp">
                <transport type="UDP" socket-binding="jgroups-udp"/>
                <protocol type="PING"/>
                <protocol type="MERGE3"/>
                <protocol type="FD_SOCK" socket-binding="jgroups-udp-fd"/>
                <protocol type="FD"/>
                <protocol type="VERIFY_SUSPECT"/>
                <protocol type="pbcast.NAKACK"/>
                <protocol type="UNICAST2"/>
                <protocol type="pbcast.STABLE"/>
                <protocol type="pbcast.GMS"/>
                <protocol type="UFC"/>
                <protocol type="MFC"/>
                <protocol type="FRAG2"/>
                <protocol type="RSVP"/>
            </stack>
            <stack name="tcp">
                <transport type="TCP" socket-binding="jgroups-tcp"/>
                <protocol type="MPING" socket-binding="jgroups-mping"/>
                <protocol type="MERGE2"/>
                <protocol type="FD_SOCK" socket-binding="jgroups-tcp-fd"/>
                <protocol type="FD"/>
                <protocol type="VERIFY_SUSPECT"/>
                <protocol type="pbcast.NAKACK"/>
                <protocol type="UNICAST2"/>
                <protocol type="pbcast.STABLE"/>
                <protocol type="pbcast.GMS"/>
                <protocol type="UFC"/>
                <protocol type="MFC"/>
                <protocol type="FRAG2"/>
                <protocol type="RSVP"/>
            </stack>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jmx:1.3">
            <expose-resolved-model/>
            <expose-expression-model/>
            <remoting-connector/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jpa:1.1">
            <jpa default-datasource="" default-extended-persistence-inheritance="DEEP"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jsf:1.0"/>
        <subsystem xmlns="urn:jboss:domain:jsr77:1.0"/>
        <subsystem xmlns="urn:jboss:domain:mail:1.1">
            <mail-session jndi-name="java:jboss/mail/Default">
                <smtp-server outbound-socket-binding-ref="mail-smtp"/>
            </mail-session>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:messaging:1.4">
            <hornetq-server>
                <persistence-enabled>true</persistence-enabled>
                <cluster-password>clusterPassword1!</cluster-password>
                <backup>false</backup>
                <allow-failback>true</allow-failback>
                <failover-on-shutdown>false</failover-on-shutdown>
                <shared-store>false</shared-store>
                <journal-type>NIO</journal-type>
                <journal-min-files>2</journal-min-files>
                <max-saved-replicated-journal-size>-1</max-saved-replicated-journal-size>
                <check-for-live-server>true</check-for-live-server>
                <backup-group-name>group-1</backup-group-name>

                <connectors>
                    <netty-connector name="netty" socket-binding="messaging"/>
                    <netty-connector name="netty-throughput" socket-binding="messaging-throughput">
                        <param key="batch-delay" value="50"/>
                    </netty-connector>
                    <in-vm-connector name="in-vm" server-id="1"/>
                </connectors>

                <acceptors>
                    <netty-acceptor name="netty" socket-binding="messaging"/>
                    <netty-acceptor name="netty-throughput" socket-binding="messaging-throughput">
                        <param key="batch-delay" value="50"/>
                        <param key="direct-deliver" value="false"/>
                    </netty-acceptor>
                    <in-vm-acceptor name="in-vm" server-id="1"/>
                </acceptors>

                <broadcast-groups>
                    <broadcast-group name="bg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <broadcast-period>5000</broadcast-period>
                        <connector-ref>
                            netty
                        </connector-ref>
                    </broadcast-group>
                </broadcast-groups>

                <discovery-groups>
                    <discovery-group name="dg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <refresh-timeout>10000</refresh-timeout>
                    </discovery-group>
                </discovery-groups>

                <cluster-connections>
                    <cluster-connection name="my-cluster">
                        <address>jms</address>
                        <connector-ref>netty</connector-ref>
                        <discovery-group-ref discovery-group-name="dg-group1"/>
                    </cluster-connection>
                </cluster-connections>

                <security-settings>
                    <security-setting match="#">
                        <permission type="send" roles="guest"/>
                        <permission type="consume" roles="guest"/>
                        <permission type="createNonDurableQueue" roles="guest"/>
                        <permission type="deleteNonDurableQueue" roles="guest"/>
                    </security-setting>
                </security-settings>

                <address-settings>
                    <address-setting match="#">
                        <dead-letter-address>jms.queue.DLQ</dead-letter-address>
                        <expiry-address>jms.queue.ExpiryQueue</expiry-address>
                        <redelivery-delay>0</redelivery-delay>
                        <max-size-bytes>10485760</max-size-bytes>
                        <address-full-policy>BLOCK</address-full-policy>
                        <message-counter-history-day-limit>10</message-counter-history-day-limit>
                        <redistribution-delay>1000</redistribution-delay>
                    </address-setting>
                </address-settings>

                <jms-connection-factories>
                    <connection-factory name="InVmConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/ConnectionFactory"/>
                        </entries>
                    </connection-factory>
                    <connection-factory name="RemoteConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="netty"/>
                        </connectors>
                        <entries>
                            <entry name="java:jboss/exported/jms/RemoteConnectionFactory"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1.0</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </connection-factory>
                    <pooled-connection-factory name="hornetq-ra">
                        <transaction mode="xa"/>
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/JmsXA"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </pooled-connection-factory>
                </jms-connection-factories>
            </hornetq-server>
            <hornetq-server name="backup-server">
                <persistence-enabled>true</persistence-enabled>
                <cluster-password>clusterPassword1!</cluster-password>
                <backup>true</backup>
                <allow-failback>true</allow-failback>
                <failover-on-shutdown>false</failover-on-shutdown>
                <shared-store>false</shared-store>
                <journal-type>NIO</journal-type>
                <journal-min-files>2</journal-min-files>
                <max-saved-replicated-journal-size>-1</max-saved-replicated-journal-size>
                <check-for-live-server>true</check-for-live-server>
                <backup-group-name>group-2</backup-group-name>
                <paging-directory path="messagingpagingbackupa"/>
                <bindings-directory path="messagingbindingsbackupa"/>
                <journal-directory path="messagingjournalbackupa"/>
                <large-messages-directory path="messaginglargemessagesbackupa"/>

                <connectors>
                    <netty-connector name="netty" socket-binding="messaging-backup"/>
                    <in-vm-connector name="in-vm" server-id="2"/>
                </connectors>

                <acceptors>
                    <netty-acceptor name="netty" socket-binding="messaging-backup"/>
                    <in-vm-acceptor name="in-vm" server-id="2"/>
                </acceptors>

                <broadcast-groups>
                    <broadcast-group name="bg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <broadcast-period>5000</broadcast-period>
                        <connector-ref>
                            netty
                        </connector-ref>
                    </broadcast-group>
                </broadcast-groups>

                <discovery-groups>
                    <discovery-group name="dg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <refresh-timeout>10000</refresh-timeout>
                    </discovery-group>
                </discovery-groups>

                <cluster-connections>
                    <cluster-connection name="my-cluster">
                        <address>jms</address>
                        <connector-ref>netty</connector-ref>
                        <discovery-group-ref discovery-group-name="dg-group1"/>
                    </cluster-connection>
                </cluster-connections>

                <security-settings>
                    <security-setting match="#">
                        <permission type="send" roles="guest"/>
                        <permission type="consume" roles="guest"/>
                        <permission type="createNonDurableQueue" roles="guest"/>
                        <permission type="deleteNonDurableQueue" roles="guest"/>
                    </security-setting>
                </security-settings>

                <address-settings>
                    <address-setting match="#">
                        <dead-letter-address>jms.queue.DLQ</dead-letter-address>
                        <expiry-address>jms.queue.ExpiryQueue</expiry-address>
                        <redelivery-delay>0</redelivery-delay>
                        <max-size-bytes>10485760</max-size-bytes>
                        <address-full-policy>BLOCK</address-full-policy>
                        <message-counter-history-day-limit>10</message-counter-history-day-limit>
                        <redistribution-delay>1000</redistribution-delay>
                    </address-setting>
                </address-settings>

                <jms-connection-factories>
                    <connection-factory name="InVmConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/ConnectionFactory"/>
                        </entries>
                    </connection-factory>
                    <connection-factory name="RemoteConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="netty"/>
                        </connectors>
                        <entries>
                            <entry name="java:jboss/exported/jms/RemoteConnectionFactory"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1.0</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </connection-factory>
                    <pooled-connection-factory name="hornetq-ra">
                        <transaction mode="xa"/>
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/JmsXA"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </pooled-connection-factory>
                </jms-connection-factories>
            </hornetq-server>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:modcluster:1.1">
            <mod-cluster-config advertise-socket="modcluster" connector="ajp">
                <dynamic-load-provider>
                    <load-metric type="busyness"/>
                </dynamic-load-provider>
            </mod-cluster-config>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:naming:1.4">
            <remote-naming/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:pojo:1.0"/>
        <subsystem xmlns="urn:jboss:domain:remoting:1.1">
            <connector name="remoting-connector" socket-binding="remoting" security-realm="ApplicationRealm"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:resource-adapters:1.1"/>
        <subsystem xmlns="urn:jboss:domain:sar:1.0"/>
        <subsystem xmlns="urn:jboss:domain:security:1.2">
            <security-domains>
                <security-domain name="other" cache-type="default">
                    <authentication>
                        <login-module code="Remoting" flag="optional">
                            <module-option name="password-stacking" value="useFirstPass"/>
                        </login-module>
                        <login-module code="RealmDirect" flag="required">
                            <module-option name="password-stacking" value="useFirstPass"/>
                        </login-module>
                    </authentication>
                </security-domain>
                <security-domain name="jboss-web-policy" cache-type="default">
                    <authorization>
                        <policy-module code="Delegating" flag="required"/>
                    </authorization>
                </security-domain>
                <security-domain name="jboss-ejb-policy" cache-type="default">
                    <authorization>
                        <policy-module code="Delegating" flag="required"/>
                    </authorization>
                </security-domain>
            </security-domains>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:threads:1.1"/>
        <subsystem xmlns="urn:jboss:domain:transactions:1.4">
            <core-environment>
                <process-id>
                    <uuid/>
                </process-id>
            </core-environment>
            <recovery-environment socket-binding="txn-recovery-environment" status-socket-binding="txn-status-manager"/>
            <coordinator-environment default-timeout="300"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:web:1.5" default-virtual-server="default-host" native="false">
            <connector name="http" protocol="HTTP/1.1" scheme="http" socket-binding="http"/>
            <connector name="ajp" protocol="AJP/1.3" scheme="http" socket-binding="ajp"/>
            <virtual-server name="default-host" enable-welcome-root="true">
                <alias name="localhost"/>
                <alias name="example.com"/>
            </virtual-server>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:webservices:1.2">
            <modify-wsdl-address>true</modify-wsdl-address>
            <wsdl-host>${jboss.bind.address:127.0.0.1}</wsdl-host>
            <endpoint-config name="Standard-Endpoint-Config"/>
            <endpoint-config name="Recording-Endpoint-Config">
                <pre-handler-chain name="recording-handlers" protocol-bindings="##SOAP11_HTTP ##SOAP11_HTTP_MTOM ##SOAP12_HTTP ##SOAP12_HTTP_MTOM">
                    <handler name="RecordingHandler" class="org.jboss.ws.common.invocation.RecordingServerHandler"/>
                </pre-handler-chain>
            </endpoint-config>
            <client-config name="Standard-Client-Config"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:weld:1.0"/>
    </profile>

    <interfaces>
        <interface name="management">
            <inet-address value="${jboss.bind.address.management:127.0.0.1}"/>
        </interface>
        <interface name="public">
            <inet-address value="${jboss.bind.address:127.0.0.1}"/>
        </interface>
        <interface name="unsecure">
            <inet-address value="${jboss.bind.address.unsecure:127.0.0.1}"/>
        </interface>
    </interfaces>

    <socket-binding-group name="standard-sockets" default-interface="public" port-offset="${jboss.socket.binding.port-offset:0}">
        <socket-binding name="management-native" interface="management" port="${jboss.management.native.port:9999}"/>
        <socket-binding name="management-http" interface="management" port="${jboss.management.http.port:9990}"/>
        <socket-binding name="management-https" interface="management" port="${jboss.management.https.port:9443}"/>
        <socket-binding name="ajp" port="8009"/>
        <socket-binding name="http" port="8080"/>
        <socket-binding name="https" port="8443"/>
        <socket-binding name="jacorb" interface="unsecure" port="3528"/>
        <socket-binding name="jacorb-ssl" interface="unsecure" port="3529"/>
        <socket-binding name="jgroups-mping" port="0" multicast-address="${jboss.default.multicast.address:230.0.0.4}" multicast-port="45700"/>
        <socket-binding name="jgroups-tcp" port="7600"/>
        <socket-binding name="jgroups-tcp-fd" port="57600"/>
        <socket-binding name="jgroups-udp" port="55200" multicast-address="${jboss.default.multicast.address:230.0.0.4}" multicast-port="45688"/>
        <socket-binding name="jgroups-udp-fd" port="54200"/>
        <socket-binding name="messaging" port="5445"/>
        <socket-binding name="messaging-group" port="0" multicast-address="${jboss.messaging.group.address:231.7.7.7}" multicast-port="${jboss.messaging.group.port:9876}"/>
        <socket-binding name="messaging-throughput" port="5455"/>
        <socket-binding name="messaging-backup" port="5446"/>
        <socket-binding name="modcluster" port="0" multicast-address="224.0.1.105" multicast-port="23364"/>
        <socket-binding name="remoting" port="4447"/>
        <socket-binding name="txn-recovery-environment" port="4712"/>
        <socket-binding name="txn-status-manager" port="4713"/>
        <outbound-socket-binding name="mail-smtp">
            <remote-destination host="localhost" port="25"/>
        </outbound-socket-binding>
    </socket-binding-group>
</server>

2. 修改server2的standalone-full-ha.xml文件内容如下:

主要是替换了hornetq-server部分的内容:

<?xml version='1.0' encoding='UTF-8'?>
<server xmlns="urn:jboss:domain:1.5">

    <extensions>
        <extension module="org.jboss.as.clustering.infinispan"/>
        <extension module="org.jboss.as.clustering.jgroups"/>
        <extension module="org.jboss.as.cmp"/>
        <extension module="org.jboss.as.connector"/>
        <extension module="org.jboss.as.deployment-scanner"/>
        <extension module="org.jboss.as.ee"/>
        <extension module="org.jboss.as.ejb3"/>
        <extension module="org.jboss.as.jacorb"/>
        <extension module="org.jboss.as.jaxr"/>
        <extension module="org.jboss.as.jaxrs"/>
        <extension module="org.jboss.as.jdr"/>
        <extension module="org.jboss.as.jmx"/>
        <extension module="org.jboss.as.jpa"/>
        <extension module="org.jboss.as.jsf"/>
        <extension module="org.jboss.as.jsr77"/>
        <extension module="org.jboss.as.logging"/>
        <extension module="org.jboss.as.mail"/>
        <extension module="org.jboss.as.messaging"/>
        <extension module="org.jboss.as.modcluster"/>
        <extension module="org.jboss.as.naming"/>
        <extension module="org.jboss.as.pojo"/>
        <extension module="org.jboss.as.remoting"/>
        <extension module="org.jboss.as.sar"/>
        <extension module="org.jboss.as.security"/>
        <extension module="org.jboss.as.threads"/>
        <extension module="org.jboss.as.transactions"/>
        <extension module="org.jboss.as.web"/>
        <extension module="org.jboss.as.webservices"/>
        <extension module="org.jboss.as.weld"/>
    </extensions>


    <management>
        <security-realms>
            <security-realm name="ManagementRealm">
                <authentication>
                    <local default-user="$local"/>
                    <properties path="mgmt-users.properties" relative-to="jboss.server.config.dir"/>
                </authentication>
                <authorization map-groups-to-roles="false">
                    <properties path="mgmt-groups.properties" relative-to="jboss.server.config.dir"/>
                </authorization>
            </security-realm>
            <security-realm name="ApplicationRealm">
                <authentication>
                    <local default-user="$local" allowed-users="*"/>
                    <properties path="application-users.properties" relative-to="jboss.server.config.dir"/>
                </authentication>
                <authorization>
                    <properties path="application-roles.properties" relative-to="jboss.server.config.dir"/>
                </authorization>
            </security-realm>
        </security-realms>
        <audit-log>
            <formatters>
                <json-formatter name="json-formatter"/>
            </formatters>
            <handlers>
                <file-handler name="file" formatter="json-formatter" path="audit-log.log" relative-to="jboss.server.data.dir"/>
            </handlers>
            <logger log-boot="true" log-read-only="false" enabled="false">
                <handlers>
                    <handler name="file"/>
                </handlers>
            </logger>
        </audit-log>
        <management-interfaces>
            <native-interface security-realm="ManagementRealm">
                <socket-binding native="management-native"/>
            </native-interface>
            <http-interface security-realm="ManagementRealm">
                <socket-binding http="management-http"/>
            </http-interface>
        </management-interfaces>
        <access-control provider="simple">
            <role-mapping>
                <role name="SuperUser">
                    <include>
                        <user name="$local"/>
                    </include>
                </role>
            </role-mapping>
        </access-control>
    </management>

    <profile>
        <subsystem xmlns="urn:jboss:domain:logging:1.3">
            <console-handler name="CONSOLE">
                <level name="INFO"/>
                <formatter>
                    <pattern-formatter pattern="%K{level}%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
                </formatter>
            </console-handler>
            <periodic-rotating-file-handler name="FILE" autoflush="true">
                <formatter>
                    <pattern-formatter pattern="%d{HH:mm:ss,SSS} %-5p [%c] (%t) %s%E%n"/>
                </formatter>
                <file relative-to="jboss.server.log.dir" path="server.log"/>
                <suffix value=".yyyy-MM-dd"/>
                <append value="true"/>
            </periodic-rotating-file-handler>
            <logger category="com.arjuna">
                <level name="WARN"/>
            </logger>
            <logger category="org.apache.tomcat.util.modeler">
                <level name="WARN"/>
            </logger>
            <logger category="org.jboss.as.config">
                <level name="DEBUG"/>
            </logger>
            <logger category="sun.rmi">
                <level name="WARN"/>
            </logger>
            <logger category="jacorb">
                <level name="WARN"/>
            </logger>
            <logger category="jacorb.config">
                <level name="ERROR"/>
            </logger>
            <root-logger>
                <level name="INFO"/>
                <handlers>
                    <handler name="CONSOLE"/>
                    <handler name="FILE"/>
                </handlers>
            </root-logger>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:cmp:1.1"/>
        <subsystem xmlns="urn:jboss:domain:datasources:1.1">
            <datasources>
                <datasource jndi-name="java:jboss/datasources/ExampleDS" pool-name="ExampleDS" enabled="true" use-java-context="true">
                    <connection-url>jdbc:h2:mem:test;DB_CLOSE_DELAY=-1;DB_CLOSE_ON_EXIT=FALSE</connection-url>
                    <driver>h2</driver>
                    <security>
                        <user-name>sa</user-name>
                        <password>sa</password>
                    </security>
                </datasource>
                <drivers>
                    <driver name="h2" module="com.h2database.h2">
                        <xa-datasource-class>org.h2.jdbcx.JdbcDataSource</xa-datasource-class>
                    </driver>
                </drivers>
            </datasources>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:deployment-scanner:1.1">
            <deployment-scanner path="deployments" relative-to="jboss.server.base.dir" scan-interval="0"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:ee:1.1">
            <spec-descriptor-property-replacement>false</spec-descriptor-property-replacement>
            <jboss-descriptor-property-replacement>true</jboss-descriptor-property-replacement>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:ejb3:1.4">
            <session-bean>
                <stateless>
                    <bean-instance-pool-ref pool-name="slsb-strict-max-pool"/>
                </stateless>
                <stateful default-access-timeout="5000" cache-ref="simple" clustered-cache-ref="clustered"/>
                <singleton default-access-timeout="5000"/>
            </session-bean>
            <mdb>
                <resource-adapter-ref resource-adapter-name="${ejb.resource-adapter-name:hornetq-ra}"/>
                <bean-instance-pool-ref pool-name="mdb-strict-max-pool"/>
            </mdb>
            <pools>
                <bean-instance-pools>
                    <strict-max-pool name="slsb-strict-max-pool" max-pool-size="20" instance-acquisition-timeout="5" instance-acquisition-timeout-unit="MINUTES"/>
                    <strict-max-pool name="mdb-strict-max-pool" max-pool-size="20" instance-acquisition-timeout="5" instance-acquisition-timeout-unit="MINUTES"/>
                </bean-instance-pools>
            </pools>
            <caches>
                <cache name="simple" aliases="NoPassivationCache"/>
                <cache name="passivating" passivation-store-ref="file" aliases="SimpleStatefulCache"/>
                <cache name="clustered" passivation-store-ref="infinispan" aliases="StatefulTreeCache"/>
            </caches>
            <passivation-stores>
                <file-passivation-store name="file"/>
                <cluster-passivation-store name="infinispan" cache-container="ejb"/>
            </passivation-stores>
            <async thread-pool-name="default"/>
            <timer-service thread-pool-name="default">
                <data-store path="timer-service-data" relative-to="jboss.server.data.dir"/>
            </timer-service>
            <remote connector-ref="remoting-connector" thread-pool-name="default"/>
            <thread-pools>
                <thread-pool name="default">
                    <max-threads count="10"/>
                    <keepalive-time time="100" unit="milliseconds"/>
                </thread-pool>
            </thread-pools>
            <iiop enable-by-default="false" use-qualified-name="false"/>
            <default-security-domain value="other"/>
            <default-missing-method-permissions-deny-access value="true"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:infinispan:1.4">
            <cache-container name="singleton" aliases="cluster ha-partition" default-cache="default">
                <transport lock-timeout="60000"/>
                <replicated-cache name="default" mode="SYNC" batching="true">
                    <locking isolation="REPEATABLE_READ"/>
                </replicated-cache>
            </cache-container>
            <cache-container name="web" aliases="standard-session-cache" default-cache="repl" module="org.jboss.as.clustering.web.infinispan">
                <transport lock-timeout="60000"/>
                <replicated-cache name="repl" mode="ASYNC" batching="true">
                    <file-store/>
                </replicated-cache>
                <replicated-cache name="sso" mode="SYNC" batching="true"/>
                <distributed-cache name="dist" l1-lifespan="0" mode="ASYNC" batching="true">
                    <file-store/>
                </distributed-cache>
            </cache-container>
            <cache-container name="ejb" aliases="sfsb sfsb-cache" default-cache="repl" module="org.jboss.as.clustering.ejb3.infinispan">
                <transport lock-timeout="60000"/>
                <replicated-cache name="repl" mode="ASYNC" batching="true">
                    <eviction strategy="LRU" max-entries="10000"/>
                    <file-store/>
                </replicated-cache>
                <replicated-cache name="remote-connector-client-mappings" mode="SYNC" batching="true"/>
                <distributed-cache name="dist" l1-lifespan="0" mode="ASYNC" batching="true">
                    <eviction strategy="LRU" max-entries="10000"/>
                    <file-store/>
                </distributed-cache>
            </cache-container>
            <cache-container name="hibernate" default-cache="local-query" module="org.jboss.as.jpa.hibernate:4">
                <transport lock-timeout="60000"/>
                <local-cache name="local-query">
                    <transaction mode="NONE"/>
                    <eviction strategy="LRU" max-entries="10000"/>
                    <expiration max-idle="100000"/>
                </local-cache>
                <invalidation-cache name="entity" mode="SYNC">
                    <transaction mode="NON_XA"/>
                    <eviction strategy="LRU" max-entries="10000"/>
                    <expiration max-idle="100000"/>
                </invalidation-cache>
                <replicated-cache name="timestamps" mode="ASYNC">
                    <transaction mode="NONE"/>
                    <eviction strategy="NONE"/>
                </replicated-cache>
            </cache-container>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jacorb:1.3">
            <orb socket-binding="jacorb" ssl-socket-binding="jacorb-ssl">
                <initializers security="identity" transactions="spec"/>
            </orb>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jaxr:1.1">
            <connection-factory jndi-name="java:jboss/jaxr/ConnectionFactory"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jaxrs:1.0"/>
        <subsystem xmlns="urn:jboss:domain:jca:1.1">
            <archive-validation enabled="true" fail-on-error="true" fail-on-warn="false"/>
            <bean-validation enabled="true"/>
            <default-workmanager>
                <short-running-threads>
                    <core-threads count="50"/>
                    <queue-length count="50"/>
                    <max-threads count="50"/>
                    <keepalive-time time="10" unit="seconds"/>
                </short-running-threads>
                <long-running-threads>
                    <core-threads count="50"/>
                    <queue-length count="50"/>
                    <max-threads count="50"/>
                    <keepalive-time time="10" unit="seconds"/>
                </long-running-threads>
            </default-workmanager>
            <cached-connection-manager/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jdr:1.0"/>
        <subsystem xmlns="urn:jboss:domain:jgroups:1.1" default-stack="udp">
            <stack name="udp">
                <transport type="UDP" socket-binding="jgroups-udp"/>
                <protocol type="PING"/>
                <protocol type="MERGE3"/>
                <protocol type="FD_SOCK" socket-binding="jgroups-udp-fd"/>
                <protocol type="FD"/>
                <protocol type="VERIFY_SUSPECT"/>
                <protocol type="pbcast.NAKACK"/>
                <protocol type="UNICAST2"/>
                <protocol type="pbcast.STABLE"/>
                <protocol type="pbcast.GMS"/>
                <protocol type="UFC"/>
                <protocol type="MFC"/>
                <protocol type="FRAG2"/>
                <protocol type="RSVP"/>
            </stack>
            <stack name="tcp">
                <transport type="TCP" socket-binding="jgroups-tcp"/>
                <protocol type="MPING" socket-binding="jgroups-mping"/>
                <protocol type="MERGE2"/>
                <protocol type="FD_SOCK" socket-binding="jgroups-tcp-fd"/>
                <protocol type="FD"/>
                <protocol type="VERIFY_SUSPECT"/>
                <protocol type="pbcast.NAKACK"/>
                <protocol type="UNICAST2"/>
                <protocol type="pbcast.STABLE"/>
                <protocol type="pbcast.GMS"/>
                <protocol type="UFC"/>
                <protocol type="MFC"/>
                <protocol type="FRAG2"/>
                <protocol type="RSVP"/>
            </stack>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jmx:1.3">
            <expose-resolved-model/>
            <expose-expression-model/>
            <remoting-connector/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jpa:1.1">
            <jpa default-datasource="" default-extended-persistence-inheritance="DEEP"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:jsf:1.0"/>
        <subsystem xmlns="urn:jboss:domain:jsr77:1.0"/>
        <subsystem xmlns="urn:jboss:domain:mail:1.1">
            <mail-session jndi-name="java:jboss/mail/Default">
                <smtp-server outbound-socket-binding-ref="mail-smtp"/>
            </mail-session>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:messaging:1.4">
            <hornetq-server>
                <persistence-enabled>true</persistence-enabled>
                <cluster-password>clusterPassword1!</cluster-password>
                <backup>false</backup>
                <allow-failback>true</allow-failback>
                <failover-on-shutdown>false</failover-on-shutdown>
                <shared-store>false</shared-store>
                <journal-type>NIO</journal-type>
                <journal-min-files>2</journal-min-files>
                <max-saved-replicated-journal-size>-1</max-saved-replicated-journal-size>
                <check-for-live-server>true</check-for-live-server>
                <backup-group-name>group-2</backup-group-name>

                <connectors>
                    <netty-connector name="netty" socket-binding="messaging"/>
                    <netty-connector name="netty-throughput" socket-binding="messaging-throughput">
                        <param key="batch-delay" value="50"/>
                    </netty-connector>
                    <in-vm-connector name="in-vm" server-id="1"/>
                </connectors>

                <acceptors>
                    <netty-acceptor name="netty" socket-binding="messaging"/>
                    <netty-acceptor name="netty-throughput" socket-binding="messaging-throughput">
                        <param key="batch-delay" value="50"/>
                        <param key="direct-deliver" value="false"/>
                    </netty-acceptor>
                    <in-vm-acceptor name="in-vm" server-id="1"/>
                </acceptors>

                <broadcast-groups>
                    <broadcast-group name="bg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <broadcast-period>5000</broadcast-period>
                        <connector-ref>
                            netty
                        </connector-ref>
                    </broadcast-group>
                </broadcast-groups>

                <discovery-groups>
                    <discovery-group name="dg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <refresh-timeout>10000</refresh-timeout>
                    </discovery-group>
                </discovery-groups>

                <cluster-connections>
                    <cluster-connection name="my-cluster">
                        <address>jms</address>
                        <connector-ref>netty</connector-ref>
                        <discovery-group-ref discovery-group-name="dg-group1"/>
                    </cluster-connection>
                </cluster-connections>

                <security-settings>
                    <security-setting match="#">
                        <permission type="send" roles="guest"/>
                        <permission type="consume" roles="guest"/>
                        <permission type="createNonDurableQueue" roles="guest"/>
                        <permission type="deleteNonDurableQueue" roles="guest"/>
                    </security-setting>
                </security-settings>

                <address-settings>
                    <address-setting match="#">
                        <dead-letter-address>jms.queue.DLQ</dead-letter-address>
                        <expiry-address>jms.queue.ExpiryQueue</expiry-address>
                        <redelivery-delay>0</redelivery-delay>
                        <max-size-bytes>10485760</max-size-bytes>
                        <address-full-policy>BLOCK</address-full-policy>
                        <message-counter-history-day-limit>10</message-counter-history-day-limit>
                        <redistribution-delay>1000</redistribution-delay>
                    </address-setting>
                </address-settings>

                <jms-connection-factories>
                    <connection-factory name="InVmConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/ConnectionFactory"/>
                        </entries>
                    </connection-factory>
                    <connection-factory name="RemoteConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="netty"/>
                        </connectors>
                        <entries>
                            <entry name="java:jboss/exported/jms/RemoteConnectionFactory"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1.0</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </connection-factory>
                    <pooled-connection-factory name="hornetq-ra">
                        <transaction mode="xa"/>
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/JmsXA"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </pooled-connection-factory>
                </jms-connection-factories>
</hornetq-server>
            <hornetq-server name="backup-server">
                <persistence-enabled>true</persistence-enabled>
                <cluster-password>clusterPassword1!</cluster-password>
                <backup>true</backup>
                <allow-failback>true</allow-failback>
                <failover-on-shutdown>false</failover-on-shutdown>
                <shared-store>false</shared-store>
                <journal-type>NIO</journal-type>
                <journal-min-files>2</journal-min-files>
                <max-saved-replicated-journal-size>-1</max-saved-replicated-journal-size>
                <check-for-live-server>true</check-for-live-server>
                <backup-group-name>group-1</backup-group-name>
                <paging-directory path="messagingpagingbackupa"/>
                <bindings-directory path="messagingbindingsbackupa"/>
                <journal-directory path="messagingjournalbackupa"/>
                <large-messages-directory path="messaginglargemessagesbackupa"/>

                <connectors>
                    <netty-connector name="netty" socket-binding="messaging-backup"/>
                    <in-vm-connector name="in-vm" server-id="2"/>
                </connectors>

                <acceptors>
                    <netty-acceptor name="netty" socket-binding="messaging-backup"/>
                    <in-vm-acceptor name="in-vm" server-id="2"/>
                </acceptors>

                <broadcast-groups>
                    <broadcast-group name="bg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <broadcast-period>5000</broadcast-period>
                        <connector-ref>
                            netty
                        </connector-ref>
                    </broadcast-group>
                </broadcast-groups>

                <discovery-groups>
                    <discovery-group name="dg-group1">
                        <socket-binding>messaging-group</socket-binding>
                        <refresh-timeout>10000</refresh-timeout>
                    </discovery-group>
                </discovery-groups>

                <cluster-connections>
                    <cluster-connection name="my-cluster">
                        <address>jms</address>
                        <connector-ref>netty</connector-ref>
                        <discovery-group-ref discovery-group-name="dg-group1"/>
                    </cluster-connection>
                </cluster-connections>

                <security-settings>
                    <security-setting match="#">
                        <permission type="send" roles="guest"/>
                        <permission type="consume" roles="guest"/>
                        <permission type="createNonDurableQueue" roles="guest"/>
                        <permission type="deleteNonDurableQueue" roles="guest"/>
                    </security-setting>
                </security-settings>

                <address-settings>
                    <address-setting match="#">
                        <dead-letter-address>jms.queue.DLQ</dead-letter-address>
                        <expiry-address>jms.queue.ExpiryQueue</expiry-address>
                        <redelivery-delay>0</redelivery-delay>
                        <max-size-bytes>10485760</max-size-bytes>
                        <address-full-policy>BLOCK</address-full-policy>
                        <message-counter-history-day-limit>10</message-counter-history-day-limit>
                        <redistribution-delay>1000</redistribution-delay>
                    </address-setting>
                </address-settings>

                <jms-connection-factories>
                    <connection-factory name="InVmConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/ConnectionFactory"/>
                        </entries>
                    </connection-factory>
                    <connection-factory name="RemoteConnectionFactory">
                        <connectors>
                            <connector-ref connector-name="netty"/>
                        </connectors>
                        <entries>
                            <entry name="java:jboss/exported/jms/RemoteConnectionFactory"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1.0</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </connection-factory>
                    <pooled-connection-factory name="hornetq-ra">
                        <transaction mode="xa"/>
                        <connectors>
                            <connector-ref connector-name="in-vm"/>
                        </connectors>
                        <entries>
                            <entry name="java:/JmsXA"/>
                        </entries>
                        <ha>true</ha>
                        <block-on-acknowledge>true</block-on-acknowledge>
                        <retry-interval>1000</retry-interval>
                        <retry-interval-multiplier>1</retry-interval-multiplier>
                        <reconnect-attempts>-1</reconnect-attempts>
                    </pooled-connection-factory>
                </jms-connection-factories>
</hornetq-server>
</subsystem>
        <subsystem xmlns="urn:jboss:domain:modcluster:1.1">
            <mod-cluster-config advertise-socket="modcluster" connector="ajp">
                <dynamic-load-provider>
                    <load-metric type="busyness"/>
                </dynamic-load-provider>
            </mod-cluster-config>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:naming:1.4">
            <remote-naming/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:pojo:1.0"/>
        <subsystem xmlns="urn:jboss:domain:remoting:1.1">
            <connector name="remoting-connector" socket-binding="remoting" security-realm="ApplicationRealm"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:resource-adapters:1.1"/>
        <subsystem xmlns="urn:jboss:domain:sar:1.0"/>
        <subsystem xmlns="urn:jboss:domain:security:1.2">
            <security-domains>
                <security-domain name="other" cache-type="default">
                    <authentication>
                        <login-module code="Remoting" flag="optional">
                            <module-option name="password-stacking" value="useFirstPass"/>
                        </login-module>
                        <login-module code="RealmDirect" flag="required">
                            <module-option name="password-stacking" value="useFirstPass"/>
                        </login-module>
                    </authentication>
                </security-domain>
                <security-domain name="jboss-web-policy" cache-type="default">
                    <authorization>
                        <policy-module code="Delegating" flag="required"/>
                    </authorization>
                </security-domain>
                <security-domain name="jboss-ejb-policy" cache-type="default">
                    <authorization>
                        <policy-module code="Delegating" flag="required"/>
                    </authorization>
                </security-domain>
            </security-domains>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:threads:1.1"/>
        <subsystem xmlns="urn:jboss:domain:transactions:1.4">
            <core-environment>
                <process-id>
                    <uuid/>
                </process-id>
            </core-environment>
            <recovery-environment socket-binding="txn-recovery-environment" status-socket-binding="txn-status-manager"/>
            <coordinator-environment default-timeout="300"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:web:1.5" default-virtual-server="default-host" native="false">
            <connector name="http" protocol="HTTP/1.1" scheme="http" socket-binding="http"/>
            <connector name="ajp" protocol="AJP/1.3" scheme="http" socket-binding="ajp"/>
            <virtual-server name="default-host" enable-welcome-root="true">
                <alias name="localhost"/>
                <alias name="example.com"/>
            </virtual-server>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:webservices:1.2">
            <modify-wsdl-address>true</modify-wsdl-address>
            <wsdl-host>${jboss.bind.address:127.0.0.1}</wsdl-host>
            <endpoint-config name="Standard-Endpoint-Config"/>
            <endpoint-config name="Recording-Endpoint-Config">
                <pre-handler-chain name="recording-handlers" protocol-bindings="##SOAP11_HTTP ##SOAP11_HTTP_MTOM ##SOAP12_HTTP ##SOAP12_HTTP_MTOM">
                    <handler name="RecordingHandler" class="org.jboss.ws.common.invocation.RecordingServerHandler"/>
                </pre-handler-chain>
            </endpoint-config>
            <client-config name="Standard-Client-Config"/>
        </subsystem>
        <subsystem xmlns="urn:jboss:domain:weld:1.0"/>
    </profile>

    <interfaces>
        <interface name="management">
            <inet-address value="${jboss.bind.address.management:127.0.0.1}"/>
        </interface>
        <interface name="public">
            <inet-address value="${jboss.bind.address:127.0.0.1}"/>
        </interface>
        <interface name="unsecure">
            <inet-address value="${jboss.bind.address.unsecure:127.0.0.1}"/>
        </interface>
    </interfaces>

    <socket-binding-group name="standard-sockets" default-interface="public" port-offset="${jboss.socket.binding.port-offset:0}">
        <socket-binding name="management-native" interface="management" port="${jboss.management.native.port:9999}"/>
        <socket-binding name="management-http" interface="management" port="${jboss.management.http.port:9990}"/>
        <socket-binding name="management-https" interface="management" port="${jboss.management.https.port:9443}"/>
        <socket-binding name="ajp" port="8009"/>
        <socket-binding name="http" port="8080"/>
        <socket-binding name="https" port="8443"/>
        <socket-binding name="jacorb" interface="unsecure" port="3528"/>
        <socket-binding name="jacorb-ssl" interface="unsecure" port="3529"/>
        <socket-binding name="jgroups-mping" port="0" multicast-address="${jboss.default.multicast.address:230.0.0.4}" multicast-port="45700"/>
        <socket-binding name="jgroups-tcp" port="7600"/>
        <socket-binding name="jgroups-tcp-fd" port="57600"/>
        <socket-binding name="jgroups-udp" port="55200" multicast-address="${jboss.default.multicast.address:230.0.0.4}" multicast-port="45688"/>
        <socket-binding name="jgroups-udp-fd" port="54200"/>
        <socket-binding name="messaging" port="5445"/>
        <socket-binding name="messaging-group" port="0" multicast-address="${jboss.messaging.group.address:231.7.7.7}" multicast-port="${jboss.messaging.group.port:9876}"/>
        <socket-binding name="messaging-throughput" port="5455"/>
        <socket-binding name="messaging-backup" port="5446"/>
        <socket-binding name="modcluster" port="0" multicast-address="224.0.1.105" multicast-port="23364"/>
        <socket-binding name="remoting" port="4447"/>
        <socket-binding name="txn-recovery-environment" port="4712"/>
        <socket-binding name="txn-status-manager" port="4713"/>
        <outbound-socket-binding name="mail-smtp">
            <remote-destination host="localhost" port="25"/>
        </outbound-socket-binding>
    </socket-binding-group>

</server>

4. 启动server1

 ./standalone.sh -c standalone-full-ha.xml -b 10.0.2.15 -bmanagement=10.0.2.15 -u 239.255.100.100 -Djboss.node.name=node1 -Djboss.mod_cluster.jvmRoute=node1

5. 启动server2

./standalone.sh -c standalone-full-ha.xml -Djboss.socket.binding.port-offset=100 -b 10.0.2.15 -bmanagement=10.0.2.15 -u 239.255.100.100 -Djboss.node.name=node2 -Djboss.mod_cluster.jvmRoute=node2

6. 测试
(1)从JMSClient程序发送消息到server1上,会发现单数消息在server1上接收,双数消息在server2上接收。
(2)停掉server1,发现剩余单数消息由server2接管,这就是fail over的作用。
(3)重启server1
(4)继续从JMSClient程序发送消息到server1上,会发现单数消息在server1上接收,双数消息在server2上接收。
(5)再次停掉server1,这次发现单数消息并没有由server2接管。

附上JMSClient.java 代码:

import java.io.Serializable;
import java.util.HashMap;
import java.util.Properties;

import javax.jms.Connection;
import javax.jms.ConnectionFactory;
import javax.jms.Destination;
import javax.jms.MessageProducer;
import javax.jms.ObjectMessage;
import javax.jms.Session;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;

public class JMSClient {
private Context getContext() throws NamingException {

final Properties env = new Properties();
env.put(Context.INITIAL_CONTEXT_FACTORY, "org.jboss.naming.remote.client.InitialContextFactory");
//env.put(Context.PROVIDER_URL, "remote://10.66.218.47:4447");
                env.put(Context.PROVIDER_URL, "remote://192.168.0.103:4447");
env.put(Context.SECURITY_PRINCIPAL,"democlient");
env.put(Context.SECURITY_CREDENTIALS,"password1!");

return new InitialContext(env);
}
private Context context;

private void execute() throws Exception {

context = getContext();
ConnectionFactory connectionFactory = null;
        Connection connection = null;
        Session session = null;
        MessageProducer producer = null;
        Destination destination = null;
        
        try {
connectionFactory = (ConnectionFactory) context.lookup("jms/RemoteConnectionFactory");
System.out.println("Acquiring connection factory success, " + connectionFactory);
destination = (Destination) context.lookup("jms/queue/DistributedQueue");
System.out.println("Acquiring destination success, " + destination);
connection = connectionFactory.createConnection("democlient", "password1!");
System.out.println("Creating connection success, " + connection);
session = connection.createSession(false, Session.AUTO_ACKNOWLEDGE);
System.out.println("Creating session success, " + session);
            producer = session.createProducer(destination);
            System.out.println("Creating producer success, " + producer);
            
            connection.start();
            
            HashMap map = new HashMap();
            map.put( "delay", new Long(1000 * 10) );
            map.put( "message", "JBoss 7/WildFly HornetQ Messaging High Available" );
            System.out.println("Send 10 messages to DistributedQueue");
            for (int index = 1; index <= 10; index++) {
map.put( "count", index );
ObjectMessage objectMessage = session.createObjectMessage();
objectMessage.setObject( map );
producer.send( objectMessage );
}
            
            System.out.println("JMSClient exit");
} catch (Exception e) {
throw e;
} finally {

if (producer != null) {
producer.close();
}

if (session != null) {
session.close();
}

if (connection != null) {
connection.close();
}
}

}
public static void main(String[] args) throws Exception {
new JMSClient().execute();
}

}


7. 解决办法
JBoss已经确认这是一个BUG,目前只在6.2.0上有一个解决办法:
为hornetq-server增加一个属性:max-saved-replicated-journal-size,并将其设置为-1。
该参数含义如下:The maximum number of backup journals to keep after failback occurs, -1 表示不限次数。
但是,目前还不能直接加到配置文件中,因为对应的schema还没有修改,只能通过CLI方式添加:

步骤如下: 以server1 为例(对server2要执行同样的操作)
进入bin目录:
(1)./jboss-cli.sh
(2)connect 10.0.2.15:9999 (换成你的IP地址和端口)
(3)/subsystem=messaging/hornetq-server=default:write-attribute(name=max-saved-replicated-journal-size,value=-1)
(4)/subsystem=messaging/hornetq-server=backup-server:write-attribute(name=max-saved-replicated-journal-size,value=-1)
(3)(4)步把两个hornetq server:default和backup-server都增加了属性
max-saved-replicated-journal-size并设置为-1。

重启server1和server2。

再次测试,发现多次shutdown server1后,message 都会 fail over 到 server2上。

参考文献:
1. http://blog.csdn.net/kylinsoong/article/details/16830581
2. https://bugzilla.redhat.com/show_bug.cgi?id=1013536
3. http://wildscribe.github.io/JBoss%20EAP/6.2.0/subsystem/messaging/hornetq-server/index.html