GNOME Bugzilla – Bug 592036
integer overflow bug causes misrendering of Nepali characters
Last modified: 2009-08-18 05:07:27 UTC
Originally reported at http://bugzilla.abisource.com/show_bug.cgi?id=12288 I'm working on a Nepali text rendering problem on AbiWord. Specifically I'm working with the combination of characters U+0915 and U+0901. When rendered correctly, the 2nd character is rendered on top of the first one, basically adding a "flying thing" to the base consonant "KA". Using the Samanata font from: http://parpg-trac.cvsdude.com/parpg/browser/trunk/demo/fonts/samanata.ttf?rev=26&format=raw This rendering works fine up to and including point size 58, but at point size 59 and higher in AbiWord the flying thing completely misses the KA. Here is the character shown at sizes 12, 48, 58 and 59: http://bugzilla.abisource.com/attachment.cgi?id=5032&action=view I tracked this down to an integer overflow when positioning the 2nd glyph. Get_Anchor() in harfbuzz-gpos.c case 1: *x_value = x_scale * an->af.af1.XCoordinate / 0x10000; At font size 59, x_scale is 2416640 and the XCoordinate is 899. The result of multiplying these values overflows the 32 bit integer used in this calculation. Therefore the resultant x_value is about -32000 rather than about 32000, causing the 2nd glyph to be rendered quite far away from the character it's supposed to be sitting on. Here's a hacky patch I've used to solve the issue. One question is why x_scale is so high? This is because AbiWord is calling pango_cairo_font_map_set_resolution() with a DPI value of 1440. It uses such a high value so that scaling at different zoom levels looks OK, and for printing. I noticed that the line below could also overflow in a similar fashion: *y_value = y_scale * an->af.af1.YCoordinate / 0x10000; and things get stranger here. At a small font size where no overflow happens (e.g. 12), the resultant y_value is positive and the flying thing gets rendered in the right place. At a large font size where an overflow already happens (e.g. 20), the resultant y_value is negative yet the flying thing gets rendered at the right place. So, fixing the overflow in y_value actually broke rendering again, except for a very select few font sizes e.g. 44 (which previously incorrectly rendered the flying thing below the character, and now puts it in the right place). What's going on here!?
Created attachment 140942 [details] [review] fix integer overflow in x_value
Created attachment 140943 [details] test program which demonstrates the bug This demo program renders the glyphs at size 72. It outputs a png image in the current directory called out.png With current pango, the flying thing appears way too far to the left. After the above patch is applied, the flying thing is in the right place. If you also fix the y_value overflow, the flying thing gets rendered waaay too high up.
Created attachment 140947 [details] [review] fix 6 integer overflows OK, the y_value strangeness was simply 2 integer overflows cancelling each other out. (base vs mark) this patch fixes another 4 overflows, which makes everything work nicely.
Fixed in master. Please test. Thanks.
seems to be working, thanks!