aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core/SkFindAndPlaceGlyph.h
diff options
context:
space:
mode:
authorGravatar herb <herb@google.com>2015-12-07 12:12:29 -0800
committerGravatar Commit bot <commit-bot@chromium.org>2015-12-07 12:12:29 -0800
commitd4c24f67496ff2e5e83bc7ce7945cbb85484bfa6 (patch)
tree45d549ae162159aa0100652ab2759acd305ebc05 /src/core/SkFindAndPlaceGlyph.h
parentba923d38a5ea092aaa37967c5367ae19e2e4f017 (diff)
Simplify D1G so that it can inline DrawOneGlyph, and fix a bug in codegen
that only happens on ARM64 using GCC 4.9. Review URL: https://codereview.chromium.org/1507633004
Diffstat (limited to 'src/core/SkFindAndPlaceGlyph.h')
-rw-r--r--src/core/SkFindAndPlaceGlyph.h25
1 files changed, 23 insertions, 2 deletions
diff --git a/src/core/SkFindAndPlaceGlyph.h b/src/core/SkFindAndPlaceGlyph.h
index 278be07e0b..bd6338d587 100644
--- a/src/core/SkFindAndPlaceGlyph.h
+++ b/src/core/SkFindAndPlaceGlyph.h
@@ -30,6 +30,16 @@ struct SkMaxSizeOf<H, Ts...> {
sizeof(H) >= SkMaxSizeOf<Ts...>::value ? sizeof(H) : SkMaxSizeOf<Ts...>::value;
};
+
+// This is a temporary helper function to work around a bug in the code generation
+// for aarch64 (arm) on GCC 4.9. This bug does not show up on other platforms, so it
+// seems to be an aarch64 backend problem.
+//
+// GCC 4.9 on ARM64 does not generate the proper constructor code for PositionReader or
+// GlyphFindAndPlace. The vtable is not set properly without adding the fixme code.
+// The implementation is in SkDraw.cpp.
+extern void FixGCC49Arm64Bug(int v);
+
class SkFindAndPlaceGlyph {
public:
template<typename ProcessOneGlyph>
@@ -229,6 +239,9 @@ private:
public:
virtual ~PositionReaderInterface() { }
virtual SkPoint nextPoint() = 0;
+ // This is only here to fix a GCC 4.9 aarch64 code gen bug.
+ // See comment at the top of the file.
+ virtual int forceUseForBug() = 0;
};
class HorizontalPositions final : public PositionReaderInterface {
@@ -241,6 +254,8 @@ private:
return {x, 0};
}
+ int forceUseForBug() override { return 1; }
+
private:
const SkScalar* fPositions;
};
@@ -256,6 +271,8 @@ private:
return to_return;
}
+ int forceUseForBug() override { return 2; }
+
private:
const SkScalar* fPositions;
};
@@ -410,7 +427,9 @@ private:
class GlyphFindAndPlaceSubpixel final : public GlyphFindAndPlaceInterface<ProcessOneGlyph> {
public:
GlyphFindAndPlaceSubpixel(LookupGlyph& glyphFinder)
- : fGlyphFinder(glyphFinder) { }
+ : fGlyphFinder(glyphFinder) {
+ FixGCC49Arm64Bug(1);
+ }
SkPoint findAndPositionGlyph(
const char** text, SkPoint position, ProcessOneGlyph&& processOneGlyph) override {
@@ -464,6 +483,7 @@ private:
public:
GlyphFindAndPlaceFullPixel(LookupGlyph& glyphFinder)
: fGlyphFinder(glyphFinder) {
+ FixGCC49Arm64Bug(2);
// Kerning can only be used with SkPaint::kLeft_Align
static_assert(!kUseKerning || SkPaint::kLeft_Align == kTextAlignment,
"Kerning can only be used with left aligned text.");
@@ -601,6 +621,7 @@ inline void SkFindAndPlaceGlyph::ProcessPosText(
} else {
to_init->initialize<HorizontalPositions>(pos);
}
+ positionReader->forceUseForBug();
}
};
@@ -617,7 +638,7 @@ inline void SkFindAndPlaceGlyph::ProcessPosText(
}
};
- GlyphFindAndPlace<ProcessOneGlyph> findAndPosition{
+ GlyphFindAndPlace<ProcessOneGlyph> findAndPosition {
[&](typename GlyphFindAndPlace<ProcessOneGlyph>::Variants* to_init) {
if (cache->isSubpixel()) {
switch (textAlignment) {