2 * Copyright © 2020 Google, Inc.
4 * This is part of HarfBuzz, a text shaping library.
6 * Permission is hereby granted, without written agreement and without
7 * license or royalty fees, to use, copy, modify, and distribute this
8 * software and its documentation for any purpose, provided that the
9 * above copyright notice and the following two paragraphs appear in
10 * all copies of this software.
12 * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
13 * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
14 * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
15 * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
18 * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
19 * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
20 * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
21 * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
22 * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
24 * Google Author(s): Garret Rieger
29 #include "hb-repacker.hh"
30 #include "hb-open-type.hh"
32 static void start_object(const char* tag,
34 hb_serialize_context_t* c)
37 char* obj = c->allocate_size<char> (len);
38 strncpy (obj, tag, len);
42 static unsigned add_object(const char* tag,
44 hb_serialize_context_t* c)
46 start_object (tag, len, c);
47 return c->pop_pack (false);
51 static void add_offset (unsigned id,
52 hb_serialize_context_t* c)
54 OT::Offset16* offset = c->start_embed<OT::Offset16> ();
55 c->extend_min (offset);
56 c->add_link (*offset, id);
59 static void add_wide_offset (unsigned id,
60 hb_serialize_context_t* c)
62 OT::Offset32* offset = c->start_embed<OT::Offset32> ();
63 c->extend_min (offset);
64 c->add_link (*offset, id);
67 static void run_resolve_overflow_test (const char* name,
68 hb_serialize_context_t& overflowing,
69 hb_serialize_context_t& expected,
70 unsigned num_iterations = 0)
72 printf (">>> Testing overflowing resolution for %s\n",
75 graph_t graph (overflowing.object_graph ());
78 assert (overflowing.offset_overflow ());
79 hb_blob_t* out = hb_resolve_overflows (overflowing.object_graph (),
80 HB_TAG ('G', 'S', 'U', 'B'), num_iterations);
83 hb_bytes_t result = out->as_bytes ();
85 assert (!expected.offset_overflow ());
86 hb_bytes_t expected_result = expected.copy_bytes ();
88 assert (result.length == expected_result.length);
89 for (unsigned i = 0; i < expected_result.length; i++)
91 assert (result[i] == expected_result[i]);
94 expected_result.fini ();
95 hb_blob_destroy (out);
98 static void add_virtual_offset (unsigned id,
99 hb_serialize_context_t* c)
101 c->add_virtual_link (id);
105 populate_serializer_simple (hb_serialize_context_t* c)
107 c->start_serialize<char> ();
109 unsigned obj_1 = add_object ("ghi", 3, c);
110 unsigned obj_2 = add_object ("def", 3, c);
112 start_object ("abc", 3, c);
113 add_offset (obj_2, c);
114 add_offset (obj_1, c);
121 populate_serializer_with_overflow (hb_serialize_context_t* c)
123 std::string large_string(50000, 'a');
124 c->start_serialize<char> ();
126 unsigned obj_1 = add_object (large_string.c_str(), 10000, c);
127 unsigned obj_2 = add_object (large_string.c_str(), 20000, c);
128 unsigned obj_3 = add_object (large_string.c_str(), 50000, c);
130 start_object ("abc", 3, c);
131 add_offset (obj_3, c);
132 add_offset (obj_2, c);
133 add_offset (obj_1, c);
140 populate_serializer_with_priority_overflow (hb_serialize_context_t* c)
142 std::string large_string(50000, 'a');
143 c->start_serialize<char> ();
145 unsigned obj_e = add_object ("e", 1, c);
146 unsigned obj_d = add_object ("d", 1, c);
148 start_object (large_string.c_str (), 50000, c);
149 add_offset (obj_e, c);
150 unsigned obj_c = c->pop_pack (false);
152 start_object (large_string.c_str (), 20000, c);
153 add_offset (obj_d, c);
154 unsigned obj_b = c->pop_pack (false);
156 start_object ("a", 1, c);
157 add_offset (obj_b, c);
158 add_offset (obj_c, c);
165 populate_serializer_with_priority_overflow_expected (hb_serialize_context_t* c)
167 std::string large_string(50000, 'a');
168 c->start_serialize<char> ();
170 unsigned obj_e = add_object ("e", 1, c);
172 start_object (large_string.c_str (), 50000, c);
173 add_offset (obj_e, c);
174 unsigned obj_c = c->pop_pack (false);
176 unsigned obj_d = add_object ("d", 1, c);
178 start_object (large_string.c_str (), 20000, c);
179 add_offset (obj_d, c);
180 unsigned obj_b = c->pop_pack (false);
182 start_object ("a", 1, c);
183 add_offset (obj_b, c);
184 add_offset (obj_c, c);
192 populate_serializer_with_dedup_overflow (hb_serialize_context_t* c)
194 std::string large_string(70000, 'a');
195 c->start_serialize<char> ();
197 unsigned obj_1 = add_object ("def", 3, c);
199 start_object (large_string.c_str(), 60000, c);
200 add_offset (obj_1, c);
201 unsigned obj_2 = c->pop_pack (false);
203 start_object (large_string.c_str(), 10000, c);
204 add_offset (obj_2, c);
205 add_offset (obj_1, c);
212 populate_serializer_with_isolation_overflow (hb_serialize_context_t* c)
214 std::string large_string(70000, 'a');
215 c->start_serialize<char> ();
217 unsigned obj_4 = add_object ("4", 1, c);
219 start_object (large_string.c_str(), 60000, c);
220 add_offset (obj_4, c);
221 unsigned obj_3 = c->pop_pack (false);
223 start_object (large_string.c_str(), 10000, c);
224 add_offset (obj_4, c);
225 unsigned obj_2 = c->pop_pack (false);
227 start_object ("1", 1, c);
228 add_wide_offset (obj_3, c);
229 add_offset (obj_2, c);
236 populate_serializer_with_isolation_overflow_complex (hb_serialize_context_t* c)
238 std::string large_string(70000, 'a');
239 c->start_serialize<char> ();
241 unsigned obj_f = add_object ("f", 1, c);
243 start_object ("e", 1, c);
244 add_offset (obj_f, c);
245 unsigned obj_e = c->pop_pack (false);
247 start_object ("c", 1, c);
248 add_offset (obj_e, c);
249 unsigned obj_c = c->pop_pack (false);
251 start_object ("d", 1, c);
252 add_offset (obj_e, c);
253 unsigned obj_d = c->pop_pack (false);
255 start_object (large_string.c_str(), 60000, c);
256 add_offset (obj_d, c);
257 unsigned obj_h = c->pop_pack (false);
259 start_object (large_string.c_str(), 60000, c);
260 add_offset (obj_c, c);
261 add_offset (obj_h, c);
262 unsigned obj_b = c->pop_pack (false);
264 start_object (large_string.c_str(), 10000, c);
265 add_offset (obj_d, c);
266 unsigned obj_g = c->pop_pack (false);
268 start_object (large_string.c_str(), 11000, c);
269 add_offset (obj_d, c);
270 unsigned obj_i = c->pop_pack (false);
272 start_object ("a", 1, c);
273 add_wide_offset (obj_b, c);
274 add_offset (obj_g, c);
275 add_offset (obj_i, c);
282 populate_serializer_with_isolation_overflow_complex_expected (hb_serialize_context_t* c)
284 std::string large_string(70000, 'a');
285 c->start_serialize<char> ();
290 unsigned obj_f_prime = add_object ("f", 1, c);
292 start_object ("e", 1, c);
293 add_offset (obj_f_prime, c);
294 unsigned obj_e_prime = c->pop_pack (false);
296 start_object ("d", 1, c);
297 add_offset (obj_e_prime, c);
298 unsigned obj_d_prime = c->pop_pack (false);
300 start_object (large_string.c_str(), 60000, c);
301 add_offset (obj_d_prime, c);
302 unsigned obj_h = c->pop_pack (false);
304 start_object ("c", 1, c);
305 add_offset (obj_e_prime, c);
306 unsigned obj_c = c->pop_pack (false);
308 start_object (large_string.c_str(), 60000, c);
309 add_offset (obj_c, c);
310 add_offset (obj_h, c);
311 unsigned obj_b = c->pop_pack (false);
315 unsigned obj_f = add_object ("f", 1, c);
317 start_object ("e", 1, c);
318 add_offset (obj_f, c);
319 unsigned obj_e = c->pop_pack (false);
322 start_object ("d", 1, c);
323 add_offset (obj_e, c);
324 unsigned obj_d = c->pop_pack (false);
326 start_object (large_string.c_str(), 11000, c);
327 add_offset (obj_d, c);
328 unsigned obj_i = c->pop_pack (false);
330 start_object (large_string.c_str(), 10000, c);
331 add_offset (obj_d, c);
332 unsigned obj_g = c->pop_pack (false);
334 start_object ("a", 1, c);
335 add_wide_offset (obj_b, c);
336 add_offset (obj_g, c);
337 add_offset (obj_i, c);
344 populate_serializer_with_isolation_overflow_spaces (hb_serialize_context_t* c)
346 std::string large_string(70000, 'a');
347 c->start_serialize<char> ();
349 unsigned obj_d = add_object ("f", 1, c);
350 unsigned obj_e = add_object ("f", 1, c);
352 start_object (large_string.c_str(), 60000, c);
353 add_offset (obj_d, c);
354 unsigned obj_b = c->pop_pack ();
356 start_object (large_string.c_str(), 60000, c);
357 add_offset (obj_e, c);
358 unsigned obj_c = c->pop_pack ();
361 start_object ("a", 1, c);
362 add_wide_offset (obj_b, c);
363 add_wide_offset (obj_c, c);
370 populate_serializer_spaces (hb_serialize_context_t* c, bool with_overflow)
372 std::string large_string(70000, 'a');
373 c->start_serialize<char> ();
378 obj_i = add_object ("i", 1, c);
381 unsigned obj_h = add_object ("h", 1, c);
383 start_object (large_string.c_str(), 30000, c);
384 add_offset (obj_h, c);
385 unsigned obj_e = c->pop_pack (false);
387 start_object ("b", 1, c);
388 add_offset (obj_e, c);
389 unsigned obj_b = c->pop_pack (false);
393 obj_i = add_object ("i", 1, c);
395 start_object (large_string.c_str(), 30000, c);
396 add_offset (obj_i, c);
397 unsigned obj_g = c->pop_pack (false);
399 start_object (large_string.c_str(), 30000, c);
400 add_offset (obj_i, c);
401 unsigned obj_f = c->pop_pack (false);
403 start_object ("d", 1, c);
404 add_offset (obj_g, c);
405 unsigned obj_d = c->pop_pack (false);
407 start_object ("c", 1, c);
408 add_offset (obj_f, c);
409 unsigned obj_c = c->pop_pack (false);
411 start_object ("a", 1, c);
412 add_wide_offset (obj_b, c);
413 add_wide_offset (obj_c, c);
414 add_wide_offset (obj_d, c);
421 populate_serializer_spaces_16bit_connection (hb_serialize_context_t* c)
423 std::string large_string(70000, 'a');
424 c->start_serialize<char> ();
426 unsigned obj_g = add_object ("g", 1, c);
427 unsigned obj_h = add_object ("h", 1, c);
429 start_object (large_string.c_str (), 40000, c);
430 add_offset (obj_g, c);
431 unsigned obj_e = c->pop_pack (false);
433 start_object (large_string.c_str (), 40000, c);
434 add_offset (obj_h, c);
435 unsigned obj_f = c->pop_pack (false);
437 start_object ("c", 1, c);
438 add_offset (obj_e, c);
439 unsigned obj_c = c->pop_pack (false);
441 start_object ("d", 1, c);
442 add_offset (obj_f, c);
443 unsigned obj_d = c->pop_pack (false);
445 start_object ("b", 1, c);
446 add_offset (obj_e, c);
447 add_offset (obj_h, c);
448 unsigned obj_b = c->pop_pack (false);
450 start_object ("a", 1, c);
451 add_offset (obj_b, c);
452 add_wide_offset (obj_c, c);
453 add_wide_offset (obj_d, c);
460 populate_serializer_spaces_16bit_connection_expected (hb_serialize_context_t* c)
462 std::string large_string(70000, 'a');
463 c->start_serialize<char> ();
465 unsigned obj_g_prime = add_object ("g", 1, c);
467 start_object (large_string.c_str (), 40000, c);
468 add_offset (obj_g_prime, c);
469 unsigned obj_e_prime = c->pop_pack (false);
471 start_object ("c", 1, c);
472 add_offset (obj_e_prime, c);
473 unsigned obj_c = c->pop_pack (false);
475 unsigned obj_h_prime = add_object ("h", 1, c);
477 start_object (large_string.c_str (), 40000, c);
478 add_offset (obj_h_prime, c);
479 unsigned obj_f = c->pop_pack (false);
481 start_object ("d", 1, c);
482 add_offset (obj_f, c);
483 unsigned obj_d = c->pop_pack (false);
485 unsigned obj_g = add_object ("g", 1, c);
487 start_object (large_string.c_str (), 40000, c);
488 add_offset (obj_g, c);
489 unsigned obj_e = c->pop_pack (false);
491 unsigned obj_h = add_object ("h", 1, c);
493 start_object ("b", 1, c);
494 add_offset (obj_e, c);
495 add_offset (obj_h, c);
496 unsigned obj_b = c->pop_pack (false);
498 start_object ("a", 1, c);
499 add_offset (obj_b, c);
500 add_wide_offset (obj_c, c);
501 add_wide_offset (obj_d, c);
508 populate_serializer_short_and_wide_subgraph_root (hb_serialize_context_t* c)
510 std::string large_string(70000, 'a');
511 c->start_serialize<char> ();
513 unsigned obj_e = add_object ("e", 1, c);
515 start_object (large_string.c_str (), 40000, c);
516 add_offset (obj_e, c);
517 unsigned obj_c = c->pop_pack (false);
519 start_object (large_string.c_str (), 40000, c);
520 add_offset (obj_c, c);
521 unsigned obj_d = c->pop_pack (false);
523 start_object ("b", 1, c);
524 add_offset (obj_c, c);
525 add_offset (obj_e, c);
526 unsigned obj_b = c->pop_pack (false);
528 start_object ("a", 1, c);
529 add_offset (obj_b, c);
530 add_wide_offset (obj_c, c);
531 add_wide_offset (obj_d, c);
538 populate_serializer_short_and_wide_subgraph_root_expected (hb_serialize_context_t* c)
540 std::string large_string(70000, 'a');
541 c->start_serialize<char> ();
543 unsigned obj_e_prime = add_object ("e", 1, c);
545 start_object (large_string.c_str (), 40000, c);
546 add_offset (obj_e_prime, c);
547 unsigned obj_c_prime = c->pop_pack (false);
549 start_object (large_string.c_str (), 40000, c);
550 add_offset (obj_c_prime, c);
551 unsigned obj_d = c->pop_pack (false);
553 unsigned obj_e = add_object ("e", 1, c);
555 start_object (large_string.c_str (), 40000, c);
556 add_offset (obj_e, c);
557 unsigned obj_c = c->pop_pack (false);
560 start_object ("b", 1, c);
561 add_offset (obj_c, c);
562 add_offset (obj_e, c);
563 unsigned obj_b = c->pop_pack (false);
565 start_object ("a", 1, c);
566 add_offset (obj_b, c);
567 add_wide_offset (obj_c_prime, c);
568 add_wide_offset (obj_d, c);
575 populate_serializer_with_split_spaces (hb_serialize_context_t* c)
577 // Overflow needs to be resolved by splitting the single space
578 std::string large_string(70000, 'a');
579 c->start_serialize<char> ();
581 unsigned obj_f = add_object ("f", 1, c);
583 start_object (large_string.c_str(), 40000, c);
584 add_offset (obj_f, c);
585 unsigned obj_d = c->pop_pack (false);
587 start_object (large_string.c_str(), 40000, c);
588 add_offset (obj_f, c);
589 unsigned obj_e = c->pop_pack (false);
591 start_object ("b", 1, c);
592 add_offset (obj_d, c);
593 unsigned obj_b = c->pop_pack (false);
595 start_object ("c", 1, c);
596 add_offset (obj_e, c);
597 unsigned obj_c = c->pop_pack (false);
599 start_object ("a", 1, c);
600 add_wide_offset (obj_b, c);
601 add_wide_offset (obj_c, c);
608 populate_serializer_with_split_spaces_2 (hb_serialize_context_t* c)
610 // Overflow needs to be resolved by splitting the single space
611 std::string large_string(70000, 'a');
612 c->start_serialize<char> ();
614 unsigned obj_f = add_object ("f", 1, c);
616 start_object (large_string.c_str(), 40000, c);
617 add_offset (obj_f, c);
618 unsigned obj_d = c->pop_pack (false);
620 start_object (large_string.c_str(), 40000, c);
621 add_offset (obj_f, c);
622 unsigned obj_e = c->pop_pack (false);
624 start_object ("b", 1, c);
625 add_offset (obj_d, c);
626 unsigned obj_b = c->pop_pack (false);
628 start_object ("c", 1, c);
629 add_offset (obj_e, c);
630 unsigned obj_c = c->pop_pack (false);
632 start_object ("a", 1, c);
633 add_offset (obj_b, c);
634 add_wide_offset (obj_b, c);
635 add_wide_offset (obj_c, c);
642 populate_serializer_with_split_spaces_expected (hb_serialize_context_t* c)
644 // Overflow needs to be resolved by splitting the single space
646 std::string large_string(70000, 'a');
647 c->start_serialize<char> ();
649 unsigned obj_f_prime = add_object ("f", 1, c);
651 start_object (large_string.c_str(), 40000, c);
652 add_offset (obj_f_prime, c);
653 unsigned obj_d = c->pop_pack (false);
655 start_object ("b", 1, c);
656 add_offset (obj_d, c);
657 unsigned obj_b = c->pop_pack (false);
659 unsigned obj_f = add_object ("f", 1, c);
661 start_object (large_string.c_str(), 40000, c);
662 add_offset (obj_f, c);
663 unsigned obj_e = c->pop_pack (false);
665 start_object ("c", 1, c);
666 add_offset (obj_e, c);
667 unsigned obj_c = c->pop_pack (false);
669 start_object ("a", 1, c);
670 add_wide_offset (obj_b, c);
671 add_wide_offset (obj_c, c);
678 populate_serializer_with_split_spaces_expected_2 (hb_serialize_context_t* c)
680 // Overflow needs to be resolved by splitting the single space
682 std::string large_string(70000, 'a');
683 c->start_serialize<char> ();
687 unsigned obj_f_double_prime = add_object ("f", 1, c);
689 start_object (large_string.c_str(), 40000, c);
690 add_offset (obj_f_double_prime, c);
691 unsigned obj_d_prime = c->pop_pack (false);
693 start_object ("b", 1, c);
694 add_offset (obj_d_prime, c);
695 unsigned obj_b_prime = c->pop_pack (false);
699 unsigned obj_f_prime = add_object ("f", 1, c);
701 start_object (large_string.c_str(), 40000, c);
702 add_offset (obj_f_prime, c);
703 unsigned obj_e = c->pop_pack (false);
705 start_object ("c", 1, c);
706 add_offset (obj_e, c);
707 unsigned obj_c = c->pop_pack (false);
711 unsigned obj_f = add_object ("f", 1, c);
713 start_object (large_string.c_str(), 40000, c);
714 add_offset (obj_f, c);
715 unsigned obj_d = c->pop_pack (false);
717 start_object ("b", 1, c);
718 add_offset (obj_d, c);
719 unsigned obj_b = c->pop_pack (false);
722 start_object ("a", 1, c);
723 add_offset (obj_b, c);
724 add_wide_offset (obj_b_prime, c);
725 add_wide_offset (obj_c, c);
732 populate_serializer_complex_1 (hb_serialize_context_t* c)
734 c->start_serialize<char> ();
736 unsigned obj_4 = add_object ("jkl", 3, c);
737 unsigned obj_3 = add_object ("ghi", 3, c);
739 start_object ("def", 3, c);
740 add_offset (obj_3, c);
741 unsigned obj_2 = c->pop_pack (false);
743 start_object ("abc", 3, c);
744 add_offset (obj_2, c);
745 add_offset (obj_4, c);
752 populate_serializer_complex_2 (hb_serialize_context_t* c)
754 c->start_serialize<char> ();
756 unsigned obj_5 = add_object ("mn", 2, c);
758 unsigned obj_4 = add_object ("jkl", 3, c);
760 start_object ("ghi", 3, c);
761 add_offset (obj_4, c);
762 unsigned obj_3 = c->pop_pack (false);
764 start_object ("def", 3, c);
765 add_offset (obj_3, c);
766 unsigned obj_2 = c->pop_pack (false);
768 start_object ("abc", 3, c);
769 add_offset (obj_2, c);
770 add_offset (obj_4, c);
771 add_offset (obj_5, c);
778 populate_serializer_complex_3 (hb_serialize_context_t* c)
780 c->start_serialize<char> ();
782 unsigned obj_6 = add_object ("opqrst", 6, c);
784 unsigned obj_5 = add_object ("mn", 2, c);
786 start_object ("jkl", 3, c);
787 add_offset (obj_6, c);
788 unsigned obj_4 = c->pop_pack (false);
790 start_object ("ghi", 3, c);
791 add_offset (obj_4, c);
792 unsigned obj_3 = c->pop_pack (false);
794 start_object ("def", 3, c);
795 add_offset (obj_3, c);
796 unsigned obj_2 = c->pop_pack (false);
798 start_object ("abc", 3, c);
799 add_offset (obj_2, c);
800 add_offset (obj_4, c);
801 add_offset (obj_5, c);
808 populate_serializer_virtual_link (hb_serialize_context_t* c)
810 c->start_serialize<char> ();
812 unsigned obj_d = add_object ("d", 1, c);
814 start_object ("b", 1, c);
815 add_offset (obj_d, c);
816 unsigned obj_b = c->pop_pack (false);
818 start_object ("e", 1, c);
819 add_virtual_offset (obj_b, c);
820 unsigned obj_e = c->pop_pack (false);
822 start_object ("c", 1, c);
823 add_offset (obj_e, c);
824 unsigned obj_c = c->pop_pack (false);
826 start_object ("a", 1, c);
827 add_offset (obj_b, c);
828 add_offset (obj_c, c);
834 static void test_sort_kahn_1 ()
836 size_t buffer_size = 100;
837 void* buffer = malloc (buffer_size);
838 hb_serialize_context_t c (buffer, buffer_size);
839 populate_serializer_complex_1 (&c);
841 graph_t graph (c.object_graph ());
844 assert(strncmp (graph.object (3).head, "abc", 3) == 0);
845 assert(graph.object (3).real_links.length == 2);
846 assert(graph.object (3).real_links[0].objidx == 2);
847 assert(graph.object (3).real_links[1].objidx == 1);
849 assert(strncmp (graph.object (2).head, "def", 3) == 0);
850 assert(graph.object (2).real_links.length == 1);
851 assert(graph.object (2).real_links[0].objidx == 0);
853 assert(strncmp (graph.object (1).head, "jkl", 3) == 0);
854 assert(graph.object (1).real_links.length == 0);
856 assert(strncmp (graph.object (0).head, "ghi", 3) == 0);
857 assert(graph.object (0).real_links.length == 0);
862 static void test_sort_kahn_2 ()
864 size_t buffer_size = 100;
865 void* buffer = malloc (buffer_size);
866 hb_serialize_context_t c (buffer, buffer_size);
867 populate_serializer_complex_2 (&c);
869 graph_t graph (c.object_graph ());
873 assert(strncmp (graph.object (4).head, "abc", 3) == 0);
874 assert(graph.object (4).real_links.length == 3);
875 assert(graph.object (4).real_links[0].objidx == 3);
876 assert(graph.object (4).real_links[1].objidx == 0);
877 assert(graph.object (4).real_links[2].objidx == 2);
879 assert(strncmp (graph.object (3).head, "def", 3) == 0);
880 assert(graph.object (3).real_links.length == 1);
881 assert(graph.object (3).real_links[0].objidx == 1);
883 assert(strncmp (graph.object (2).head, "mn", 2) == 0);
884 assert(graph.object (2).real_links.length == 0);
886 assert(strncmp (graph.object (1).head, "ghi", 3) == 0);
887 assert(graph.object (1).real_links.length == 1);
888 assert(graph.object (1).real_links[0].objidx == 0);
890 assert(strncmp (graph.object (0).head, "jkl", 3) == 0);
891 assert(graph.object (0).real_links.length == 0);
896 static void test_sort_shortest ()
898 size_t buffer_size = 100;
899 void* buffer = malloc (buffer_size);
900 hb_serialize_context_t c (buffer, buffer_size);
901 populate_serializer_complex_2 (&c);
903 graph_t graph (c.object_graph ());
904 graph.sort_shortest_distance ();
906 assert(strncmp (graph.object (4).head, "abc", 3) == 0);
907 assert(graph.object (4).real_links.length == 3);
908 assert(graph.object (4).real_links[0].objidx == 2);
909 assert(graph.object (4).real_links[1].objidx == 0);
910 assert(graph.object (4).real_links[2].objidx == 3);
912 assert(strncmp (graph.object (3).head, "mn", 2) == 0);
913 assert(graph.object (3).real_links.length == 0);
915 assert(strncmp (graph.object (2).head, "def", 3) == 0);
916 assert(graph.object (2).real_links.length == 1);
917 assert(graph.object (2).real_links[0].objidx == 1);
919 assert(strncmp (graph.object (1).head, "ghi", 3) == 0);
920 assert(graph.object (1).real_links.length == 1);
921 assert(graph.object (1).real_links[0].objidx == 0);
923 assert(strncmp (graph.object (0).head, "jkl", 3) == 0);
924 assert(graph.object (0).real_links.length == 0);
929 static void test_duplicate_leaf ()
931 size_t buffer_size = 100;
932 void* buffer = malloc (buffer_size);
933 hb_serialize_context_t c (buffer, buffer_size);
934 populate_serializer_complex_2 (&c);
936 graph_t graph (c.object_graph ());
937 graph.duplicate (4, 1);
939 assert(strncmp (graph.object (5).head, "abc", 3) == 0);
940 assert(graph.object (5).real_links.length == 3);
941 assert(graph.object (5).real_links[0].objidx == 3);
942 assert(graph.object (5).real_links[1].objidx == 4);
943 assert(graph.object (5).real_links[2].objidx == 0);
945 assert(strncmp (graph.object (4).head, "jkl", 3) == 0);
946 assert(graph.object (4).real_links.length == 0);
948 assert(strncmp (graph.object (3).head, "def", 3) == 0);
949 assert(graph.object (3).real_links.length == 1);
950 assert(graph.object (3).real_links[0].objidx == 2);
952 assert(strncmp (graph.object (2).head, "ghi", 3) == 0);
953 assert(graph.object (2).real_links.length == 1);
954 assert(graph.object (2).real_links[0].objidx == 1);
956 assert(strncmp (graph.object (1).head, "jkl", 3) == 0);
957 assert(graph.object (1).real_links.length == 0);
959 assert(strncmp (graph.object (0).head, "mn", 2) == 0);
960 assert(graph.object (0).real_links.length == 0);
965 static void test_duplicate_interior ()
967 size_t buffer_size = 100;
968 void* buffer = malloc (buffer_size);
969 hb_serialize_context_t c (buffer, buffer_size);
970 populate_serializer_complex_3 (&c);
972 graph_t graph (c.object_graph ());
973 graph.duplicate (3, 2);
975 assert(strncmp (graph.object (6).head, "abc", 3) == 0);
976 assert(graph.object (6).real_links.length == 3);
977 assert(graph.object (6).real_links[0].objidx == 4);
978 assert(graph.object (6).real_links[1].objidx == 2);
979 assert(graph.object (6).real_links[2].objidx == 1);
981 assert(strncmp (graph.object (5).head, "jkl", 3) == 0);
982 assert(graph.object (5).real_links.length == 1);
983 assert(graph.object (5).real_links[0].objidx == 0);
985 assert(strncmp (graph.object (4).head, "def", 3) == 0);
986 assert(graph.object (4).real_links.length == 1);
987 assert(graph.object (4).real_links[0].objidx == 3);
989 assert(strncmp (graph.object (3).head, "ghi", 3) == 0);
990 assert(graph.object (3).real_links.length == 1);
991 assert(graph.object (3).real_links[0].objidx == 5);
993 assert(strncmp (graph.object (2).head, "jkl", 3) == 0);
994 assert(graph.object (2).real_links.length == 1);
995 assert(graph.object (2).real_links[0].objidx == 0);
997 assert(strncmp (graph.object (1).head, "mn", 2) == 0);
998 assert(graph.object (1).real_links.length == 0);
1000 assert(strncmp (graph.object (0).head, "opqrst", 6) == 0);
1001 assert(graph.object (0).real_links.length == 0);
1009 size_t buffer_size = 100;
1010 void* buffer_1 = malloc (buffer_size);
1011 hb_serialize_context_t c1 (buffer_1, buffer_size);
1012 populate_serializer_simple (&c1);
1013 hb_bytes_t expected = c1.copy_bytes ();
1015 graph_t graph (c1.object_graph ());
1016 hb_blob_t* out = graph.serialize ();
1019 hb_bytes_t actual = out->as_bytes ();
1020 assert (actual == expected);
1022 hb_blob_destroy (out);
1025 static void test_will_overflow_1 ()
1027 size_t buffer_size = 100;
1028 void* buffer = malloc (buffer_size);
1029 hb_serialize_context_t c (buffer, buffer_size);
1030 populate_serializer_complex_2 (&c);
1031 graph_t graph (c.object_graph ());
1033 assert (!graph.will_overflow (nullptr));
1038 static void test_will_overflow_2 ()
1040 size_t buffer_size = 160000;
1041 void* buffer = malloc (buffer_size);
1042 hb_serialize_context_t c (buffer, buffer_size);
1043 populate_serializer_with_overflow (&c);
1044 graph_t graph (c.object_graph ());
1046 assert (graph.will_overflow (nullptr));
1051 static void test_will_overflow_3 ()
1053 size_t buffer_size = 160000;
1054 void* buffer = malloc (buffer_size);
1055 hb_serialize_context_t c (buffer, buffer_size);
1056 populate_serializer_with_dedup_overflow (&c);
1057 graph_t graph (c.object_graph ());
1059 assert (graph.will_overflow (nullptr));
1064 static void test_resolve_overflows_via_sort ()
1066 size_t buffer_size = 160000;
1067 void* buffer = malloc (buffer_size);
1068 hb_serialize_context_t c (buffer, buffer_size);
1069 populate_serializer_with_overflow (&c);
1070 graph_t graph (c.object_graph ());
1072 hb_blob_t* out = hb_resolve_overflows (c.object_graph (), HB_TAG_NONE);
1074 hb_bytes_t result = out->as_bytes ();
1075 assert (result.length == (80000 + 3 + 3 * 2));
1078 hb_blob_destroy (out);
1081 static void test_resolve_overflows_via_duplication ()
1083 size_t buffer_size = 160000;
1084 void* buffer = malloc (buffer_size);
1085 hb_serialize_context_t c (buffer, buffer_size);
1086 populate_serializer_with_dedup_overflow (&c);
1087 graph_t graph (c.object_graph ());
1089 hb_blob_t* out = hb_resolve_overflows (c.object_graph (), HB_TAG_NONE);
1091 hb_bytes_t result = out->as_bytes ();
1092 assert (result.length == (10000 + 2 * 2 + 60000 + 2 + 3 * 2));
1095 hb_blob_destroy (out);
1098 static void test_resolve_overflows_via_space_assignment ()
1100 size_t buffer_size = 160000;
1101 void* buffer = malloc (buffer_size);
1102 hb_serialize_context_t c (buffer, buffer_size);
1103 populate_serializer_spaces (&c, true);
1105 void* expected_buffer = malloc (buffer_size);
1106 hb_serialize_context_t e (expected_buffer, buffer_size);
1107 populate_serializer_spaces (&e, false);
1109 run_resolve_overflow_test ("test_resolve_overflows_via_space_assignment",
1114 free (expected_buffer);
1117 static void test_resolve_overflows_via_isolation ()
1119 size_t buffer_size = 160000;
1120 void* buffer = malloc (buffer_size);
1121 hb_serialize_context_t c (buffer, buffer_size);
1122 populate_serializer_with_isolation_overflow (&c);
1123 graph_t graph (c.object_graph ());
1125 assert (c.offset_overflow ());
1126 hb_blob_t* out = hb_resolve_overflows (c.object_graph (), HB_TAG ('G', 'S', 'U', 'B'), 0);
1128 hb_bytes_t result = out->as_bytes ();
1129 assert (result.length == (1 + 10000 + 60000 + 1 + 1
1133 hb_blob_destroy (out);
1136 static void test_resolve_overflows_via_isolation_with_recursive_duplication ()
1138 size_t buffer_size = 160000;
1139 void* buffer = malloc (buffer_size);
1140 hb_serialize_context_t c (buffer, buffer_size);
1141 populate_serializer_with_isolation_overflow_complex (&c);
1143 void* expected_buffer = malloc (buffer_size);
1144 hb_serialize_context_t e (expected_buffer, buffer_size);
1145 populate_serializer_with_isolation_overflow_complex_expected (&e);
1147 run_resolve_overflow_test ("test_resolve_overflows_via_isolation_with_recursive_duplication",
1151 free (expected_buffer);
1154 static void test_resolve_overflows_via_isolating_16bit_space ()
1156 size_t buffer_size = 160000;
1157 void* buffer = malloc (buffer_size);
1158 hb_serialize_context_t c (buffer, buffer_size);
1159 populate_serializer_spaces_16bit_connection (&c);
1161 void* expected_buffer = malloc (buffer_size);
1162 hb_serialize_context_t e (expected_buffer, buffer_size);
1163 populate_serializer_spaces_16bit_connection_expected (&e);
1165 run_resolve_overflow_test ("test_resolve_overflows_via_isolating_16bit_space",
1170 free (expected_buffer);
1173 static void test_resolve_overflows_via_isolating_16bit_space_2 ()
1175 size_t buffer_size = 160000;
1176 void* buffer = malloc (buffer_size);
1177 hb_serialize_context_t c (buffer, buffer_size);
1178 populate_serializer_short_and_wide_subgraph_root (&c);
1180 void* expected_buffer = malloc (buffer_size);
1181 hb_serialize_context_t e (expected_buffer, buffer_size);
1182 populate_serializer_short_and_wide_subgraph_root_expected (&e);
1184 run_resolve_overflow_test ("test_resolve_overflows_via_isolating_16bit_space_2",
1189 free (expected_buffer);
1192 static void test_resolve_overflows_via_isolation_spaces ()
1194 size_t buffer_size = 160000;
1195 void* buffer = malloc (buffer_size);
1196 hb_serialize_context_t c (buffer, buffer_size);
1197 populate_serializer_with_isolation_overflow_spaces (&c);
1198 graph_t graph (c.object_graph ());
1200 assert (c.offset_overflow ());
1201 hb_blob_t* out = hb_resolve_overflows (c.object_graph (), HB_TAG ('G', 'S', 'U', 'B'), 0);
1203 hb_bytes_t result = out->as_bytes ();
1205 unsigned expected_length = 3 + 2 * 60000; // objects
1206 expected_length += 2 * 4 + 2 * 2; // links
1207 assert (result.length == expected_length);
1210 hb_blob_destroy (out);
1213 static void test_resolve_overflows_via_splitting_spaces ()
1215 size_t buffer_size = 160000;
1216 void* buffer = malloc (buffer_size);
1217 hb_serialize_context_t c (buffer, buffer_size);
1218 populate_serializer_with_split_spaces (&c);
1220 void* expected_buffer = malloc (buffer_size);
1221 hb_serialize_context_t e (expected_buffer, buffer_size);
1222 populate_serializer_with_split_spaces_expected (&e);
1224 run_resolve_overflow_test ("test_resolve_overflows_via_splitting_spaces",
1230 free (expected_buffer);
1234 static void test_resolve_overflows_via_splitting_spaces_2 ()
1236 size_t buffer_size = 160000;
1237 void* buffer = malloc (buffer_size);
1238 hb_serialize_context_t c (buffer, buffer_size);
1239 populate_serializer_with_split_spaces_2 (&c);
1241 void* expected_buffer = malloc (buffer_size);
1242 hb_serialize_context_t e (expected_buffer, buffer_size);
1243 populate_serializer_with_split_spaces_expected_2 (&e);
1245 run_resolve_overflow_test ("test_resolve_overflows_via_splitting_spaces_2",
1250 free (expected_buffer);
1253 static void test_resolve_overflows_via_priority ()
1255 size_t buffer_size = 160000;
1256 void* buffer = malloc (buffer_size);
1257 hb_serialize_context_t c (buffer, buffer_size);
1258 populate_serializer_with_priority_overflow (&c);
1260 void* expected_buffer = malloc (buffer_size);
1261 hb_serialize_context_t e (expected_buffer, buffer_size);
1262 populate_serializer_with_priority_overflow_expected (&e);
1264 run_resolve_overflow_test ("test_resolve_overflows_via_priority",
1269 free (expected_buffer);
1273 static void test_virtual_link ()
1275 size_t buffer_size = 100;
1276 void* buffer = malloc (buffer_size);
1277 hb_serialize_context_t c (buffer, buffer_size);
1278 populate_serializer_virtual_link (&c);
1280 hb_blob_t* out = hb_resolve_overflows (c.object_graph (), HB_TAG_NONE);
1283 hb_bytes_t result = out->as_bytes ();
1284 assert (result.length == 5 + 4 * 2);
1285 assert (result[0] == 'a');
1286 assert (result[5] == 'c');
1287 assert (result[8] == 'e');
1288 assert (result[9] == 'b');
1289 assert (result[12] == 'd');
1292 hb_blob_destroy (out);
1296 test_shared_node_with_virtual_links ()
1298 size_t buffer_size = 100;
1299 void* buffer = malloc (buffer_size);
1300 hb_serialize_context_t c (buffer, buffer_size);
1302 c.start_serialize<char> ();
1304 unsigned obj_b = add_object ("b", 1, &c);
1305 unsigned obj_c = add_object ("c", 1, &c);
1307 start_object ("d", 1, &c);
1308 add_virtual_offset (obj_b, &c);
1309 unsigned obj_d_1 = c.pop_pack ();
1311 start_object ("d", 1, &c);
1312 add_virtual_offset (obj_c, &c);
1313 unsigned obj_d_2 = c.pop_pack ();
1315 assert (obj_d_1 == obj_d_2);
1317 start_object ("a", 1, &c);
1318 add_offset (obj_b, &c);
1319 add_offset (obj_c, &c);
1320 add_offset (obj_d_1, &c);
1321 add_offset (obj_d_2, &c);
1325 assert(c.object_graph() [obj_d_1]->virtual_links.length == 2);
1326 assert(c.object_graph() [obj_d_1]->virtual_links[0].objidx == obj_b);
1327 assert(c.object_graph() [obj_d_1]->virtual_links[1].objidx == obj_c);
1332 // TODO(garretrieger): update will_overflow tests to check the overflows array.
1333 // TODO(garretrieger): add tests for priority raising.
1336 main (int argc, char **argv)
1339 test_sort_kahn_1 ();
1340 test_sort_kahn_2 ();
1341 test_sort_shortest ();
1342 test_will_overflow_1 ();
1343 test_will_overflow_2 ();
1344 test_will_overflow_3 ();
1345 test_resolve_overflows_via_sort ();
1346 test_resolve_overflows_via_duplication ();
1347 test_resolve_overflows_via_priority ();
1348 test_resolve_overflows_via_space_assignment ();
1349 test_resolve_overflows_via_isolation ();
1350 test_resolve_overflows_via_isolation_with_recursive_duplication ();
1351 test_resolve_overflows_via_isolation_spaces ();
1352 test_resolve_overflows_via_isolating_16bit_space ();
1353 test_resolve_overflows_via_isolating_16bit_space_2 ();
1354 test_resolve_overflows_via_splitting_spaces ();
1355 test_resolve_overflows_via_splitting_spaces_2 ();
1356 test_duplicate_leaf ();
1357 test_duplicate_interior ();
1358 test_virtual_link ();
1359 test_shared_node_with_virtual_links ();