Committed by
Gerrit Code Review
Adding support for writing metadata instruction.
Needed by Centec driver. Change-Id: I705015c4d7ac881c273a01b36b05d39d9cd9ba87
Showing
10 changed files
with
156 additions
and
10 deletions
| ... | @@ -43,6 +43,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -43,6 +43,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 43 | private final List<Instruction> deferred; | 43 | private final List<Instruction> deferred; |
| 44 | private final List<Instruction> all; | 44 | private final List<Instruction> all; |
| 45 | private final Instructions.TableTypeTransition table; | 45 | private final Instructions.TableTypeTransition table; |
| 46 | + private final Instructions.MetadataInstruction meta; | ||
| 46 | 47 | ||
| 47 | private final boolean hasClear; | 48 | private final boolean hasClear; |
| 48 | 49 | ||
| ... | @@ -60,6 +61,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -60,6 +61,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 60 | this.all = this.immediate; | 61 | this.all = this.immediate; |
| 61 | this.hasClear = false; | 62 | this.hasClear = false; |
| 62 | this.table = null; | 63 | this.table = null; |
| 64 | + this.meta = null; | ||
| 63 | } | 65 | } |
| 64 | 66 | ||
| 65 | /** | 67 | /** |
| ... | @@ -73,13 +75,14 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -73,13 +75,14 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 73 | private DefaultTrafficTreatment(List<Instruction> deferred, | 75 | private DefaultTrafficTreatment(List<Instruction> deferred, |
| 74 | List<Instruction> immediate, | 76 | List<Instruction> immediate, |
| 75 | Instructions.TableTypeTransition table, | 77 | Instructions.TableTypeTransition table, |
| 76 | - boolean clear) { | 78 | + boolean clear, |
| 79 | + Instructions.MetadataInstruction meta) { | ||
| 77 | this.immediate = ImmutableList.copyOf(checkNotNull(immediate)); | 80 | this.immediate = ImmutableList.copyOf(checkNotNull(immediate)); |
| 78 | this.deferred = ImmutableList.copyOf(checkNotNull(deferred)); | 81 | this.deferred = ImmutableList.copyOf(checkNotNull(deferred)); |
| 79 | this.all = ListUtils.union(this.immediate, this.deferred); | 82 | this.all = ListUtils.union(this.immediate, this.deferred); |
| 80 | this.table = table; | 83 | this.table = table; |
| 84 | + this.meta = meta; | ||
| 81 | this.hasClear = clear; | 85 | this.hasClear = clear; |
| 82 | - | ||
| 83 | } | 86 | } |
| 84 | 87 | ||
| 85 | @Override | 88 | @Override |
| ... | @@ -107,6 +110,11 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -107,6 +110,11 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 107 | return hasClear; | 110 | return hasClear; |
| 108 | } | 111 | } |
| 109 | 112 | ||
| 113 | + @Override | ||
| 114 | + public Instructions.MetadataInstruction writeMetadata() { | ||
| 115 | + return meta; | ||
| 116 | + } | ||
| 117 | + | ||
| 110 | /** | 118 | /** |
| 111 | * Returns a new traffic treatment builder. | 119 | * Returns a new traffic treatment builder. |
| 112 | * | 120 | * |
| ... | @@ -139,7 +147,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -139,7 +147,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 139 | //FIXME: Order of instructions may affect hashcode | 147 | //FIXME: Order of instructions may affect hashcode |
| 140 | @Override | 148 | @Override |
| 141 | public int hashCode() { | 149 | public int hashCode() { |
| 142 | - return Objects.hash(immediate, deferred, table); | 150 | + return Objects.hash(immediate, deferred, table, meta); |
| 143 | } | 151 | } |
| 144 | 152 | ||
| 145 | @Override | 153 | @Override |
| ... | @@ -151,7 +159,8 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -151,7 +159,8 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 151 | DefaultTrafficTreatment that = (DefaultTrafficTreatment) obj; | 159 | DefaultTrafficTreatment that = (DefaultTrafficTreatment) obj; |
| 152 | return Objects.equals(immediate, that.immediate) && | 160 | return Objects.equals(immediate, that.immediate) && |
| 153 | Objects.equals(deferred, that.deferred) && | 161 | Objects.equals(deferred, that.deferred) && |
| 154 | - Objects.equals(table, that.table); | 162 | + Objects.equals(table, that.table) && |
| 163 | + Objects.equals(meta, that.meta); | ||
| 155 | 164 | ||
| 156 | } | 165 | } |
| 157 | return false; | 166 | return false; |
| ... | @@ -164,6 +173,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -164,6 +173,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 164 | .add("deferred", deferred) | 173 | .add("deferred", deferred) |
| 165 | .add("transition", table == null ? "None" : table.toString()) | 174 | .add("transition", table == null ? "None" : table.toString()) |
| 166 | .add("cleared", hasClear) | 175 | .add("cleared", hasClear) |
| 176 | + .add("metadata", meta) | ||
| 167 | .toString(); | 177 | .toString(); |
| 168 | } | 178 | } |
| 169 | 179 | ||
| ... | @@ -177,6 +187,8 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -177,6 +187,8 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 177 | 187 | ||
| 178 | Instructions.TableTypeTransition table; | 188 | Instructions.TableTypeTransition table; |
| 179 | 189 | ||
| 190 | + Instructions.MetadataInstruction meta; | ||
| 191 | + | ||
| 180 | List<Instruction> deferred = Lists.newLinkedList(); | 192 | List<Instruction> deferred = Lists.newLinkedList(); |
| 181 | 193 | ||
| 182 | List<Instruction> immediate = Lists.newLinkedList(); | 194 | List<Instruction> immediate = Lists.newLinkedList(); |
| ... | @@ -213,6 +225,9 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -213,6 +225,9 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 213 | case TABLE: | 225 | case TABLE: |
| 214 | table = (Instructions.TableTypeTransition) instruction; | 226 | table = (Instructions.TableTypeTransition) instruction; |
| 215 | break; | 227 | break; |
| 228 | + case METADATA: | ||
| 229 | + meta = (Instructions.MetadataInstruction) instruction; | ||
| 230 | + break; | ||
| 216 | default: | 231 | default: |
| 217 | throw new IllegalArgumentException("Unknown instruction type: " + | 232 | throw new IllegalArgumentException("Unknown instruction type: " + |
| 218 | instruction.type()); | 233 | instruction.type()); |
| ... | @@ -355,6 +370,11 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -355,6 +370,11 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 355 | } | 370 | } |
| 356 | 371 | ||
| 357 | @Override | 372 | @Override |
| 373 | + public Builder writeMetadata(long metadata, long metadataMask) { | ||
| 374 | + return add(Instructions.writeMetadata(metadata, metadataMask)); | ||
| 375 | + } | ||
| 376 | + | ||
| 377 | + @Override | ||
| 358 | public TrafficTreatment build() { | 378 | public TrafficTreatment build() { |
| 359 | //Don't add DROP instruction by default when instruction | 379 | //Don't add DROP instruction by default when instruction |
| 360 | //set is empty. This will be handled in DefaultSingleTablePipeline | 380 | //set is empty. This will be handled in DefaultSingleTablePipeline |
| ... | @@ -364,7 +384,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { | ... | @@ -364,7 +384,7 @@ public final class DefaultTrafficTreatment implements TrafficTreatment { |
| 364 | // && table == null && !clear) { | 384 | // && table == null && !clear) { |
| 365 | // drop(); | 385 | // drop(); |
| 366 | //} | 386 | //} |
| 367 | - return new DefaultTrafficTreatment(deferred, immediate, table, clear); | 387 | + return new DefaultTrafficTreatment(deferred, immediate, table, clear, meta); |
| 368 | } | 388 | } |
| 369 | 389 | ||
| 370 | } | 390 | } | ... | ... |
| ... | @@ -67,6 +67,13 @@ public interface TrafficTreatment { | ... | @@ -67,6 +67,13 @@ public interface TrafficTreatment { |
| 67 | boolean clearedDeferred(); | 67 | boolean clearedDeferred(); |
| 68 | 68 | ||
| 69 | /** | 69 | /** |
| 70 | + * Returns the metadata instruction if there is one. | ||
| 71 | + * | ||
| 72 | + * @return a metadata instruction that may be null | ||
| 73 | + */ | ||
| 74 | + Instructions.MetadataInstruction writeMetadata(); | ||
| 75 | + | ||
| 76 | + /** | ||
| 70 | * Builder of traffic treatment entities. | 77 | * Builder of traffic treatment entities. |
| 71 | */ | 78 | */ |
| 72 | interface Builder { | 79 | interface Builder { |
| ... | @@ -276,6 +283,20 @@ public interface TrafficTreatment { | ... | @@ -276,6 +283,20 @@ public interface TrafficTreatment { |
| 276 | Builder wipeDeferred(); | 283 | Builder wipeDeferred(); |
| 277 | 284 | ||
| 278 | /** | 285 | /** |
| 286 | + * Writes metadata to associate with a packet. | ||
| 287 | + * <pre> | ||
| 288 | + * {@code | ||
| 289 | + * new_metadata = (old_metadata & ̃mask) | (value & mask) | ||
| 290 | + * } | ||
| 291 | + * </pre> | ||
| 292 | + * | ||
| 293 | + * @param value the metadata to write | ||
| 294 | + * @param mask the masked bits for the value | ||
| 295 | + * @return a treatment builder | ||
| 296 | + */ | ||
| 297 | + Builder writeMetadata(long value, long mask); | ||
| 298 | + | ||
| 299 | + /** | ||
| 279 | * Builds an immutable traffic treatment descriptor. | 300 | * Builds an immutable traffic treatment descriptor. |
| 280 | * <p> | 301 | * <p> |
| 281 | * If the treatment is empty when build() is called, it will add a default | 302 | * If the treatment is empty when build() is called, it will add a default |
| ... | @@ -286,5 +307,7 @@ public interface TrafficTreatment { | ... | @@ -286,5 +307,7 @@ public interface TrafficTreatment { |
| 286 | * @return traffic treatment | 307 | * @return traffic treatment |
| 287 | */ | 308 | */ |
| 288 | TrafficTreatment build(); | 309 | TrafficTreatment build(); |
| 310 | + | ||
| 289 | } | 311 | } |
| 312 | + | ||
| 290 | } | 313 | } | ... | ... |
| ... | @@ -35,7 +35,7 @@ public interface Instruction { | ... | @@ -35,7 +35,7 @@ public interface Instruction { |
| 35 | OUTPUT, | 35 | OUTPUT, |
| 36 | 36 | ||
| 37 | /** | 37 | /** |
| 38 | - * Signifies that.... (do we need this?) | 38 | + * Signifies that traffic should be sent out of a group. |
| 39 | */ | 39 | */ |
| 40 | GROUP, | 40 | GROUP, |
| 41 | 41 | ||
| ... | @@ -57,7 +57,12 @@ public interface Instruction { | ... | @@ -57,7 +57,12 @@ public interface Instruction { |
| 57 | /** | 57 | /** |
| 58 | * Signifies that the traffic should be modified in L3 way. | 58 | * Signifies that the traffic should be modified in L3 way. |
| 59 | */ | 59 | */ |
| 60 | - L3MODIFICATION | 60 | + L3MODIFICATION, |
| 61 | + | ||
| 62 | + /** | ||
| 63 | + * Signifies that metadata be attached to traffic. | ||
| 64 | + */ | ||
| 65 | + METADATA | ||
| 61 | } | 66 | } |
| 62 | 67 | ||
| 63 | /** | 68 | /** | ... | ... |
| ... | @@ -323,6 +323,17 @@ public final class Instructions { | ... | @@ -323,6 +323,17 @@ public final class Instructions { |
| 323 | } | 323 | } |
| 324 | 324 | ||
| 325 | /** | 325 | /** |
| 326 | + * Writes metadata to associate with a packet. | ||
| 327 | + * | ||
| 328 | + * @param metadata the metadata value to write | ||
| 329 | + * @param metadataMask the bits to mask for the metadata value | ||
| 330 | + * @return metadata instruction | ||
| 331 | + */ | ||
| 332 | + public static Instruction writeMetadata(long metadata, long metadataMask) { | ||
| 333 | + return new MetadataInstruction(metadata, metadataMask); | ||
| 334 | + } | ||
| 335 | + | ||
| 336 | + /** | ||
| 326 | * Drop instruction. | 337 | * Drop instruction. |
| 327 | */ | 338 | */ |
| 328 | public static final class DropInstruction implements Instruction { | 339 | public static final class DropInstruction implements Instruction { |
| ... | @@ -443,7 +454,9 @@ public final class Instructions { | ... | @@ -443,7 +454,9 @@ public final class Instructions { |
| 443 | } | 454 | } |
| 444 | } | 455 | } |
| 445 | 456 | ||
| 446 | - | 457 | + /** |
| 458 | + * Transition instruction. | ||
| 459 | + */ | ||
| 447 | public static class TableTypeTransition implements Instruction { | 460 | public static class TableTypeTransition implements Instruction { |
| 448 | private final Integer tableId; | 461 | private final Integer tableId; |
| 449 | 462 | ||
| ... | @@ -483,7 +496,59 @@ public final class Instructions { | ... | @@ -483,7 +496,59 @@ public final class Instructions { |
| 483 | } | 496 | } |
| 484 | return false; | 497 | return false; |
| 485 | } | 498 | } |
| 499 | + } | ||
| 500 | + | ||
| 501 | + /** | ||
| 502 | + * Metadata instruction. | ||
| 503 | + */ | ||
| 504 | + public static class MetadataInstruction implements Instruction { | ||
| 505 | + private final long metadata; | ||
| 506 | + private final long metadataMask; | ||
| 507 | + | ||
| 508 | + MetadataInstruction(long metadata, long metadataMask) { | ||
| 509 | + this.metadata = metadata; | ||
| 510 | + this.metadataMask = metadataMask; | ||
| 511 | + } | ||
| 512 | + | ||
| 513 | + @Override | ||
| 514 | + public Type type() { | ||
| 515 | + return Type.METADATA; | ||
| 516 | + } | ||
| 517 | + | ||
| 518 | + public long metadata() { | ||
| 519 | + return this.metadata; | ||
| 520 | + } | ||
| 486 | 521 | ||
| 522 | + public long metadataMask() { | ||
| 523 | + return this.metadataMask; | ||
| 524 | + } | ||
| 525 | + | ||
| 526 | + @Override | ||
| 527 | + public String toString() { | ||
| 528 | + return toStringHelper(type().toString()) | ||
| 529 | + .add("metadata", Long.toHexString(this.metadata)) | ||
| 530 | + .add("metadata mask", Long.toHexString(this.metadataMask)) | ||
| 531 | + .toString(); | ||
| 532 | + } | ||
| 533 | + | ||
| 534 | + @Override | ||
| 535 | + public int hashCode() { | ||
| 536 | + return Objects.hash(type(), metadata, metadataMask); | ||
| 537 | + } | ||
| 538 | + | ||
| 539 | + @Override | ||
| 540 | + public boolean equals(Object obj) { | ||
| 541 | + if (this == obj) { | ||
| 542 | + return true; | ||
| 543 | + } | ||
| 544 | + if (obj instanceof MetadataInstruction) { | ||
| 545 | + MetadataInstruction that = (MetadataInstruction) obj; | ||
| 546 | + return Objects.equals(metadata, that.metadata) && | ||
| 547 | + Objects.equals(metadataMask, that.metadataMask); | ||
| 548 | + | ||
| 549 | + } | ||
| 550 | + return false; | ||
| 551 | + } | ||
| 487 | } | 552 | } |
| 488 | } | 553 | } |
| 489 | 554 | ... | ... |
| ... | @@ -36,6 +36,7 @@ import org.onosproject.net.flow.criteria.Criterion; | ... | @@ -36,6 +36,7 @@ import org.onosproject.net.flow.criteria.Criterion; |
| 36 | import org.onosproject.net.flow.criteria.Criterion.Type; | 36 | import org.onosproject.net.flow.criteria.Criterion.Type; |
| 37 | import org.onosproject.net.flow.instructions.Instruction; | 37 | import org.onosproject.net.flow.instructions.Instruction; |
| 38 | import org.onosproject.net.flow.instructions.Instructions; | 38 | import org.onosproject.net.flow.instructions.Instructions; |
| 39 | +import org.onosproject.net.flow.instructions.Instructions.MetadataInstruction; | ||
| 39 | import org.onosproject.net.resource.link.BandwidthResource; | 40 | import org.onosproject.net.resource.link.BandwidthResource; |
| 40 | import org.onosproject.net.resource.link.BandwidthResourceRequest; | 41 | import org.onosproject.net.resource.link.BandwidthResourceRequest; |
| 41 | import org.onosproject.net.resource.link.LambdaResource; | 42 | import org.onosproject.net.resource.link.LambdaResource; |
| ... | @@ -118,6 +119,11 @@ public class IntentTestsMocks { | ... | @@ -118,6 +119,11 @@ public class IntentTestsMocks { |
| 118 | public boolean clearedDeferred() { | 119 | public boolean clearedDeferred() { |
| 119 | return false; | 120 | return false; |
| 120 | } | 121 | } |
| 122 | + | ||
| 123 | + @Override | ||
| 124 | + public MetadataInstruction writeMetadata() { | ||
| 125 | + return null; | ||
| 126 | + } | ||
| 121 | } | 127 | } |
| 122 | 128 | ||
| 123 | /** | 129 | /** | ... | ... |
| ... | @@ -21,6 +21,7 @@ import com.google.common.collect.Lists; | ... | @@ -21,6 +21,7 @@ import com.google.common.collect.Lists; |
| 21 | import com.google.common.collect.Sets; | 21 | import com.google.common.collect.Sets; |
| 22 | import com.google.common.util.concurrent.ListenableFuture; | 22 | import com.google.common.util.concurrent.ListenableFuture; |
| 23 | import com.google.common.util.concurrent.MoreExecutors; | 23 | import com.google.common.util.concurrent.MoreExecutors; |
| 24 | + | ||
| 24 | import org.junit.After; | 25 | import org.junit.After; |
| 25 | import org.junit.Before; | 26 | import org.junit.Before; |
| 26 | import org.junit.Test; | 27 | import org.junit.Test; |
| ... | @@ -58,6 +59,7 @@ import org.onosproject.net.flow.TrafficTreatment; | ... | @@ -58,6 +59,7 @@ import org.onosproject.net.flow.TrafficTreatment; |
| 58 | import org.onosproject.net.flow.criteria.Criterion; | 59 | import org.onosproject.net.flow.criteria.Criterion; |
| 59 | import org.onosproject.net.flow.instructions.Instruction; | 60 | import org.onosproject.net.flow.instructions.Instruction; |
| 60 | import org.onosproject.net.flow.instructions.Instructions; | 61 | import org.onosproject.net.flow.instructions.Instructions; |
| 62 | +import org.onosproject.net.flow.instructions.Instructions.MetadataInstruction; | ||
| 61 | import org.onosproject.net.provider.AbstractProvider; | 63 | import org.onosproject.net.provider.AbstractProvider; |
| 62 | import org.onosproject.net.provider.ProviderId; | 64 | import org.onosproject.net.provider.ProviderId; |
| 63 | import org.onosproject.store.trivial.impl.SimpleFlowRuleStore; | 65 | import org.onosproject.store.trivial.impl.SimpleFlowRuleStore; |
| ... | @@ -595,6 +597,11 @@ public class FlowRuleManagerTest { | ... | @@ -595,6 +597,11 @@ public class FlowRuleManagerTest { |
| 595 | return false; | 597 | return false; |
| 596 | } | 598 | } |
| 597 | 599 | ||
| 600 | + @Override | ||
| 601 | + public MetadataInstruction writeMetadata() { | ||
| 602 | + return null; | ||
| 603 | + } | ||
| 604 | + | ||
| 598 | } | 605 | } |
| 599 | 606 | ||
| 600 | public class TestApplicationId extends DefaultApplicationId { | 607 | public class TestApplicationId extends DefaultApplicationId { | ... | ... |
| ... | @@ -78,6 +78,7 @@ public class CentecV350Pipeline extends AbstractHandlerBehaviour implements Pipe | ... | @@ -78,6 +78,7 @@ public class CentecV350Pipeline extends AbstractHandlerBehaviour implements Pipe |
| 78 | protected static final int ROUTE_TABLE = 3; | 78 | protected static final int ROUTE_TABLE = 3; |
| 79 | 79 | ||
| 80 | private static final long DEFAULT_METADATA = 100; | 80 | private static final long DEFAULT_METADATA = 100; |
| 81 | + private static final long DEFAULT_METADATA_MASK = 0xff; | ||
| 81 | 82 | ||
| 82 | // Priority used in PORT_VLAN Table, the only priority accepted is PORT_VLAN_TABLE_PRIORITY. | 83 | // Priority used in PORT_VLAN Table, the only priority accepted is PORT_VLAN_TABLE_PRIORITY. |
| 83 | // The packet passed PORT+VLAN check will goto FILTER Table. | 84 | // The packet passed PORT+VLAN check will goto FILTER Table. |
| ... | @@ -408,10 +409,10 @@ public class CentecV350Pipeline extends AbstractHandlerBehaviour implements Pipe | ... | @@ -408,10 +409,10 @@ public class CentecV350Pipeline extends AbstractHandlerBehaviour implements Pipe |
| 408 | selector.matchInPort(p.port()); | 409 | selector.matchInPort(p.port()); |
| 409 | // Although the accepted packets will be sent to filter table, we must | 410 | // Although the accepted packets will be sent to filter table, we must |
| 410 | // explicitly set goto_table instruction here. | 411 | // explicitly set goto_table instruction here. |
| 412 | + treatment.writeMetadata(DEFAULT_METADATA, DEFAULT_METADATA_MASK); | ||
| 413 | + // set default metadata written by PORT_VLAN Table. | ||
| 411 | treatment.transition(FILTER_TABLE); | 414 | treatment.transition(FILTER_TABLE); |
| 412 | // We do not support strip vlan here, treatment.deferred().popVlan(); | 415 | // We do not support strip vlan here, treatment.deferred().popVlan(); |
| 413 | - // XXX: write_metadata seems not supported by ONOS now, use the switch CLI to | ||
| 414 | - // set default metadata written by PORT_VLAN Table. | ||
| 415 | // PORT_VLAN table only accept 0xffff priority since it does exact match only. | 416 | // PORT_VLAN table only accept 0xffff priority since it does exact match only. |
| 416 | FlowRule rule = DefaultFlowRule.builder() | 417 | FlowRule rule = DefaultFlowRule.builder() |
| 417 | .forDevice(deviceId) | 418 | .forDevice(deviceId) | ... | ... |
| ... | @@ -16,6 +16,7 @@ | ... | @@ -16,6 +16,7 @@ |
| 16 | package org.onosproject.provider.of.flow.impl; | 16 | package org.onosproject.provider.of.flow.impl; |
| 17 | 17 | ||
| 18 | import com.google.common.collect.Lists; | 18 | import com.google.common.collect.Lists; |
| 19 | + | ||
| 19 | import org.onlab.packet.Ip4Address; | 20 | import org.onlab.packet.Ip4Address; |
| 20 | import org.onlab.packet.Ip4Prefix; | 21 | import org.onlab.packet.Ip4Prefix; |
| 21 | import org.onlab.packet.Ip6Address; | 22 | import org.onlab.packet.Ip6Address; |
| ... | @@ -56,6 +57,7 @@ import org.projectfloodlight.openflow.protocol.instruction.OFInstruction; | ... | @@ -56,6 +57,7 @@ import org.projectfloodlight.openflow.protocol.instruction.OFInstruction; |
| 56 | import org.projectfloodlight.openflow.protocol.instruction.OFInstructionApplyActions; | 57 | import org.projectfloodlight.openflow.protocol.instruction.OFInstructionApplyActions; |
| 57 | import org.projectfloodlight.openflow.protocol.instruction.OFInstructionGotoTable; | 58 | import org.projectfloodlight.openflow.protocol.instruction.OFInstructionGotoTable; |
| 58 | import org.projectfloodlight.openflow.protocol.instruction.OFInstructionWriteActions; | 59 | import org.projectfloodlight.openflow.protocol.instruction.OFInstructionWriteActions; |
| 60 | +import org.projectfloodlight.openflow.protocol.instruction.OFInstructionWriteMetadata; | ||
| 59 | import org.projectfloodlight.openflow.protocol.match.Match; | 61 | import org.projectfloodlight.openflow.protocol.match.Match; |
| 60 | import org.projectfloodlight.openflow.protocol.match.MatchField; | 62 | import org.projectfloodlight.openflow.protocol.match.MatchField; |
| 61 | import org.projectfloodlight.openflow.protocol.oxm.OFOxm; | 63 | import org.projectfloodlight.openflow.protocol.oxm.OFOxm; |
| ... | @@ -219,6 +221,9 @@ public class FlowEntryBuilder { | ... | @@ -219,6 +221,9 @@ public class FlowEntryBuilder { |
| 219 | .getTableId().getValue())); | 221 | .getTableId().getValue())); |
| 220 | break; | 222 | break; |
| 221 | case WRITE_METADATA: | 223 | case WRITE_METADATA: |
| 224 | + OFInstructionWriteMetadata m = (OFInstructionWriteMetadata) in; | ||
| 225 | + builder.writeMetadata(m.getMetadata().getValue(), | ||
| 226 | + m.getMetadataMask().getValue()); | ||
| 222 | break; | 227 | break; |
| 223 | case WRITE_ACTIONS: | 228 | case WRITE_ACTIONS: |
| 224 | builder.deferred(); | 229 | builder.deferred(); | ... | ... |
providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowModBuilderVer10.java
| ... | @@ -167,6 +167,8 @@ public class FlowModBuilderVer10 extends FlowModBuilder { | ... | @@ -167,6 +167,8 @@ public class FlowModBuilderVer10 extends FlowModBuilder { |
| 167 | break; | 167 | break; |
| 168 | case L0MODIFICATION: | 168 | case L0MODIFICATION: |
| 169 | case GROUP: | 169 | case GROUP: |
| 170 | + case TABLE: | ||
| 171 | + case METADATA: | ||
| 170 | log.warn("Instruction type {} not supported with protocol version {}", | 172 | log.warn("Instruction type {} not supported with protocol version {}", |
| 171 | i.type(), factory().getVersion()); | 173 | i.type(), factory().getVersion()); |
| 172 | break; | 174 | break; | ... | ... |
providers/openflow/flow/src/main/java/org/onosproject/provider/of/flow/impl/FlowModBuilderVer13.java
| ... | @@ -117,6 +117,9 @@ public class FlowModBuilderVer13 extends FlowModBuilder { | ... | @@ -117,6 +117,9 @@ public class FlowModBuilderVer13 extends FlowModBuilder { |
| 117 | if (treatment.tableTransition() != null) { | 117 | if (treatment.tableTransition() != null) { |
| 118 | instructions.add(buildTableGoto(treatment.tableTransition())); | 118 | instructions.add(buildTableGoto(treatment.tableTransition())); |
| 119 | } | 119 | } |
| 120 | + if (treatment.writeMetadata() != null) { | ||
| 121 | + instructions.add(buildMetadata(treatment.writeMetadata())); | ||
| 122 | + } | ||
| 120 | 123 | ||
| 121 | long cookie = flowRule().id().value(); | 124 | long cookie = flowRule().id().value(); |
| 122 | 125 | ||
| ... | @@ -154,6 +157,9 @@ public class FlowModBuilderVer13 extends FlowModBuilder { | ... | @@ -154,6 +157,9 @@ public class FlowModBuilderVer13 extends FlowModBuilder { |
| 154 | if (treatment.tableTransition() != null) { | 157 | if (treatment.tableTransition() != null) { |
| 155 | instructions.add(buildTableGoto(treatment.tableTransition())); | 158 | instructions.add(buildTableGoto(treatment.tableTransition())); |
| 156 | } | 159 | } |
| 160 | + if (treatment.writeMetadata() != null) { | ||
| 161 | + instructions.add(buildMetadata(treatment.writeMetadata())); | ||
| 162 | + } | ||
| 157 | 163 | ||
| 158 | long cookie = flowRule().id().value(); | 164 | long cookie = flowRule().id().value(); |
| 159 | 165 | ||
| ... | @@ -247,6 +253,12 @@ public class FlowModBuilderVer13 extends FlowModBuilder { | ... | @@ -247,6 +253,12 @@ public class FlowModBuilderVer13 extends FlowModBuilder { |
| 247 | return instruction; | 253 | return instruction; |
| 248 | } | 254 | } |
| 249 | 255 | ||
| 256 | + private OFInstruction buildMetadata(Instructions.MetadataInstruction m) { | ||
| 257 | + OFInstruction instruction = factory().instructions().writeMetadata( | ||
| 258 | + U64.of(m.metadata()), U64.of(m.metadataMask())); | ||
| 259 | + return instruction; | ||
| 260 | + } | ||
| 261 | + | ||
| 250 | private OFAction buildL0Modification(Instruction i) { | 262 | private OFAction buildL0Modification(Instruction i) { |
| 251 | L0ModificationInstruction l0m = (L0ModificationInstruction) i; | 263 | L0ModificationInstruction l0m = (L0ModificationInstruction) i; |
| 252 | switch (l0m.subtype()) { | 264 | switch (l0m.subtype()) { | ... | ... |
-
Please register or login to post a comment