Replace Preconditions.CheckNotNull per RequireNonNull
[bgpcep.git] / bgp / bmp-spi / src / main / java / org / opendaylight / protocol / bmp / spi / parser / AbstractBmpPerPeerMessageParser.java
1 /*
2  * Copyright (c) 2015 Cisco Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8
9 package org.opendaylight.protocol.bmp.spi.parser;
10
11 import static java.util.Objects.requireNonNull;
12
13 import com.google.common.base.Preconditions;
14 import io.netty.buffer.ByteBuf;
15 import org.opendaylight.bgp.concepts.RouteDistinguisherUtil;
16 import org.opendaylight.protocol.bgp.parser.spi.MessageRegistry;
17 import org.opendaylight.protocol.util.BitArray;
18 import org.opendaylight.protocol.util.ByteArray;
19 import org.opendaylight.protocol.util.ByteBufWriteUtil;
20 import org.opendaylight.protocol.util.Ipv4Util;
21 import org.opendaylight.protocol.util.Ipv6Util;
22 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.AsNumber;
23 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.IpAddress;
24 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.types.rev130715.Timestamp;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.AdjRibInType;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.Peer.PeerDistinguisher;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.PeerType;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.peer.header.PeerHeader;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.peer.header.PeerHeaderBuilder;
30 import org.opendaylight.yangtools.concepts.Builder;
31 import org.opendaylight.yangtools.yang.binding.Notification;
32
33 public abstract class AbstractBmpPerPeerMessageParser<T  extends Builder<?>> extends AbstractBmpMessageWithTlvParser<T> {
34
35     private static final int L_FLAG_POS = 1;
36     private static final int V_FLAG_POS = 0;
37     private static final int FLAGS_SIZE = 8;
38     private static final int PEER_DISTINGUISHER_SIZE = 8;
39     private static final int PER_PEER_HEADER_SIZE = 32;
40
41     private final MessageRegistry bgpMssageRegistry;
42
43     public AbstractBmpPerPeerMessageParser(final MessageRegistry bgpMssageRegistry) {
44         this(bgpMssageRegistry, null);
45     }
46
47     public AbstractBmpPerPeerMessageParser(final MessageRegistry bgpMssageRegistry, final BmpTlvRegistry tlvRegistry) {
48         super(tlvRegistry);
49         this.bgpMssageRegistry = requireNonNull(bgpMssageRegistry);
50     }
51
52     @Override
53     public void serializeMessageBody(final Notification message, final ByteBuf buffer) {
54         if (message instanceof org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.PeerHeader) {
55             final org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.PeerHeader messageWithPerPeerHeader =
56                 (org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bmp.message.rev150512.PeerHeader) message;
57             serializePerPeerHeader(messageWithPerPeerHeader.getPeerHeader(), buffer);
58         }
59     }
60
61     protected static final PeerHeader parsePerPeerHeader(final ByteBuf bytes) {
62         Preconditions.checkArgument(bytes.readableBytes() >= PER_PEER_HEADER_SIZE);
63         final PeerHeaderBuilder phBuilder = new PeerHeaderBuilder();
64         final PeerType peerType = PeerType.forValue(bytes.readByte());
65         phBuilder.setType(peerType);
66         final BitArray flags = BitArray.valueOf(bytes, FLAGS_SIZE);
67         phBuilder.setAdjRibInType(AdjRibInType.forValue(flags.get(L_FLAG_POS) ? 1 : 0));
68         phBuilder.setIpv4(!flags.get(V_FLAG_POS));
69         switch (peerType) {
70         case L3vpn:
71             phBuilder.setDistinguisher(PeerDistinguisherUtil.parsePeerDistingisher(bytes.slice()));
72             phBuilder.setPeerDistinguisher(new PeerDistinguisher(RouteDistinguisherUtil.parseRouteDistinguisher(bytes)));
73             break;
74         case Local:
75             phBuilder.setPeerDistinguisher(new PeerDistinguisher(ByteArray.readBytes(bytes, PEER_DISTINGUISHER_SIZE)));
76             break;
77         case Global:
78         default:
79             bytes.skipBytes(PEER_DISTINGUISHER_SIZE);
80             break;
81         }
82         if (phBuilder.isIpv4()) {
83             bytes.skipBytes(Ipv6Util.IPV6_LENGTH - Ipv4Util.IP4_LENGTH);
84             phBuilder.setAddress(new IpAddress(Ipv4Util.addressForByteBuf(bytes)));
85         } else {
86             phBuilder.setAddress(new IpAddress(Ipv6Util.addressForByteBuf(bytes)));
87         }
88         phBuilder.setAs(new AsNumber(bytes.readUnsignedInt()));
89         phBuilder.setBgpId(Ipv4Util.addressForByteBuf(bytes));
90         phBuilder.setTimestampSec(new Timestamp(bytes.readUnsignedInt()));
91         phBuilder.setTimestampMicro(new Timestamp(bytes.readUnsignedInt()));
92         return phBuilder.build();
93     }
94
95     protected void serializePerPeerHeader(final PeerHeader peerHeader, final ByteBuf output) {
96         Preconditions.checkArgument(peerHeader != null, "Per-peer header cannot be null.");
97         final PeerType peerType = peerHeader.getType();
98         output.writeByte(peerType.getIntValue());
99         final BitArray flags = new BitArray(FLAGS_SIZE);
100         flags.set(L_FLAG_POS, peerHeader.getAdjRibInType().getIntValue() == 0 ? false : true);
101         flags.set(V_FLAG_POS, !peerHeader.isIpv4());
102         flags.toByteBuf(output);
103         final PeerDistinguisher peerDistinguisher = peerHeader.getPeerDistinguisher();
104         switch (peerType) {
105         case L3vpn:
106             if (peerDistinguisher.getRouteDistinguisher() != null) {
107                 RouteDistinguisherUtil.serializeRouteDistinquisher(peerDistinguisher.getRouteDistinguisher(), output);
108             } else {
109                 PeerDistinguisherUtil.serializePeerDistinguisher(peerHeader.getDistinguisher(), output);
110             }
111             break;
112         case Local:
113             output.writeBytes(peerDistinguisher.getBinary());
114             break;
115         case Global:
116         default:
117             output.writeZero(PEER_DISTINGUISHER_SIZE);
118             break;
119         }
120         if (peerHeader.isIpv4()) {
121             output.writeZero(Ipv6Util.IPV6_LENGTH - Ipv4Util.IP4_LENGTH);
122             ByteBufWriteUtil.writeIpv4Address(peerHeader.getAddress().getIpv4Address(), output);
123         } else {
124             ByteBufWriteUtil.writeIpv6Address(peerHeader.getAddress().getIpv6Address(), output);
125         }
126         ByteBufWriteUtil.writeUnsignedInt(peerHeader.getAs().getValue(), output);
127         ByteBufWriteUtil.writeIpv4Address(peerHeader.getBgpId(), output);
128         if (peerHeader.getTimestampSec() != null) {
129             ByteBufWriteUtil.writeUnsignedInt(peerHeader.getTimestampSec().getValue(), output);
130         } else {
131             output.writeZero(ByteBufWriteUtil.INT_BYTES_LENGTH);
132         }
133         if (peerHeader.getTimestampMicro() != null) {
134             ByteBufWriteUtil.writeUnsignedInt(peerHeader.getTimestampMicro().getValue(), output);
135         } else {
136             output.writeZero(ByteBufWriteUtil.INT_BYTES_LENGTH);
137         }
138     }
139
140     protected final MessageRegistry getBgpMessageRegistry() {
141         return this.bgpMssageRegistry;
142     }
143 }