fixes bug 190549 "Textarea with lots of text within refuses to submit"

r=sicking sr=bzbarsky a=asa


git-svn-id: svn://10.0.0.236/trunk@137068 18797224-902f-48f8-a5cc-f745e15eee43
This commit is contained in:
darin%netscape.com
2003-01-29 06:40:16 +00:00
parent f4dbfceb41
commit 57bac18c51
5 changed files with 67 additions and 64 deletions

View File

@@ -55,11 +55,9 @@ interface nsIInputStream;
* Implementers should return the following:
*
* @return NS_OK and (*aWriteCount > 0) if consumed some data
* @return NS_BASE_STREAM_WOULD_BLOCK if not interested in consuming any data
* @return <other-error> on failure
* @return <any-error> if not interested in consuming any data
*
* Errors are passed to the caller of ReadSegments, unless aToOffset is
* greater than zero.
* Errors are never passed to the caller of ReadSegments.
*
* NOTE: returning NS_OK and (*aWriteCount = 0) has undefined behavior.
*
@@ -99,7 +97,7 @@ interface nsIInputStream : nsISupports
* @param aBuf the buffer into which the data is to be read
* @param aCount the maximum number of bytes to be read
*
* @return number of bytes read
* @return number of bytes read (may be less than aCount).
* @return 0 if reached end of file
*
* @throws NS_BASE_STREAM_WOULD_BLOCK if reading from the input stream would
@@ -109,15 +107,18 @@ interface nsIInputStream : nsISupports
[noscript] unsigned long read(in charPtr aBuf, in unsigned long aCount);
/**
* Low-level read method that has access to the stream's underlying buffer. The
* writer function may be called multiple times for segmented buffers.
* Low-level read method that has access to the stream's underlying buffer.
* The writer function may be called multiple times for segmented buffers.
* ReadSegments is expected to keep calling the writer until either there is
* nothing left to read or the writer returns an error. ReadSegments should
* not call the writer with zero bytes to consume.
*
* @param aWriter the "consumer" of the data to be read
* @param aClosure opaque parameter passed to writer
* @param aCount the maximum number of bytes to be read
*
* @return number of bytes read
* @return 0 if reached end of file
* @return number of bytes read (may be less than aCount)
* @return 0 if reached end of file (or if aWriter refused to consume data)
*
* @throws NS_BASE_STREAM_WOULD_BLOCK if reading from the input stream would
* block the calling thread (non-blocking mode only)

View File

@@ -57,11 +57,9 @@ interface nsIInputStream;
*
* @return NS_OK and (*aReadCount > 0) if successfully provided some data
* @return NS_OK and (*aReadCount = 0) or
* @return NS_BASE_STREAM_WOULD_BLOCK if not interested in providing any data
* @return <other-error> on failure
* @return <any-error> if not interested in providing any data
*
* Errors are passed to the caller of WriteSegments, unless aFromOffset is
* greater than zero.
* Errors are never passed to the caller of WriteSegments.
*
* @status FROZEN
*/
@@ -105,7 +103,7 @@ interface nsIOutputStream : nsISupports
* @param aBuf the buffer containing the data to be written
* @param aCount the maximum number of bytes to be written
*
* @return number of bytes written
* @return number of bytes written (may be less than aCount)
*
* @throws NS_BASE_STREAM_WOULD_BLOCK if writing to the output stream would
* block the calling thread (non-blocking mode only)
@@ -119,7 +117,7 @@ interface nsIOutputStream : nsISupports
* @param aFromStream the stream containing the data to be written
* @param aCount the maximum number of bytes to be written
*
* @return number of bytes written
* @return number of bytes written (may be less than aCount)
*
* @throws NS_BASE_STREAM_WOULD_BLOCK if writing to the output stream would
* block the calling thread (non-blocking mode only)
@@ -135,14 +133,17 @@ interface nsIOutputStream : nsISupports
in unsigned long aCount);
/**
* Low-level write method that has access to the stream's underlying buffer. The
* reader function may be called multiple times for segmented buffers.
* Low-level write method that has access to the stream's underlying buffer.
* The reader function may be called multiple times for segmented buffers.
* WriteSegments is expected to keep calling the reader until either there
* is nothing left to write or the reader returns an error. WriteSegments
* should not call the reader with zero bytes to provide.
*
* @param aReader the "provider" of the data to be written
* @param aClosure opaque parameter passed to reader
* @param aCount the maximum number of bytes to be written
*
* @return number of bytes written
* @return number of bytes written (may be less than aCount)
*
* @throws NS_BASE_STREAM_WOULD_BLOCK if writing to the output stream would
* block the calling thread (non-blocking mode only)
@@ -157,6 +158,9 @@ interface nsIOutputStream : nsISupports
/**
* @return true if stream is non-blocking
*
* NOTE: writing to a blocking output stream will block the calling thread
* until all given data can be consumed by the stream.
*/
boolean isNonBlocking();
};

View File

@@ -187,34 +187,38 @@ nsMultiplexInputStream::Available(PRUint32 *_retval)
NS_IMETHODIMP
nsMultiplexInputStream::Read(char * aBuf, PRUint32 aCount, PRUint32 *_retval)
{
nsresult rv;
PRUint32 len;
nsresult rv = NS_OK;
PRUint32 len, read;
*_retval = 0;
mStreams.Count(&len);
PRUint32 read = 0;
while (mCurrentStream < len && aCount > 0) {
while (mCurrentStream < len && aCount) {
nsCOMPtr<nsIInputStream> stream(do_QueryElementAt(&mStreams,
mCurrentStream));
rv = stream->Read(aBuf, aCount, _retval);
if (rv == NS_BASE_STREAM_WOULD_BLOCK) {
*_retval = read;
return read == 0 ? NS_BASE_STREAM_WOULD_BLOCK : NS_OK;
rv = stream->Read(aBuf, aCount, &read);
// XXX some streams return NS_BASE_STREAM_CLOSED to indicate EOF.
if (rv == NS_BASE_STREAM_CLOSED) {
rv = NS_OK;
read = 0;
}
NS_ENSURE_SUCCESS(rv, rv);
if (!*_retval) {
// we're done with this stream, proceed to next
else if (NS_FAILED(rv))
break;
if (read == 0) {
++mCurrentStream;
mStartedReadingCurrent = PR_FALSE;
}
else {
read += *_retval;
aBuf += *_retval;
aCount -= *_retval;
NS_ASSERTION(aCount >= read, "Read more than requested");
*_retval += read;
aCount -= read;
aBuf += read;
mStartedReadingCurrent = PR_TRUE;
}
}
*_retval = read;
return NS_OK;
return *_retval ? NS_OK : rv;
}
/* [noscript] unsigned long readSegments (in nsWriteSegmentFun writer,
@@ -226,7 +230,7 @@ nsMultiplexInputStream::ReadSegments(nsWriteSegmentFun aWriter, void *aClosure,
{
NS_ASSERTION(aWriter, "missing aWriter");
nsresult rv;
nsresult rv = NS_OK;
ReadSegmentsState state;
state.mThisStream = this;
state.mOffset = 0;
@@ -236,46 +240,38 @@ nsMultiplexInputStream::ReadSegments(nsWriteSegmentFun aWriter, void *aClosure,
PRUint32 len;
mStreams.Count(&len);
while (mCurrentStream < len) {
while (mCurrentStream < len && aCount) {
nsCOMPtr<nsIInputStream> stream(do_QueryElementAt(&mStreams,
mCurrentStream));
PRUint32 read;
rv = stream->ReadSegments(ReadSegCb, &state, aCount, &read);
// If we got an NS_BASE_STREAM_WOULD_BLOCK error since the reader
// didn't want any more data. This might not be an error for us if
// data was read from a previous stream in this run
if (state.mDone && rv == NS_BASE_STREAM_WOULD_BLOCK &&
!read && state.mOffset)
break;
// If the return value is NS_BASE_STREAM_CLOSED, we are done with this
// stream.
// XXX some streams return NS_BASE_STREAM_CLOSED to indicate EOF.
if (rv == NS_BASE_STREAM_CLOSED) {
++mCurrentStream;
mStartedReadingCurrent = PR_FALSE;
continue;
rv = NS_OK;
read = 0;
}
NS_ENSURE_SUCCESS(rv, rv);
NS_ASSERTION(aCount >= read, "Read more than requested");
mStartedReadingCurrent = PR_TRUE;
state.mOffset += read;
aCount -= read;
if (state.mDone || // writer doesn't want anymore data
aCount == 0) // the current stream still has data
// if |aWriter| decided to stop reading segments...
if (state.mDone || NS_FAILED(rv))
break;
// If the writer accepted all data but we didn't read any, this stream
// is finished. Go on to the next stream. These aren't the droids
// you're looking for.
// if stream is empty, then advance to the next stream.
if (read == 0) {
++mCurrentStream;
mStartedReadingCurrent = PR_FALSE;
}
else {
NS_ASSERTION(aCount >= read, "Read more than requested");
state.mOffset += read;
aCount -= read;
mStartedReadingCurrent = PR_TRUE;
}
}
// if we successfully read some data, then this call succeeded.
*_retval = state.mOffset;
return NS_OK;
return state.mOffset ? NS_OK : rv;
}
NS_METHOD
@@ -292,10 +288,8 @@ nsMultiplexInputStream::ReadSegCb(nsIInputStream* aIn, void* aClosure,
aToOffset + state->mOffset,
aCount,
aWriteCount);
if (rv == NS_BASE_STREAM_WOULD_BLOCK ||
(NS_SUCCEEDED(rv) && *aWriteCount < aCount && aCount != 0))
if (NS_FAILED(rv))
state->mDone = PR_TRUE;
return rv;
}

View File

@@ -408,10 +408,10 @@ NS_AsyncCopy(nsIAsyncInputStream *source,
//
// fire off two async copies :-)
//
rv = NS_AsyncCopy(source, pipeOut, segmentSize, PR_FALSE, PR_TRUE);
rv = NS_AsyncCopy(source, pipeOut, PR_FALSE, PR_TRUE, segmentSize, 1, segmentAlloc);
if (NS_FAILED(rv)) return rv;
rv = NS_AsyncCopy(pipeIn, sink, segmentSize, PR_TRUE, PR_FALSE);
rv = NS_AsyncCopy(pipeIn, sink, PR_TRUE, PR_FALSE, segmentSize, 1, segmentAlloc);
// maybe calling NS_AsyncCopy twice is a bad idea!
NS_ASSERTION(NS_SUCCEEDED(rv), "uh-oh");

View File

@@ -312,6 +312,10 @@ class ConstCharImpl
PRUint32 aCount, PRUint32 *result) {
nsresult rv;
PRInt32 maxCount = mLength - mOffset;
if (maxCount == 0) {
*result = 0;
return NS_OK;
}
if ((PRInt32)aCount > maxCount)
aCount = maxCount;
rv = writer(this, closure, mConstString + mOffset,