ReactOS  0.4.14-dev-358-gbef841c
psconv.c
Go to the documentation of this file.
1 /***************************************************************************/
2 /* */
3 /* psconv.c */
4 /* */
5 /* Some convenience conversions (body). */
6 /* */
7 /* Copyright 2006-2018 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 <ft2build.h>
20 #include FT_INTERNAL_POSTSCRIPT_AUX_H
21 #include FT_INTERNAL_DEBUG_H
22 
23 #include "psconv.h"
24 #include "psauxerr.h"
25 
26 
27  /*************************************************************************/
28  /* */
29  /* The macro FT_COMPONENT is used in trace mode. It is an implicit */
30  /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */
31  /* messages during execution. */
32  /* */
33 #undef FT_COMPONENT
34 #define FT_COMPONENT trace_psconv
35 
36 
37  /* The following array is used by various functions to quickly convert */
38  /* digits (both decimal and non-decimal) into numbers. */
39 
40 #if 'A' == 65
41  /* ASCII */
42 
43  static const FT_Char ft_char_table[128] =
44  {
45  /* 0x00 */
46  -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
47  -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
48  -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
49  0, 1, 2, 3, 4, 5, 6, 7, 8, 9, -1, -1, -1, -1, -1, -1,
50  -1, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24,
51  25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, -1, -1, -1, -1, -1,
52  -1, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24,
53  25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, -1, -1, -1, -1, -1,
54  };
55 
56  /* no character >= 0x80 can represent a valid number */
57 #define OP >=
58 
59 #endif /* 'A' == 65 */
60 
61 #if 'A' == 193
62  /* EBCDIC */
63 
64  static const FT_Char ft_char_table[128] =
65  {
66  /* 0x80 */
67  -1, 10, 11, 12, 13, 14, 15, 16, 17, 18, -1, -1, -1, -1, -1, -1,
68  -1, 19, 20, 21, 22, 23, 24, 25, 26, 27, -1, -1, -1, -1, -1, -1,
69  -1, -1, 28, 29, 30, 31, 32, 33, 34, 35, -1, -1, -1, -1, -1, -1,
70  -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
71  -1, 10, 11, 12, 13, 14, 15, 16, 17, 18, -1, -1, -1, -1, -1, -1,
72  -1, 19, 20, 21, 22, 23, 24, 25, 26, 27, -1, -1, -1, -1, -1, -1,
73  -1, -1, 28, 29, 30, 31, 32, 33, 34, 35, -1, -1, -1, -1, -1, -1,
74  0, 1, 2, 3, 4, 5, 6, 7, 8, 9, -1, -1, -1, -1, -1, -1,
75  };
76 
77  /* no character < 0x80 can represent a valid number */
78 #define OP <
79 
80 #endif /* 'A' == 193 */
81 
82 
85  FT_Byte* limit,
86  FT_Long base )
87  {
88  FT_Byte* p = *cursor;
89 
90  FT_Long num = 0;
91  FT_Bool sign = 0;
92  FT_Bool have_overflow = 0;
93 
94  FT_Long num_limit;
96 
97 
98  if ( p >= limit )
99  goto Bad;
100 
101  if ( base < 2 || base > 36 )
102  {
103  FT_TRACE4(( "!!!INVALID BASE:!!!" ));
104  return 0;
105  }
106 
107  if ( *p == '-' || *p == '+' )
108  {
109  sign = FT_BOOL( *p == '-' );
110 
111  p++;
112  if ( p == limit )
113  goto Bad;
114 
115  /* only a single sign is allowed */
116  if ( *p == '-' || *p == '+' )
117  return 0;
118  }
119 
120  num_limit = 0x7FFFFFFFL / base;
121  c_limit = (FT_Char)( 0x7FFFFFFFL % base );
122 
123  for ( ; p < limit; p++ )
124  {
125  FT_Char c;
126 
127 
128  if ( IS_PS_SPACE( *p ) || *p OP 0x80 )
129  break;
130 
131  c = ft_char_table[*p & 0x7F];
132 
133  if ( c < 0 || c >= base )
134  break;
135 
136  if ( num > num_limit || ( num == num_limit && c > c_limit ) )
137  have_overflow = 1;
138  else
139  num = num * base + c;
140  }
141 
142  *cursor = p;
143 
144  if ( have_overflow )
145  {
146  num = 0x7FFFFFFFL;
147  FT_TRACE4(( "!!!OVERFLOW:!!!" ));
148  }
149 
150  if ( sign )
151  num = -num;
152 
153  return num;
154 
155  Bad:
156  FT_TRACE4(( "!!!END OF DATA:!!!" ));
157  return 0;
158  }
159 
160 
163  FT_Byte* limit )
164 
165  {
166  FT_Byte* p = *cursor;
167  FT_Byte* curp;
168 
169  FT_Long num;
170 
171 
172  curp = p;
173  num = PS_Conv_Strtol( &p, limit, 10 );
174 
175  if ( p == curp )
176  return 0;
177 
178  if ( p < limit && *p == '#' )
179  {
180  p++;
181 
182  curp = p;
183  num = PS_Conv_Strtol( &p, limit, num );
184 
185  if ( p == curp )
186  return 0;
187  }
188 
189  *cursor = p;
190 
191  return num;
192  }
193 
194 
197  FT_Byte* limit,
198  FT_Long power_ten )
199  {
200  FT_Byte* p = *cursor;
201  FT_Byte* curp;
202 
203  FT_Fixed integral = 0;
204  FT_Long decimal = 0;
205  FT_Long divider = 1;
206 
207  FT_Bool sign = 0;
208  FT_Bool have_overflow = 0;
209  FT_Bool have_underflow = 0;
210 
211 
212  if ( p >= limit )
213  goto Bad;
214 
215  if ( *p == '-' || *p == '+' )
216  {
217  sign = FT_BOOL( *p == '-' );
218 
219  p++;
220  if ( p == limit )
221  goto Bad;
222 
223  /* only a single sign is allowed */
224  if ( *p == '-' || *p == '+' )
225  return 0;
226  }
227 
228  /* read the integer part */
229  if ( *p != '.' )
230  {
231  curp = p;
232  integral = PS_Conv_ToInt( &p, limit );
233 
234  if ( p == curp )
235  return 0;
236 
237  if ( integral > 0x7FFF )
238  have_overflow = 1;
239  else
240  integral = (FT_Fixed)( (FT_UInt32)integral << 16 );
241  }
242 
243  /* read the decimal part */
244  if ( p < limit && *p == '.' )
245  {
246  p++;
247 
248  for ( ; p < limit; p++ )
249  {
250  FT_Char c;
251 
252 
253  if ( IS_PS_SPACE( *p ) || *p OP 0x80 )
254  break;
255 
256  c = ft_char_table[*p & 0x7F];
257 
258  if ( c < 0 || c >= 10 )
259  break;
260 
261  /* only add digit if we don't overflow */
262  if ( divider < 0xCCCCCCCL && decimal < 0xCCCCCCCL )
263  {
264  decimal = decimal * 10 + c;
265 
266  if ( !integral && power_ten > 0 )
267  power_ten--;
268  else
269  divider *= 10;
270  }
271  }
272  }
273 
274  /* read exponent, if any */
275  if ( p + 1 < limit && ( *p == 'e' || *p == 'E' ) )
276  {
277  FT_Long exponent;
278 
279 
280  p++;
281 
282  curp = p;
283  exponent = PS_Conv_ToInt( &p, limit );
284 
285  if ( curp == p )
286  return 0;
287 
288  /* arbitrarily limit exponent */
289  if ( exponent > 1000 )
290  have_overflow = 1;
291  else if ( exponent < -1000 )
292  have_underflow = 1;
293  else
294  power_ten += exponent;
295  }
296 
297  *cursor = p;
298 
299  if ( !integral && !decimal )
300  return 0;
301 
302  if ( have_overflow )
303  goto Overflow;
304  if ( have_underflow )
305  goto Underflow;
306 
307  while ( power_ten > 0 )
308  {
309  if ( integral >= 0xCCCCCCCL )
310  goto Overflow;
311  integral *= 10;
312 
313  if ( decimal >= 0xCCCCCCCL )
314  {
315  if ( divider == 1 )
316  goto Overflow;
317  divider /= 10;
318  }
319  else
320  decimal *= 10;
321 
322  power_ten--;
323  }
324 
325  while ( power_ten < 0 )
326  {
327  integral /= 10;
328  if ( divider < 0xCCCCCCCL )
329  divider *= 10;
330  else
331  decimal /= 10;
332 
333  if ( !integral && !decimal )
334  goto Underflow;
335 
336  power_ten++;
337  }
338 
339  if ( decimal )
340  {
341  decimal = FT_DivFix( decimal, divider );
342  /* it's not necessary to check this addition for overflow */
343  /* due to the structure of the real number representation */
344  integral += decimal;
345  }
346 
347  Exit:
348  if ( sign )
349  integral = -integral;
350 
351  return integral;
352 
353  Bad:
354  FT_TRACE4(( "!!!END OF DATA:!!!" ));
355  return 0;
356 
357  Overflow:
358  integral = 0x7FFFFFFFL;
359  FT_TRACE4(( "!!!OVERFLOW:!!!" ));
360  goto Exit;
361 
362  Underflow:
363  FT_TRACE4(( "!!!UNDERFLOW:!!!" ));
364  return 0;
365  }
366 
367 
368 #if 0
370  PS_Conv_StringDecode( FT_Byte** cursor,
371  FT_Byte* limit,
372  FT_Byte* buffer,
373  FT_Offset n )
374  {
375  FT_Byte* p;
376  FT_UInt r = 0;
377 
378 
379  for ( p = *cursor; r < n && p < limit; p++ )
380  {
381  FT_Byte b;
382 
383 
384  if ( *p != '\\' )
385  {
386  buffer[r++] = *p;
387 
388  continue;
389  }
390 
391  p++;
392 
393  switch ( *p )
394  {
395  case 'n':
396  b = '\n';
397  break;
398  case 'r':
399  b = '\r';
400  break;
401  case 't':
402  b = '\t';
403  break;
404  case 'b':
405  b = '\b';
406  break;
407  case 'f':
408  b = '\f';
409  break;
410  case '\r':
411  p++;
412  if ( *p != '\n' )
413  {
414  b = *p;
415 
416  break;
417  }
418  /* no break */
419  case '\n':
420  continue;
421  break;
422  default:
423  if ( IS_PS_DIGIT( *p ) )
424  {
425  b = *p - '0';
426 
427  p++;
428 
429  if ( IS_PS_DIGIT( *p ) )
430  {
431  b = b * 8 + *p - '0';
432 
433  p++;
434 
435  if ( IS_PS_DIGIT( *p ) )
436  b = b * 8 + *p - '0';
437  else
438  {
439  buffer[r++] = b;
440  b = *p;
441  }
442  }
443  else
444  {
445  buffer[r++] = b;
446  b = *p;
447  }
448  }
449  else
450  b = *p;
451  break;
452  }
453 
454  buffer[r++] = b;
455  }
456 
457  *cursor = p;
458 
459  return r;
460  }
461 #endif /* 0 */
462 
463 
466  FT_Byte* limit,
467  FT_Byte* buffer,
468  FT_Offset n )
469  {
470  FT_Byte* p;
471  FT_UInt r = 0;
472  FT_UInt w = 0;
473  FT_UInt pad = 0x01;
474 
475 
476  n *= 2;
477 
478 #if 1
479 
480  p = *cursor;
481 
482  if ( p >= limit )
483  return 0;
484 
485  if ( n > (FT_UInt)( limit - p ) )
486  n = (FT_UInt)( limit - p );
487 
488  /* we try to process two nibbles at a time to be as fast as possible */
489  for ( ; r < n; r++ )
490  {
491  FT_UInt c = p[r];
492 
493 
494  if ( IS_PS_SPACE( c ) )
495  continue;
496 
497  if ( c OP 0x80 )
498  break;
499 
500  c = (FT_UInt)ft_char_table[c & 0x7F];
501  if ( c >= 16 )
502  break;
503 
504  pad = ( pad << 4 ) | c;
505  if ( pad & 0x100 )
506  {
507  buffer[w++] = (FT_Byte)pad;
508  pad = 0x01;
509  }
510  }
511 
512  if ( pad != 0x01 )
513  buffer[w++] = (FT_Byte)( pad << 4 );
514 
515  *cursor = p + r;
516 
517  return w;
518 
519 #else /* 0 */
520 
521  for ( r = 0; r < n; r++ )
522  {
523  FT_Char c;
524 
525 
526  if ( IS_PS_SPACE( *p ) )
527  continue;
528 
529  if ( *p OP 0x80 )
530  break;
531 
532  c = ft_char_table[*p & 0x7F];
533 
534  if ( (unsigned)c >= 16 )
535  break;
536 
537  if ( r & 1 )
538  {
539  *buffer = (FT_Byte)(*buffer + c);
540  buffer++;
541  }
542  else
543  *buffer = (FT_Byte)(c << 4);
544 
545  r++;
546  }
547 
548  *cursor = p;
549 
550  return ( r + 1 ) / 2;
551 
552 #endif /* 0 */
553 
554  }
555 
556 
559  FT_Byte* limit,
560  FT_Byte* buffer,
561  FT_Offset n,
562  FT_UShort* seed )
563  {
564  FT_Byte* p;
565  FT_UInt r;
566  FT_UInt s = *seed;
567 
568 
569 #if 1
570 
571  p = *cursor;
572 
573  if ( p >= limit )
574  return 0;
575 
576  if ( n > (FT_UInt)(limit - p) )
577  n = (FT_UInt)(limit - p);
578 
579  for ( r = 0; r < n; r++ )
580  {
581  FT_UInt val = p[r];
582  FT_UInt b = ( val ^ ( s >> 8 ) );
583 
584 
585  s = ( (val + s)*52845U + 22719 ) & 0xFFFFU;
586  buffer[r] = (FT_Byte) b;
587  }
588 
589  *cursor = p + n;
590  *seed = (FT_UShort)s;
591 
592 #else /* 0 */
593 
594  for ( r = 0, p = *cursor; r < n && p < limit; r++, p++ )
595  {
596  FT_Byte b = (FT_Byte)( *p ^ ( s >> 8 ) );
597 
598 
599  s = (FT_UShort)( ( *p + s ) * 52845U + 22719 );
600  *buffer++ = b;
601  }
602  *cursor = p;
603  *seed = s;
604 
605 #endif /* 0 */
606 
607  return r;
608  }
609 
610 
611 /* END */
static size_t double int int int * sign
Definition: printf.c:69
FT_DivFix(FT_Long a, FT_Long b)
Definition: ftcalc.c:608
signed long FT_Long
Definition: fttypes.h:242
GLubyte GLubyte GLubyte GLubyte w
Definition: glext.h:6102
PS_Conv_ToFixed(FT_Byte **cursor, FT_Byte *limit, FT_Long power_ten)
Definition: psconv.c:196
GLdouble GLdouble GLdouble r
Definition: gl.h:2055
#define U(x)
Definition: wordpad.c:44
GLdouble n
Definition: glext.h:7729
PS_Conv_EexecDecode(FT_Byte **cursor, FT_Byte *limit, FT_Byte *buffer, FT_Offset n, FT_UShort *seed)
Definition: psconv.c:558
GLuint buffer
Definition: glext.h:5915
signed char FT_Char
Definition: fttypes.h:143
#define IS_PS_SPACE(ch)
Definition: psaux.h:1329
GLint limit
Definition: glext.h:10326
OP
Definition: DragDrop.cpp:26
FT_BEGIN_HEADER typedef unsigned char FT_Bool
Definition: fttypes.h:108
unsigned char FT_Byte
Definition: fttypes.h:154
GLuint base
Definition: 3dtext.c:35
#define FT_TRACE4(varformat)
Definition: ftdebug.h:161
PS_Conv_Strtol(FT_Byte **cursor, FT_Byte *limit, FT_Long base)
Definition: psconv.c:84
#define FT_LOCAL_DEF(x)
Definition: ftconfig.h:388
#define b
Definition: ke_i.h:79
GLuint GLfloat * val
Definition: glext.h:7180
GLboolean GLboolean GLboolean b
Definition: glext.h:6204
PS_Conv_ASCIIHexDecode(FT_Byte **cursor, FT_Byte *limit, FT_Byte *buffer, FT_Offset n)
Definition: psconv.c:465
static void Exit(void)
Definition: sock.c:1331
const GLubyte * c
Definition: glext.h:8905
GLuint GLuint num
Definition: glext.h:9618
static const WCHAR L[]
Definition: oid.c:1250
GLdouble s
Definition: gl.h:2039
#define FT_BOOL(x)
Definition: fttypes.h:578
signed long FT_Fixed
Definition: fttypes.h:288
const char cursor[]
Definition: icontest.c:13
unsigned int FT_UInt
Definition: fttypes.h:231
Definition: synths.h:13
#define IS_PS_DIGIT(ch)
Definition: psaux.h:1348
#define c
Definition: ke_i.h:80
PS_Conv_ToInt(FT_Byte **cursor, FT_Byte *limit)
Definition: psconv.c:162
GLfloat GLfloat p
Definition: glext.h:8902
unsigned short FT_UShort
Definition: fttypes.h:209
size_t FT_Offset
Definition: fttypes.h:324