sdk-world v2026.11.05
PS2 SDK - world tier (copyleft-allowed, non-essential packages)
Loading...
Searching...
No Matches
cffparse.c
1/****************************************************************************
2 *
3 * cffparse.c
4 *
5 * CFF token stream parser (body)
6 *
7 * Copyright (C) 1996-2025 by
8 * David Turner, Robert Wilhelm, and Werner Lemberg.
9 *
10 * This file is part of the FreeType project, and may only be used,
11 * modified, and distributed under the terms of the FreeType project
12 * license, LICENSE.TXT. By continuing to use, modify, or distribute
13 * this file you indicate that you have read the license and
14 * understand and accept it fully.
15 *
16 */
17
18
19#include "cffparse.h"
24#include <freetype/ftlist.h>
25
26#include "cfferrs.h"
27#include "cffload.h"
28
29
30 /**************************************************************************
31 *
32 * The macro FT_COMPONENT is used in trace mode. It is an implicit
33 * parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log
34 * messages during execution.
35 */
36#undef FT_COMPONENT
37#define FT_COMPONENT cffparse
38
39
40 FT_LOCAL_DEF( FT_Error )
41 cff_parser_init( CFF_Parser parser,
42 FT_UInt code,
43 void* object,
44 FT_Library library,
45 FT_UInt stackSize,
46 FT_UShort num_designs,
47 FT_UShort num_axes )
48 {
49 FT_Memory memory = library->memory; /* for FT_NEW_ARRAY */
50 FT_Error error; /* for FT_NEW_ARRAY */
51
52
53 FT_ZERO( parser );
54
55#if 0
56 parser->top = parser->stack;
57#endif
58 parser->object_code = code;
59 parser->object = object;
60 parser->library = library;
61 parser->num_designs = num_designs;
62 parser->num_axes = num_axes;
63
64 /* allocate the stack buffer */
65 if ( FT_QNEW_ARRAY( parser->stack, stackSize ) )
66 goto Exit;
67
68 parser->stackSize = stackSize;
69 parser->top = parser->stack; /* empty stack */
70
71 Exit:
72 return error;
73 }
74
75
76 FT_LOCAL_DEF( void )
77 cff_parser_done( CFF_Parser parser )
78 {
79 FT_Memory memory = parser->library->memory; /* for FT_FREE */
80
81
82 FT_FREE( parser->stack );
83
84#ifdef CFF_CONFIG_OPTION_OLD_ENGINE
85 FT_List_Finalize( &parser->t2_strings, NULL, memory, NULL );
86#endif
87 }
88
89
90 /* The parser limit checks in the next two functions are supposed */
91 /* to detect the immediate crossing of the stream boundary. They */
92 /* shall not be triggered from the distant t2_strings buffers. */
93
94 /* read an integer */
95 static FT_Long
96 cff_parse_integer( FT_Byte* start,
97 FT_Byte* limit )
98 {
99 FT_Byte* p = start;
100 FT_Int v = *p++;
101 FT_Long val = 0;
102
103
104 if ( v == 28 )
105 {
106 if ( p + 2 > limit && limit >= p )
107 goto Bad;
108
109 val = (FT_Short)( ( (FT_UShort)p[0] << 8 ) | p[1] );
110 }
111 else if ( v == 29 )
112 {
113 if ( p + 4 > limit && limit >= p )
114 goto Bad;
115
116 val = (FT_Long)( ( (FT_ULong)p[0] << 24 ) |
117 ( (FT_ULong)p[1] << 16 ) |
118 ( (FT_ULong)p[2] << 8 ) |
119 (FT_ULong)p[3] );
120 }
121 else if ( v < 247 )
122 {
123 val = v - 139;
124 }
125 else if ( v < 251 )
126 {
127 if ( p + 1 > limit && limit >= p )
128 goto Bad;
129
130 val = ( v - 247 ) * 256 + p[0] + 108;
131 }
132 else
133 {
134 if ( p + 1 > limit && limit >= p )
135 goto Bad;
136
137 val = -( v - 251 ) * 256 - p[0] - 108;
138 }
139
140 Exit:
141 return val;
142
143 Bad:
144 val = 0;
145 FT_TRACE4(( "!!!END OF DATA:!!!" ));
146 goto Exit;
147 }
148
149
150 static const FT_Long power_tens[] =
151 {
152 1L,
153 10L,
154 100L,
155 1000L,
156 10000L,
157 100000L,
158 1000000L,
159 10000000L,
160 100000000L,
161 1000000000L
162 };
163
164 /* maximum values allowed for multiplying */
165 /* with the corresponding `power_tens' element */
166 static const FT_Long power_ten_limits[] =
167 {
168 FT_LONG_MAX / 1L,
169 FT_LONG_MAX / 10L,
170 FT_LONG_MAX / 100L,
171 FT_LONG_MAX / 1000L,
172 FT_LONG_MAX / 10000L,
173 FT_LONG_MAX / 100000L,
174 FT_LONG_MAX / 1000000L,
175 FT_LONG_MAX / 10000000L,
176 FT_LONG_MAX / 100000000L,
177 FT_LONG_MAX / 1000000000L,
178 };
179
180
181 /* read a real */
182 static FT_Fixed
183 cff_parse_real( FT_Byte* start,
184 FT_Byte* limit,
185 FT_Long power_ten,
186 FT_Long* scaling )
187 {
188 FT_Byte* p = start;
189 FT_Int nib;
190 FT_UInt phase;
191
192 FT_Long result, number, exponent;
193 FT_Int sign = 0, exponent_sign = 0, have_overflow = 0;
194 FT_Long exponent_add, integer_length, fraction_length;
195
196
197 if ( scaling )
198 *scaling = 0;
199
200 result = 0;
201
202 number = 0;
203 exponent = 0;
204
205 exponent_add = 0;
206 integer_length = 0;
207 fraction_length = 0;
208
209 /* First of all, read the integer part. */
210 phase = 4;
211
212 for (;;)
213 {
214 /* If we entered this iteration with phase == 4, we need to */
215 /* read a new byte. This also skips past the initial 0x1E. */
216 if ( phase )
217 {
218 p++;
219
220 /* Make sure we don't read past the end. */
221 if ( p + 1 > limit && limit >= p )
222 goto Bad;
223 }
224
225 /* Get the nibble. */
226 nib = (FT_Int)( p[0] >> phase ) & 0xF;
227 phase = 4 - phase;
228
229 if ( nib == 0xE )
230 sign = 1;
231 else if ( nib > 9 )
232 break;
233 else
234 {
235 /* Increase exponent if we can't add the digit. */
236 if ( number >= 0xCCCCCCCL )
237 exponent_add++;
238 /* Skip leading zeros. */
239 else if ( nib || number )
240 {
241 integer_length++;
242 number = number * 10 + nib;
243 }
244 }
245 }
246
247 /* Read fraction part, if any. */
248 if ( nib == 0xA )
249 for (;;)
250 {
251 /* If we entered this iteration with phase == 4, we need */
252 /* to read a new byte. */
253 if ( phase )
254 {
255 p++;
256
257 /* Make sure we don't read past the end. */
258 if ( p + 1 > limit && limit >= p )
259 goto Bad;
260 }
261
262 /* Get the nibble. */
263 nib = ( p[0] >> phase ) & 0xF;
264 phase = 4 - phase;
265 if ( nib >= 10 )
266 break;
267
268 /* Skip leading zeros if possible. */
269 if ( !nib && !number )
270 exponent_add--;
271 /* Only add digit if we don't overflow. */
272 else if ( number < 0xCCCCCCCL && fraction_length < 9 )
273 {
274 fraction_length++;
275 number = number * 10 + nib;
276 }
277 }
278
279 /* Read exponent, if any. */
280 if ( nib == 12 )
281 {
282 exponent_sign = 1;
283 nib = 11;
284 }
285
286 if ( nib == 11 )
287 {
288 for (;;)
289 {
290 /* If we entered this iteration with phase == 4, */
291 /* we need to read a new byte. */
292 if ( phase )
293 {
294 p++;
295
296 /* Make sure we don't read past the end. */
297 if ( p + 1 > limit && limit >= p )
298 goto Bad;
299 }
300
301 /* Get the nibble. */
302 nib = ( p[0] >> phase ) & 0xF;
303 phase = 4 - phase;
304 if ( nib >= 10 )
305 break;
306
307 /* Arbitrarily limit exponent. */
308 if ( exponent > 1000 )
309 have_overflow = 1;
310 else
311 exponent = exponent * 10 + nib;
312 }
313
314 if ( exponent_sign )
315 exponent = -exponent;
316 }
317
318 if ( !number )
319 goto Exit;
320
321 if ( have_overflow )
322 {
323 if ( exponent_sign )
324 goto Underflow;
325 else
326 goto Overflow;
327 }
328
329 /* We don't check `power_ten' and `exponent_add'. */
330 exponent += power_ten + exponent_add;
331
332 if ( scaling )
333 {
334 /* Only use `fraction_length'. */
335 fraction_length += integer_length;
336 exponent += integer_length;
337
338 if ( fraction_length <= 5 )
339 {
340 if ( number > 0x7FFFL )
341 {
342 result = FT_DivFix( number, 10 );
343 *scaling = exponent - fraction_length + 1;
344 }
345 else
346 {
347 if ( exponent > 0 )
348 {
349 FT_Long new_fraction_length, shift;
350
351
352 /* Make `scaling' as small as possible. */
353 new_fraction_length = FT_MIN( exponent, 5 );
354 shift = new_fraction_length - fraction_length;
355
356 if ( shift > 0 )
357 {
358 exponent -= new_fraction_length;
359 number *= power_tens[shift];
360 if ( number > 0x7FFFL )
361 {
362 number /= 10;
363 exponent += 1;
364 }
365 }
366 else
367 exponent -= fraction_length;
368 }
369 else
370 exponent -= fraction_length;
371
372 result = (FT_Long)( (FT_ULong)number << 16 );
373 *scaling = exponent;
374 }
375 }
376 else
377 {
378 if ( ( number / power_tens[fraction_length - 5] ) > 0x7FFFL )
379 {
380 result = FT_DivFix( number, power_tens[fraction_length - 4] );
381 *scaling = exponent - 4;
382 }
383 else
384 {
385 result = FT_DivFix( number, power_tens[fraction_length - 5] );
386 *scaling = exponent - 5;
387 }
388 }
389 }
390 else
391 {
392 integer_length += exponent;
393 fraction_length -= exponent;
394
395 if ( integer_length > 5 )
396 goto Overflow;
397 if ( integer_length < -5 )
398 goto Underflow;
399
400 /* Remove non-significant digits. */
401 if ( integer_length < 0 )
402 {
403 number /= power_tens[-integer_length];
404 fraction_length += integer_length;
405 }
406
407 /* this can only happen if exponent was non-zero */
408 if ( fraction_length == 10 )
409 {
410 number /= 10;
411 fraction_length -= 1;
412 }
413
414 /* Convert into 16.16 format. */
415 if ( fraction_length > 0 )
416 {
417 if ( ( number / power_tens[fraction_length] ) > 0x7FFFL )
418 goto Exit;
419
420 result = FT_DivFix( number, power_tens[fraction_length] );
421 }
422 else
423 {
424 number *= power_tens[-fraction_length];
425
426 if ( number > 0x7FFFL )
427 goto Overflow;
428
429 result = (FT_Long)( (FT_ULong)number << 16 );
430 }
431 }
432
433 Exit:
434 if ( sign )
435 result = -result;
436
437 return result;
438
439 Overflow:
440 result = 0x7FFFFFFFL;
441 FT_TRACE4(( "!!!OVERFLOW:!!!" ));
442 goto Exit;
443
444 Underflow:
445 result = 0;
446 FT_TRACE4(( "!!!UNDERFLOW:!!!" ));
447 goto Exit;
448
449 Bad:
450 result = 0;
451 FT_TRACE4(( "!!!END OF DATA:!!!" ));
452 goto Exit;
453 }
454
455
456 /* read a number, either integer or real */
457 FT_LOCAL_DEF( FT_Long )
458 cff_parse_num( CFF_Parser parser,
459 FT_Byte** d )
460 {
461 if ( **d == 30 )
462 {
463 /* binary-coded decimal is truncated to integer */
464 return cff_parse_real( *d, parser->limit, 0, NULL ) >> 16;
465 }
466
467 else if ( **d == 255 )
468 {
469 /* 16.16 fixed-point is used internally for CFF2 blend results. */
470 /* Since these are trusted values, a limit check is not needed. */
471
472 /* After the 255, 4 bytes give the number. */
473 /* The blend value is converted to integer, with rounding; */
474 /* due to the right-shift we don't need the lowest byte. */
475#if 0
476 return (FT_Short)(
477 ( ( ( (FT_UInt32)*( d[0] + 1 ) << 24 ) |
478 ( (FT_UInt32)*( d[0] + 2 ) << 16 ) |
479 ( (FT_UInt32)*( d[0] + 3 ) << 8 ) |
480 (FT_UInt32)*( d[0] + 4 ) ) + 0x8000U ) >> 16 );
481#else
482 return (FT_Short)(
483 ( ( ( (FT_UInt32)*( d[0] + 1 ) << 16 ) |
484 ( (FT_UInt32)*( d[0] + 2 ) << 8 ) |
485 (FT_UInt32)*( d[0] + 3 ) ) + 0x80U ) >> 8 );
486#endif
487 }
488
489 else
490 return cff_parse_integer( *d, parser->limit );
491 }
492
493
494 /* read a floating point number, either integer or real */
495 static FT_Fixed
496 do_fixed( CFF_Parser parser,
497 FT_Byte** d,
498 FT_Long scaling )
499 {
500 if ( **d == 30 )
501 return cff_parse_real( *d, parser->limit, scaling, NULL );
502 else if ( **d == 255 )
503 {
504 FT_Fixed val = (FT_Int32)( ( ( (FT_UInt32)*( d[0] + 1 ) << 24 ) |
505 ( (FT_UInt32)*( d[0] + 2 ) << 16 ) |
506 ( (FT_UInt32)*( d[0] + 3 ) << 8 ) |
507 (FT_UInt32)*( d[0] + 4 ) ) );
508
509 if ( scaling )
510 {
511 if ( FT_ABS( val ) > power_ten_limits[scaling] )
512 {
513 FT_TRACE4(( "!!!OVERFLOW:!!!" ));
514 return val > 0 ? 0x7FFFFFFFL : -0x7FFFFFFFL;
515 }
516 val *= power_tens[scaling];
517 }
518 return val;
519 }
520 else
521 {
522 FT_Long val = cff_parse_integer( *d, parser->limit );
523
524
525 if ( scaling )
526 {
527 if ( ( FT_ABS( val ) << 16 ) > power_ten_limits[scaling] )
528 {
529 val = val > 0 ? 0x7FFFFFFFL : -0x7FFFFFFFL;
530 goto Overflow;
531 }
532
533 val *= power_tens[scaling];
534 }
535
536 if ( val > 0x7FFF )
537 {
538 val = 0x7FFFFFFFL;
539 goto Overflow;
540 }
541 else if ( val < -0x7FFF )
542 {
543 val = -0x7FFFFFFFL;
544 goto Overflow;
545 }
546
547 return (FT_Long)( (FT_ULong)val << 16 );
548
549 Overflow:
550 FT_TRACE4(( "!!!OVERFLOW:!!!" ));
551 return val;
552 }
553 }
554
555
556 /* read a floating point number, either integer or real */
557 FT_LOCAL_DEF( FT_Fixed )
558 cff_parse_fixed( CFF_Parser parser,
559 FT_Byte** d )
560 {
561 return do_fixed( parser, d, 0 );
562 }
563
564
565 /* read a floating point number, either integer or real, */
566 /* but return `10^scaling' times the number read in */
567 static FT_Fixed
568 cff_parse_fixed_scaled( CFF_Parser parser,
569 FT_Byte** d,
570 FT_Long scaling )
571 {
572 return do_fixed( parser, d, scaling );
573 }
574
575
576 /* read a floating point number, either integer or real, */
577 /* and return it as precise as possible -- `scaling' returns */
578 /* the scaling factor (as a power of 10) */
579 static FT_Fixed
580 cff_parse_fixed_dynamic( CFF_Parser parser,
581 FT_Byte** d,
582 FT_Long* scaling )
583 {
584 FT_ASSERT( scaling );
585
586 if ( **d == 30 )
587 return cff_parse_real( *d, parser->limit, 0, scaling );
588 else
589 {
590 FT_Long number;
591 FT_Int integer_length;
592
593
594 number = cff_parse_integer( *d, parser->limit );
595
596 if ( number > 0x7FFFL )
597 {
598 for ( integer_length = 5; integer_length < 10; integer_length++ )
599 if ( number < power_tens[integer_length] )
600 break;
601
602 if ( ( number / power_tens[integer_length - 5] ) > 0x7FFFL )
603 {
604 *scaling = integer_length - 4;
605 return FT_DivFix( number, power_tens[integer_length - 4] );
606 }
607 else
608 {
609 *scaling = integer_length - 5;
610 return FT_DivFix( number, power_tens[integer_length - 5] );
611 }
612 }
613 else
614 {
615 *scaling = 0;
616 return (FT_Long)( (FT_ULong)number << 16 );
617 }
618 }
619 }
620
621
622 static FT_Error
623 cff_parse_font_matrix( CFF_Parser parser )
624 {
625 CFF_FontRecDict dict = (CFF_FontRecDict)parser->object;
626 FT_Matrix* matrix = &dict->font_matrix;
627 FT_Vector* offset = &dict->font_offset;
628 FT_ULong* upm = &dict->units_per_em;
629 FT_Byte** data = parser->stack;
630
631
632 if ( parser->top >= parser->stack + 6 )
633 {
634 FT_Fixed values[6];
635 FT_Long scalings[6];
636
637 FT_Long min_scaling, max_scaling;
638 int i;
639
640
641 dict->has_font_matrix = TRUE;
642
643 /* We expect a well-formed font matrix, that is, the matrix elements */
644 /* `xx' and `yy' are of approximately the same magnitude. To avoid */
645 /* loss of precision, we use the magnitude of the largest matrix */
646 /* element to scale all other elements. The scaling factor is then */
647 /* contained in the `units_per_em' value. */
648
649 max_scaling = FT_LONG_MIN;
650 min_scaling = FT_LONG_MAX;
651
652 for ( i = 0; i < 6; i++ )
653 {
654 values[i] = cff_parse_fixed_dynamic( parser, data++, &scalings[i] );
655 if ( values[i] )
656 {
657 if ( scalings[i] > max_scaling )
658 max_scaling = scalings[i];
659 if ( scalings[i] < min_scaling )
660 min_scaling = scalings[i];
661 }
662 }
663
664 if ( max_scaling < -9 ||
665 max_scaling > 0 ||
666 ( max_scaling - min_scaling ) < 0 ||
667 ( max_scaling - min_scaling ) > 9 )
668 {
669 FT_TRACE1(( "cff_parse_font_matrix:"
670 " strange scaling values (minimum %ld, maximum %ld),\n",
671 min_scaling, max_scaling ));
672 FT_TRACE1(( " "
673 " using default matrix\n" ));
674 goto Unlikely;
675 }
676
677 for ( i = 0; i < 6; i++ )
678 {
679 FT_Fixed value = values[i];
680 FT_Long divisor, half_divisor;
681
682
683 if ( !value )
684 continue;
685
686 divisor = power_tens[max_scaling - scalings[i]];
687 half_divisor = divisor >> 1;
688
689 if ( value < 0 )
690 {
691 if ( FT_LONG_MIN + half_divisor < value )
692 values[i] = ( value - half_divisor ) / divisor;
693 else
694 values[i] = FT_LONG_MIN / divisor;
695 }
696 else
697 {
698 if ( FT_LONG_MAX - half_divisor > value )
699 values[i] = ( value + half_divisor ) / divisor;
700 else
701 values[i] = FT_LONG_MAX / divisor;
702 }
703 }
704
705 matrix->xx = values[0];
706 matrix->yx = values[1];
707 matrix->xy = values[2];
708 matrix->yy = values[3];
709 offset->x = values[4];
710 offset->y = values[5];
711
712 *upm = (FT_ULong)power_tens[-max_scaling];
713
714 FT_TRACE4(( " [%f %f %f %f %f %f]\n",
715 (double)matrix->xx / (double)*upm / 65536,
716 (double)matrix->xy / (double)*upm / 65536,
717 (double)matrix->yx / (double)*upm / 65536,
718 (double)matrix->yy / (double)*upm / 65536,
719 (double)offset->x / (double)*upm / 65536,
720 (double)offset->y / (double)*upm / 65536 ));
721
722 if ( !FT_Matrix_Check( matrix ) )
723 {
724 FT_TRACE1(( "cff_parse_font_matrix:"
725 " degenerate values, using default matrix\n" ));
726 goto Unlikely;
727 }
728
729 return FT_Err_Ok;
730 }
731 else
732 return FT_THROW( Stack_Underflow );
733
734 Unlikely:
735 /* Return default matrix in case of unlikely values. */
736
737 matrix->xx = 0x10000L;
738 matrix->yx = 0;
739 matrix->xy = 0;
740 matrix->yy = 0x10000L;
741 offset->x = 0;
742 offset->y = 0;
743 *upm = 1;
744
745 return FT_Err_Ok;
746 }
747
748
749 static FT_Error
750 cff_parse_font_bbox( CFF_Parser parser )
751 {
752 CFF_FontRecDict dict = (CFF_FontRecDict)parser->object;
753 FT_BBox* bbox = &dict->font_bbox;
754 FT_Byte** data = parser->stack;
755 FT_Error error;
756
757
758 error = FT_ERR( Stack_Underflow );
759
760 if ( parser->top >= parser->stack + 4 )
761 {
762 bbox->xMin = FT_RoundFix( cff_parse_fixed( parser, data++ ) );
763 bbox->yMin = FT_RoundFix( cff_parse_fixed( parser, data++ ) );
764 bbox->xMax = FT_RoundFix( cff_parse_fixed( parser, data++ ) );
765 bbox->yMax = FT_RoundFix( cff_parse_fixed( parser, data ) );
766 error = FT_Err_Ok;
767
768 FT_TRACE4(( " [%ld %ld %ld %ld]\n",
769 bbox->xMin / 65536,
770 bbox->yMin / 65536,
771 bbox->xMax / 65536,
772 bbox->yMax / 65536 ));
773 }
774
775 return error;
776 }
777
778
779 static FT_Error
780 cff_parse_private_dict( CFF_Parser parser )
781 {
782 CFF_FontRecDict dict = (CFF_FontRecDict)parser->object;
783 FT_Byte** data = parser->stack;
784 FT_Error error;
785
786
787 error = FT_ERR( Stack_Underflow );
788
789 if ( parser->top >= parser->stack + 2 )
790 {
791 FT_Long tmp;
792
793
794 tmp = cff_parse_num( parser, data++ );
795 if ( tmp < 0 )
796 {
797 FT_ERROR(( "cff_parse_private_dict: Invalid dictionary size\n" ));
798 error = FT_THROW( Invalid_File_Format );
799 goto Fail;
800 }
801 dict->private_size = (FT_ULong)tmp;
802
803 tmp = cff_parse_num( parser, data );
804 if ( tmp < 0 )
805 {
806 FT_ERROR(( "cff_parse_private_dict: Invalid dictionary offset\n" ));
807 error = FT_THROW( Invalid_File_Format );
808 goto Fail;
809 }
810 dict->private_offset = (FT_ULong)tmp;
811
812 FT_TRACE4(( " %lu %lu\n",
813 dict->private_size, dict->private_offset ));
814
815 error = FT_Err_Ok;
816 }
817
818 Fail:
819 return error;
820 }
821
822
823 /* The `MultipleMaster' operator comes before any */
824 /* top DICT operators that contain T2 charstrings. */
825
826 static FT_Error
827 cff_parse_multiple_master( CFF_Parser parser )
828 {
829 CFF_FontRecDict dict = (CFF_FontRecDict)parser->object;
830 FT_Error error;
831
832
833#ifdef FT_DEBUG_LEVEL_TRACE
834 /* beautify tracing message */
835 if ( ft_trace_levels[FT_TRACE_COMP( FT_COMPONENT )] < 4 )
836 FT_TRACE1(( "Multiple Master CFFs not supported yet,"
837 " handling first master design only\n" ));
838 else
839 FT_TRACE1(( " (not supported yet,"
840 " handling first master design only)\n" ));
841#endif
842
843 error = FT_ERR( Stack_Underflow );
844
845 /* currently, we handle only the first argument */
846 if ( parser->top >= parser->stack + 5 )
847 {
848 FT_Long num_designs = cff_parse_num( parser, parser->stack );
849
850
851 if ( num_designs > 16 || num_designs < 2 )
852 {
853 FT_ERROR(( "cff_parse_multiple_master:"
854 " Invalid number of designs\n" ));
855 error = FT_THROW( Invalid_File_Format );
856 }
857 else
858 {
859 dict->num_designs = (FT_UShort)num_designs;
860 dict->num_axes = (FT_UShort)( parser->top - parser->stack - 4 );
861
862 parser->num_designs = dict->num_designs;
863 parser->num_axes = dict->num_axes;
864
865 error = FT_Err_Ok;
866 }
867 }
868
869 return error;
870 }
871
872
873 static FT_Error
874 cff_parse_cid_ros( CFF_Parser parser )
875 {
876 CFF_FontRecDict dict = (CFF_FontRecDict)parser->object;
877 FT_Byte** data = parser->stack;
878 FT_Error error;
879
880
881 error = FT_ERR( Stack_Underflow );
882
883 if ( parser->top >= parser->stack + 3 )
884 {
885 dict->cid_registry = (FT_UInt)cff_parse_num( parser, data++ );
886 dict->cid_ordering = (FT_UInt)cff_parse_num( parser, data++ );
887 if ( **data == 30 )
888 FT_TRACE1(( "cff_parse_cid_ros: real supplement is rounded\n" ));
889 dict->cid_supplement = cff_parse_num( parser, data );
890 if ( dict->cid_supplement < 0 )
891 FT_TRACE1(( "cff_parse_cid_ros: negative supplement %ld is found\n",
892 dict->cid_supplement ));
893 error = FT_Err_Ok;
894
895 FT_TRACE4(( " %u %u %ld\n",
896 dict->cid_registry,
897 dict->cid_ordering,
898 dict->cid_supplement ));
899 }
900
901 return error;
902 }
903
904
905 static FT_Error
906 cff_parse_vsindex( CFF_Parser parser )
907 {
908 /* vsindex operator can only be used in a Private DICT */
909 CFF_Private priv = (CFF_Private)parser->object;
910 FT_Byte** data = parser->stack;
911 CFF_Blend blend;
912 FT_Error error;
913
914
915 if ( !priv || !priv->subfont )
916 {
917 error = FT_THROW( Invalid_File_Format );
918 goto Exit;
919 }
920
921 blend = &priv->subfont->blend;
922
923 if ( blend->usedBV )
924 {
925 FT_ERROR(( " cff_parse_vsindex: vsindex not allowed after blend\n" ));
926 error = FT_THROW( Syntax_Error );
927 goto Exit;
928 }
929
930 priv->vsindex = (FT_UInt)cff_parse_num( parser, data++ );
931
932 FT_TRACE4(( " %u\n", priv->vsindex ));
933
934 error = FT_Err_Ok;
935
936 Exit:
937 return error;
938 }
939
940
941 static FT_Error
942 cff_parse_blend( CFF_Parser parser )
943 {
944 /* blend operator can only be used in a Private DICT */
945 CFF_Private priv = (CFF_Private)parser->object;
946 CFF_SubFont subFont;
947 CFF_Blend blend;
948 FT_UInt numBlends;
949 FT_Error error;
950
951
952 if ( !priv || !priv->subfont )
953 {
954 error = FT_THROW( Invalid_File_Format );
955 goto Exit;
956 }
957
958 subFont = priv->subfont;
959 blend = &subFont->blend;
960
961 if ( cff_blend_check_vector( blend,
962 priv->vsindex,
963 subFont->lenNDV,
964 subFont->NDV ) )
965 {
966 error = cff_blend_build_vector( blend,
967 priv->vsindex,
968 subFont->lenNDV,
969 subFont->NDV );
970 if ( error )
971 goto Exit;
972 }
973
974 numBlends = (FT_UInt)cff_parse_num( parser, parser->top - 1 );
975 if ( numBlends > parser->stackSize )
976 {
977 FT_ERROR(( "cff_parse_blend: Invalid number of blends\n" ));
978 error = FT_THROW( Invalid_File_Format );
979 goto Exit;
980 }
981
982 FT_TRACE4(( " %u value%s blended\n",
983 numBlends,
984 numBlends == 1 ? "" : "s" ));
985
986 error = cff_blend_doBlend( subFont, parser, numBlends );
987
988 blend->usedBV = TRUE;
989
990 Exit:
991 return error;
992 }
993
994
995 /* maxstack operator increases parser and operand stacks for CFF2 */
996 static FT_Error
997 cff_parse_maxstack( CFF_Parser parser )
998 {
999 /* maxstack operator can only be used in a Top DICT */
1000 CFF_FontRecDict dict = (CFF_FontRecDict)parser->object;
1001 FT_Byte** data = parser->stack;
1002 FT_Error error = FT_Err_Ok;
1003
1004
1005 if ( !dict )
1006 {
1007 error = FT_THROW( Invalid_File_Format );
1008 goto Exit;
1009 }
1010
1011 dict->maxstack = (FT_UInt)cff_parse_num( parser, data++ );
1012 if ( dict->maxstack > CFF2_MAX_STACK )
1013 dict->maxstack = CFF2_MAX_STACK;
1014 if ( dict->maxstack < CFF2_DEFAULT_STACK )
1015 dict->maxstack = CFF2_DEFAULT_STACK;
1016
1017 FT_TRACE4(( " %u\n", dict->maxstack ));
1018
1019 Exit:
1020 return error;
1021 }
1022
1023
1024#define CFF_FIELD_NUM( code, name, id ) \
1025 CFF_FIELD( code, name, id, cff_kind_num )
1026#define CFF_FIELD_FIXED( code, name, id ) \
1027 CFF_FIELD( code, name, id, cff_kind_fixed )
1028#define CFF_FIELD_FIXED_1000( code, name, id ) \
1029 CFF_FIELD( code, name, id, cff_kind_fixed_thousand )
1030#define CFF_FIELD_STRING( code, name, id ) \
1031 CFF_FIELD( code, name, id, cff_kind_string )
1032#define CFF_FIELD_BOOL( code, name, id ) \
1033 CFF_FIELD( code, name, id, cff_kind_bool )
1034#define CFF_FIELD_DELTA( code, name, max, id ) \
1035 CFF_FIELD_DELTA_KIND( code, name, max, id, cff_kind_delta )
1036#define CFF_FIELD_DELTA_FIXED( code, name, max, id ) \
1037 CFF_FIELD_DELTA_KIND( code, name, max, id, cff_kind_delta_fixed )
1038
1039
1040#undef CFF_FIELD
1041#undef CFF_FIELD_DELTA_KIND
1042
1043
1044#ifndef FT_DEBUG_LEVEL_TRACE
1045
1046
1047#define CFF_FIELD_CALLBACK( code, name, id ) \
1048 { \
1049 cff_kind_callback, \
1050 code | CFFCODE, \
1051 0, 0, \
1052 cff_parse_ ## name, \
1053 0, 0 \
1054 },
1055
1056#define CFF_FIELD_BLEND( code, id ) \
1057 { \
1058 cff_kind_blend, \
1059 code | CFFCODE, \
1060 0, 0, \
1061 cff_parse_blend, \
1062 0, 0 \
1063 },
1064
1065#define CFF_FIELD( code, name, id, kind ) \
1066 { \
1067 kind, \
1068 code | CFFCODE, \
1069 FT_FIELD_OFFSET( name ), \
1070 FT_FIELD_SIZE( name ), \
1071 NULL, 0, 0 \
1072 },
1073
1074#define CFF_FIELD_DELTA_KIND( code, name, max, id, kind ) \
1075 { \
1076 kind, \
1077 code | CFFCODE, \
1078 FT_FIELD_OFFSET( name ), \
1079 FT_FIELD_SIZE_DELTA( name ), \
1080 NULL, \
1081 max, \
1082 FT_FIELD_OFFSET( num_ ## name ) \
1083 },
1084
1085 static const CFF_Field_Handler cff_field_handlers[] =
1086 {
1087
1088#include "cfftoken.h"
1089
1090 { 0, 0, 0, 0, NULL, 0, 0 }
1091 };
1092
1093
1094#else /* FT_DEBUG_LEVEL_TRACE */
1095
1096
1097
1098#define CFF_FIELD_CALLBACK( code, name, id ) \
1099 { \
1100 cff_kind_callback, \
1101 code | CFFCODE, \
1102 0, 0, \
1103 cff_parse_ ## name, \
1104 0, 0, \
1105 id \
1106 },
1107
1108#define CFF_FIELD_BLEND( code, id ) \
1109 { \
1110 cff_kind_blend, \
1111 code | CFFCODE, \
1112 0, 0, \
1113 cff_parse_blend, \
1114 0, 0, \
1115 id \
1116 },
1117
1118#define CFF_FIELD( code, name, id, kind ) \
1119 { \
1120 kind, \
1121 code | CFFCODE, \
1122 FT_FIELD_OFFSET( name ), \
1123 FT_FIELD_SIZE( name ), \
1124 NULL, 0, 0, \
1125 id \
1126 },
1127
1128#define CFF_FIELD_DELTA_KIND( code, name, max, id, kind ) \
1129 { \
1130 kind, \
1131 code | CFFCODE, \
1132 FT_FIELD_OFFSET( name ), \
1133 FT_FIELD_SIZE_DELTA( name ), \
1134 NULL, \
1135 max, \
1136 FT_FIELD_OFFSET( num_ ## name ), \
1137 id \
1138 },
1139
1140 static const CFF_Field_Handler cff_field_handlers[] =
1141 {
1142
1143#include "cfftoken.h"
1144
1145 { 0, 0, 0, 0, NULL, 0, 0, NULL }
1146 };
1147
1148
1149#endif /* FT_DEBUG_LEVEL_TRACE */
1150
1151
1152 FT_LOCAL_DEF( FT_Error )
1153 cff_parser_run( CFF_Parser parser,
1154 FT_Byte* start,
1155 FT_Byte* limit )
1156 {
1157 FT_Byte* p = start;
1158 FT_Error error = FT_Err_Ok;
1159
1160#ifdef CFF_CONFIG_OPTION_OLD_ENGINE
1161 PSAux_Service psaux;
1162
1163 FT_Library library = parser->library;
1164 FT_Memory memory = library->memory;
1165#endif
1166
1167 parser->top = parser->stack;
1168 parser->start = start;
1169 parser->limit = limit;
1170 parser->cursor = start;
1171
1172 while ( p < limit )
1173 {
1174 FT_UInt v = *p;
1175
1176
1177 /* Opcode 31 is legacy MM T2 operator, not a number. */
1178 /* Opcode 255 is reserved and should not appear in fonts; */
1179 /* it is used internally for CFF2 blends. */
1180 if ( v >= 27 && v != 31 && v != 255 )
1181 {
1182 /* it's a number; we will push its position on the stack */
1183 if ( (FT_UInt)( parser->top - parser->stack ) >= parser->stackSize )
1184 goto Stack_Overflow;
1185
1186 *parser->top++ = p;
1187
1188 /* now, skip it */
1189 if ( v == 30 )
1190 {
1191 /* skip real number */
1192 p++;
1193 for (;;)
1194 {
1195 /* An unterminated floating point number at the */
1196 /* end of a dictionary is invalid but harmless. */
1197 if ( p >= limit )
1198 goto Exit;
1199 v = p[0] >> 4;
1200 if ( v == 15 )
1201 break;
1202 v = p[0] & 0xF;
1203 if ( v == 15 )
1204 break;
1205 p++;
1206 }
1207 }
1208 else if ( v == 28 )
1209 p += 2;
1210 else if ( v == 29 )
1211 p += 4;
1212 else if ( v > 246 )
1213 p += 1;
1214 }
1215#ifdef CFF_CONFIG_OPTION_OLD_ENGINE
1216 else if ( v == 31 )
1217 {
1218 /* a Type 2 charstring */
1219
1220 CFF_Decoder decoder;
1221 CFF_FontRec cff_rec;
1222 FT_Byte* charstring_base;
1223 FT_ULong charstring_len;
1224
1225 FT_Fixed* stack;
1226 FT_Byte* q = NULL;
1227
1228
1229 charstring_base = ++p;
1230
1231 /* search `endchar' operator */
1232 for (;;)
1233 {
1234 if ( p >= limit )
1235 goto Exit;
1236 if ( *p == 14 )
1237 break;
1238 p++;
1239 }
1240
1241 charstring_len = (FT_ULong)( p - charstring_base ) + 1;
1242
1243 /* construct CFF_Decoder object */
1244 FT_ZERO( &decoder );
1245 FT_ZERO( &cff_rec );
1246
1247 cff_rec.top_font.font_dict.num_designs = parser->num_designs;
1248 cff_rec.top_font.font_dict.num_axes = parser->num_axes;
1249 decoder.cff = &cff_rec;
1250
1251 psaux = (PSAux_Service)FT_Get_Module_Interface( library, "psaux" );
1252 if ( !psaux )
1253 {
1254 FT_ERROR(( "cff_parser_run: cannot access `psaux' module\n" ));
1255 error = FT_THROW( Missing_Module );
1256 goto Exit;
1257 }
1258
1259 error = psaux->cff_decoder_funcs->parse_charstrings_old(
1260 &decoder, charstring_base, charstring_len, 1 );
1261 if ( error )
1262 goto Exit;
1263
1264 /* Now copy the stack data in the temporary decoder object, */
1265 /* converting it back to charstring number representations */
1266 /* (this is ugly, I know). */
1267 /* The maximum required size is 5 bytes per stack element. */
1268 if ( FT_QALLOC( q, (FT_Long)( 2 * sizeof ( FT_ListNode ) ) +
1269 5 * ( decoder.top - decoder.stack ) ) )
1270 goto Exit;
1271
1272 FT_List_Add( &parser->t2_strings, (FT_ListNode)q );
1273
1274 q += 2 * sizeof ( FT_ListNode );
1275
1276 for ( stack = decoder.stack; stack < decoder.top; stack++ )
1277 {
1278 FT_Long num = *stack;
1279
1280
1281 if ( (FT_UInt)( parser->top - parser->stack ) >= parser->stackSize )
1282 goto Stack_Overflow;
1283
1284 *parser->top++ = q;
1285
1286 if ( num & 0xFFFFU )
1287 {
1288 *q++ = 255;
1289 *q++ = (FT_Byte)( ( num >> 24 ) & 0xFF );
1290 *q++ = (FT_Byte)( ( num >> 16 ) & 0xFF );
1291 *q++ = (FT_Byte)( ( num >> 8 ) & 0xFF );
1292 *q++ = (FT_Byte)( ( num ) & 0xFF );
1293 }
1294 else
1295 {
1296 num >>= 16;
1297
1298 if ( -107 <= num && num <= 107 )
1299 *q++ = (FT_Byte)( num + 139 );
1300 else if ( 108 <= num && num <= 1131 )
1301 {
1302 *q++ = (FT_Byte)( ( ( num - 108 ) >> 8 ) + 247 );
1303 *q++ = (FT_Byte)( ( num - 108 ) & 0xFF );
1304 }
1305 else if ( -1131 <= num && num <= -108 )
1306 {
1307 *q++ = (FT_Byte)( ( ( -num - 108 ) >> 8 ) + 251 );
1308 *q++ = (FT_Byte)( ( -num - 108) & 0xFF );
1309 }
1310 else
1311 {
1312 *q++ = 28;
1313 *q++ = (FT_Byte)( num >> 8 );
1314 *q++ = (FT_Byte)( num & 0xFF );
1315 }
1316 }
1317 }
1318 }
1319#endif /* CFF_CONFIG_OPTION_OLD_ENGINE */
1320 else
1321 {
1322 /* This is not a number, hence it's an operator. Compute its code */
1323 /* and look for it in our current list. */
1324
1325 FT_UInt code;
1326 FT_UInt num_args;
1327 const CFF_Field_Handler* field;
1328
1329
1330 if ( (FT_UInt)( parser->top - parser->stack ) >= parser->stackSize )
1331 goto Stack_Overflow;
1332
1333 num_args = (FT_UInt)( parser->top - parser->stack );
1334 *parser->top = p;
1335 code = v;
1336
1337 if ( v == 12 )
1338 {
1339 /* two byte operator */
1340 p++;
1341 if ( p >= limit )
1342 goto Syntax_Error;
1343
1344 code = 0x100 | p[0];
1345 }
1346 code = code | parser->object_code;
1347
1348 for ( field = cff_field_handlers; field->kind; field++ )
1349 {
1350 if ( field->code == (FT_Int)code )
1351 {
1352 /* we found our field's handler; read it */
1353 FT_Long val;
1354 FT_Byte* q = (FT_Byte*)parser->object + field->offset;
1355
1356
1357#ifdef FT_DEBUG_LEVEL_TRACE
1358 FT_TRACE4(( " %s", field->id ));
1359#endif
1360
1361 /* check that we have enough arguments -- except for */
1362 /* delta encoded arrays, which can be empty */
1363 if ( field->kind != cff_kind_delta &&
1364 field->kind != cff_kind_delta_fixed && num_args < 1 )
1365 goto Stack_Underflow;
1366
1367 switch ( field->kind )
1368 {
1369 case cff_kind_bool:
1370 case cff_kind_string:
1371 case cff_kind_num:
1372 val = cff_parse_num( parser, parser->stack );
1373 goto Store_Number;
1374
1375 case cff_kind_fixed:
1376 val = cff_parse_fixed( parser, parser->stack );
1377 goto Store_Number;
1378
1379 case cff_kind_fixed_thousand:
1380 val = cff_parse_fixed_scaled( parser, parser->stack, 3 );
1381
1382 Store_Number:
1383 switch ( field->size )
1384 {
1385 case (8 / FT_CHAR_BIT):
1386 *(FT_Byte*)q = (FT_Byte)val;
1387 break;
1388
1389 case (16 / FT_CHAR_BIT):
1390 *(FT_Short*)q = (FT_Short)val;
1391 break;
1392
1393 case (32 / FT_CHAR_BIT):
1394 *(FT_Int32*)q = (FT_Int)val;
1395 break;
1396
1397 default: /* for 64-bit systems */
1398 *(FT_Long*)q = val;
1399 }
1400
1401#ifdef FT_DEBUG_LEVEL_TRACE
1402 switch ( field->kind )
1403 {
1404 case cff_kind_bool:
1405 FT_TRACE4(( " %s\n", val ? "true" : "false" ));
1406 break;
1407
1408 case cff_kind_string:
1409 FT_TRACE4(( " %ld (SID)\n", val ));
1410 break;
1411
1412 case cff_kind_num:
1413 FT_TRACE4(( " %ld\n", val ));
1414 break;
1415
1416 case cff_kind_fixed:
1417 FT_TRACE4(( " %f\n", (double)val / 65536 ));
1418 break;
1419
1420 case cff_kind_fixed_thousand:
1421 FT_TRACE4(( " %f\n", (double)val / 65536 / 1000 ));
1422 break;
1423
1424 default:
1425 ; /* never reached */
1426 }
1427#endif
1428
1429 break;
1430
1431 case cff_kind_delta:
1432 {
1433 FT_Byte* qcount = (FT_Byte*)parser->object +
1434 field->count_offset;
1435
1436 FT_Byte** data = parser->stack;
1437
1438
1439 if ( num_args > field->array_max )
1440 num_args = field->array_max;
1441
1442 FT_TRACE4(( " [" ));
1443
1444 /* store count */
1445 *qcount = (FT_Byte)num_args;
1446
1447 val = 0;
1448 while ( num_args > 0 )
1449 {
1450 val = ADD_LONG( val, cff_parse_num( parser, data++ ) );
1451 switch ( field->size )
1452 {
1453 case (8 / FT_CHAR_BIT):
1454 *(FT_Byte*)q = (FT_Byte)val;
1455 break;
1456
1457 case (16 / FT_CHAR_BIT):
1458 *(FT_Short*)q = (FT_Short)val;
1459 break;
1460
1461 case (32 / FT_CHAR_BIT):
1462 *(FT_Int32*)q = (FT_Int)val;
1463 break;
1464
1465 default: /* for 64-bit systems */
1466 *(FT_Long*)q = val;
1467 }
1468
1469 FT_TRACE4(( " %ld", val ));
1470
1471 q += field->size;
1472 num_args--;
1473 }
1474
1475 FT_TRACE4(( "]\n" ));
1476 }
1477 break;
1478
1479 case cff_kind_delta_fixed:
1480 {
1481 FT_Byte* qcount = (FT_Byte*)parser->object +
1482 field->count_offset;
1483
1484 FT_Byte** data = parser->stack;
1485
1486
1487 if ( num_args > field->array_max )
1488 num_args = field->array_max;
1489
1490 FT_TRACE4(( " [" ));
1491
1492 /* store count */
1493 *qcount = (FT_Byte)num_args;
1494
1495 val = 0;
1496 while ( num_args > 0 )
1497 {
1498 val = ADD_LONG( val, cff_parse_fixed( parser, data++ ) );
1499 *(FT_Long*)q = val;
1500
1501 FT_TRACE4(( " %f\n", (double)val / 65536 ));
1502
1503 q += field->size;
1504 num_args--;
1505 }
1506
1507 FT_TRACE4(( "]\n" ));
1508 }
1509 break;
1510
1511 default: /* callback or blend */
1512 error = field->reader( parser );
1513 if ( error )
1514 goto Exit;
1515 }
1516 goto Found;
1517 }
1518 }
1519
1520 /* this is an unknown operator, or it is unsupported; */
1521 /* we will ignore it for now. */
1522
1523 Found:
1524 /* clear stack */
1525 /* TODO: could clear blend stack here, */
1526 /* but we don't have access to subFont */
1527 if ( field->kind != cff_kind_blend )
1528 parser->top = parser->stack;
1529 }
1530 p++;
1531 } /* while ( p < limit ) */
1532
1533 Exit:
1534 return error;
1535
1536 Stack_Overflow:
1537 error = FT_THROW( Invalid_Argument );
1538 goto Exit;
1539
1540 Stack_Underflow:
1541 error = FT_THROW( Invalid_Argument );
1542 goto Exit;
1543
1544 Syntax_Error:
1545 error = FT_THROW( Invalid_Argument );
1546 goto Exit;
1547 }
1548
1549
1550/* END */