@@ -193,20 +193,30 @@ void Scanner<EncodingPolicy>::PrepareForBackgroundParse(Js::ScriptContext *scrip
193
193
// This is used to determine a length of BSTR, which can't contain a NUL character.
194
194
// -----------------------------------------------------------------------------
195
195
template <typename EncodingPolicy>
196
- charcount_t Scanner<EncodingPolicy>::LineLength(EncodedCharPtr first, EncodedCharPtr last)
196
+ charcount_t Scanner<EncodingPolicy>::LineLength(EncodedCharPtr first, EncodedCharPtr last, size_t * cb )
197
197
{
198
+ Assert (cb != nullptr );
199
+
198
200
charcount_t result = 0 ;
199
201
EncodedCharPtr p = first;
200
202
201
203
for (;;)
202
204
{
205
+ EncodedCharPtr prev = p;
203
206
switch ( this ->template ReadFull <false >(p, last) )
204
207
{
205
208
case kchNWL: // _C_NWL
206
209
case kchRET:
207
210
case kchLS:
208
211
case kchPS:
209
212
case kchNUL: // _C_NUL
213
+ // p is now advanced past the line terminator character.
214
+ // We need to know the number of bytes making up the line, not including the line terminator character.
215
+ // To avoid subtracting a variable number of bytes because the line terminator characters are different
216
+ // number of bytes long (plus there may be multiple valid encodings for these characters) just keep
217
+ // track of the first byte of the line terminator character in prev.
218
+ Assert (prev >= first);
219
+ *cb = prev - first;
210
220
return result;
211
221
}
212
222
result++;
@@ -2313,10 +2323,11 @@ HRESULT Scanner<EncodingPolicy>::SysAllocErrorLine(int32 ichMinLine, __out BSTR*
2313
2323
typename EncodingPolicy::EncodedCharPtr pStart = static_cast <size_t >(ichMinLine) == IchMinLine () ? m_pchMinLine : m_pchBase + this ->CharacterOffsetToUnitOffset (m_pchBase, m_currentCharacter, m_pchLast, ichMinLine);
2314
2324
2315
2325
// Determine the length by scanning for the next newline
2316
- charcount_t cch = LineLength (pStart, m_pchLast);
2326
+ size_t cb = 0 ;
2327
+ charcount_t cch = LineLength (pStart, m_pchLast, &cb);
2317
2328
Assert (cch <= LONG_MAX);
2318
2329
2319
- typename EncodingPolicy::EncodedCharPtr pEnd = static_cast <size_t >(ichMinLine) == IchMinLine () ? m_pchMinLine + cch : m_pchBase + this ->CharacterOffsetToUnitOffset (m_pchBase, m_currentCharacter, m_pchLast, cch);
2330
+ typename EncodingPolicy::EncodedCharPtr pEnd = static_cast <size_t >(ichMinLine) == IchMinLine () ? m_pchMinLine + cb : m_pchBase + this ->CharacterOffsetToUnitOffset (m_pchBase, m_currentCharacter, m_pchLast, cch);
2320
2331
2321
2332
*pbstrLine = SysAllocStringLen (NULL , cch);
2322
2333
if (!*pbstrLine)
0 commit comments