View Javadoc
1   /*
2    * Copyright 2011 The Netty Project
3    *
4    * The Netty Project licenses this file to you under the Apache License,
5    * version 2.0 (the "License"); you may not use this file except in compliance
6    * with the License. You may obtain a copy of the License at:
7    *
8    * https://www.apache.org/licenses/LICENSE-2.0
9    *
10   * Unless required by applicable law or agreed to in writing, software
11   * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12   * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13   * License for the specific language governing permissions and limitations
14   * under the License.
15   */
16  package io.netty.channel.sctp;
17  
18  import com.sun.nio.sctp.MessageInfo;
19  import io.netty.buffer.ByteBuf;
20  import io.netty.buffer.DefaultByteBufHolder;
21  import io.netty.util.internal.ObjectUtil;
22  
23  /**
24   * Representation of SCTP Data Chunk
25   */
26  public final class SctpMessage extends DefaultByteBufHolder {
27      private final int streamIdentifier;
28      private final int protocolIdentifier;
29      private final boolean unordered;
30  
31      private final MessageInfo msgInfo;
32  
33      /**
34       * Essential data that is being carried within SCTP Data Chunk
35       * @param protocolIdentifier of payload
36       * @param streamIdentifier that you want to send the payload
37       * @param payloadBuffer channel buffer
38       */
39      public SctpMessage(int protocolIdentifier, int streamIdentifier, ByteBuf payloadBuffer) {
40          this(protocolIdentifier, streamIdentifier, false, payloadBuffer);
41      }
42  
43      /**
44       * Essential data that is being carried within SCTP Data Chunk
45       * @param protocolIdentifier of payload
46       * @param streamIdentifier that you want to send the payload
47       * @param unordered if {@literal true}, the SCTP Data Chunk will be sent with the U (unordered) flag set.
48       * @param payloadBuffer channel buffer
49       */
50      public SctpMessage(int protocolIdentifier, int streamIdentifier, boolean unordered, ByteBuf payloadBuffer) {
51          super(payloadBuffer);
52          this.protocolIdentifier = protocolIdentifier;
53          this.streamIdentifier = streamIdentifier;
54          this.unordered = unordered;
55          msgInfo = null;
56      }
57  
58      /**
59       * Essential data that is being carried within SCTP Data Chunk
60       * @param msgInfo       the {@link MessageInfo}
61       * @param payloadBuffer channel buffer
62       */
63      public SctpMessage(MessageInfo msgInfo, ByteBuf payloadBuffer) {
64          super(payloadBuffer);
65          this.msgInfo = ObjectUtil.checkNotNull(msgInfo, "msgInfo");
66          this.streamIdentifier = msgInfo.streamNumber();
67          this.protocolIdentifier = msgInfo.payloadProtocolID();
68          this.unordered = msgInfo.isUnordered();
69      }
70  
71      /**
72       * Return the stream-identifier
73       */
74      public int streamIdentifier() {
75          return streamIdentifier;
76      }
77  
78      /**
79       * Return the protocol-identifier
80       */
81      public int protocolIdentifier() {
82          return protocolIdentifier;
83      }
84  
85      /**
86       * return the unordered flag
87       */
88      public boolean isUnordered() {
89          return unordered;
90      }
91  
92      /**
93       * Return the {@link MessageInfo} for inbound messages or {@code null} for
94       * outbound messages.
95       */
96      public MessageInfo messageInfo() {
97          return msgInfo;
98      }
99  
100     /**
101      * Return {@code true} if this message is complete.
102      */
103     public boolean isComplete() {
104         if (msgInfo != null) {
105             return msgInfo.isComplete();
106         }  else {
107             //all outbound sctp messages are complete
108             return true;
109         }
110     }
111 
112     @Override
113     public boolean equals(Object o) {
114         if (this == o) {
115             return true;
116         }
117 
118         if (o == null || getClass() != o.getClass()) {
119             return false;
120         }
121 
122         SctpMessage sctpFrame = (SctpMessage) o;
123 
124         if (protocolIdentifier != sctpFrame.protocolIdentifier) {
125             return false;
126         }
127 
128         if (streamIdentifier != sctpFrame.streamIdentifier) {
129             return false;
130         }
131 
132         if (unordered != sctpFrame.unordered) {
133             return false;
134         }
135 
136         return content().equals(sctpFrame.content());
137     }
138 
139     @Override
140     public int hashCode() {
141         int result = streamIdentifier;
142         result = 31 * result + protocolIdentifier;
143         // values 1231 and 1237 are referenced in the javadocs of Boolean#hashCode()
144         result = 31 * result + (unordered ? 1231 : 1237);
145         result = 31 * result + content().hashCode();
146         return result;
147     }
148 
149     @Override
150     public SctpMessage copy() {
151         return (SctpMessage) super.copy();
152     }
153 
154     @Override
155     public SctpMessage duplicate() {
156         return (SctpMessage) super.duplicate();
157     }
158 
159     @Override
160     public SctpMessage retainedDuplicate() {
161         return (SctpMessage) super.retainedDuplicate();
162     }
163 
164     @Override
165     public SctpMessage replace(ByteBuf content) {
166         if (msgInfo == null) {
167             return new SctpMessage(protocolIdentifier, streamIdentifier, unordered, content);
168         } else {
169             return new SctpMessage(msgInfo, content);
170         }
171     }
172 
173     @Override
174     public SctpMessage retain() {
175         super.retain();
176         return this;
177     }
178 
179     @Override
180     public SctpMessage retain(int increment) {
181         super.retain(increment);
182         return this;
183     }
184 
185     @Override
186     public SctpMessage touch() {
187         super.touch();
188         return this;
189     }
190 
191     @Override
192     public SctpMessage touch(Object hint) {
193         super.touch(hint);
194         return this;
195     }
196 
197     @Override
198     public String toString() {
199         return "SctpFrame{" +
200                "streamIdentifier=" + streamIdentifier + ", protocolIdentifier=" + protocolIdentifier +
201                ", unordered=" + unordered +
202                ", data=" + contentToString() + '}';
203     }
204 }