Sun GlassFish Communications Server 2.0 发行说明

第 3 章 Sun GlassFish Communications Server 的已知问题和限制

本章介绍 Communications Server 软件的已知问题和相应的解决方法。如果汇总说明未指明特定平台,则所有平台都可能出现此问题。本部分信息按以下内容进行组织:

Communications Server 管理

Communications Server 不检测与群集的心跳端口的冲突(问题号 1967)

描述

创建群集时,Communications Server 会随机分配一个介于 1026 到 45556 之间的心跳端口。对于默认群集(由 Communications Server 安装创建的默认群集),会在 0 到 45556 之间选择一个随机数。群集创建过程不会精确检测心跳端口是否正被另一个服务使用。

解决方法

如果自动群集创建配置选择了一个心跳端口,该端口与正在使用它的另一个服务冲突,请将群集心跳端口更新为系统未使用的端口。

要更改群集的心跳端口,请使用下面的 asadmin 命令:

asadmin set 群集名称.heartbeat-port=新端口号

域创建操作在运行 64 位 Linux 的 NFS 服务器上停止(问题号 1961)

描述

当尝试在安装了网络文件系统 (NFS) 的文件系统(NFS 服务器运行 64 位 Linux)上创建域时,asadmin create-domain 命令可能会失败。

解决方法

没有已知的解决方法。

流量很小或没有时 CPU 使用率居高不下(问题号 1966)

说明

启用 CPU 过载保护时,即使流量很小或没有,Communications Server 实例有时也会显示高 CPU 使用率。此问题是由 JDK 错误 6693490 引起的。JDK 6 Update 18 中已解决该错误。

解决方法

将 JDK 6 Update 18 与 Communications Server 搭配使用。

即使未绑定 SIP/SIPS 端口,Communications Server 实例也会启动(问题号 998)

说明

即使无法绑定至 SIP 或 SIPS 端口,Communications Server 实例也会启动。

解决方法

在启动服务器实例前,先确保端口处于空闲状态。检查日志文件 (server.log),确保启动期间没有任何的 SIP 容器错误或异常。

Communications Server 不使用 ––javahome 选项指定的 JDK(问题号 789)

说明

通过 ––javahome 选项,可使用预先安装的 JDK 来替代安装的默认版本。默认情况下,Communications Server 使用 as-install/jdk 中的 JDK 版本。

解决方法

asenv.conf 文件中的 AS_JAVA 变量始终会指向 as-install/jdk。如果要使用不同的 JDK 版本,请手动更新 asenv.conf 文件并更改 AS_JAVA 的值。

使用 3.5 GB Java 堆可导致实例在收到流量时重新启动(问题 1169)

说明

JVM 堆大小设置为 3.5 GB 时,Communications Server 实例会在收到流量时失败并重新启动。

解决方法

确保将最大 JVM 堆大小设置为 3.0 GB 或以下。

仅使用多核系统的一个核心时,Communications Server 不能正确地报告 CPU 使用率(问题 1344)

说明

在 Solaris 平台上,Communications Server 根据可用的处理器数量和每个核心的 CPU 使用率来计算 CPU 使用率。但是,Communications Server 是以核心数的静态值为准,而不是 JVM 所用的核心数。

解决方法

如果没有使用机器中的全部核心,请重新计算 CPU 阈值。

聚合负载平衡器

由于应用程序部署后聚合负载平衡器的动态重新配置,日志中出现 SEVERE 消息(问题 1161)

说明

如果在目标上修改了聚合负载平衡器的配置,并在该目标上重新部署应用程序,实例日志将显示 SEVERE 消息。

解决方法

这些消息不会影响聚合负载平衡器或实例的运行,可以忽略。

使用完整 URI 时,连接头中的 BEKey 参数不能正确转义(问题 1466)

说明

使用聚合负载平衡器时,如果数据导向规则文件会为 BEKey 参数返回完整 URI,则连接头中的 BEKey 参数不能正确转义。“:”字符不能按照 RFC 3261 中的指定进行正确转义。

解决方法

没有已知的解决方法。

安装

Communications Server 基于文件的安装程序不安装 Basic3pcc 示例应用程序(错误号 6894932)

说明

Communications Server 基于文件的安装程序不安装 Basic3pcc 示例应用程序。而使用 JAR 安装程序时,可安装该应用程序。

解决方法

没有已知的解决方法。

Communications Server 安装程序在 Linux 上崩溃 (6739013)

说明

已在运行 Linux 并且环境变量 MALLOC_CHECK_ 设置为 2 的系统上发现该问题。

解决方法

将环境变量 MALLOC_CHECK_ 设置为 0。运行以下命令之一:

在有 64 位 JDK 的情况下,安装失败 (6796171)

描述

在有 64 位 JDK 的 64 位系统上,安装失败,因为安装程序试图使用 64 位 JDK。

解决方法

如果要在 64 位系统上安装 Sun GlassFish Communications Server,请下载 32 位 JDK,并使用它在 64 位计算机上安装 Sun GlassFish Communications Server。您需要使用以下命令:./分发文件名 —javahome 32 位 JDK 位置路径

安装后,为确保 Sun GlassFish Communications Server 使用 64 位 JDK,请编辑 asenv.conf 文件中的 AS_JAVA 变量值,以指向 64 位 JDK 安装。

安全性

sun-sip.xml 中未指定 trust-auth-realm-ref 属性时,Communications Server 抛出异常 (CR 6786131)

说明

sun-sip.xml 中配置有 P-Asserted-Identity 验证时,Communications Server 会抛出“未配置领域”空指针异常。

解决方法

请在 sun-sip.xml 中使用 trust-auth-realm-ref 属性来配置领域。

SIP 容器

SIP 容器在发送 100 响应后无法处理 CANCEL(问题 712)

说明

在发送 100 响应之后,SIP 容器无法处理 CANCEL 请求。

解决方法

应用程序需要发送一个临时响应(如 1xx),以便远程端可以取消该 INVITE 请求。

SIP 会话和 HTTP 会话不应用相同的会话到期时间模型(问题 1180)

说明

SIP 会话的会话到期模型与 HTTP 失效时间逻辑不同。在 HTTP 中,HTTP 会话在收到新的 HTTP 请求时会自动延长,并不受应用程序的控制。

而对于 SIP 会话,应用程序可在 SIP 容器批准下,控制 SipApplicationSession (SAS) 的持续时间。应用程序可使用 setExpires 方法来指示 SAS 应该在何时失效。setExpires 会相对于调用 setExpires 方法的时刻指定一个失效时间。容器可以修改、拒绝或接受 setExpires 中指示的持续时间。如果会话没有失效,则在 setExpires 定义的时刻执行 sessionExpired 回调。在回调中,应用程序可通过调用新的 setExpires 来尝试延长 SAS 的持续时间,但仍由容器来决定是否修改、拒绝或接受。

出于这个原因,尽管在聚合应用程序启动时,SipApplicationSession (SAS) 和 HTTP 会话上的失效时间是相同,如果在 HTTP 会话上收到了新请求,SAS 将会在 HTTP 会话之前超时。

解决方法

解决 SIP 和 HTTP 会话到期时间不同的最佳方法是,启动时设置足够长的 SAS 失效时间,大小相当于应用程序会话预期存活的总时间(包含几个 HTTP 请求)。甚至,还可以将 SAS 生命周期设置为无限长,尤其是在使用了 invalidateWhenReady 语义时;在这种情形下,SipApplicationSession 到最后一个协议子会话到期时才会失效。SAS 的初始失效时间可以在部署描述符中进行配置。

如果可以事先估计总持续时间的最大值,则无需使用更多代码,因为在 SAS 失效时 SIP 会话和 HTTP 会话也会同时失效。如果不能事先估计总持续时间的最大值,则可在到期时延长 SipApplicationSession,代码片段如下所示。

SipApplicationSessionListener 实施中,可使用类似如下的代码:

public void sessionExpired(SipApplicationSessionEvent sasEvent) {
                // check if the SAS needs to be extended first, if so:
		int granted = sasEvent.getApplicationSession().setExpires(2);
		if (granted <= 0) {
			System.out.println("extension rejected");
		} else if (granted < 2) {
			System.out.println("extension granted with lower value " + granted);
		} // else allowed 
	}

容器回调 sessionExpired 时 SIP 会话依旧存活(问题 1265)

说明

这是间歇性的问题。在 200 NOTIFY(指示会话已删除)与客户端在收到该 NOTIFY 时发送的 SUBSCRIBE 之间存在竞争条件时,SIP 容器间歇性地响应“500 服务器内部错误”消息,而不是“481 调用/事务不存在”消息。

解决方法

客户端需要在订阅到期之前早早刷新 SUBSCRIBE。

Communications Server 先扮演 UAS 角色,接着是代理角色,然后生成 NOP(问题 1432)

说明

在收到 INVITE 请求时,Communications Server 先扮演 UAS 角色,以 1XX 回复该请求,然后将此 INVITE 请求代理至另一实例,而该实例回复 200 OK。1xx 创建内部虚拟分支,而 200 消息则创建实际分支。从 B 收到 200 OK 时,内部虚拟分支应会取消。

解决方法

此异常跟踪不会影响虚拟代理分支的功能。

getLastAccessedTime 方法不能提供准确的结果(问题 1351)

说明

SIP 会话的 getLastAccessedTime 方法不能提供准确的结果。

解决方法

需要准确跟踪 lastAccessedTime 的应用程序必须自行将其存储到 SipApplicationSession 中。

synchronized (sas) {
	Long last = (Long) sas.getAttribute("myLastAccessedTime");
	if (last == null) {last = 0};
	// do something with the last one
	// and...
	// set the new one.
	sas.setAttribute("myLastAccessedTime", System.currentTimeMillis());
}

SIP 侦听器在删除后还能在一段时间内保持活动状态(问题 1294)

说明

为 TCP 和 UDP 请求配置的 SIP 侦听器在删除后,还能在一段时间内保持活动状态。发送至该侦听器的 UDP 请求会收到其响应。

解决方法

没有已知的解决方法。该 SIP 侦听器会在一段时间后停止侦听 UDP 请求。此问题不影响 TCP 请求。

Communications Server 在收到不带“<>”的连接头时抛出异常(问题 1489)

说明

Communications Server 在收到不带“<>”的连接头时抛出异常。根据 SIP RFC 3261,地址中不强制使用“<>”。这会引起与其他符合 SIP 的设备的互操作性问题。

解决方法

在连接头中使用“<>”。

Communications Server 在无效 UUID 值上抛出异常(问题 1494)

说明

Communications Server 在无效 UUID 值上抛出异常,而不是返回“400 错误的请求”。UUID 值驻留在 SIP 连接头的 sip.instance 值中。

解决方法

没有已知的解决方法。

Windows:Communications Server 有时收不到 UDP 消息(无编号)

说明

此问题仅会间歇性地在 Windows 上出现。Communications Server 收不到 UDP 消息。

解决方法

按以下方式设置如下 JVM 选项,再重新启动 Communications Server。

org.jvnet.glassfish.comms.disableUDPSourcePort=true

SIP 会话复制

聚合应用程序将 SAS 对象用作同步锁定时可能会出现死锁(问题号 1954)

说明

如果具有 HTTP 和 SIP Servlet 的聚合应用程序将 sipApplicationSession 对象用作 SIP 和 HTTP 工作线程访问的同步锁,会出现死锁。

解决方法

不要将 sipApplicationSession 用作同步锁。而是将设置为 sipApplicationSession 中属性的可系列化对象用作锁定。