mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-12-02 01:48:05 +00:00
Added yet another defense to make Mozilla really robust when font resources run out, the patch makes font metrics to be fail safe or at least very hard to break -- to the point that failure means that the system is barely working (testing showed that Mozilla stayed alive while other applications were dying). Per request of super-reviewer & driver, also removed wallpaper null-checks sprinkled in the past for the problem. b=136248, r=shanjian, sr=attinasi
This commit is contained in:
parent
b1e82db052
commit
ca47d8b903
@ -223,17 +223,10 @@ nscoord CalcLength(const nsCSSValue& aValue,
|
||||
case eCSSUnit_XHeight: {
|
||||
aInherited = PR_TRUE;
|
||||
const nsFont* font = aStyleContext ? &(((nsStyleFont*)aStyleContext->GetStyleData(eStyleStruct_Font))->mFont) : aFont;
|
||||
nsIFontMetrics* fm;
|
||||
aPresContext->GetMetricsFor(*font, &fm);
|
||||
NS_ASSERTION(nsnull != fm, "can't get font metrics");
|
||||
nsCOMPtr<nsIFontMetrics> fm;
|
||||
aPresContext->GetMetricsFor(*font, getter_AddRefs(fm));
|
||||
nscoord xHeight;
|
||||
if (nsnull != fm) {
|
||||
fm->GetXHeight(xHeight);
|
||||
NS_RELEASE(fm);
|
||||
}
|
||||
else {
|
||||
xHeight = ((font->size * 2) / 3);
|
||||
}
|
||||
fm->GetXHeight(xHeight);
|
||||
return NSToCoordRound(aValue.GetFloatValue() * (float)xHeight);
|
||||
}
|
||||
case eCSSUnit_CapHeight: {
|
||||
|
@ -651,6 +651,7 @@ nsFontCache::GetMetricsFor(const nsFont& aFont, nsIAtom* aLangGroup,
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_POSTCONDITION(NS_SUCCEEDED(rv), "font metrics should not be null - bug 136248");
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
@ -2400,7 +2400,15 @@ nsFontMetricsWin::FindSubstituteFont(HDC aDC, PRUint32 c)
|
||||
}
|
||||
}
|
||||
|
||||
// if we ever reach here, the replacement char should be changed to a more common char
|
||||
// We are running out of resources if we reach here... Try a stock font
|
||||
NS_ASSERTION(::GetMapMode(aDC) == MM_TEXT, "mapping mode needs to be MM_TEXT");
|
||||
nsFontWin* font = LoadSubstituteFont(aDC, nsnull);
|
||||
if (font) {
|
||||
((nsFontWinSubstitute*)font)->SetRepresentable(c);
|
||||
mSubstituteFont = font;
|
||||
return font;
|
||||
}
|
||||
|
||||
NS_ERROR("Could not provide a substititute font");
|
||||
return nsnull;
|
||||
}
|
||||
@ -2409,12 +2417,15 @@ nsFontWin*
|
||||
nsFontMetricsWin::LoadSubstituteFont(HDC aDC, nsString* aName)
|
||||
{
|
||||
LOGFONT logFont;
|
||||
HFONT hfont = CreateFontHandle(aDC, aName, &logFont);
|
||||
HFONT hfont = aName
|
||||
? CreateFontHandle(aDC, aName, &logFont)
|
||||
: (HFONT)::GetStockObject(SYSTEM_FONT);
|
||||
if (hfont) {
|
||||
// XXX 'displayUnicode' has to be initialized based on the desired rendering mode
|
||||
PRBool displayUnicode = PR_FALSE;
|
||||
/* substitute font does not need ccmap */
|
||||
nsFontWinSubstitute* font = new nsFontWinSubstitute(&logFont, hfont, nsnull, displayUnicode);
|
||||
LOGFONT* lfont = aName ? &logFont : nsnull;
|
||||
nsFontWinSubstitute* font = new nsFontWinSubstitute(lfont, hfont, nsnull, displayUnicode);
|
||||
if (font) {
|
||||
HFONT oldFont = (HFONT)::SelectObject(aDC, (HGDIOBJ)hfont);
|
||||
InitMetricsFor(aDC, font);
|
||||
|
@ -2287,11 +2287,6 @@ ComputeLineHeight(nsIPresContext* aPresContext,
|
||||
}
|
||||
nsCOMPtr<nsIFontMetrics> fm;
|
||||
deviceContext->GetMetricsFor(font->mFont, langGroup, *getter_AddRefs(fm));
|
||||
|
||||
if (!fm) {
|
||||
NS_WARNING( "null font metrics for the device context - we have to fix this someday...");
|
||||
}
|
||||
|
||||
if (unit == eStyleUnit_Factor) {
|
||||
// For factor units the computed value of the line-height property
|
||||
// is found by multiplying the factor by the font's <b>actual</b>
|
||||
@ -2305,7 +2300,7 @@ ComputeLineHeight(nsIPresContext* aPresContext,
|
||||
// precise layout in the face of imprecise fonts.
|
||||
nscoord emHeight = font->mFont.size;
|
||||
#ifdef NEW_FONT_HEIGHT_APIS
|
||||
if (!nsHTMLReflowState::UseComputedHeight() && fm) {
|
||||
if (!nsHTMLReflowState::UseComputedHeight()) {
|
||||
fm->GetEmHeight(emHeight);
|
||||
}
|
||||
#endif
|
||||
@ -2314,7 +2309,7 @@ ComputeLineHeight(nsIPresContext* aPresContext,
|
||||
NS_ASSERTION(eStyleUnit_Normal == unit, "bad unit");
|
||||
lineHeight = font->mFont.size;
|
||||
#ifdef NEW_FONT_HEIGHT_APIS
|
||||
if (!nsHTMLReflowState::UseComputedHeight() && fm) {
|
||||
if (!nsHTMLReflowState::UseComputedHeight()) {
|
||||
lineHeight = GetNormalLineHeight(fm);
|
||||
}
|
||||
#endif
|
||||
|
@ -569,14 +569,11 @@ public:
|
||||
}
|
||||
mAveCharWidth = 0;
|
||||
deviceContext->GetMetricsFor(*plainFont, langGroup, mNormalFont);
|
||||
NS_ASSERTION(mNormalFont, "null normal font cannot be handled");
|
||||
if (mNormalFont) {
|
||||
aRenderingContext.SetFont(mNormalFont); // some users of the struct expect this state
|
||||
mNormalFont->GetSpaceWidth(mSpaceWidth);
|
||||
aRenderingContext.SetFont(mNormalFont); // some users of the struct expect this state
|
||||
mNormalFont->GetSpaceWidth(mSpaceWidth);
|
||||
#if defined(_WIN32) || defined(XP_OS2)
|
||||
mNormalFont->GetAveCharWidth(mAveCharWidth);
|
||||
mNormalFont->GetAveCharWidth(mAveCharWidth);
|
||||
#endif
|
||||
}
|
||||
if (0 == mAveCharWidth) {
|
||||
// provide a default if it could not be resolved
|
||||
mAveCharWidth = 10;
|
||||
@ -4612,18 +4609,8 @@ nsTextFrame::MeasureText(nsIPresContext* aPresContext,
|
||||
|
||||
aTextData.mX = 0;
|
||||
if (aTextData.mMeasureText) {
|
||||
// NOTE: in some cases, when font resources are exhausted, we end up with no normal font.
|
||||
// This will cause a crash because we are not handling it at the source and everyplace else
|
||||
// assumes the normal font is non-null.
|
||||
// This bit of ASSERTION / Runtime checking is to prevent the crash, but is only wallpaper.
|
||||
// We need to handle the problem when the font is being realized - currently that just throws
|
||||
// an assertion and we continue on.
|
||||
// See bug 117736
|
||||
NS_ASSERTION(aTs.mNormalFont, "null normal font, probably ran out of font resources");
|
||||
if (aTs.mNormalFont) {
|
||||
aTs.mNormalFont->GetMaxAscent(aTextData.mAscent);
|
||||
aTs.mNormalFont->GetMaxDescent(aTextData.mDescent);
|
||||
}
|
||||
aTs.mNormalFont->GetMaxAscent(aTextData.mAscent);
|
||||
aTs.mNormalFont->GetMaxDescent(aTextData.mDescent);
|
||||
}
|
||||
for (;;firstThing = PR_FALSE) {
|
||||
#ifdef IBMBIDI
|
||||
|
@ -2287,11 +2287,6 @@ ComputeLineHeight(nsIPresContext* aPresContext,
|
||||
}
|
||||
nsCOMPtr<nsIFontMetrics> fm;
|
||||
deviceContext->GetMetricsFor(font->mFont, langGroup, *getter_AddRefs(fm));
|
||||
|
||||
if (!fm) {
|
||||
NS_WARNING( "null font metrics for the device context - we have to fix this someday...");
|
||||
}
|
||||
|
||||
if (unit == eStyleUnit_Factor) {
|
||||
// For factor units the computed value of the line-height property
|
||||
// is found by multiplying the factor by the font's <b>actual</b>
|
||||
@ -2305,7 +2300,7 @@ ComputeLineHeight(nsIPresContext* aPresContext,
|
||||
// precise layout in the face of imprecise fonts.
|
||||
nscoord emHeight = font->mFont.size;
|
||||
#ifdef NEW_FONT_HEIGHT_APIS
|
||||
if (!nsHTMLReflowState::UseComputedHeight() && fm) {
|
||||
if (!nsHTMLReflowState::UseComputedHeight()) {
|
||||
fm->GetEmHeight(emHeight);
|
||||
}
|
||||
#endif
|
||||
@ -2314,7 +2309,7 @@ ComputeLineHeight(nsIPresContext* aPresContext,
|
||||
NS_ASSERTION(eStyleUnit_Normal == unit, "bad unit");
|
||||
lineHeight = font->mFont.size;
|
||||
#ifdef NEW_FONT_HEIGHT_APIS
|
||||
if (!nsHTMLReflowState::UseComputedHeight() && fm) {
|
||||
if (!nsHTMLReflowState::UseComputedHeight()) {
|
||||
lineHeight = GetNormalLineHeight(fm);
|
||||
}
|
||||
#endif
|
||||
|
@ -569,14 +569,11 @@ public:
|
||||
}
|
||||
mAveCharWidth = 0;
|
||||
deviceContext->GetMetricsFor(*plainFont, langGroup, mNormalFont);
|
||||
NS_ASSERTION(mNormalFont, "null normal font cannot be handled");
|
||||
if (mNormalFont) {
|
||||
aRenderingContext.SetFont(mNormalFont); // some users of the struct expect this state
|
||||
mNormalFont->GetSpaceWidth(mSpaceWidth);
|
||||
aRenderingContext.SetFont(mNormalFont); // some users of the struct expect this state
|
||||
mNormalFont->GetSpaceWidth(mSpaceWidth);
|
||||
#if defined(_WIN32) || defined(XP_OS2)
|
||||
mNormalFont->GetAveCharWidth(mAveCharWidth);
|
||||
mNormalFont->GetAveCharWidth(mAveCharWidth);
|
||||
#endif
|
||||
}
|
||||
if (0 == mAveCharWidth) {
|
||||
// provide a default if it could not be resolved
|
||||
mAveCharWidth = 10;
|
||||
@ -4612,18 +4609,8 @@ nsTextFrame::MeasureText(nsIPresContext* aPresContext,
|
||||
|
||||
aTextData.mX = 0;
|
||||
if (aTextData.mMeasureText) {
|
||||
// NOTE: in some cases, when font resources are exhausted, we end up with no normal font.
|
||||
// This will cause a crash because we are not handling it at the source and everyplace else
|
||||
// assumes the normal font is non-null.
|
||||
// This bit of ASSERTION / Runtime checking is to prevent the crash, but is only wallpaper.
|
||||
// We need to handle the problem when the font is being realized - currently that just throws
|
||||
// an assertion and we continue on.
|
||||
// See bug 117736
|
||||
NS_ASSERTION(aTs.mNormalFont, "null normal font, probably ran out of font resources");
|
||||
if (aTs.mNormalFont) {
|
||||
aTs.mNormalFont->GetMaxAscent(aTextData.mAscent);
|
||||
aTs.mNormalFont->GetMaxDescent(aTextData.mDescent);
|
||||
}
|
||||
aTs.mNormalFont->GetMaxAscent(aTextData.mAscent);
|
||||
aTs.mNormalFont->GetMaxDescent(aTextData.mDescent);
|
||||
}
|
||||
for (;;firstThing = PR_FALSE) {
|
||||
#ifdef IBMBIDI
|
||||
|
@ -1174,11 +1174,9 @@ nsMathMLContainerFrame::PlaceTokenFor(nsIFrame* aFrame,
|
||||
aFrame->GetStyleData(eStyleStruct_Font, (const nsStyleStruct*&)font);
|
||||
nsCOMPtr<nsIFontMetrics> fm;
|
||||
aPresContext->GetMetricsFor(font->mFont, getter_AddRefs(fm));
|
||||
nscoord ascent = 0, descent = 0;
|
||||
if (fm) {
|
||||
fm->GetMaxAscent(ascent);
|
||||
fm->GetMaxDescent(descent);
|
||||
}
|
||||
nscoord ascent, descent;
|
||||
fm->GetMaxAscent(ascent);
|
||||
fm->GetMaxDescent(descent);
|
||||
|
||||
nsBoundingMetrics bm;
|
||||
NS_STATIC_CAST(nsMathMLContainerFrame*, aFrame)->GetBoundingMetrics(bm);
|
||||
|
@ -223,17 +223,10 @@ nscoord CalcLength(const nsCSSValue& aValue,
|
||||
case eCSSUnit_XHeight: {
|
||||
aInherited = PR_TRUE;
|
||||
const nsFont* font = aStyleContext ? &(((nsStyleFont*)aStyleContext->GetStyleData(eStyleStruct_Font))->mFont) : aFont;
|
||||
nsIFontMetrics* fm;
|
||||
aPresContext->GetMetricsFor(*font, &fm);
|
||||
NS_ASSERTION(nsnull != fm, "can't get font metrics");
|
||||
nsCOMPtr<nsIFontMetrics> fm;
|
||||
aPresContext->GetMetricsFor(*font, getter_AddRefs(fm));
|
||||
nscoord xHeight;
|
||||
if (nsnull != fm) {
|
||||
fm->GetXHeight(xHeight);
|
||||
NS_RELEASE(fm);
|
||||
}
|
||||
else {
|
||||
xHeight = ((font->size * 2) / 3);
|
||||
}
|
||||
fm->GetXHeight(xHeight);
|
||||
return NSToCoordRound(aValue.GetFloatValue() * (float)xHeight);
|
||||
}
|
||||
case eCSSUnit_CapHeight: {
|
||||
|
Loading…
Reference in New Issue
Block a user