summaryrefslogtreecommitdiff
path: root/src/sfnt.c
diff options
context:
space:
mode:
authorPo Lu <luangruo@yahoo.com>2023-12-19 16:42:38 +0800
committerPo Lu <luangruo@yahoo.com>2023-12-19 16:42:38 +0800
commit0a57e1cd2c97db3a990f88043dc4a53619390228 (patch)
tree4ea79d103cfb19e2de9748f3c50c2fc8e8a58bb9 /src/sfnt.c
parentd0e3dfa764cdb5c15c2a525b455df495097a86bb (diff)
downloademacs-0a57e1cd2c97db3a990f88043dc4a53619390228.tar.gz
Improve efficiency of operations involving font interpreter scale
* src/sfnt.c (sfnt_mul_f26dot6_fixed): Correct rounding constant. (sfnt_make_interpreter, SSW, WCVTF, sfnt_compute_phantom_points) (sfnt_interpret_simple_glyph, sfnt_interpret_compound_glyph_1) (sfnt_vary_interpreter, sfnt_check_ssw): Account for the fractional bits in a f26dot6 when computing the interpreter scale factor.
Diffstat (limited to 'src/sfnt.c')
-rw-r--r--src/sfnt.c41
1 files changed, 21 insertions, 20 deletions
diff --git a/src/sfnt.c b/src/sfnt.c
index c33f21215a6..eb3add7390e 100644
--- a/src/sfnt.c
+++ b/src/sfnt.c
@@ -6456,7 +6456,8 @@ sfnt_mul_f26dot6_fixed (sfnt_f26dot6 x, sfnt_fixed y)
product = (uint64_t) y * (uint64_t) x;
/* This can be done quickly with int64_t. */
- return ((int64_t) (product + 32676) / (int64_t) 65536) * sign;
+ return ((int64_t) (product + 32768)
+ / (int64_t) 65536) * sign;
#else
struct sfnt_large_integer temp;
int sign;
@@ -6685,7 +6686,7 @@ sfnt_make_interpreter (struct sfnt_maxp_table *maxp,
/* Now compute the scale. Then, scale up the control value table
values. */
interpreter->scale
- = sfnt_div_fixed (pixel_size, head->units_per_em);
+ = sfnt_div_fixed (pixel_size * 64, head->units_per_em);
/* Set the PPEM. */
interpreter->ppem = pixel_size;
@@ -6701,7 +6702,7 @@ sfnt_make_interpreter (struct sfnt_maxp_table *maxp,
/* Load the control value table. */
for (i = 0; i < interpreter->cvt_size; ++i)
interpreter->cvt[i]
- = sfnt_mul_f26dot6_fixed (cvt->values[i] * 64,
+ = sfnt_mul_f26dot6_fixed (cvt->values[i],
interpreter->scale);
/* Fill in the default values for phase, period and threshold. */
@@ -7016,8 +7017,8 @@ sfnt_interpret_trap (struct sfnt_interpreter *interpreter,
single_width = POP (); \
\
interpreter->state.single_width_value \
- = (interpreter->scale * single_width \
- / 1024); \
+ = sfnt_mul_fixed (single_width, \
+ interpreter->scale); \
}
#define DUP() \
@@ -7545,8 +7546,8 @@ sfnt_interpret_trap (struct sfnt_interpreter *interpreter,
TRAP ("WCVTF out of bounds"); \
\
interpreter->cvt[location] \
- = (interpreter->scale * value \
- / 1024); \
+ = sfnt_mul_fixed (value, \
+ interpreter->scale); \
}
#define JROT() \
@@ -12258,8 +12259,8 @@ sfnt_compute_phantom_points (struct sfnt_glyph *glyph,
f2 += glyph->advance_distortion;
/* Next, scale both up. */
- *s1 = sfnt_mul_f26dot6_fixed (f1 * 64, scale);
- *s2 = sfnt_mul_f26dot6_fixed (f2 * 64, scale);
+ *s1 = sfnt_mul_f26dot6_fixed (f1, scale);
+ *s2 = sfnt_mul_f26dot6_fixed (f2, scale);
/* While not expressly provided in the manual, the phantom points
(at times termed the advance and origin points) represent pixel
@@ -12343,7 +12344,7 @@ sfnt_interpret_simple_glyph (struct sfnt_glyph *glyph,
tem = glyph->simple->x_coordinates[i];
/* Scale that fword. */
- tem = sfnt_mul_f26dot6_fixed (tem * 64, interpreter->scale);
+ tem = sfnt_mul_f26dot6_fixed (tem, interpreter->scale);
/* Set x_points and x_current. */
zone->x_points[i] = tem;
@@ -12371,7 +12372,7 @@ sfnt_interpret_simple_glyph (struct sfnt_glyph *glyph,
/* Scale that fword. Make sure not to round Y, as this could
lead to Y spilling over to the next line. */
- tem = sfnt_mul_fixed (tem * 64, interpreter->scale);
+ tem = sfnt_mul_f26dot6_fixed (tem, interpreter->scale);
/* Set y_points and y_current. */
zone->y_points[i] = tem;
@@ -12824,14 +12825,14 @@ sfnt_interpret_compound_glyph_1 (struct sfnt_glyph *glyph,
if (!(component->flags & 01)) /* ARG_1_AND_2_ARE_WORDS */
{
/* X and Y are signed bytes. */
- x = component->argument1.b * 64;
- y = component->argument2.b * 64;
+ x = component->argument1.b;
+ y = component->argument2.b;
}
else
{
/* X and Y are signed words. */
- x = component->argument1.d * 64;
- y = component->argument2.d * 64;
+ x = component->argument1.d;
+ y = component->argument2.d;
}
/* Now convert X and Y into device coordinates. */
@@ -16335,7 +16336,7 @@ sfnt_vary_interpreter (struct sfnt_interpreter *interpreter,
/* Multiply the delta by the interpreter scale factor and
then the tuple scale factor. */
- delta = sfnt_mul_f26dot6_fixed (variation->deltas[j] * 64,
+ delta = sfnt_mul_f26dot6_fixed (variation->deltas[j],
interpreter->scale);
delta = sfnt_mul_fixed_round (delta, scale);
@@ -17352,13 +17353,13 @@ sfnt_check_ssw (struct sfnt_interpreter *interpreter,
}
if (interpreter->state.single_width_value
- != sfnt_mul_f26dot6_fixed (-64, interpreter->scale))
+ != sfnt_mul_f26dot6_fixed (-1, interpreter->scale))
{
fprintf (stderr, "failed, got %d at scale %d,"
" expected %d\n",
interpreter->state.single_width_value,
interpreter->scale,
- sfnt_mul_f26dot6_fixed (-64, interpreter->scale));
+ sfnt_mul_f26dot6_fixed (-1, interpreter->scale));
return;
}
@@ -20532,8 +20533,8 @@ main (int argc, char **argv)
return 1;
}
-#define FANCY_PPEM 14
-#define EASY_PPEM 14
+#define FANCY_PPEM 12
+#define EASY_PPEM 12
interpreter = NULL;
head = sfnt_read_head_table (fd, font);