2 * Copyright (c) 2016 Brocade Communications Systems, Inc. and others. All rights reserved.
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
8 package org.opendaylight.protocol.bgp.flowspec.l3vpn;
10 import static org.opendaylight.bgp.concepts.RouteDistinguisherUtil.extractRouteDistinguisher;
12 import com.google.common.annotations.VisibleForTesting;
13 import io.netty.buffer.ByteBuf;
14 import io.netty.buffer.Unpooled;
15 import java.util.ArrayList;
16 import java.util.List;
17 import org.eclipse.jdt.annotation.NonNull;
18 import org.eclipse.jdt.annotation.Nullable;
19 import org.opendaylight.bgp.concepts.RouteDistinguisherUtil;
20 import org.opendaylight.protocol.bgp.flowspec.AbstractFlowspecNlriParser;
21 import org.opendaylight.protocol.bgp.flowspec.FlowspecTypeRegistry;
22 import org.opendaylight.protocol.bgp.parser.BGPParsingException;
23 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev200120.flowspec.destination.Flowspec;
24 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev200120.flowspec.destination.FlowspecBuilder;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev200120.PathId;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev180329.destination.DestinationType;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.types.rev200120.RouteDistinguisher;
28 import org.opendaylight.yangtools.yang.common.QName;
29 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifier;
30 import org.opendaylight.yangtools.yang.data.api.schema.DataContainerNode;
31 import org.slf4j.Logger;
32 import org.slf4j.LoggerFactory;
34 public abstract class AbstractFlowspecL3vpnNlriParser extends AbstractFlowspecNlriParser {
35 private static final Logger LOG = LoggerFactory.getLogger(AbstractFlowspecL3vpnNlriParser.class);
36 public static final NodeIdentifier RD_NID =
37 new NodeIdentifier(QName.create(Flowspec.QNAME, "route-distinguisher").intern());
39 protected AbstractFlowspecL3vpnNlriParser(final FlowspecTypeRegistry flowspecTypeRegistry) {
40 super(flowspecTypeRegistry);
44 public final String stringNlri(final DataContainerNode flowspec) {
45 final StringBuilder buffer = new StringBuilder();
46 final RouteDistinguisher rd = extractRouteDistinguisher(flowspec, RD_NID);
48 buffer.append("[l3vpn with route-distinguisher ").append(rd.stringValue()).append("] ");
50 buffer.append(super.stringNlri(flowspec));
51 return buffer.toString();
55 * For flowspec-l3vpn, there is a route distinguisher field at the beginning of NLRI (8 bytes).
57 private static @NonNull RouteDistinguisher readRouteDistinguisher(final ByteBuf nlri) {
58 final var rd = RouteDistinguisherUtil.parseRouteDistinguisher(nlri);
59 LOG.trace("Route Distinguisher read from NLRI: {}", rd);
64 public final void serializeNlri(final @NonNull RouteDistinguisher rd, final List<Flowspec> flowspecList,
65 final @Nullable PathId pathId, final @NonNull ByteBuf buffer) {
66 final var nlri = Unpooled.buffer();
67 RouteDistinguisherUtil.serializeRouteDistinquisher(rd, nlri);
68 serializeNlri(flowspecList, nlri);
69 appendNlri(pathId, nlri, buffer);
73 protected final DestinationType parseAdvertizedNlri(final ByteBuf nlri, final PathId pathId)
74 throws BGPParsingException {
76 return createAdvertizedRoutesDestinationType(readRouteDistinguisher(nlri),
77 parseL3vpnNlriFlowspecList(nlri), pathId);
81 * Create advertized destination type.
83 * @param rd the RouteDistinguisher
84 * @param flowspecList a list of {@link Flowspec}s
85 * @param pathId associated path id with given destination
86 * @return created destination type
88 protected abstract @NonNull DestinationType createAdvertizedRoutesDestinationType(RouteDistinguisher rd,
89 @Nullable List<Flowspec> flowspecList, @Nullable PathId pathId);
92 protected final DestinationType parseWithdrawnNlri(final ByteBuf nlri, final PathId pathId)
93 throws BGPParsingException {
95 return createWithdrawnDestinationType(readRouteDistinguisher(nlri), parseL3vpnNlriFlowspecList(nlri), pathId);
99 * Create withdrawn destination type.
101 * @param rd the RouteDistinguisher
102 * @param flowspecList a list of {@link Flowspec}s
103 * @param pathId associated path id with given destination
104 * @return created destination type
106 protected abstract @NonNull DestinationType createWithdrawnDestinationType(RouteDistinguisher rd,
107 @Nullable List<Flowspec> flowspecList, @Nullable PathId pathId);
109 private @Nullable List<Flowspec> parseL3vpnNlriFlowspecList(final ByteBuf nlri) {
110 if (!nlri.isReadable()) {
114 final var fss = new ArrayList<Flowspec>();
115 while (nlri.isReadable()) {
116 fss.add(new FlowspecBuilder().setFlowspecType(flowspecTypeRegistry.parseFlowspecType(nlri)).build());