ReactOS 0.4.16-dev-306-g647d351
gxvcommn.c
Go to the documentation of this file.
1/***************************************************************************/
2/* */
3/* gxvcommn.c */
4/* */
5/* TrueTypeGX/AAT common tables validation (body). */
6/* */
7/* Copyright 2004-2018 by */
8/* suzuki toshiya, Masatake YAMATO, Red Hat K.K., */
9/* David Turner, Robert Wilhelm, and Werner Lemberg. */
10/* */
11/* This file is part of the FreeType project, and may only be used, */
12/* modified, and distributed under the terms of the FreeType project */
13/* license, LICENSE.TXT. By continuing to use, modify, or distribute */
14/* this file you indicate that you have read the license and */
15/* understand and accept it fully. */
16/* */
17/***************************************************************************/
18
19/***************************************************************************/
20/* */
21/* gxvalid is derived from both gxlayout module and otvalid module. */
22/* Development of gxlayout is supported by the Information-technology */
23/* Promotion Agency(IPA), Japan. */
24/* */
25/***************************************************************************/
26
27
28#include "gxvcommn.h"
29
30
31 /*************************************************************************/
32 /* */
33 /* The macro FT_COMPONENT is used in trace mode. It is an implicit */
34 /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */
35 /* messages during execution. */
36 /* */
37#undef FT_COMPONENT
38#define FT_COMPONENT trace_gxvcommon
39
40
41 /*************************************************************************/
42 /*************************************************************************/
43 /***** *****/
44 /***** 16bit offset sorter *****/
45 /***** *****/
46 /*************************************************************************/
47 /*************************************************************************/
48
49 static int
51 FT_UShort* b )
52 {
53 if ( *a < *b )
54 return -1;
55 else if ( *a > *b )
56 return 1;
57 else
58 return 0;
59 }
60
61
62 FT_LOCAL_DEF( void )
66 FT_UInt nmemb,
68 GXV_Validator gxvalid )
69 {
70 FT_UInt i;
71
72
73 for ( i = 0; i < nmemb; i++ )
74 *(length[i]) = 0;
75
76 for ( i = 0; i < nmemb; i++ )
77 buff[i] = offset[i];
78 buff[nmemb] = limit;
79
80 ft_qsort( buff, ( nmemb + 1 ), sizeof ( FT_UShort ),
81 ( int(*)(const void*, const void*) )gxv_compare_ushort_offset );
82
83 if ( buff[nmemb] > limit )
85
86 for ( i = 0; i < nmemb; i++ )
87 {
88 FT_UInt j;
89
90
91 for ( j = 0; j < nmemb; j++ )
92 if ( buff[j] == offset[i] )
93 break;
94
95 if ( j == nmemb )
97
98 *(length[i]) = (FT_UShort)( buff[j + 1] - buff[j] );
99
100 if ( 0 != offset[i] && 0 == *(length[i]) )
102 }
103 }
104
105
106 /*************************************************************************/
107 /*************************************************************************/
108 /***** *****/
109 /***** 32bit offset sorter *****/
110 /***** *****/
111 /*************************************************************************/
112 /*************************************************************************/
113
114 static int
116 FT_ULong* b )
117 {
118 if ( *a < *b )
119 return -1;
120 else if ( *a > *b )
121 return 1;
122 else
123 return 0;
124 }
125
126
127 FT_LOCAL_DEF( void )
130 FT_ULong* buff,
131 FT_UInt nmemb,
133 GXV_Validator gxvalid)
134 {
135 FT_UInt i;
136
137
138 for ( i = 0; i < nmemb; i++ )
139 *(length[i]) = 0;
140
141 for ( i = 0; i < nmemb; i++ )
142 buff[i] = offset[i];
143 buff[nmemb] = limit;
144
145 ft_qsort( buff, ( nmemb + 1 ), sizeof ( FT_ULong ),
146 ( int(*)(const void*, const void*) )gxv_compare_ulong_offset );
147
148 if ( buff[nmemb] > limit )
150
151 for ( i = 0; i < nmemb; i++ )
152 {
153 FT_UInt j;
154
155
156 for ( j = 0; j < nmemb; j++ )
157 if ( buff[j] == offset[i] )
158 break;
159
160 if ( j == nmemb )
162
163 *(length[i]) = buff[j + 1] - buff[j];
164
165 if ( 0 != offset[i] && 0 == *(length[i]) )
167 }
168 }
169
170
171 /*************************************************************************/
172 /*************************************************************************/
173 /***** *****/
174 /***** scan value array and get min & max *****/
175 /***** *****/
176 /*************************************************************************/
177 /*************************************************************************/
178
179
180 FT_LOCAL_DEF( void )
183 FT_Byte* min,
184 FT_Byte* max,
185 GXV_Validator gxvalid )
186 {
187 FT_Bytes p = table;
188
189
190 *min = 0xFF;
191 *max = 0x00;
192
193 while ( p < limit )
194 {
195 FT_Byte val;
196
197
198 GXV_LIMIT_CHECK( 1 );
199 val = FT_NEXT_BYTE( p );
200
201 *min = (FT_Byte)FT_MIN( *min, val );
202 *max = (FT_Byte)FT_MAX( *max, val );
203 }
204
205 gxvalid->subtable_length = (FT_ULong)( p - table );
206 }
207
208
209 FT_LOCAL_DEF( void )
212 FT_UShort* min,
213 FT_UShort* max,
214 GXV_Validator gxvalid )
215 {
216 FT_Bytes p = table;
217
218
219 *min = 0xFFFFU;
220 *max = 0x0000;
221
222 while ( p < limit )
223 {
225
226
227 GXV_LIMIT_CHECK( 2 );
228 val = FT_NEXT_USHORT( p );
229
230 *min = (FT_Byte)FT_MIN( *min, val );
231 *max = (FT_Byte)FT_MAX( *max, val );
232 }
233
234 gxvalid->subtable_length = (FT_ULong)( p - table );
235 }
236
237
238 /*************************************************************************/
239 /*************************************************************************/
240 /***** *****/
241 /***** BINSEARCHHEADER *****/
242 /***** *****/
243 /*************************************************************************/
244 /*************************************************************************/
245
246 typedef struct GXV_BinSrchHeader_
247 {
253
255
256
257 static void
259 GXV_Validator gxvalid )
260 {
261 FT_UShort searchRange;
262 FT_UShort entrySelector;
263 FT_UShort rangeShift;
264
265
266 if ( binSrchHeader->unitSize == 0 )
268
269 if ( binSrchHeader->nUnits == 0 )
270 {
271 if ( binSrchHeader->searchRange == 0 &&
272 binSrchHeader->entrySelector == 0 &&
273 binSrchHeader->rangeShift == 0 )
274 return;
275 else
277 }
278
279 for ( searchRange = 1, entrySelector = 1;
280 ( searchRange * 2 ) <= binSrchHeader->nUnits &&
281 searchRange < 0x8000U;
282 searchRange *= 2, entrySelector++ )
283 ;
284
285 entrySelector--;
286 searchRange = (FT_UShort)( searchRange * binSrchHeader->unitSize );
287 rangeShift = (FT_UShort)( binSrchHeader->nUnits * binSrchHeader->unitSize
288 - searchRange );
289
290 if ( searchRange != binSrchHeader->searchRange ||
291 entrySelector != binSrchHeader->entrySelector ||
292 rangeShift != binSrchHeader->rangeShift )
293 {
294 GXV_TRACE(( "Inconsistency found in BinSrchHeader\n" ));
295 GXV_TRACE(( "originally: unitSize=%d, nUnits=%d, "
296 "searchRange=%d, entrySelector=%d, "
297 "rangeShift=%d\n",
298 binSrchHeader->unitSize, binSrchHeader->nUnits,
299 binSrchHeader->searchRange, binSrchHeader->entrySelector,
300 binSrchHeader->rangeShift ));
301 GXV_TRACE(( "calculated: unitSize=%d, nUnits=%d, "
302 "searchRange=%d, entrySelector=%d, "
303 "rangeShift=%d\n",
304 binSrchHeader->unitSize, binSrchHeader->nUnits,
305 searchRange, entrySelector, rangeShift ));
306
308 }
309 }
310
311
312 /*
313 * parser & validator of BinSrchHeader
314 * which is used in LookupTable format 2, 4, 6.
315 *
316 * Essential parameters (unitSize, nUnits) are returned by
317 * given pointer, others (searchRange, entrySelector, rangeShift)
318 * can be calculated by essential parameters, so they are just
319 * validated and discarded.
320 *
321 * However, wrong values in searchRange, entrySelector, rangeShift
322 * won't cause fatal errors, because these parameters might be
323 * only used in old m68k font driver in MacOS.
324 * -- suzuki toshiya <mpsuzuki@hiroshima-u.ac.jp>
325 */
326
327 FT_LOCAL_DEF( void )
330 FT_UShort* unitSize_p,
331 FT_UShort* nUnits_p,
332 GXV_Validator gxvalid )
333 {
334 FT_Bytes p = table;
335 GXV_BinSrchHeader binSrchHeader;
336
337
338 GXV_NAME_ENTER( "BinSrchHeader validate" );
339
340 if ( *unitSize_p == 0 )
341 {
342 GXV_LIMIT_CHECK( 2 );
343 binSrchHeader.unitSize = FT_NEXT_USHORT( p );
344 }
345 else
346 binSrchHeader.unitSize = *unitSize_p;
347
348 if ( *nUnits_p == 0 )
349 {
350 GXV_LIMIT_CHECK( 2 );
351 binSrchHeader.nUnits = FT_NEXT_USHORT( p );
352 }
353 else
354 binSrchHeader.nUnits = *nUnits_p;
355
356 GXV_LIMIT_CHECK( 2 + 2 + 2 );
357 binSrchHeader.searchRange = FT_NEXT_USHORT( p );
358 binSrchHeader.entrySelector = FT_NEXT_USHORT( p );
359 binSrchHeader.rangeShift = FT_NEXT_USHORT( p );
360 GXV_TRACE(( "nUnits %d\n", binSrchHeader.nUnits ));
361
362 gxv_BinSrchHeader_check_consistency( &binSrchHeader, gxvalid );
363
364 if ( *unitSize_p == 0 )
365 *unitSize_p = binSrchHeader.unitSize;
366
367 if ( *nUnits_p == 0 )
368 *nUnits_p = binSrchHeader.nUnits;
369
370 gxvalid->subtable_length = (FT_ULong)( p - table );
371 GXV_EXIT;
372 }
373
374
375 /*************************************************************************/
376 /*************************************************************************/
377 /***** *****/
378 /***** LOOKUP TABLE *****/
379 /***** *****/
380 /*************************************************************************/
381 /*************************************************************************/
382
383#define GXV_LOOKUP_VALUE_LOAD( P, SIGNSPEC ) \
384 ( P += 2, gxv_lookup_value_load( P - 2, SIGNSPEC ) )
385
388 int signspec )
389 {
391
392
393 if ( signspec == GXV_LOOKUPVALUE_UNSIGNED )
394 v.u = FT_NEXT_USHORT( p );
395 else
396 v.s = FT_NEXT_SHORT( p );
397
398 return v;
399 }
400
401
402#define GXV_UNITSIZE_VALIDATE( FORMAT, UNITSIZE, NUNITS, CORRECTSIZE ) \
403 FT_BEGIN_STMNT \
404 if ( UNITSIZE != CORRECTSIZE ) \
405 { \
406 FT_ERROR(( "unitSize=%d differs from" \
407 " expected unitSize=%d" \
408 " in LookupTable %s\n", \
409 UNITSIZE, CORRECTSIZE, FORMAT )); \
410 if ( UNITSIZE != 0 && NUNITS != 0 ) \
411 { \
412 FT_ERROR(( " cannot validate anymore\n" )); \
413 FT_INVALID_FORMAT; \
414 } \
415 else \
416 FT_ERROR(( " forcibly continues\n" )); \
417 } \
418 FT_END_STMNT
419
420
421 /* ================= Simple Array Format 0 Lookup Table ================ */
422 static void
425 GXV_Validator gxvalid )
426 {
427 FT_Bytes p = table;
428 FT_UShort i;
429
431
432
433 GXV_NAME_ENTER( "LookupTable format 0" );
434
435 GXV_LIMIT_CHECK( 2 * gxvalid->face->num_glyphs );
436
437 for ( i = 0; i < gxvalid->face->num_glyphs; i++ )
438 {
439 GXV_LIMIT_CHECK( 2 );
440 if ( p + 2 >= limit ) /* some fonts have too-short fmt0 array */
441 {
442 GXV_TRACE(( "too short, glyphs %d - %d are missing\n",
443 i, gxvalid->face->num_glyphs ));
445 break;
446 }
447
449 gxvalid->lookupval_func( i, &value, gxvalid );
450 }
451
452 gxvalid->subtable_length = (FT_ULong)( p - table );
453 GXV_EXIT;
454 }
455
456
457 /* ================= Segment Single Format 2 Lookup Table ============== */
458 /*
459 * Apple spec says:
460 *
461 * To guarantee that a binary search terminates, you must include one or
462 * more special `end of search table' values at the end of the data to
463 * be searched. The number of termination values that need to be
464 * included is table-specific. The value that indicates binary search
465 * termination is 0xFFFF.
466 *
467 * The problem is that nUnits does not include this end-marker. It's
468 * quite difficult to discriminate whether the following 0xFFFF comes from
469 * the end-marker or some next data.
470 *
471 * -- suzuki toshiya <mpsuzuki@hiroshima-u.ac.jp>
472 */
473 static void
475 FT_UShort unitSize,
476 GXV_Validator gxvalid )
477 {
478 FT_Bytes p = table;
479
480
481 while ( ( p + 4 ) < gxvalid->root->limit )
482 {
483 if ( p[0] != 0xFF || p[1] != 0xFF || /* lastGlyph */
484 p[2] != 0xFF || p[3] != 0xFF ) /* firstGlyph */
485 break;
486 p += unitSize;
487 }
488
489 gxvalid->subtable_length = (FT_ULong)( p - table );
490 }
491
492
493 static void
496 GXV_Validator gxvalid )
497 {
498 FT_Bytes p = table;
499 FT_UShort gid;
500
501 FT_UShort unitSize;
502 FT_UShort nUnits;
504 FT_UShort lastGlyph;
507
508
509 GXV_NAME_ENTER( "LookupTable format 2" );
510
511 unitSize = nUnits = 0;
512 gxv_BinSrchHeader_validate( p, limit, &unitSize, &nUnits, gxvalid );
513 p += gxvalid->subtable_length;
514
515 GXV_UNITSIZE_VALIDATE( "format2", unitSize, nUnits, 6 );
516
517 for ( unit = 0, gid = 0; unit < nUnits; unit++ )
518 {
519 GXV_LIMIT_CHECK( 2 + 2 + 2 );
520 lastGlyph = FT_NEXT_USHORT( p );
523
525 gxv_glyphid_validate( lastGlyph, gxvalid );
526
527 if ( lastGlyph < gid )
528 {
529 GXV_TRACE(( "reverse ordered segment specification:"
530 " lastGlyph[%d]=%d < lastGlyph[%d]=%d\n",
531 unit, lastGlyph, unit - 1 , gid ));
533 }
534
535 if ( lastGlyph < firstGlyph )
536 {
537 GXV_TRACE(( "reverse ordered range specification at unit %d:",
538 " lastGlyph %d < firstGlyph %d ",
539 unit, lastGlyph, firstGlyph ));
541
542 if ( gxvalid->root->level == FT_VALIDATE_TIGHT )
543 continue; /* ftxvalidator silently skips such an entry */
544
545 FT_TRACE4(( "continuing with exchanged values\n" ));
546 gid = firstGlyph;
547 firstGlyph = lastGlyph;
548 lastGlyph = gid;
549 }
550
551 for ( gid = firstGlyph; gid <= lastGlyph; gid++ )
552 gxvalid->lookupval_func( gid, &value, gxvalid );
553 }
554
555 gxv_LookupTable_fmt2_skip_endmarkers( p, unitSize, gxvalid );
556 p += gxvalid->subtable_length;
557
558 gxvalid->subtable_length = (FT_ULong)( p - table );
559 GXV_EXIT;
560 }
561
562
563 /* ================= Segment Array Format 4 Lookup Table =============== */
564 static void
567 GXV_Validator gxvalid )
568 {
569 FT_Bytes p = table;
571 FT_UShort gid;
572
573 FT_UShort unitSize;
574 FT_UShort nUnits;
575 FT_UShort lastGlyph;
577 GXV_LookupValueDesc base_value;
579
580
581 GXV_NAME_ENTER( "LookupTable format 4" );
582
583 unitSize = nUnits = 0;
584 gxv_BinSrchHeader_validate( p, limit, &unitSize, &nUnits, gxvalid );
585 p += gxvalid->subtable_length;
586
587 GXV_UNITSIZE_VALIDATE( "format4", unitSize, nUnits, 6 );
588
589 for ( unit = 0, gid = 0; unit < nUnits; unit++ )
590 {
591 GXV_LIMIT_CHECK( 2 + 2 );
592 lastGlyph = FT_NEXT_USHORT( p );
594
596 gxv_glyphid_validate( lastGlyph, gxvalid );
597
598 if ( lastGlyph < gid )
599 {
600 GXV_TRACE(( "reverse ordered segment specification:"
601 " lastGlyph[%d]=%d < lastGlyph[%d]=%d\n",
602 unit, lastGlyph, unit - 1 , gid ));
604 }
605
606 if ( lastGlyph < firstGlyph )
607 {
608 GXV_TRACE(( "reverse ordered range specification at unit %d:",
609 " lastGlyph %d < firstGlyph %d ",
610 unit, lastGlyph, firstGlyph ));
612
613 if ( gxvalid->root->level == FT_VALIDATE_TIGHT )
614 continue; /* ftxvalidator silently skips such an entry */
615
616 FT_TRACE4(( "continuing with exchanged values\n" ));
617 gid = firstGlyph;
618 firstGlyph = lastGlyph;
619 lastGlyph = gid;
620 }
621
622 GXV_LIMIT_CHECK( 2 );
624
625 for ( gid = firstGlyph; gid <= lastGlyph; gid++ )
626 {
627 value = gxvalid->lookupfmt4_trans( (FT_UShort)( gid - firstGlyph ),
628 &base_value,
629 limit,
630 gxvalid );
631
632 gxvalid->lookupval_func( gid, &value, gxvalid );
633 }
634 }
635
636 gxv_LookupTable_fmt2_skip_endmarkers( p, unitSize, gxvalid );
637 p += gxvalid->subtable_length;
638
639 gxvalid->subtable_length = (FT_ULong)( p - table );
640 GXV_EXIT;
641 }
642
643
644 /* ================= Segment Table Format 6 Lookup Table =============== */
645 static void
647 FT_UShort unitSize,
648 GXV_Validator gxvalid )
649 {
650 FT_Bytes p = table;
651
652
653 while ( p < gxvalid->root->limit )
654 {
655 if ( p[0] != 0xFF || p[1] != 0xFF )
656 break;
657 p += unitSize;
658 }
659
660 gxvalid->subtable_length = (FT_ULong)( p - table );
661 }
662
663
664 static void
667 GXV_Validator gxvalid )
668 {
669 FT_Bytes p = table;
671 FT_UShort prev_glyph;
672
673 FT_UShort unitSize;
674 FT_UShort nUnits;
675 FT_UShort glyph;
677
678
679 GXV_NAME_ENTER( "LookupTable format 6" );
680
681 unitSize = nUnits = 0;
682 gxv_BinSrchHeader_validate( p, limit, &unitSize, &nUnits, gxvalid );
683 p += gxvalid->subtable_length;
684
685 GXV_UNITSIZE_VALIDATE( "format6", unitSize, nUnits, 4 );
686
687 for ( unit = 0, prev_glyph = 0; unit < nUnits; unit++ )
688 {
689 GXV_LIMIT_CHECK( 2 + 2 );
690 glyph = FT_NEXT_USHORT( p );
692
693 if ( gxv_glyphid_validate( glyph, gxvalid ) )
694 GXV_TRACE(( " endmarker found within defined range"
695 " (entry %d < nUnits=%d)\n",
696 unit, nUnits ));
697
698 if ( prev_glyph > glyph )
699 {
700 GXV_TRACE(( "current gid 0x%04x < previous gid 0x%04x\n",
701 glyph, prev_glyph ));
703 }
704 prev_glyph = glyph;
705
706 gxvalid->lookupval_func( glyph, &value, gxvalid );
707 }
708
709 gxv_LookupTable_fmt6_skip_endmarkers( p, unitSize, gxvalid );
710 p += gxvalid->subtable_length;
711
712 gxvalid->subtable_length = (FT_ULong)( p - table );
713 GXV_EXIT;
714 }
715
716
717 /* ================= Trimmed Array Format 8 Lookup Table =============== */
718 static void
721 GXV_Validator gxvalid )
722 {
723 FT_Bytes p = table;
724 FT_UShort i;
725
728 FT_UShort glyphCount;
729
730
731 GXV_NAME_ENTER( "LookupTable format 8" );
732
733 /* firstGlyph + glyphCount */
734 GXV_LIMIT_CHECK( 2 + 2 );
736 glyphCount = FT_NEXT_USHORT( p );
737
739 gxv_glyphid_validate( (FT_UShort)( firstGlyph + glyphCount ), gxvalid );
740
741 /* valueArray */
742 for ( i = 0; i < glyphCount; i++ )
743 {
744 GXV_LIMIT_CHECK( 2 );
746 gxvalid->lookupval_func( (FT_UShort)( firstGlyph + i ), &value, gxvalid );
747 }
748
749 gxvalid->subtable_length = (FT_ULong)( p - table );
750 GXV_EXIT;
751 }
752
753
754 FT_LOCAL_DEF( void )
757 GXV_Validator gxvalid )
758 {
759 FT_Bytes p = table;
761
762 GXV_Validate_Func fmt_funcs_table[] =
763 {
765 NULL, /* 1 */
767 NULL, /* 3 */
769 NULL, /* 5 */
771 NULL, /* 7 */
773 };
774
776
777
778 GXV_NAME_ENTER( "LookupTable" );
779
780 /* lookuptbl_head may be used in fmt4 transit function. */
781 gxvalid->lookuptbl_head = table;
782
783 /* format */
784 GXV_LIMIT_CHECK( 2 );
786 GXV_TRACE(( " (format %d)\n", format ));
787
788 if ( format > 8 )
790
791 func = fmt_funcs_table[format];
792 if ( !func )
794
795 func( p, limit, gxvalid );
796 p += gxvalid->subtable_length;
797
798 gxvalid->subtable_length = (FT_ULong)( p - table );
799
800 GXV_EXIT;
801 }
802
803
804 /*************************************************************************/
805 /*************************************************************************/
806 /***** *****/
807 /***** Glyph ID *****/
808 /***** *****/
809 /*************************************************************************/
810 /*************************************************************************/
811
814 GXV_Validator gxvalid )
815 {
817
818
819 if ( gid == 0xFFFFU )
820 {
821 GXV_EXIT;
822 return 1;
823 }
824
825 face = gxvalid->face;
826 if ( face->num_glyphs < gid )
827 {
828 GXV_TRACE(( " gxv_glyphid_check() gid overflow: num_glyphs %d < %d\n",
829 face->num_glyphs, gid ));
831 }
832
833 return 0;
834 }
835
836
837 /*************************************************************************/
838 /*************************************************************************/
839 /***** *****/
840 /***** CONTROL POINT *****/
841 /***** *****/
842 /*************************************************************************/
843 /*************************************************************************/
844
845 FT_LOCAL_DEF( void )
847 FT_UShort ctl_point,
848 GXV_Validator gxvalid )
849 {
852
853 FT_GlyphSlot glyph;
855 FT_UShort n_points;
856
857
858 face = gxvalid->face;
859
861 gid,
863 if ( error )
865
866 glyph = face->glyph;
867 outline = glyph->outline;
868 n_points = (FT_UShort)outline.n_points;
869
870 if ( !( ctl_point < n_points ) )
872 }
873
874
875 /*************************************************************************/
876 /*************************************************************************/
877 /***** *****/
878 /***** SFNT NAME *****/
879 /***** *****/
880 /*************************************************************************/
881 /*************************************************************************/
882
883 FT_LOCAL_DEF( void )
885 FT_UShort min_index,
886 FT_UShort max_index,
887 GXV_Validator gxvalid )
888 {
890 FT_UInt i;
891 FT_UInt nnames;
892
893
894 GXV_NAME_ENTER( "sfntName" );
895
896 if ( name_index < min_index || max_index < name_index )
898
899 nnames = FT_Get_Sfnt_Name_Count( gxvalid->face );
900 for ( i = 0; i < nnames; i++ )
901 {
902 if ( FT_Get_Sfnt_Name( gxvalid->face, i, &name ) != FT_Err_Ok )
903 continue;
904
905 if ( name.name_id == name_index )
906 goto Out;
907 }
908
909 GXV_TRACE(( " nameIndex = %d (UNTITLED)\n", name_index ));
911 goto Exit; /* make compiler happy */
912
913 Out:
914 FT_TRACE1(( " nameIndex = %d (", name_index ));
916 FT_TRACE1(( ")\n" ));
917
918 Exit:
919 GXV_EXIT;
920 }
921
922
923 /*************************************************************************/
924 /*************************************************************************/
925 /***** *****/
926 /***** STATE TABLE *****/
927 /***** *****/
928 /*************************************************************************/
929 /*************************************************************************/
930
931 /* -------------------------- Class Table --------------------------- */
932
933 /*
934 * highestClass specifies how many classes are defined in this
935 * Class Subtable. Apple spec does not mention whether undefined
936 * holes in the class (e.g.: 0-3 are predefined, 4 is unused, 5 is used)
937 * are permitted. At present, holes in a defined class are not checked.
938 * -- suzuki toshiya <mpsuzuki@hiroshima-u.ac.jp>
939 */
940
941 static void
943 FT_UShort* length_p,
944 FT_UShort stateSize,
945 FT_Byte* maxClassID_p,
946 GXV_Validator gxvalid )
947 {
948 FT_Bytes p = table;
949 FT_Bytes limit = table + *length_p;
951 FT_UShort nGlyphs;
952
953
954 GXV_NAME_ENTER( "ClassTable" );
955
956 *maxClassID_p = 3; /* Classes 0, 2, and 3 are predefined */
957
958 GXV_LIMIT_CHECK( 2 + 2 );
960 nGlyphs = FT_NEXT_USHORT( p );
961
962 GXV_TRACE(( " (firstGlyph = %d, nGlyphs = %d)\n", firstGlyph, nGlyphs ));
963
964 if ( !nGlyphs )
965 goto Out;
966
967 gxv_glyphid_validate( (FT_UShort)( firstGlyph + nGlyphs ), gxvalid );
968
969 {
970 FT_Byte nGlyphInClass[256];
971 FT_Byte classID;
972 FT_UShort i;
973
974
975 FT_MEM_ZERO( nGlyphInClass, 256 );
976
977
978 for ( i = 0; i < nGlyphs; i++ )
979 {
980 GXV_LIMIT_CHECK( 1 );
981 classID = FT_NEXT_BYTE( p );
982 switch ( classID )
983 {
984 /* following classes should not appear in class array */
985 case 0: /* end of text */
986 case 2: /* out of bounds */
987 case 3: /* end of line */
989 break;
990
991 case 1: /* out of bounds */
992 default: /* user-defined: 4 - ( stateSize - 1 ) */
993 if ( classID >= stateSize )
994 FT_INVALID_DATA; /* assign glyph to undefined state */
995
996 nGlyphInClass[classID]++;
997 break;
998 }
999 }
1000 *length_p = (FT_UShort)( p - table );
1001
1002 /* scan max ClassID in use */
1003 for ( i = 0; i < stateSize; i++ )
1004 if ( ( 3 < i ) && ( nGlyphInClass[i] > 0 ) )
1005 *maxClassID_p = (FT_Byte)i; /* XXX: Check Range? */
1006 }
1007
1008 Out:
1009 GXV_TRACE(( "Declared stateSize=0x%02x, Used maxClassID=0x%02x\n",
1010 stateSize, *maxClassID_p ));
1011 GXV_EXIT;
1012 }
1013
1014
1015 /* --------------------------- State Array ----------------------------- */
1016
1017 static void
1019 FT_UShort* length_p,
1020 FT_Byte maxClassID,
1021 FT_UShort stateSize,
1022 FT_Byte* maxState_p,
1023 FT_Byte* maxEntry_p,
1024 GXV_Validator gxvalid )
1025 {
1026 FT_Bytes p = table;
1027 FT_Bytes limit = table + *length_p;
1028 FT_Byte clazz;
1029 FT_Byte entry;
1030
1031 FT_UNUSED( stateSize ); /* for the non-debugging case */
1032
1033
1034 GXV_NAME_ENTER( "StateArray" );
1035
1036 GXV_TRACE(( "parse %d bytes by stateSize=%d maxClassID=%d\n",
1037 (int)(*length_p), stateSize, (int)(maxClassID) ));
1038
1039 /*
1040 * 2 states are predefined and must be described in StateArray:
1041 * state 0 (start of text), 1 (start of line)
1042 */
1043 GXV_LIMIT_CHECK( ( 1 + maxClassID ) * 2 );
1044
1045 *maxState_p = 0;
1046 *maxEntry_p = 0;
1047
1048 /* read if enough to read another state */
1049 while ( p + ( 1 + maxClassID ) <= limit )
1050 {
1051 (*maxState_p)++;
1052 for ( clazz = 0; clazz <= maxClassID; clazz++ )
1053 {
1054 entry = FT_NEXT_BYTE( p );
1055 *maxEntry_p = (FT_Byte)FT_MAX( *maxEntry_p, entry );
1056 }
1057 }
1058 GXV_TRACE(( "parsed: maxState=%d, maxEntry=%d\n",
1059 *maxState_p, *maxEntry_p ));
1060
1061 *length_p = (FT_UShort)( p - table );
1062
1063 GXV_EXIT;
1064 }
1065
1066
1067 /* --------------------------- Entry Table ----------------------------- */
1068
1069 static void
1071 FT_UShort* length_p,
1072 FT_Byte maxEntry,
1073 FT_UShort stateArray,
1074 FT_UShort stateArray_length,
1075 FT_Byte maxClassID,
1076 FT_Bytes statetable_table,
1077 FT_Bytes statetable_limit,
1078 GXV_Validator gxvalid )
1079 {
1080 FT_Bytes p = table;
1081 FT_Bytes limit = table + *length_p;
1082 FT_Byte entry;
1083 FT_Byte state;
1084 FT_Int entrySize = 2 + 2 + GXV_GLYPHOFFSET_SIZE( statetable );
1085
1087
1088
1089 GXV_NAME_ENTER( "EntryTable" );
1090
1091 GXV_TRACE(( "maxEntry=%d entrySize=%d\n", maxEntry, entrySize ));
1092
1093 if ( ( maxEntry + 1 ) * entrySize > *length_p )
1094 {
1096
1097 /* ftxvalidator and FontValidator both warn and continue */
1098 maxEntry = (FT_Byte)( *length_p / entrySize - 1 );
1099 GXV_TRACE(( "too large maxEntry, shrinking to %d fit EntryTable length\n",
1100 maxEntry ));
1101 }
1102
1103 for ( entry = 0; entry <= maxEntry; entry++ )
1104 {
1105 FT_UShort newState;
1107
1108
1109 GXV_LIMIT_CHECK( 2 + 2 );
1110 newState = FT_NEXT_USHORT( p );
1111 flags = FT_NEXT_USHORT( p );
1112
1113
1114 if ( newState < stateArray ||
1115 stateArray + stateArray_length < newState )
1116 {
1117 GXV_TRACE(( " newState offset 0x%04x is out of stateArray\n",
1118 newState ));
1120 continue;
1121 }
1122
1123 if ( 0 != ( ( newState - stateArray ) % ( 1 + maxClassID ) ) )
1124 {
1125 GXV_TRACE(( " newState offset 0x%04x is not aligned to %d-classes\n",
1126 newState, 1 + maxClassID ));
1128 continue;
1129 }
1130
1131 state = (FT_Byte)( ( newState - stateArray ) / ( 1 + maxClassID ) );
1132
1133 switch ( GXV_GLYPHOFFSET_FMT( statetable ) )
1134 {
1136 glyphOffset.uc = 0; /* make compiler happy */
1137 break;
1138
1140 glyphOffset.uc = FT_NEXT_BYTE( p );
1141 break;
1142
1144 glyphOffset.c = FT_NEXT_CHAR( p );
1145 break;
1146
1148 glyphOffset.u = FT_NEXT_USHORT( p );
1149 break;
1150
1152 glyphOffset.s = FT_NEXT_SHORT( p );
1153 break;
1154
1156 glyphOffset.ul = FT_NEXT_ULONG( p );
1157 break;
1158
1160 glyphOffset.l = FT_NEXT_LONG( p );
1161 break;
1162 }
1163
1164 if ( gxvalid->statetable.entry_validate_func )
1166 flags,
1167 &glyphOffset,
1168 statetable_table,
1169 statetable_limit,
1170 gxvalid );
1171 }
1172
1173 *length_p = (FT_UShort)( p - table );
1174
1175 GXV_EXIT;
1176 }
1177
1178
1179 /* =========================== State Table ============================= */
1180
1181 FT_LOCAL_DEF( void )
1183 FT_UShort classTable,
1184 FT_UShort stateArray,
1185 FT_UShort entryTable,
1186 FT_UShort* classTable_length_p,
1187 FT_UShort* stateArray_length_p,
1188 FT_UShort* entryTable_length_p,
1189 GXV_Validator gxvalid )
1190 {
1191 FT_UShort o[3];
1192 FT_UShort* l[3];
1193 FT_UShort buff[4];
1194
1195
1196 o[0] = classTable;
1197 o[1] = stateArray;
1198 o[2] = entryTable;
1199 l[0] = classTable_length_p;
1200 l[1] = stateArray_length_p;
1201 l[2] = entryTable_length_p;
1202
1204 }
1205
1206
1207 FT_LOCAL_DEF( void )
1210 GXV_Validator gxvalid )
1211 {
1212 FT_UShort stateSize;
1213 FT_UShort classTable; /* offset to Class(Sub)Table */
1214 FT_UShort stateArray; /* offset to StateArray */
1215 FT_UShort entryTable; /* offset to EntryTable */
1216
1217 FT_UShort classTable_length;
1218 FT_UShort stateArray_length;
1219 FT_UShort entryTable_length;
1220 FT_Byte maxClassID;
1221 FT_Byte maxState;
1222 FT_Byte maxEntry;
1223
1225
1226 FT_Bytes p = table;
1227
1228
1229 GXV_NAME_ENTER( "StateTable" );
1230
1231 GXV_TRACE(( "StateTable header\n" ));
1232
1233 GXV_LIMIT_CHECK( 2 + 2 + 2 + 2 );
1234 stateSize = FT_NEXT_USHORT( p );
1235 classTable = FT_NEXT_USHORT( p );
1236 stateArray = FT_NEXT_USHORT( p );
1237 entryTable = FT_NEXT_USHORT( p );
1238
1239 GXV_TRACE(( "stateSize=0x%04x\n", stateSize ));
1240 GXV_TRACE(( "offset to classTable=0x%04x\n", classTable ));
1241 GXV_TRACE(( "offset to stateArray=0x%04x\n", stateArray ));
1242 GXV_TRACE(( "offset to entryTable=0x%04x\n", entryTable ));
1243
1244 if ( stateSize > 0xFF )
1246
1247 if ( gxvalid->statetable.optdata_load_func )
1248 gxvalid->statetable.optdata_load_func( p, limit, gxvalid );
1249
1250 if ( gxvalid->statetable.subtable_setup_func )
1251 setup_func = gxvalid->statetable.subtable_setup_func;
1252 else
1253 setup_func = gxv_StateTable_subtable_setup;
1254
1255 setup_func( (FT_UShort)( limit - table ),
1256 classTable,
1257 stateArray,
1258 entryTable,
1259 &classTable_length,
1260 &stateArray_length,
1261 &entryTable_length,
1262 gxvalid );
1263
1264 GXV_TRACE(( "StateTable Subtables\n" ));
1265
1266 if ( classTable != 0 )
1267 gxv_ClassTable_validate( table + classTable,
1268 &classTable_length,
1269 stateSize,
1270 &maxClassID,
1271 gxvalid );
1272 else
1273 maxClassID = (FT_Byte)( stateSize - 1 );
1274
1275 if ( stateArray != 0 )
1276 gxv_StateArray_validate( table + stateArray,
1277 &stateArray_length,
1278 maxClassID,
1279 stateSize,
1280 &maxState,
1281 &maxEntry,
1282 gxvalid );
1283 else
1284 {
1285#if 0
1286 maxState = 1; /* 0:start of text, 1:start of line are predefined */
1287#endif
1288 maxEntry = 0;
1289 }
1290
1291 if ( maxEntry > 0 && entryTable == 0 )
1293
1294 if ( entryTable != 0 )
1295 gxv_EntryTable_validate( table + entryTable,
1296 &entryTable_length,
1297 maxEntry,
1298 stateArray,
1299 stateArray_length,
1300 maxClassID,
1301 table,
1302 limit,
1303 gxvalid );
1304
1305 GXV_EXIT;
1306 }
1307
1308
1309 /* ================= eXtended State Table (for morx) =================== */
1310
1311 FT_LOCAL_DEF( void )
1313 FT_ULong classTable,
1314 FT_ULong stateArray,
1315 FT_ULong entryTable,
1316 FT_ULong* classTable_length_p,
1317 FT_ULong* stateArray_length_p,
1318 FT_ULong* entryTable_length_p,
1319 GXV_Validator gxvalid )
1320 {
1321 FT_ULong o[3];
1322 FT_ULong* l[3];
1323 FT_ULong buff[4];
1324
1325
1326 o[0] = classTable;
1327 o[1] = stateArray;
1328 o[2] = entryTable;
1329 l[0] = classTable_length_p;
1330 l[1] = stateArray_length_p;
1331 l[2] = entryTable_length_p;
1332
1333 gxv_set_length_by_ulong_offset( o, l, buff, 3, table_size, gxvalid );
1334 }
1335
1336
1337 static void
1339 GXV_LookupValueCPtr value_p,
1340 GXV_Validator gxvalid )
1341 {
1342 FT_UNUSED( glyph );
1343
1344 if ( value_p->u >= gxvalid->xstatetable.nClasses )
1346 if ( value_p->u > gxvalid->xstatetable.maxClassID )
1347 gxvalid->xstatetable.maxClassID = value_p->u;
1348 }
1349
1350
1351 /*
1352 +===============+ --------+
1353 | lookup header | |
1354 +===============+ |
1355 | BinSrchHeader | |
1356 +===============+ |
1357 | lastGlyph[0] | |
1358 +---------------+ |
1359 | firstGlyph[0] | | head of lookup table
1360 +---------------+ | +
1361 | offset[0] | -> | offset [byte]
1362 +===============+ | +
1363 | lastGlyph[1] | | (glyphID - firstGlyph) * 2 [byte]
1364 +---------------+ |
1365 | firstGlyph[1] | |
1366 +---------------+ |
1367 | offset[1] | |
1368 +===============+ |
1369 |
1370 .... |
1371 |
1372 16bit value array |
1373 +===============+ |
1374 | value | <-------+
1375 ....
1376 */
1377 static GXV_LookupValueDesc
1379 GXV_LookupValueCPtr base_value_p,
1380 FT_Bytes lookuptbl_limit,
1381 GXV_Validator gxvalid )
1382 {
1383 FT_Bytes p;
1387
1388 /* XXX: check range? */
1389 offset = (FT_UShort)( base_value_p->u +
1390 relative_gindex * sizeof ( FT_UShort ) );
1391
1392 p = gxvalid->lookuptbl_head + offset;
1393 limit = lookuptbl_limit;
1394
1395 GXV_LIMIT_CHECK ( 2 );
1396 value.u = FT_NEXT_USHORT( p );
1397
1398 return value;
1399 }
1400
1401
1402 static void
1404 FT_ULong* length_p,
1405 FT_UShort maxClassID,
1406 FT_ULong stateSize,
1407 FT_UShort* maxState_p,
1408 FT_UShort* maxEntry_p,
1409 GXV_Validator gxvalid )
1410 {
1411 FT_Bytes p = table;
1412 FT_Bytes limit = table + *length_p;
1413 FT_UShort clazz;
1415
1416 FT_UNUSED( stateSize ); /* for the non-debugging case */
1417
1418
1419 GXV_NAME_ENTER( "XStateArray" );
1420
1421 GXV_TRACE(( "parse % 3d bytes by stateSize=% 3d maxClassID=% 3d\n",
1422 (int)(*length_p), stateSize, (int)(maxClassID) ));
1423
1424 /*
1425 * 2 states are predefined and must be described:
1426 * state 0 (start of text), 1 (start of line)
1427 */
1428 GXV_LIMIT_CHECK( ( 1 + maxClassID ) * 2 * 2 );
1429
1430 *maxState_p = 0;
1431 *maxEntry_p = 0;
1432
1433 /* read if enough to read another state */
1434 while ( p + ( ( 1 + maxClassID ) * 2 ) <= limit )
1435 {
1436 (*maxState_p)++;
1437 for ( clazz = 0; clazz <= maxClassID; clazz++ )
1438 {
1439 entry = FT_NEXT_USHORT( p );
1440 *maxEntry_p = (FT_UShort)FT_MAX( *maxEntry_p, entry );
1441 }
1442 }
1443 GXV_TRACE(( "parsed: maxState=%d, maxEntry=%d\n",
1444 *maxState_p, *maxEntry_p ));
1445
1446 *length_p = (FT_ULong)( p - table );
1447
1448 GXV_EXIT;
1449 }
1450
1451
1452 static void
1454 FT_ULong* length_p,
1455 FT_UShort maxEntry,
1456 FT_ULong stateArray_length,
1457 FT_UShort maxClassID,
1458 FT_Bytes xstatetable_table,
1459 FT_Bytes xstatetable_limit,
1460 GXV_Validator gxvalid )
1461 {
1462 FT_Bytes p = table;
1463 FT_Bytes limit = table + *length_p;
1466 FT_Int entrySize = 2 + 2 + GXV_GLYPHOFFSET_SIZE( xstatetable );
1467
1468
1469 GXV_NAME_ENTER( "XEntryTable" );
1470 GXV_TRACE(( "maxEntry=%d entrySize=%d\n", maxEntry, entrySize ));
1471
1472 if ( ( p + ( maxEntry + 1 ) * entrySize ) > limit )
1474
1475 for (entry = 0; entry <= maxEntry; entry++ )
1476 {
1477 FT_UShort newState_idx;
1480
1481
1482 GXV_LIMIT_CHECK( 2 + 2 );
1483 newState_idx = FT_NEXT_USHORT( p );
1484 flags = FT_NEXT_USHORT( p );
1485
1486 if ( stateArray_length < (FT_ULong)( newState_idx * 2 ) )
1487 {
1488 GXV_TRACE(( " newState index 0x%04x points out of stateArray\n",
1489 newState_idx ));
1491 }
1492
1493 state = (FT_UShort)( newState_idx / ( 1 + maxClassID ) );
1494 if ( 0 != ( newState_idx % ( 1 + maxClassID ) ) )
1495 {
1496 FT_TRACE4(( "-> new state = %d (supposed)\n"
1497 "but newState index 0x%04x is not aligned to %d-classes\n",
1498 state, newState_idx, 1 + maxClassID ));
1500 }
1501
1502 switch ( GXV_GLYPHOFFSET_FMT( xstatetable ) )
1503 {
1505 glyphOffset.uc = 0; /* make compiler happy */
1506 break;
1507
1509 glyphOffset.uc = FT_NEXT_BYTE( p );
1510 break;
1511
1513 glyphOffset.c = FT_NEXT_CHAR( p );
1514 break;
1515
1517 glyphOffset.u = FT_NEXT_USHORT( p );
1518 break;
1519
1521 glyphOffset.s = FT_NEXT_SHORT( p );
1522 break;
1523
1525 glyphOffset.ul = FT_NEXT_ULONG( p );
1526 break;
1527
1529 glyphOffset.l = FT_NEXT_LONG( p );
1530 break;
1531
1532 default:
1534 goto Exit;
1535 }
1536
1537 if ( gxvalid->xstatetable.entry_validate_func )
1539 flags,
1540 &glyphOffset,
1541 xstatetable_table,
1542 xstatetable_limit,
1543 gxvalid );
1544 }
1545
1546 Exit:
1547 *length_p = (FT_ULong)( p - table );
1548
1549 GXV_EXIT;
1550 }
1551
1552
1553 FT_LOCAL_DEF( void )
1556 GXV_Validator gxvalid )
1557 {
1558 /* StateHeader members */
1559 FT_ULong classTable; /* offset to Class(Sub)Table */
1560 FT_ULong stateArray; /* offset to StateArray */
1561 FT_ULong entryTable; /* offset to EntryTable */
1562
1563 FT_ULong classTable_length;
1564 FT_ULong stateArray_length;
1565 FT_ULong entryTable_length;
1566 FT_UShort maxState;
1567 FT_UShort maxEntry;
1568
1570
1571 FT_Bytes p = table;
1572
1573
1574 GXV_NAME_ENTER( "XStateTable" );
1575
1576 GXV_TRACE(( "XStateTable header\n" ));
1577
1578 GXV_LIMIT_CHECK( 4 + 4 + 4 + 4 );
1579 gxvalid->xstatetable.nClasses = FT_NEXT_ULONG( p );
1580 classTable = FT_NEXT_ULONG( p );
1581 stateArray = FT_NEXT_ULONG( p );
1582 entryTable = FT_NEXT_ULONG( p );
1583
1584 GXV_TRACE(( "nClasses =0x%08x\n", gxvalid->xstatetable.nClasses ));
1585 GXV_TRACE(( "offset to classTable=0x%08x\n", classTable ));
1586 GXV_TRACE(( "offset to stateArray=0x%08x\n", stateArray ));
1587 GXV_TRACE(( "offset to entryTable=0x%08x\n", entryTable ));
1588
1589 if ( gxvalid->xstatetable.nClasses > 0xFFFFU )
1591
1592 GXV_TRACE(( "StateTable Subtables\n" ));
1593
1594 if ( gxvalid->xstatetable.optdata_load_func )
1595 gxvalid->xstatetable.optdata_load_func( p, limit, gxvalid );
1596
1597 if ( gxvalid->xstatetable.subtable_setup_func )
1598 setup_func = gxvalid->xstatetable.subtable_setup_func;
1599 else
1600 setup_func = gxv_XStateTable_subtable_setup;
1601
1602 setup_func( (FT_ULong)( limit - table ),
1603 classTable,
1604 stateArray,
1605 entryTable,
1606 &classTable_length,
1607 &stateArray_length,
1608 &entryTable_length,
1609 gxvalid );
1610
1611 if ( classTable != 0 )
1612 {
1613 gxvalid->xstatetable.maxClassID = 0;
1614 gxvalid->lookupval_sign = GXV_LOOKUPVALUE_UNSIGNED;
1615 gxvalid->lookupval_func = gxv_XClassTable_lookupval_validate;
1616 gxvalid->lookupfmt4_trans = gxv_XClassTable_lookupfmt4_transit;
1617 gxv_LookupTable_validate( table + classTable,
1618 table + classTable + classTable_length,
1619 gxvalid );
1620#if 0
1621 if ( gxvalid->subtable_length < classTable_length )
1622 classTable_length = gxvalid->subtable_length;
1623#endif
1624 }
1625 else
1626 {
1627 /* XXX: check range? */
1628 gxvalid->xstatetable.maxClassID =
1629 (FT_UShort)( gxvalid->xstatetable.nClasses - 1 );
1630 }
1631
1632 if ( stateArray != 0 )
1633 gxv_XStateArray_validate( table + stateArray,
1634 &stateArray_length,
1635 gxvalid->xstatetable.maxClassID,
1636 gxvalid->xstatetable.nClasses,
1637 &maxState,
1638 &maxEntry,
1639 gxvalid );
1640 else
1641 {
1642#if 0
1643 maxState = 1; /* 0:start of text, 1:start of line are predefined */
1644#endif
1645 maxEntry = 0;
1646 }
1647
1648 if ( maxEntry > 0 && entryTable == 0 )
1650
1651 if ( entryTable != 0 )
1652 gxv_XEntryTable_validate( table + entryTable,
1653 &entryTable_length,
1654 maxEntry,
1655 stateArray_length,
1656 gxvalid->xstatetable.maxClassID,
1657 table,
1658 limit,
1659 gxvalid );
1660
1661 GXV_EXIT;
1662 }
1663
1664
1665 /*************************************************************************/
1666 /*************************************************************************/
1667 /***** *****/
1668 /***** Table overlapping *****/
1669 /***** *****/
1670 /*************************************************************************/
1671 /*************************************************************************/
1672
1673 static int
1675 FT_ULong table1_length,
1676 FT_Bytes table2_start,
1677 FT_ULong table2_length )
1678 {
1679 if ( table1_start == table2_start )
1680 {
1681 if ( ( table1_length == 0 || table2_length == 0 ) )
1682 goto Out;
1683 }
1684 else if ( table1_start < table2_start )
1685 {
1686 if ( ( table1_start + table1_length ) <= table2_start )
1687 goto Out;
1688 }
1689 else if ( table1_start > table2_start )
1690 {
1691 if ( ( table1_start >= table2_start + table2_length ) )
1692 goto Out;
1693 }
1694 return 1;
1695
1696 Out:
1697 return 0;
1698 }
1699
1700
1701 FT_LOCAL_DEF( void )
1705 GXV_odtect_Range odtect )
1706 {
1707 odtect->range[odtect->nRanges].start = start;
1708 odtect->range[odtect->nRanges].length = length;
1709 odtect->range[odtect->nRanges].name = (FT_String*)name;
1710 odtect->nRanges++;
1711 }
1712
1713
1714 FT_LOCAL_DEF( void )
1716 GXV_Validator gxvalid )
1717 {
1718 FT_UInt i, j;
1719
1720
1721 GXV_NAME_ENTER( "check overlap among multi ranges" );
1722
1723 for ( i = 0; i < odtect->nRanges; i++ )
1724 for ( j = 0; j < i; j++ )
1725 if ( 0 != gxv_compare_ranges( odtect->range[i].start,
1726 odtect->range[i].length,
1727 odtect->range[j].start,
1728 odtect->range[j].length ) )
1729 {
1730#ifdef FT_DEBUG_LEVEL_TRACE
1731 if ( odtect->range[i].name || odtect->range[j].name )
1732 GXV_TRACE(( "found overlap between range %d and range %d\n",
1733 i, j ));
1734 else
1735 GXV_TRACE(( "found overlap between `%s' and `%s\'\n",
1736 odtect->range[i].name,
1737 odtect->range[j].name ));
1738#endif
1740 }
1741
1742 GXV_EXIT;
1743 }
1744
1745
1746/* END */
static int state
Definition: maze.c:121
r l[0]
Definition: byte_order.h:168
@ Out
#define NULL
Definition: types.h:112
WORD face[3]
Definition: mesh.c:4747
static unsigned char buff[32768]
Definition: fatten.c:17
FT_Load_Glyph(FT_Face face, FT_UInt glyph_index, FT_Int32 load_flags)
Definition: ftobjs.c:760
#define FT_LOAD_NO_BITMAP
Definition: freetype.h:3012
#define FT_LOAD_IGNORE_TRANSFORM
Definition: freetype.h:3019
return FT_Err_Ok
Definition: ftbbox.c:511
#define FT_LOCAL_DEF(x)
Definition: ftconfig.h:388
#define FT_UNUSED(arg)
Definition: ftconfig.h:101
#define FT_TRACE1(varformat)
Definition: ftdebug.h:158
#define FT_TRACE4(varformat)
Definition: ftdebug.h:161
#define FT_MEM_ZERO(dest, count)
Definition: ftmemory.h:235
#define FT_MIN(a, b)
Definition: ftobjs.h:71
#define FT_MAX(a, b)
Definition: ftobjs.h:72
FT_Get_Sfnt_Name_Count(FT_Face face)
FT_BEGIN_HEADER struct FT_SfntName_ FT_SfntName
FT_Get_Sfnt_Name(FT_Face face, FT_UInt idx, FT_SfntName *aname)
#define ft_qsort
Definition: ftstdlib.h:122
#define FT_NEXT_USHORT(buffer)
Definition: ftstream.h:226
#define FT_NEXT_CHAR(buffer)
Definition: ftstream.h:217
#define FT_NEXT_LONG(buffer)
Definition: ftstream.h:235
#define FT_NEXT_SHORT(buffer)
Definition: ftstream.h:223
#define FT_NEXT_ULONG(buffer)
Definition: ftstream.h:238
#define FT_NEXT_BYTE(buffer)
Definition: ftstream.h:220
unsigned long FT_ULong
Definition: fttypes.h:253
unsigned char FT_Byte
Definition: fttypes.h:154
int FT_Error
Definition: fttypes.h:300
unsigned short FT_UShort
Definition: fttypes.h:209
char FT_String
Definition: fttypes.h:187
unsigned int FT_UInt
Definition: fttypes.h:231
const FT_Byte * FT_Bytes
Definition: fttypes.h:165
signed int FT_Int
Definition: fttypes.h:220
#define FT_INVALID_FORMAT
Definition: ftvalid.h:142
@ FT_VALIDATE_TIGHT
Definition: ftvalid.h:73
#define FT_INVALID_TOO_SHORT
Definition: ftvalid.h:134
#define FT_INVALID_OFFSET
Definition: ftvalid.h:138
#define FT_INVALID_DATA
Definition: ftvalid.h:150
#define FT_INVALID_GLYPH_ID
Definition: ftvalid.h:146
GLuint start
Definition: gl.h:1545
const GLdouble * v
Definition: gl.h:2040
GLenum func
Definition: glext.h:6028
GLenum GLuint GLint GLenum face
Definition: glext.h:7025
GLboolean GLboolean GLboolean b
Definition: glext.h:6204
GLint limit
Definition: glext.h:10326
GLbitfield flags
Definition: glext.h:7161
GLuint GLsizei GLsizei * length
Definition: glext.h:6040
GLenum const GLvoid GLbitfield GLuint firstGlyph
Definition: glext.h:11716
GLuint GLfloat * val
Definition: glext.h:7180
GLfloat GLfloat p
Definition: glext.h:8902
GLboolean GLboolean GLboolean GLboolean a
Definition: glext.h:6204
GLintptr offset
Definition: glext.h:5920
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
gxv_array_getlimits_byte(FT_Bytes table, FT_Bytes limit, FT_Byte *min, FT_Byte *max, GXV_Validator gxvalid)
Definition: gxvcommn.c:181
static void gxv_LookupTable_fmt6_skip_endmarkers(FT_Bytes table, FT_UShort unitSize, GXV_Validator gxvalid)
Definition: gxvcommn.c:646
static void gxv_LookupTable_fmt6_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:665
gxv_ctlPoint_validate(FT_UShort gid, FT_UShort ctl_point, GXV_Validator gxvalid)
Definition: gxvcommn.c:846
gxv_BinSrchHeader_validate(FT_Bytes table, FT_Bytes limit, FT_UShort *unitSize_p, FT_UShort *nUnits_p, GXV_Validator gxvalid)
Definition: gxvcommn.c:328
gxv_array_getlimits_ushort(FT_Bytes table, FT_Bytes limit, FT_UShort *min, FT_UShort *max, GXV_Validator gxvalid)
Definition: gxvcommn.c:210
static void gxv_LookupTable_fmt0_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:423
#define GXV_LOOKUP_VALUE_LOAD(P, SIGNSPEC)
Definition: gxvcommn.c:383
static int gxv_compare_ranges(FT_Bytes table1_start, FT_ULong table1_length, FT_Bytes table2_start, FT_ULong table2_length)
Definition: gxvcommn.c:1674
gxv_StateTable_subtable_setup(FT_UShort table_size, FT_UShort classTable, FT_UShort stateArray, FT_UShort entryTable, FT_UShort *classTable_length_p, FT_UShort *stateArray_length_p, FT_UShort *entryTable_length_p, GXV_Validator gxvalid)
Definition: gxvcommn.c:1182
gxv_set_length_by_ushort_offset(FT_UShort *offset, FT_UShort **length, FT_UShort *buff, FT_UInt nmemb, FT_UShort limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:63
static int gxv_compare_ulong_offset(FT_ULong *a, FT_ULong *b)
Definition: gxvcommn.c:115
gxv_StateTable_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:1208
static void gxv_XStateArray_validate(FT_Bytes table, FT_ULong *length_p, FT_UShort maxClassID, FT_ULong stateSize, FT_UShort *maxState_p, FT_UShort *maxEntry_p, GXV_Validator gxvalid)
Definition: gxvcommn.c:1403
gxv_LookupTable_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:755
gxv_odtect_add_range(FT_Bytes start, FT_ULong length, const FT_String *name, GXV_odtect_Range odtect)
Definition: gxvcommn.c:1702
static void gxv_StateArray_validate(FT_Bytes table, FT_UShort *length_p, FT_Byte maxClassID, FT_UShort stateSize, FT_Byte *maxState_p, FT_Byte *maxEntry_p, GXV_Validator gxvalid)
Definition: gxvcommn.c:1018
static int gxv_compare_ushort_offset(FT_UShort *a, FT_UShort *b)
Definition: gxvcommn.c:50
gxv_glyphid_validate(FT_UShort gid, GXV_Validator gxvalid)
Definition: gxvcommn.c:813
static void gxv_LookupTable_fmt8_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:719
gxv_XStateTable_subtable_setup(FT_ULong table_size, FT_ULong classTable, FT_ULong stateArray, FT_ULong entryTable, FT_ULong *classTable_length_p, FT_ULong *stateArray_length_p, FT_ULong *entryTable_length_p, GXV_Validator gxvalid)
Definition: gxvcommn.c:1312
gxv_odtect_validate(GXV_odtect_Range odtect, GXV_Validator gxvalid)
Definition: gxvcommn.c:1715
static void gxv_LookupTable_fmt2_skip_endmarkers(FT_Bytes table, FT_UShort unitSize, GXV_Validator gxvalid)
Definition: gxvcommn.c:474
static void gxv_BinSrchHeader_check_consistency(GXV_BinSrchHeader *binSrchHeader, GXV_Validator gxvalid)
Definition: gxvcommn.c:258
static void gxv_EntryTable_validate(FT_Bytes table, FT_UShort *length_p, FT_Byte maxEntry, FT_UShort stateArray, FT_UShort stateArray_length, FT_Byte maxClassID, FT_Bytes statetable_table, FT_Bytes statetable_limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:1070
gxv_sfntName_validate(FT_UShort name_index, FT_UShort min_index, FT_UShort max_index, GXV_Validator gxvalid)
Definition: gxvcommn.c:884
struct GXV_BinSrchHeader_ GXV_BinSrchHeader
gxv_set_length_by_ulong_offset(FT_ULong *offset, FT_ULong **length, FT_ULong *buff, FT_UInt nmemb, FT_ULong limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:128
static GXV_LookupValueDesc gxv_XClassTable_lookupfmt4_transit(FT_UShort relative_gindex, GXV_LookupValueCPtr base_value_p, FT_Bytes lookuptbl_limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:1378
static void gxv_ClassTable_validate(FT_Bytes table, FT_UShort *length_p, FT_UShort stateSize, FT_Byte *maxClassID_p, GXV_Validator gxvalid)
Definition: gxvcommn.c:942
gxv_XStateTable_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:1554
#define GXV_UNITSIZE_VALIDATE(FORMAT, UNITSIZE, NUNITS, CORRECTSIZE)
Definition: gxvcommn.c:402
static GXV_LookupValueDesc gxv_lookup_value_load(FT_Bytes p, int signspec)
Definition: gxvcommn.c:387
static void gxv_LookupTable_fmt4_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:565
static void gxv_LookupTable_fmt2_validate(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:494
static void gxv_XEntryTable_validate(FT_Bytes table, FT_ULong *length_p, FT_UShort maxEntry, FT_ULong stateArray_length, FT_UShort maxClassID, FT_Bytes xstatetable_table, FT_Bytes xstatetable_limit, GXV_Validator gxvalid)
Definition: gxvcommn.c:1453
static void gxv_XClassTable_lookupval_validate(FT_UShort glyph, GXV_LookupValueCPtr value_p, GXV_Validator gxvalid)
Definition: gxvcommn.c:1338
void(* GXV_Validate_Func)(FT_Bytes table, FT_Bytes limit, GXV_Validator gxvalid)
Definition: gxvcommn.h:82
#define GXV_GLYPHOFFSET_FMT(table)
Definition: gxvcommn.h:133
#define GXV_GLYPHOFFSET_SIZE(table)
Definition: gxvcommn.h:136
void(* GXV_XStateTable_Subtable_Setup_Func)(FT_ULong table_size, FT_ULong classTable, FT_ULong stateArray, FT_ULong entryTable, FT_ULong *classTable_length_p, FT_ULong *stateArray_length_p, FT_ULong *entryTable_length_p, GXV_Validator gxvalid)
Definition: gxvcommn.h:198
#define GXV_NAME_ENTER(name)
Definition: gxvcommn.h:301
#define GXV_SET_ERR_IF_PARANOID(err)
Definition: gxvcommn.h:66
@ GXV_LOOKUPVALUE_UNSIGNED
Definition: gxvcommn.h:100
#define GXV_TRACE(s)
Definition: gxvcommn.h:304
@ GXV_GLYPHOFFSET_SHORT
Definition: gxvcommn.h:126
@ GXV_GLYPHOFFSET_CHAR
Definition: gxvcommn.h:124
@ GXV_GLYPHOFFSET_USHORT
Definition: gxvcommn.h:125
@ GXV_GLYPHOFFSET_UCHAR
Definition: gxvcommn.h:123
@ GXV_GLYPHOFFSET_NONE
Definition: gxvcommn.h:122
@ GXV_GLYPHOFFSET_LONG
Definition: gxvcommn.h:128
@ GXV_GLYPHOFFSET_ULONG
Definition: gxvcommn.h:127
void(* GXV_StateTable_Subtable_Setup_Func)(FT_UShort table_size, FT_UShort classTable, FT_UShort stateArray, FT_UShort entryTable, FT_UShort *classTable_length_p, FT_UShort *stateArray_length_p, FT_UShort *entryTable_length_p, GXV_Validator gxvalid)
Definition: gxvcommn.h:156
#define GXV_TRACE_HEXDUMP_SFNTNAME(n)
Definition: gxvcommn.h:359
#define GXV_EXIT
Definition: gxvcommn.h:302
#define GXV_LIMIT_CHECK(_count)
Definition: gxvcommn.h:272
uint32_t entry
Definition: isohybrid.c:63
if(dx< 0)
Definition: linetemp.h:194
#define error(str)
Definition: mkdosfs.c:1605
#define min(a, b)
Definition: monoChain.cc:55
png_const_structrp png_const_inforp int * unit
Definition: png.h:2159
LOCAL int table_size
Definition: write.c:65
static void Exit(void)
Definition: sock.c:1330
FT_Long num_glyphs
Definition: freetype.h:1076
FT_Outline outline
Definition: freetype.h:1927
FT_UShort searchRange
Definition: gxvcommn.c:250
FT_UShort rangeShift
Definition: gxvcommn.c:252
FT_UShort nUnits
Definition: gxvcommn.c:249
FT_UShort unitSize
Definition: gxvcommn.c:248
FT_UShort entrySelector
Definition: gxvcommn.c:251
GXV_StateTable_Entry_Validate_Func entry_validate_func
Definition: gxvcommn.h:185
GXV_StateTable_ValidatorRec statetable
Definition: gxvcommn.h:254
GXV_XStateTable_ValidatorRec xstatetable
Definition: gxvcommn.h:255
GXV_Lookup_Fmt4_Transit_Func lookupfmt4_trans
Definition: gxvcommn.h:248
FT_Validator root
Definition: gxvcommn.h:239
FT_Bytes lookuptbl_head
Definition: gxvcommn.h:249
FT_ULong subtable_length
Definition: gxvcommn.h:244
GXV_Lookup_Value_Validate_Func lookupval_func
Definition: gxvcommn.h:247
GXV_LookupValue_SignSpec lookupval_sign
Definition: gxvcommn.h:246
GXV_XStateTable_Entry_Validate_Func entry_validate_func
Definition: gxvcommn.h:226
Definition: format.c:58
Definition: name.c:39
Definition: mesh.c:5330
#define max(a, b)
Definition: svc.c:63
Definition: pdh_main.c:94
ActualNumberDriverObjects * sizeof(PDRIVER_OBJECT)) PDRIVER_OBJECT *DriverObjectList
#define const
Definition: zconf.h:233