1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.directory.mitosis.service.protocol.codec;
21
22
23 import org.apache.directory.mitosis.service.protocol.message.BaseMessage;
24 import org.apache.directory.server.schema.registries.Registries;
25 import org.apache.mina.common.ByteBuffer;
26 import org.apache.mina.common.IoSession;
27 import org.apache.mina.filter.codec.ProtocolDecoderException;
28 import org.apache.mina.filter.codec.ProtocolDecoderOutput;
29 import org.apache.mina.filter.codec.demux.MessageDecoder;
30 import org.apache.mina.filter.codec.demux.MessageDecoderResult;
31
32
33 public abstract class BaseMessageDecoder implements MessageDecoder
34 {
35 private final int type;
36 private final int minBodyLength;
37 private final int maxBodyLength;
38 private boolean readHeader;
39 private int sequence;
40 private int bodyLength;
41
42
43 protected BaseMessageDecoder( int type, int minBodyLength, int maxBodyLength )
44 {
45 this.type = type;
46 this.minBodyLength = minBodyLength;
47 this.maxBodyLength = maxBodyLength;
48 }
49
50
51 public final MessageDecoderResult decodable( IoSession session, ByteBuffer buf )
52 {
53 return type == buf.get() ? OK : NOT_OK;
54 }
55
56
57 public final MessageDecoderResult decode( IoSession session, ByteBuffer in, ProtocolDecoderOutput out )
58 throws Exception
59 {
60 if ( !readHeader )
61 {
62 if ( in.remaining() < 9 )
63 {
64 return NEED_DATA;
65 }
66
67 in.get();
68 sequence = in.getInt();
69 bodyLength = in.getInt();
70
71 if ( bodyLength < minBodyLength || bodyLength > maxBodyLength )
72 {
73 throw new ProtocolDecoderException( "Wrong bodyLength: " + bodyLength );
74 }
75
76 readHeader = true;
77 }
78
79 if ( readHeader )
80 {
81 if ( in.remaining() < bodyLength )
82 {
83 return NEED_DATA;
84 }
85
86 int oldLimit = in.limit();
87
88 try
89 {
90 in.limit( in.position() + bodyLength );
91
92 Registries registries = (Registries)session.getAttribute( "registries" );
93 out.write( decodeBody( registries, sequence, bodyLength, in ) );
94 return OK;
95 }
96 finally
97 {
98 readHeader = false;
99 in.limit( oldLimit );
100 }
101 }
102
103 throw new InternalError();
104 }
105
106
107 protected abstract BaseMessage decodeBody( Registries registries, int sequence, int bodyLength, ByteBuffer in ) throws Exception;
108 }