Jonathan Hart

Unit test for Kryo namespaces to prevent people overflowing the namespaces.

Change-Id: If37283da60d59558c87e2997690b4578952ad3bf
...@@ -234,6 +234,7 @@ import java.util.concurrent.atomic.AtomicLong; ...@@ -234,6 +234,7 @@ import java.util.concurrent.atomic.AtomicLong;
234 234
235 public final class KryoNamespaces { 235 public final class KryoNamespaces {
236 236
237 + public static final int BASIC_MAX_SIZE = 50;
237 public static final KryoNamespace BASIC = KryoNamespace.newBuilder() 238 public static final KryoNamespace BASIC = KryoNamespace.newBuilder()
238 .nextId(KryoNamespace.FLOATING_ID) 239 .nextId(KryoNamespace.FLOATING_ID)
239 .register(byte[].class) 240 .register(byte[].class)
...@@ -284,6 +285,7 @@ public final class KryoNamespaces { ...@@ -284,6 +285,7 @@ public final class KryoNamespaces {
284 /** 285 /**
285 * KryoNamespace which can serialize ON.lab misc classes. 286 * KryoNamespace which can serialize ON.lab misc classes.
286 */ 287 */
288 + public static final int MISC_MAX_SIZE = 30;
287 public static final KryoNamespace MISC = KryoNamespace.newBuilder() 289 public static final KryoNamespace MISC = KryoNamespace.newBuilder()
288 .nextId(KryoNamespace.FLOATING_ID) 290 .nextId(KryoNamespace.FLOATING_ID)
289 .register(new IpPrefixSerializer(), IpPrefix.class) 291 .register(new IpPrefixSerializer(), IpPrefix.class)
...@@ -302,20 +304,15 @@ public final class KryoNamespaces { ...@@ -302,20 +304,15 @@ public final class KryoNamespaces {
302 .build("MISC"); 304 .build("MISC");
303 305
304 /** 306 /**
305 - * Kryo registration Id for user custom registration.
306 - */
307 - public static final int BEGIN_USER_CUSTOM_ID = 500;
308 -
309 - // TODO: Populate other classes
310 - /**
311 * KryoNamespace which can serialize API bundle classes. 307 * KryoNamespace which can serialize API bundle classes.
312 */ 308 */
309 + public static final int API_MAX_SIZE = 499;
313 public static final KryoNamespace API = KryoNamespace.newBuilder() 310 public static final KryoNamespace API = KryoNamespace.newBuilder()
314 .nextId(KryoNamespace.INITIAL_ID) 311 .nextId(KryoNamespace.INITIAL_ID)
315 .register(BASIC) 312 .register(BASIC)
316 - .nextId(KryoNamespace.INITIAL_ID + 50) 313 + .nextId(KryoNamespace.INITIAL_ID + BASIC_MAX_SIZE)
317 .register(MISC) 314 .register(MISC)
318 - .nextId(KryoNamespace.INITIAL_ID + 50 + 30) 315 + .nextId(KryoNamespace.INITIAL_ID + BASIC_MAX_SIZE + MISC_MAX_SIZE)
319 .register( 316 .register(
320 Instructions.MeterInstruction.class, 317 Instructions.MeterInstruction.class,
321 MeterId.class, 318 MeterId.class,
...@@ -552,6 +549,10 @@ public final class KryoNamespaces { ...@@ -552,6 +549,10 @@ public final class KryoNamespaces {
552 .register(new ImmutableByteSequenceSerializer(), ImmutableByteSequence.class) 549 .register(new ImmutableByteSequenceSerializer(), ImmutableByteSequence.class)
553 .build("API"); 550 .build("API");
554 551
552 + /**
553 + * Kryo registration Id for user custom registration.
554 + */
555 + public static final int BEGIN_USER_CUSTOM_ID = API_MAX_SIZE + 1;
555 556
556 // not to be instantiated 557 // not to be instantiated
557 private KryoNamespaces() { 558 private KryoNamespaces() {
......
1 +package org.onosproject.store.serializers;
2 +
3 +import org.junit.Test;
4 +import org.onlab.util.KryoNamespace;
5 +
6 +import static org.junit.Assert.assertTrue;
7 +
8 +/**
9 + * Tests pre-defined Kryo namespaces to catch basic errors such as someone
10 + * adding too many registrations which may flow into another namespace.
11 + */
12 +public class KryoNamespacesTest {
13 +
14 + /**
15 + * Verifies that the BASIC namespace has not exceeded its allocated size.
16 + */
17 + @Test
18 + public void basicNamespaceSizeTest() {
19 + testNamespaceSize(KryoNamespaces.BASIC, KryoNamespaces.BASIC_MAX_SIZE);
20 + }
21 +
22 + /**
23 + * Verifies that the MISC namespace has not exceeded its allocated size.
24 + */
25 + @Test
26 + public void miscNamespaceSizeTest() {
27 + testNamespaceSize(KryoNamespaces.MISC, KryoNamespaces.MISC_MAX_SIZE);
28 + }
29 +
30 + /**
31 + * Verifies that the API namespace has not exceeded its allocated size.
32 + */
33 + @Test
34 + public void apiNamespaceSizeTest() {
35 + testNamespaceSize(KryoNamespaces.API, KryoNamespaces.API_MAX_SIZE);
36 + }
37 +
38 + private void testNamespaceSize(KryoNamespace namespace, int maxSize) {
39 + assertTrue("Kryo namespace has exceeded its allocated size",
40 + namespace.size() < maxSize);
41 + }
42 +}
...@@ -79,7 +79,6 @@ public final class KryoNamespace implements KryoFactory, KryoPool { ...@@ -79,7 +79,6 @@ public final class KryoNamespace implements KryoFactory, KryoPool {
79 private final boolean registrationRequired; 79 private final boolean registrationRequired;
80 private final String friendlyName; 80 private final String friendlyName;
81 81
82 -
83 /** 82 /**
84 * KryoNamespace builder. 83 * KryoNamespace builder.
85 */ 84 */
...@@ -406,6 +405,17 @@ public final class KryoNamespace implements KryoFactory, KryoPool { ...@@ -406,6 +405,17 @@ public final class KryoNamespace implements KryoFactory, KryoPool {
406 } 405 }
407 406
408 /** 407 /**
408 + * Gets the number of classes registered in this Kryo namespace.
409 + *
410 + * @return size of namespace
411 + */
412 + public int size() {
413 + return (int) registeredBlocks.stream()
414 + .flatMap(block -> block.types().stream())
415 + .count();
416 + }
417 +
418 + /**
409 * Creates a Kryo instance. 419 * Creates a Kryo instance.
410 * 420 *
411 * @return Kryo instance 421 * @return Kryo instance
......