Fix buffer overflow on 'clusterBuffer' and improve error handling in FillClusterBuffer(). b=307537 r+sr=dbaron

This commit is contained in:
mats.palmgren%bredband.net 2005-09-12 01:05:58 +00:00
parent 667d1f2104
commit 2909dabcf6

View File

@ -29,6 +29,7 @@
* Daniel Glazman <glazman@netscape.com>
* Neil Deakin <neil@mozdevgroup.com>
* Masayuki Nakano <masayuki@d-toybox.com>
* Mats Palmgren <mats.palmgren@bredband.net>
*
* Alternatively, the contents of this file may be used under the terms of
* either of the GNU General Public License Version 2 or later (the "GPL"),
@ -858,8 +859,8 @@ protected:
PRBool IsChineseJapaneseLangGroup();
PRBool IsJustifiableCharacter(PRUnichar aChar, PRBool aLangIsCJ);
void FillClusterBuffer(nsPresContext *aPresContext, const PRUnichar *aText,
PRUint32 aLength, PRUint8 *aClusterStarts);
nsresult FillClusterBuffer(nsPresContext *aPresContext, const PRUnichar *aText,
PRUint32 aLength, nsAutoPRUint8Buffer& aClusterBuffer);
};
#ifdef ACCESSIBILITY
@ -1646,32 +1647,37 @@ nsTextFrame::IsJustifiableCharacter(PRUnichar aChar, PRBool aLangIsCJ)
return PR_FALSE;
}
void
nsresult
nsTextFrame::FillClusterBuffer(nsPresContext *aPresContext, const PRUnichar *aText,
PRUint32 aLength, PRUint8 *aClusterStarts)
PRUint32 aLength, nsAutoPRUint8Buffer& aClusterBuffer)
{
nsresult rv = aClusterBuffer.GrowTo(aLength);
NS_ENSURE_SUCCESS(rv, rv);
// Fill in the cluster hint information, if it's available.
nsCOMPtr<nsIRenderingContext> acx;
PRUint32 clusterHint = 0;
nsIPresShell *shell = aPresContext->GetPresShell();
if (shell) {
shell->CreateRenderingContext(this, getter_AddRefs(acx));
rv = shell->CreateRenderingContext(this, getter_AddRefs(acx));
NS_ENSURE_SUCCESS(rv, rv);
// Find the font metrics for this text
SetFontFromStyle(acx, mStyleContext);
if (acx)
acx->GetHints(clusterHint);
acx->GetHints(clusterHint);
clusterHint &= NS_RENDERING_HINT_TEXT_CLUSTERS;
}
if (clusterHint) {
acx->GetClusterInfo(aText, aLength, aClusterStarts);
rv = acx->GetClusterInfo(aText, aLength, aClusterBuffer.mBuffer);
}
else {
memset(aClusterStarts, 1, sizeof(PRInt8) * aLength);
memset(aClusterBuffer.mBuffer, 1, sizeof(PRInt8) * aLength);
}
return rv;
}
inline PRBool IsEndOfLine(nsFrameState aState)
@ -2784,7 +2790,6 @@ nsTextFrame::GetPositionSlowly(nsPresContext* aPresContext,
*aNewContent = mContent;
aOffset =0;
}
nsIDocument *doc = GetDocument(aPresContext);
// Make enough space to transform
nsAutoTextBuffer paintBuffer;
@ -3804,7 +3809,6 @@ nsTextFrame::GetPosition(nsPresContext* aPresContext,
SetFontFromStyle(rendContext, mStyleContext);
// Get the renderable form of the text
nsIDocument *doc = GetDocument(aPresContext);
nsTextTransformer tx(aPresContext);
PRInt32 textLength;
// no need to worry about justification, that's always on the slow path
@ -4137,7 +4141,6 @@ nsTextFrame::GetPointFromOffset(nsPresContext* aPresContext,
}
// Transform text from content into renderable form
nsIDocument *doc = GetDocument(aPresContext);
nsTextTransformer tx(aPresContext);
PRInt32 textLength;
PRIntn numJustifiableCharacter;
@ -4412,12 +4415,6 @@ nsTextFrame::PeekOffset(nsPresContext* aPresContext, nsPeekOffsetStruct *aPos)
}
PRInt32* ip = indexBuffer.mBuffer;
nsAutoPRUint8Buffer clusterBuffer;
rv = clusterBuffer.GrowTo(mContentLength + 1);
if (NS_FAILED(rv)) {
return rv;
}
PRInt32 textLength;
nsresult result(NS_ERROR_FAILURE);
aPos->mResultContent = mContent;//do this right off
@ -4483,8 +4480,10 @@ nsTextFrame::PeekOffset(nsPresContext* aPresContext, nsPeekOffsetStruct *aPos)
aPos->mContentOffset = 0;
PRInt32 i;
FillClusterBuffer(aPresContext, paintBuffer.mBuffer,
(PRUint32)textLength, clusterBuffer.mBuffer);
nsAutoPRUint8Buffer clusterBuffer;
rv = FillClusterBuffer(aPresContext, paintBuffer.mBuffer,
(PRUint32)textLength, clusterBuffer);
NS_ENSURE_SUCCESS(rv, rv);
for (i = aPos->mStartOffset -1 - mContentOffset; i >=0; i--){
if ((ip[i] < ip[aPos->mStartOffset - mContentOffset]) &&
@ -4539,8 +4538,10 @@ nsTextFrame::PeekOffset(nsPresContext* aPresContext, nsPeekOffsetStruct *aPos)
PRInt32 i;
aPos->mContentOffset = mContentLength;
FillClusterBuffer(aPresContext, paintBuffer.mBuffer,
(PRUint32)textLength, clusterBuffer.mBuffer);
nsAutoPRUint8Buffer clusterBuffer;
rv = FillClusterBuffer(aPresContext, paintBuffer.mBuffer,
(PRUint32)textLength, clusterBuffer);
NS_ENSURE_SUCCESS(rv, rv);
for (i = aPos->mStartOffset - mContentOffset; i <= mContentLength; i++) {
if ((ip[i] > ip[aPos->mStartOffset - mContentOffset]) &&