基于IEC104通信协议的主站实现示例(Java)

本文通过使用org.openmuc.j60870,使基于IEC104协议通信的服务端与客户端建立连接。

基于IEC104通信协议的主站实现示例(Java)

org.openmuc.j60870 包

主站发起连接示例

使用ClientConnectionBuilder创建一个新的连接,并为该连接设置对应的监听器。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
public boolean connect() {
	try{
		ClientConnectionBuilder clientConnectionBuilder = new ClientConnectionBuilder(address);
		connection = clientConnectionBuilder.build();
		ClientEventListener listener = new ClientEventListener();
		connection.setConnectionListener(listener);
		log("Connected to: ", address);
		return true;
	} catch (IOException e){
		log("Unable to connect to remote host: ", address);
		throw new RuntimeException(e);
	}
 }

实现监听器方法

使用ConnectionListener接口来实现异步的方式。ConnectionListener接口有一个方法newASdu(ASdu asdu),当收到一个新的asdu报文时,会被自动调用。可以在这个方法中对asdu报文进行解析和处理,例如获取其类型、结构、传输原因、公共地址、信息对象等属性,或者根据不同的类型进行不同的业务逻辑。也可以使用ASdu类提供的toString()方法来打印出asdu报文的内容。

发送一条命令报文,在connection中添加一个ClientEventListener,监听到回复时会自动解析回复的报文,然后可以在ClientEventListener中的newASdu中对解析出来的数据进行操作。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
public static class ClientEventListener implements ConnectionEventListener{
	@Override
	public void newASdu(ASdu aSdu) {
	System.out.println(aSdu.toString());
	// 解析aSdu
	// ...
	InformationObject[] informationObject = aSdu.getInformationObjects();
	}

	@Override
	public void connectionClosed(IOException e) {
		System.out.println("Connection closed");
	}

	@Override
	public void dataTransferStateChanged(boolean stopped) {
		System.out.println("Data transfer state changed."+" Status: "+ !stopped);
	}
}

流程

Here is a short summary of the steps to get a client running:

  • Create and configure an instance of ClientConnectionBuilder.
  • Connect to the server using ClientConnectionBuilder.build() which returns the connection. The client is now connected to the server via TCP/IP.
  • Initialize the data transfer by calling Connection.startDataTransfer.
  • Now all incoming ASDUs (except for confirmation messages) will be forwarded to the ASduListener you registered. Every ASDU contains a number of Information Objects. The information objects contain information elements that make up the actual data. You will have to cast the InformationElements of the ASDU to a concrete implementation in order to access the data inside them. Every standardized Information Element is implemented by a class starting with the letters “Ie”. The Type Identifier allows you to figure what to cast a particular Information Element to.
  • You can use the Connection instance to send commands.

IEC104协议规约

基本协议命令

  • i - interrogation C_IC_NA_1:
  • 总召唤命令,用于请求远方站发送所有的过程信息。
  • ci - counter interrogation C_CI_NA_1:
  • 计数器召唤命令,用于请求远方站发送所有或部分的累计量。
  • c - synchronize clocks C_CS_NA_1:
  • 时钟同步命令,用于将远方站的时钟与主站的时钟进行校准。
  • s - single command select C_SC_NA_1:
  • 单点命令选择,用于预置一个开关或继电器的状态。
  • e - single command execute C_SC_NA_1:
  • 单点命令执行,用于激活一个预置的开关或继电器的状态。
  • p - STOPDT act:
  • 停止数据传输激活命令,用于通知远方站停止发送任何数据。
  • t - STARTDT act:
  • 启动数据传输激活命令,用于通知远方站开始发送数据。
  • h - print help message:
  • 打印帮助信息的命令,用于显示可用的命令和参数。
  • q - quit the application:
  • 退出应用程序的命令,用于结束当前的会话和连接。
参数超时时间备注
t030s连接建立的超时
t115s发送或测试 APDU 的超时
t210s无数据报文 t2 < t1 时确认的超时
t320s长期空闲 t3 >t1状态下发送测试帧的超时

IEC104协议中,服务端回应客户端的时长主要取决于两个参数:t1t2

t1是客户端发送I帧(信息帧)或U帧(非编号控制帧)后,等待服务端回应的超时时间。如果在t1时间内没有收到服务端的S帧(确认帧)或U帧,客户端会重发该帧,并重新启动t1定时器。如果重发次数达到最大值,客户端会断开连接并重新建立连接。

t2是服务端接收到客户端的I帧后,发送S帧给客户端的最大延迟时间。如果在t2时间内没有发送S帧,服务端会在下一个I帧中附加S帧给客户端。如果服务端没有I帧要发送,它也可以单独发送S帧给客户端。

根据IEC104协议的标准规定,t1的取值范围是15s~120s,t2的取值范围是10ms~15s。不同的设备厂商可能会根据自己的实际情况进行调整,但一般要保证t1>t2。

e7ebe6b587be4f6581423262ee25da16

Written by VastCosmic & Post in 泠境
Explore the Infinity Cosmos.
Built with Hugo
Designed By VastCosmic with Hugo Theme Stack