Bug 295047 Want unicode stream readers/writers: Makes nsIUnicharInputStream and

nsIConverterInputStream scriptable, and adds nsIUnicharOutputStream and
nsIConverterOutputStream (together with implementations).
r=jshin sr=darin a=chofmann
This commit is contained in:
cbiesinger%web.de 2005-06-24 19:44:50 +00:00
Родитель dca40f4343
Коммит 2e7e16befb
22 изменённых файлов: 819 добавлений и 198 удалений

Просмотреть файл

@ -53,7 +53,6 @@ EXPORTS = \
nsIUnicodeEncoder.h \ nsIUnicodeEncoder.h \
nsICharRepresentable.h \ nsICharRepresentable.h \
nsIMappingCache.h \ nsIMappingCache.h \
nsIConverterInputStream.h \
uconvutil.h \ uconvutil.h \
nsEncoderDecoderUtils.h \ nsEncoderDecoderUtils.h \
nsUConvCID.h \ nsUConvCID.h \

Просмотреть файл

@ -1,4 +1,4 @@
# # vim:set noet ts=8:
# ***** BEGIN LICENSE BLOCK ***** # ***** BEGIN LICENSE BLOCK *****
# Version: MPL 1.1/GPL 2.0/LGPL 2.1 # Version: MPL 1.1/GPL 2.0/LGPL 2.1
# #
@ -62,6 +62,7 @@ REQUIRES = xpcom \
locale \ locale \
unicharutil \ unicharutil \
chardet \ chardet \
necko \
$(NULL) $(NULL)
CSRCS = \ CSRCS = \
@ -74,6 +75,7 @@ CPPSRCS = \
nsUConvModule.cpp \ nsUConvModule.cpp \
nsCharsetAliasImp.cpp \ nsCharsetAliasImp.cpp \
nsConverterInputStream.cpp \ nsConverterInputStream.cpp \
nsConverterOutputStream.cpp \
nsTextToSubURI.cpp \ nsTextToSubURI.cpp \
nsURLProperties.cpp \ nsURLProperties.cpp \
nsCharsetConverterManager.cpp \ nsCharsetConverterManager.cpp \

Просмотреть файл

@ -36,13 +36,14 @@
* ***** END LICENSE BLOCK ***** */ * ***** END LICENSE BLOCK ***** */
#include "nsConverterInputStream.h" #include "nsConverterInputStream.h"
#include "nsIInputStream.h"
#include "nsICharsetConverterManager.h" #include "nsICharsetConverterManager.h"
#include "nsIServiceManager.h" #include "nsIServiceManager.h"
#define CONVERTER_BUFFER_SIZE 8192 #define CONVERTER_BUFFER_SIZE 8192
NS_IMPL_ISUPPORTS2(nsConverterInputStream, nsIConverterInputStream, NS_IMPL_ISUPPORTS3(nsConverterInputStream, nsIConverterInputStream,
nsIUnicharInputStream) nsIUnicharInputStream, nsIUnicharLineInputStream)
static NS_DEFINE_CID(kCharsetConverterManagerCID, NS_ICHARSETCONVERTERMANAGER_CID); static NS_DEFINE_CID(kCharsetConverterManagerCID, NS_ICHARSETCONVERTERMANAGER_CID);
@ -50,8 +51,11 @@ NS_IMETHODIMP
nsConverterInputStream::Init(nsIInputStream* aStream, nsConverterInputStream::Init(nsIInputStream* aStream,
const char *aCharset, const char *aCharset,
PRInt32 aBufferSize, PRInt32 aBufferSize,
PRBool aRecoverFromErrors) PRUnichar aReplacementChar)
{ {
if (!aCharset)
aCharset = "UTF-8";
nsresult rv; nsresult rv;
if (aBufferSize <=0) aBufferSize=CONVERTER_BUFFER_SIZE; if (aBufferSize <=0) aBufferSize=CONVERTER_BUFFER_SIZE;
@ -72,7 +76,7 @@ nsConverterInputStream::Init(nsIInputStream* aStream,
if (NS_FAILED(rv)) return rv; if (NS_FAILED(rv)) return rv;
mInput = aStream; mInput = aStream;
mRecoverFromErrors = aRecoverFromErrors; mReplacementChar = aReplacementChar;
return NS_OK; return NS_OK;
} }
@ -80,11 +84,13 @@ nsConverterInputStream::Init(nsIInputStream* aStream,
NS_IMETHODIMP NS_IMETHODIMP
nsConverterInputStream::Close() nsConverterInputStream::Close()
{ {
nsresult rv = mInput ? mInput->Close() : NS_OK;
PR_FREEIF(mLineBuffer);
mInput = nsnull; mInput = nsnull;
mConverter = nsnull; mConverter = nsnull;
mByteData = nsnull; mByteData = nsnull;
mUnicharData = nsnull; mUnicharData = nsnull;
return NS_OK; return rv;
} }
NS_IMETHODIMP NS_IMETHODIMP
@ -93,22 +99,22 @@ nsConverterInputStream::Read(PRUnichar* aBuf,
PRUint32 *aReadCount) PRUint32 *aReadCount)
{ {
NS_ASSERTION(mUnicharDataLength >= mUnicharDataOffset, "unsigned madness"); NS_ASSERTION(mUnicharDataLength >= mUnicharDataOffset, "unsigned madness");
PRUint32 rv = mUnicharDataLength - mUnicharDataOffset; PRUint32 readCount = mUnicharDataLength - mUnicharDataOffset;
if (0 == rv) { if (0 == readCount) {
// Fill the unichar buffer // Fill the unichar buffer
rv = Fill(&mLastErrorCode); readCount = Fill(&mLastErrorCode);
if (rv == 0) { if (readCount == 0) {
*aReadCount = 0; *aReadCount = 0;
return mLastErrorCode; return mLastErrorCode;
} }
} }
if (rv > aCount) { if (readCount > aCount) {
rv = aCount; readCount = aCount;
} }
memcpy(aBuf, mUnicharData->GetBuffer() + mUnicharDataOffset, memcpy(aBuf, mUnicharData->GetBuffer() + mUnicharDataOffset,
rv * sizeof(PRUnichar)); readCount * sizeof(PRUnichar));
mUnicharDataOffset += rv; mUnicharDataOffset += readCount;
*aReadCount = rv; *aReadCount = readCount;
return NS_OK; return NS_OK;
} }
@ -155,6 +161,32 @@ nsConverterInputStream::ReadSegments(nsWriteUnicharSegmentFun aWriter,
return NS_OK; return NS_OK;
} }
NS_IMETHODIMP
nsConverterInputStream::ReadString(PRUint32 aCount, nsAString& aString,
PRUint32* aReadCount)
{
NS_ASSERTION(mUnicharDataLength >= mUnicharDataOffset, "unsigned madness");
PRUint32 readCount = mUnicharDataLength - mUnicharDataOffset;
if (0 == readCount) {
// Fill the unichar buffer
readCount = Fill(&mLastErrorCode);
if (readCount == 0) {
*aReadCount = 0;
return mLastErrorCode;
}
}
if (readCount > aCount) {
readCount = aCount;
}
const PRUnichar* buf = NS_REINTERPRET_CAST(const PRUnichar*,
mUnicharData->GetBuffer() +
mUnicharDataOffset);
aString.Assign(buf, readCount);
mUnicharDataOffset += readCount;
*aReadCount = readCount;
return NS_OK;
}
PRUint32 PRUint32
nsConverterInputStream::Fill(nsresult * aErrorCode) nsConverterInputStream::Fill(nsresult * aErrorCode)
{ {
@ -209,11 +241,11 @@ nsConverterInputStream::Fill(nsresult * aErrorCode)
// the erroneous byte sequence and try again. This is not quite // the erroneous byte sequence and try again. This is not quite
// possible right now -- see bug 160784 // possible right now -- see bug 160784
srcConsumed += srcLen; srcConsumed += srcLen;
if (NS_FAILED(*aErrorCode) && mRecoverFromErrors) { if (NS_FAILED(*aErrorCode) && mReplacementChar) {
NS_ASSERTION(0 < mUnicharData->GetBufferSize() - mUnicharDataLength, NS_ASSERTION(0 < mUnicharData->GetBufferSize() - mUnicharDataLength,
"Decoder returned an error but filled the output buffer! " "Decoder returned an error but filled the output buffer! "
"Should not happen."); "Should not happen.");
mUnicharData->GetBuffer()[mUnicharDataLength++] = (PRUnichar)0xFFFD; mUnicharData->GetBuffer()[mUnicharDataLength++] = mReplacementChar;
++srcConsumed; ++srcConsumed;
// XXX this is needed to make sure we don't underrun our buffer; // XXX this is needed to make sure we don't underrun our buffer;
// bug 160784 again // bug 160784 again
@ -222,10 +254,20 @@ nsConverterInputStream::Fill(nsresult * aErrorCode)
} }
NS_ASSERTION(srcConsumed <= mByteData->GetLength(), NS_ASSERTION(srcConsumed <= mByteData->GetLength(),
"Whoa. The converter should have returned NS_OK_UDEC_MOREINPUT before this point!"); "Whoa. The converter should have returned NS_OK_UDEC_MOREINPUT before this point!");
} while (mRecoverFromErrors && } while (mReplacementChar &&
NS_FAILED(*aErrorCode)); NS_FAILED(*aErrorCode));
mLeftOverBytes = mByteData->GetLength() - srcConsumed; mLeftOverBytes = mByteData->GetLength() - srcConsumed;
return mUnicharDataLength; return mUnicharDataLength;
} }
NS_IMETHODIMP
nsConverterInputStream::ReadLine(nsAString& aLine, PRBool* aResult)
{
if (!mLineBuffer) {
nsresult rv = NS_InitLineBuffer(&mLineBuffer);
if (NS_FAILED(rv)) return rv;
}
return NS_ReadLine(this, mLineBuffer, aLine, aResult);
}

Просмотреть файл

@ -35,8 +35,11 @@
* *
* ***** END LICENSE BLOCK ***** */ * ***** END LICENSE BLOCK ***** */
#include "nsIInputStream.h"
#include "nsIConverterInputStream.h" #include "nsIConverterInputStream.h"
#include "nsIUnicharLineInputStream.h"
#include "nsString.h" #include "nsString.h"
#include "nsReadLine.h"
#include "nsCOMPtr.h" #include "nsCOMPtr.h"
#include "nsIUnicodeDecoder.h" #include "nsIUnicodeDecoder.h"
@ -52,28 +55,24 @@
class nsConverterInputStream : nsIConverterInputStream { class nsConverterInputStream : public nsIConverterInputStream,
public nsIUnicharLineInputStream {
public: public:
NS_DECL_ISUPPORTS NS_DECL_ISUPPORTS
NS_IMETHOD Read(PRUnichar* aBuf, NS_DECL_NSIUNICHARINPUTSTREAM
PRUint32 aCount, NS_DECL_NSIUNICHARLINEINPUTSTREAM
PRUint32 *aReadCount); NS_DECL_NSICONVERTERINPUTSTREAM
NS_IMETHOD Close();
NS_IMETHOD Init(nsIInputStream* aStream, const char *aCharset,
PRInt32 aBufferSize, PRBool aRecoverFromErrors);
NS_IMETHOD ReadSegments(nsWriteUnicharSegmentFun aWriter,
void* aClosure,
PRUint32 aCount, PRUint32* aReadCount);
nsConverterInputStream() : nsConverterInputStream() :
mLastErrorCode(NS_OK), mLastErrorCode(NS_OK),
mLeftOverBytes(0), mLeftOverBytes(0),
mUnicharDataOffset(0), mUnicharDataOffset(0),
mUnicharDataLength(0), mUnicharDataLength(0),
mRecoverFromErrors(PR_FALSE) { } mReplacementChar(DEFAULT_REPLACEMENT_CHARACTER),
mLineBuffer(nsnull) { }
virtual ~nsConverterInputStream() {} virtual ~nsConverterInputStream() { Close(); }
private: private:
@ -89,6 +88,7 @@ class nsConverterInputStream : nsIConverterInputStream {
PRUint32 mLeftOverBytes; PRUint32 mLeftOverBytes;
PRUint32 mUnicharDataOffset; PRUint32 mUnicharDataOffset;
PRUint32 mUnicharDataLength; PRUint32 mUnicharDataLength;
PRBool mRecoverFromErrors; PRUnichar mReplacementChar;
nsLineBuffer<PRUnichar>* mLineBuffer;
}; };

Просмотреть файл

@ -0,0 +1,167 @@
/* vim:set expandtab ts=4 sw=4 sts=4 cin: */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org unicode stream converter code.
*
* The Initial Developer of the Original Code is
* Christian Biesinger <cbiesinger@web.de>.
* Portions created by the Initial Developer are Copyright (C) 2005
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "nsCOMPtr.h"
#include "nsAutoPtr.h"
#include "nsIServiceManager.h"
#include "nsIOutputStream.h"
#include "nsICharsetConverterManager.h"
#include "nsConverterOutputStream.h"
NS_IMPL_ISUPPORTS2(nsConverterOutputStream,
nsIUnicharOutputStream,
nsIConverterOutputStream)
nsConverterOutputStream::~nsConverterOutputStream()
{
if (mOutStream) {
Flush();
Close();
}
}
NS_IMETHODIMP
nsConverterOutputStream::Init(nsIOutputStream* aOutStream,
const char* aCharset,
PRUint32 aBufferSize /* ignored */,
PRUnichar aReplacementChar)
{
NS_PRECONDITION(aOutStream, "Null output stream!");
if (!aCharset)
aCharset = "UTF-8";
mOutStream = aOutStream;
nsresult rv;
nsCOMPtr<nsICharsetConverterManager> ccm =
do_GetService(NS_CHARSETCONVERTERMANAGER_CONTRACTID, &rv);
if (NS_FAILED(rv)) return rv;
rv = ccm->GetUnicodeEncoder(aCharset, getter_AddRefs(mConverter));
if (NS_FAILED(rv))
return rv;
PRInt32 behaviour = aReplacementChar ? nsIUnicodeEncoder::kOnError_Replace
: nsIUnicodeEncoder::kOnError_Signal;
return mConverter->
SetOutputErrorBehavior(behaviour,
nsnull,
aReplacementChar);
}
NS_IMETHODIMP
nsConverterOutputStream::Write(PRUint32 aCount, const PRUnichar* aChars,
PRBool* aSuccess)
{
PRInt32 inLen = aCount;
PRInt32 maxLen;
nsresult rv = mConverter->GetMaxLength(aChars, inLen, &maxLen);
NS_ENSURE_SUCCESS(rv, rv);
nsCAutoString buf;
buf.SetLength(maxLen);
if (buf.Length() != maxLen)
return NS_ERROR_OUT_OF_MEMORY;
PRInt32 outLen = maxLen;
rv = mConverter->Convert(aChars, &inLen, buf.BeginWriting(), &outLen);
if (NS_FAILED(rv))
return rv;
if (rv == NS_ERROR_UENC_NOMAPPING) {
// Yes, NS_ERROR_UENC_NOMAPPING is a success code
return NS_ERROR_LOSS_OF_SIGNIFICANT_DATA;
}
NS_ASSERTION(inLen == aCount,
"Converter didn't consume all the data!");
PRUint32 written;
rv = mOutStream->Write(buf.get(), outLen, &written);
*aSuccess = NS_SUCCEEDED(rv) && written == PRUint32(outLen);
return rv;
}
NS_IMETHODIMP
nsConverterOutputStream::WriteString(const nsAString& aString, PRBool* aSuccess)
{
PRInt32 inLen = aString.Length();
nsAString::const_iterator i;
aString.BeginReading(i);
return Write(inLen, i.get(), aSuccess);
}
NS_IMETHODIMP
nsConverterOutputStream::Flush()
{
if (!mOutStream)
return NS_OK; // Already closed.
char buf[1024];
PRInt32 size = sizeof(buf);
nsresult rv = mConverter->Finish(buf, &size);
NS_ASSERTION(rv != NS_OK_UENC_MOREOUTPUT,
"1024 bytes ought to be enough for everyone");
if (NS_FAILED(rv))
return rv;
PRUint32 written;
rv = mOutStream->Write(buf, size, &written);
if (NS_FAILED(rv)) {
NS_WARNING("Flush() lost data!");
return rv;
}
if (written != PRUint32(size)) {
NS_WARNING("Flush() lost data!");
return NS_ERROR_LOSS_OF_SIGNIFICANT_DATA;
}
return rv;
}
NS_IMETHODIMP
nsConverterOutputStream::Close()
{
nsresult rv1 = Flush();
nsresult rv2 = mOutStream->Close();
mOutStream = nsnull;
mConverter = nsnull;
return NS_FAILED(rv1) ? rv1 : rv2;
}

Просмотреть файл

@ -0,0 +1,68 @@
/* vim:set expandtab ts=4 sw=4 sts=4 cin: */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org unicode stream converter code.
*
* The Initial Developer of the Original Code is
* Christian Biesinger <cbiesinger@web.de>.
* Portions created by the Initial Developer are Copyright (C) 2005
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#ifndef NSCONVERTEROUTPUTSTREAM_H_
#define NSCONVERTEROUTPUTSTREAM_H_
#include "nsIOutputStream.h"
#include "nsIConverterOutputStream.h"
#include "nsCOMPtr.h"
class nsIUnicodeEncoder;
class nsIOutputStream;
/* ff8780a5-bbb1-4bc5-8ee7-057e7bc5c925 */
#define NS_CONVERTEROUTPUTSTREAM_CID \
{ 0xff8780a5, 0xbbb1, 0x4bc5, \
{ 0x8e, 0xe7, 0x05, 0x7e, 0x7b, 0xc5, 0xc9, 0x25 } }
class nsConverterOutputStream : public nsIConverterOutputStream {
public:
nsConverterOutputStream() {}
NS_DECL_ISUPPORTS
NS_DECL_NSIUNICHAROUTPUTSTREAM
NS_DECL_NSICONVERTEROUTPUTSTREAM
private:
~nsConverterOutputStream();
nsCOMPtr<nsIUnicodeEncoder> mConverter;
nsCOMPtr<nsIOutputStream> mOutStream;
};
#endif

Просмотреть файл

@ -56,6 +56,7 @@
#include "nsTextToSubURI.h" #include "nsTextToSubURI.h"
#include "nsUTF8ConverterService.h" #include "nsUTF8ConverterService.h"
#include "nsConverterInputStream.h" #include "nsConverterInputStream.h"
#include "nsConverterOutputStream.h"
#include "nsPlatformCharset.h" #include "nsPlatformCharset.h"
#ifndef MOZ_USE_NATIVE_UCONV #ifndef MOZ_USE_NATIVE_UCONV
@ -717,6 +718,7 @@ NS_GENERIC_FACTORY_CONSTRUCTOR(nsTextToSubURI)
NS_GENERIC_FACTORY_CONSTRUCTOR(nsUTF8ConverterService) NS_GENERIC_FACTORY_CONSTRUCTOR(nsUTF8ConverterService)
NS_GENERIC_FACTORY_CONSTRUCTOR(nsCharsetAlias2) NS_GENERIC_FACTORY_CONSTRUCTOR(nsCharsetAlias2)
NS_GENERIC_FACTORY_CONSTRUCTOR(nsConverterInputStream) NS_GENERIC_FACTORY_CONSTRUCTOR(nsConverterInputStream)
NS_GENERIC_FACTORY_CONSTRUCTOR(nsConverterOutputStream)
NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsPlatformCharset, Init) NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsPlatformCharset, Init)
static const nsModuleComponentInfo components[] = static const nsModuleComponentInfo components[] =
@ -746,6 +748,10 @@ static const nsModuleComponentInfo components[] =
NS_CONVERTERINPUTSTREAM_CONTRACTID, NS_CONVERTERINPUTSTREAM_CONTRACTID,
nsConverterInputStreamConstructor nsConverterInputStreamConstructor
}, },
{ "Unicode converter output stream", NS_CONVERTEROUTPUTSTREAM_CID,
"@mozilla.org/intl/converter-output-stream;1",
nsConverterOutputStreamConstructor
},
#ifdef MOZ_USE_NATIVE_UCONV #ifdef MOZ_USE_NATIVE_UCONV
{ {
"Native UConv Service", "Native UConv Service",

Просмотреть файл

@ -1212,7 +1212,9 @@ CSSLoaderImpl::LoadSheet(SheetLoadData* aLoadData, StyleSheetState aSheetState)
// 8192 is a nice magic number that happens to be what a lot of // 8192 is a nice magic number that happens to be what a lot of
// other things use for buffer sizes. // other things use for buffer sizes.
rv = converterStream->Init(stream, "UTF-8", rv = converterStream->Init(stream, "UTF-8",
8192, PR_TRUE); 8192,
nsIConverterInputStream::
DEFAULT_REPLACEMENT_CHARACTER);
if (NS_FAILED(rv)) { if (NS_FAILED(rv)) {
LOG_ERROR((" Failed to initialize converter stream")); LOG_ERROR((" Failed to initialize converter stream"));

Просмотреть файл

@ -21,6 +21,7 @@
* the Initial Developer. All Rights Reserved. * the Initial Developer. All Rights Reserved.
* *
* Contributor(s): * Contributor(s):
* Christian Biesinger <cbiesinger@web.de>
* *
* Alternatively, the contents of this file may be used under the terms of * Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or * either the GNU General Public License Version 2 or later (the "GPL"), or
@ -66,11 +67,13 @@
* @internal * @internal
* Line buffer structure, buffers data from an input stream. * Line buffer structure, buffers data from an input stream.
*/ */
struct nsLineBuffer { template<typename CharT>
char buf[kLineBufferSize+1]; class nsLineBuffer {
char* start; public:
char* current; CharT buf[kLineBufferSize+1];
char* end; CharT* start;
CharT* current;
CharT* end;
PRBool empty; PRBool empty;
}; };
@ -95,9 +98,10 @@ struct nsLineBuffer {
* } * }
* @endcode * @endcode
*/ */
static nsresult template<typename CharT>
NS_InitLineBuffer (nsLineBuffer ** aBufferPtr) { nsresult
*aBufferPtr = PR_NEW(nsLineBuffer); NS_InitLineBuffer (nsLineBuffer<CharT> ** aBufferPtr) {
*aBufferPtr = PR_NEW(nsLineBuffer<CharT>);
if (!(*aBufferPtr)) if (!(*aBufferPtr))
return NS_ERROR_OUT_OF_MEMORY; return NS_ERROR_OUT_OF_MEMORY;
@ -129,14 +133,15 @@ NS_InitLineBuffer (nsLineBuffer ** aBufferPtr) {
* Input stream returned an error upon read. See * Input stream returned an error upon read. See
* nsIInputStream::read. * nsIInputStream::read.
*/ */
static nsresult template<typename CharT, class StreamType, class StringType>
NS_ReadLine (nsIInputStream* aStream, nsLineBuffer * aBuffer, nsresult
nsACString & aLine, PRBool *more) { NS_ReadLine (StreamType* aStream, nsLineBuffer<CharT> * aBuffer,
StringType & aLine, PRBool *more) {
nsresult rv = NS_OK; nsresult rv = NS_OK;
PRUint32 bytesRead; PRUint32 bytesRead;
*more = PR_TRUE; *more = PR_TRUE;
PRBool eolStarted = PR_FALSE; PRBool eolStarted = PR_FALSE;
char eolchar = '\0'; CharT eolchar = '\0';
aLine.Truncate(); aLine.Truncate();
while (1) { // will be returning out of this loop on eol or eof while (1) { // will be returning out of this loop on eol or eof
if (aBuffer->empty) { // buffer is empty. Read into it. if (aBuffer->empty) { // buffer is empty. Read into it.

Просмотреть файл

@ -229,7 +229,7 @@ nsDirectoryIndexStream::Init(nsIFile* aDir)
nsString tmp; nsString tmp;
rv = pc->GetCharset(kPlatformCharsetSel_FileName, tmp); rv = pc->GetCharset(kPlatformCharsetSel_FileName, tmp);
if (NS_FAILED(rv)) return rv; if (NS_FAILED(rv)) return rv;
mFSCharset.Adopt(ToNewCString(tmp)); LossyCopyUTF16toASCII(tmp, mFSCharset);
#endif #endif
} }

Просмотреть файл

@ -49,7 +49,7 @@
#include "prlog.h" #include "prlog.h"
#include "prio.h" #include "prio.h"
struct nsLineBuffer; template<class CharType> class nsLineBuffer;
//////////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////////////
@ -101,7 +101,7 @@ public:
Create(nsISupports *aOuter, REFNSIID aIID, void **aResult); Create(nsISupports *aOuter, REFNSIID aIID, void **aResult);
protected: protected:
nsLineBuffer *mLineBuffer; nsLineBuffer<char> *mLineBuffer;
/** /**
* The file being opened. Only stored when DELETE_ON_CLOSE or * The file being opened. Only stored when DELETE_ON_CLOSE or

Просмотреть файл

@ -184,7 +184,7 @@ nsUnicharStreamLoader::OnStopRequest(nsIRequest *request,
rv = uin->Init(mInputStream, rv = uin->Init(mInputStream,
mCharset.get(), mCharset.get(),
mSegmentSize, mSegmentSize,
PR_TRUE); nsIConverterInputStream::DEFAULT_REPLACEMENT_CHARACTER);
if (NS_FAILED(rv)) { if (NS_FAILED(rv)) {
rv = mObserver->OnStreamComplete(this, mContext, rv, nsnull); rv = mObserver->OnStreamComplete(this, mContext, rv, nsnull);

Просмотреть файл

@ -97,7 +97,6 @@ EXPORTS = \
nsEscape.h \ nsEscape.h \
nsFastLoadPtr.h \ nsFastLoadPtr.h \
nsFastLoadService.h \ nsFastLoadService.h \
nsIUnicharInputStream.h \
nsLinebreakConverter.h \ nsLinebreakConverter.h \
nsLocalFile.h \ nsLocalFile.h \
nsMultiplexInputStream.h \ nsMultiplexInputStream.h \
@ -133,6 +132,7 @@ XPIDLSRCS = \
nsIInputStreamTee.idl \ nsIInputStreamTee.idl \
nsILocalFileWin.idl \ nsILocalFileWin.idl \
nsILineInputStream.idl \ nsILineInputStream.idl \
nsIUnicharLineInputStream.idl \
nsIMultiplexInputStream.idl \ nsIMultiplexInputStream.idl \
nsIObjectInputStream.idl \ nsIObjectInputStream.idl \
nsIObjectOutputStream.idl \ nsIObjectOutputStream.idl \
@ -143,6 +143,10 @@ XPIDLSRCS = \
nsIStreamBufferAccess.idl \ nsIStreamBufferAccess.idl \
nsIAsyncInputStream.idl \ nsIAsyncInputStream.idl \
nsIAsyncOutputStream.idl \ nsIAsyncOutputStream.idl \
nsIUnicharInputStream.idl \
nsIUnicharOutputStream.idl \
nsIConverterInputStream.idl \
nsIConverterOutputStream.idl \
$(NULL) $(NULL)
ifeq ($(MOZ_WIDGET_TOOLKIT),os2) ifeq ($(MOZ_WIDGET_TOOLKIT),os2)

Просмотреть файл

@ -0,0 +1,72 @@
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 1998
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* 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"),
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "nsIUnicharInputStream.idl"
interface nsIInputStream;
/**
* A unichar input stream that wraps an input stream.
* This allows reading unicode strings from a stream, automatically converting
* the bytes from a selected character encoding.
*/
[scriptable, uuid(FC66FFB6-5404-4908-A4A3-27F92FA0579D)]
interface nsIConverterInputStream : nsIUnicharInputStream {
/**
* Default replacement char value, U+FFFD REPLACEMENT CHARACTER.
*/
const PRUnichar DEFAULT_REPLACEMENT_CHARACTER = 0xFFFD;
/**
* Initialize this stream.
* @param aStream
* The underlying stream to read from.
* @param aCharset
* The character encoding to use for converting the bytes of the
* stream. A null charset will be interpreted as UTF-8.
* @param aBufferSize
* How many bytes to buffer.
* @param aReplacementChar
* The character to replace unknown byte sequences in the stream
* with. The standard replacement character is U+FFFD.
* A value of 0x0000 will cause an exception to be thrown if unknown
* byte sequences are encountered in the stream.
*/
void init (in nsIInputStream aStream, in string aCharset,
in long aBufferSize, in PRUnichar aReplacementChar);
};

Просмотреть файл

@ -0,0 +1,76 @@
/* vim:set expandtab ts=4 sw=4 sts=4 cin: */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org unicode stream converter code.
*
* The Initial Developer of the Original Code is
* Christian Biesinger <cbiesinger@web.de>.
* Portions created by the Initial Developer are Copyright (C) 2005
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "nsIUnicharOutputStream.idl"
interface nsIOutputStream;
/**
* This interface allows writing strings to a stream, doing automatic
* character encoding conversion.
*/
[scriptable, uuid(4b71113a-cb0d-479f-8ed5-01daeba2e8d4)]
interface nsIConverterOutputStream : nsIUnicharOutputStream
{
/**
* Initialize this stream. Must be called before any other method on this
* interface, or you will crash. The output stream passed to this method
* must not be null, or you will crash.
*
* @param aOutStream
* The underlying output stream to which the converted strings will
* be written.
* @param aCharset
* The character set to use for encoding the characters. A null
* charset will be interpreted as UTF-8.
* @param aBufferSize
* How many bytes to buffer. A value of 0 means that no bytes will be
* buffered. Implementations not supporting buffering may ignore
* this parameter.
* @param aReplacementCharacter
* The replacement character to use when an unsupported character is found.
* The character must be encodable in the selected character
* encoding; otherwise, attempts to write an unsupported character
* will throw NS_ERROR_LOSS_OF_SIGNIFICANT_DATA.
*
* A value of 0x0000 will cause an exception to be thrown upon
* attempts to write unsupported characters.
*/
void init(in nsIOutputStream aOutStream, in string aCharset,
in unsigned long aBufferSize,
in PRUnichar aReplacementCharacter);
};

Просмотреть файл

@ -53,6 +53,8 @@ interface nsILineInputStream : nsISupports
* (aLine is valid). * (aLine is valid).
* @retval true * @retval true
* The file contains further lines. * The file contains further lines.
* @note Do not mix readLine with other read functions.
* Doing so can cause various problems and is not supported.
*/ */
boolean readLine(out ACString aLine); boolean readLine(out ACString aLine);
}; };

Просмотреть файл

@ -1,96 +0,0 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 1998
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* 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"),
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#ifndef nsIUnicharInputStream_h___
#define nsIUnicharInputStream_h___
#include "nsIInputStream.h"
#include "nsString.h"
#include "nscore.h"
class nsIUnicharInputStream;
typedef NS_CALLBACK(nsWriteUnicharSegmentFun)(nsIUnicharInputStream *aInStream,
void *aClosure,
const PRUnichar *aFromSegment,
PRUint32 aToOffset,
PRUint32 aCount,
PRUint32 *aWriteCount);
/* c4bcf6ee-3a79-4d77-8d48-f17be3199b3b */
#define NS_IUNICHAR_INPUT_STREAM_IID \
{ 0xc4bcf6ee, 0x3a79, 0x4d77, \
{0x8d, 0x48, 0xf1, 0x7b, 0xe3, 0x19, 0x9b, 0x3b} }
/** Abstract unicode character input stream
* @see nsIInputStream
*/
class NS_NO_VTABLE nsIUnicharInputStream : public nsISupports {
public:
NS_DEFINE_STATIC_IID_ACCESSOR(NS_IUNICHAR_INPUT_STREAM_IID)
NS_IMETHOD Read(PRUnichar* aBuf,
PRUint32 aCount,
PRUint32 *aReadCount) = 0;
NS_IMETHOD Close() = 0;
NS_IMETHOD ReadSegments(nsWriteUnicharSegmentFun aWriter,
void* aClosure,
PRUint32 aCount,
PRUint32 *aReadCount) = 0;
};
/**
* Create a nsIUnicharInputStream that wraps up a string. Data is fed
* from the string out until the done. When this object is destroyed
* it destroys the string by calling |delete| on the pointer if
* aTakeOwnership is set. If aTakeOwnership is not set, you must
* ensure that the string outlives the stream!
*/
extern NS_COM nsresult
NS_NewStringUnicharInputStream(nsIUnicharInputStream** aInstancePtrResult,
const nsAString* aString,
PRBool aTakeOwnerhip);
/** Create a new nsUnicharInputStream that provides a converter for the
* byte input stream aStreamToWrap. If no converter can be found then
* nsnull is returned and the error code is set to
* NS_INPUTSTREAM_NO_CONVERTER.
*/
extern NS_COM nsresult
NS_NewUTF8ConverterStream(nsIUnicharInputStream** aInstancePtrResult,
nsIInputStream* aStreamToWrap,
PRInt32 aBufferSize = 0);
#endif /* nsUnicharInputStream_h___ */

Просмотреть файл

@ -0,0 +1,155 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org code.
*
* The Initial Developer of the Original Code is
* Netscape Communications Corporation.
* Portions created by the Initial Developer are Copyright (C) 1998
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* 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"),
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "nsISupports.idl"
interface nsIUnicharInputStream;
%{C++
/**
* The signature of the writer function passed to ReadSegments. This
* is the "consumer" of data that gets read from the stream's buffer.
*
* @param aInStream stream being read
* @param aClosure opaque parameter passed to ReadSegments
* @param aFromSegment pointer to memory owned by the input stream
* @param aToOffset amount already read (since ReadSegments was called)
* @param aCount length of fromSegment
* @param aWriteCount number of bytes read
*
* Implementers should return the following:
*
* @return NS_OK and (*aWriteCount > 0) if consumed some data
* @return <any-error> if not interested in consuming any data
*
* Errors are never passed to the caller of ReadSegments.
*
* NOTE: returning NS_OK and (*aWriteCount = 0) has undefined behavior.
*/
typedef NS_CALLBACK(nsWriteUnicharSegmentFun)(nsIUnicharInputStream *aInStream,
void *aClosure,
const PRUnichar *aFromSegment,
PRUint32 aToOffset,
PRUint32 aCount,
PRUint32 *aWriteCount);
%}
native nsWriteUnicharSegmentFun(nsWriteUnicharSegmentFun);
/**
* Abstract unicode character input stream
* @see nsIInputStream
*/
[scriptable, uuid(d5e3bd80-6723-4b92-b0c9-22f6162fd94f)]
interface nsIUnicharInputStream : nsISupports {
/**
* Reads into a caller-provided character array.
*
* @return The number of characters that were successfully read. May be less
* than aCount, even if there is more data in the input stream.
* A return value of 0 means EOF.
*
* @note To read more than 2^32 characters, call this method multiple times.
*/
[noscript] unsigned long read([array, size_is(aCount)] in PRUnichar 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.
* 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 characters 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 characters to be read
*
* @return number of characters 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)
* @throws <other-error> on failure
*
* NOTE: this function may be unimplemented if a stream has no underlying
* buffer
*/
[noscript] unsigned long readSegments(in nsWriteUnicharSegmentFun aWriter,
in voidPtr aClosure,
in unsigned long aCount);
/**
* Read into a string object.
* @param aCount The number of characters that should be read
* @return The number of characters that were read.
*/
unsigned long readString(in unsigned long aCount, out AString aString);
/**
* Close the stream and free associated resources. This also closes the
* underlying stream, if any.
*/
void close();
};
%{C++
#include "nsStringFwd.h"
class nsIInputStream;
/**
* Create a nsIUnicharInputStream that wraps up a string. Data is fed
* from the string out until the done. When this object is destroyed
* it destroys the string by calling |delete| on the pointer if
* aTakeOwnership is set. If aTakeOwnership is not set, you must
* ensure that the string outlives the stream!
*/
extern NS_COM nsresult
NS_NewStringUnicharInputStream(nsIUnicharInputStream** aInstancePtrResult,
const nsAString* aString,
PRBool aTakeOwnership);
/**
* Create a new nsUnicharInputStream that provides a converter for the
* byte input stream aStreamToWrap. If no converter can be found then
* nsnull is returned and the error code is set to
* NS_INPUTSTREAM_NO_CONVERTER.
*/
extern NS_COM nsresult
NS_NewUTF8ConverterStream(nsIUnicharInputStream** aInstancePtrResult,
nsIInputStream* aStreamToWrap,
PRInt32 aBufferSize = 0);
%}

Просмотреть файл

@ -1,5 +1,6 @@
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
/* ***** BEGIN LICENSE BLOCK ***** *
* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
* *
* The contents of this file are subject to the Mozilla Public License Version * The contents of this file are subject to the Mozilla Public License Version
@ -15,11 +16,12 @@
* The Original Code is mozilla.org code. * The Original Code is mozilla.org code.
* *
* The Initial Developer of the Original Code is * The Initial Developer of the Original Code is
* Netscape Communications Corporation. * Boris Zbarsky <bzbarsky@mit.edu>.
* Portions created by the Initial Developer are Copyright (C) 1998 * Portions created by the Initial Developer are Copyright (C) 2001
* the Initial Developer. All Rights Reserved. * the Initial Developer. All Rights Reserved.
* *
* Contributor(s): * Contributor(s):
* Christian Biesinger <cbiesinger@web.de>
* *
* Alternatively, the contents of this file may be used under the terms of * 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"), * either of the GNU General Public License Version 2 or later (the "GPL"),
@ -35,19 +37,23 @@
* *
* ***** END LICENSE BLOCK ***** */ * ***** END LICENSE BLOCK ***** */
#include "nsISupports.h" #include "nsISupports.idl"
#include "nsIUnicharInputStream.h"
// {FC66FFB6-5404-4908-A4A3-27F92FA0579D} [scriptable, uuid(67f42475-ba80-40f8-ac0b-649c89230184)]
#define NS_ICONVERTERSTREAM_IID \ interface nsIUnicharLineInputStream : nsISupports
{ 0xfc66ffb6, 0x5404, 0x4908, \ {
{ 0xa4, 0xa3, 0x27, 0xf9, 0x2f, 0xa0, 0x57, 0x9d } } /**
* Read a single line from the stream, where a line is a
class nsIConverterInputStream : public nsIUnicharInputStream { * possibly zero length sequence of characters terminated by a
public: * CR, LF, CRLF, LFCR, or eof.
NS_DEFINE_STATIC_IID_ACCESSOR(NS_ICONVERTERSTREAM_IID) * The line terminator is not returned.
* @retval false
NS_IMETHOD Init(nsIInputStream *aStream, const char *aCharset, * End of file. This line is the last line of the file
PRInt32 aBufferSize, PRBool aRecoverFromErrors) = 0; * (aLine is valid).
* @retval true
* The file contains further lines.
* @note Do not mix readLine with other read functions.
* Doing so can cause various problems and is not supported.
*/
boolean readLine(out AString aLine);
}; };

Просмотреть файл

@ -0,0 +1,79 @@
/* vim:set expandtab ts=4 sw=4 sts=4 cin: */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* The Original Code is mozilla.org unicode stream converter code.
*
* The Initial Developer of the Original Code is
* Christian Biesinger <cbiesinger@web.de>.
* Portions created by the Initial Developer are Copyright (C) 2005
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "nsISupports.idl"
/**
* An interface that allows writing unicode data.
*/
[scriptable, uuid(2d00b1bb-8b21-4a63-bcc6-7213f513ac2e)]
interface nsIUnicharOutputStream : nsISupports
{
/**
* Write a single character to the stream. When writing many characters,
* prefer the string-taking write method.
*
* @retval true The character was written successfully
* @retval false Not all bytes of the character could be written.
*/
boolean write(in unsigned long aCount,
[const, array, size_is(aCount)] in PRUnichar c);
/**
* Write a string to the stream.
*
* @retval true The string was written successfully
* @retval false Not all bytes of the string could be written.
*/
boolean writeString(in AString str);
/**
* Flush the stream. This finishes the conversion and writes any bytes that
* finish the current byte sequence.
*
* It does NOT flush the underlying stream.
*
* @see nsIUnicodeEncoder::Finish
*/
void flush();
/**
* Close the stream and free associated resources. This also closes the
* underlying stream.
*/
void close();
};

Просмотреть файл

@ -35,8 +35,8 @@
* *
* ***** END LICENSE BLOCK ***** */ * ***** END LICENSE BLOCK ***** */
#include "nsIUnicharInputStream.h" #include "nsIUnicharInputStream.h"
#include "nsIInputStream.h"
#include "nsIByteBuffer.h" #include "nsIByteBuffer.h"
#include "nsIUnicharBuffer.h" #include "nsIUnicharBuffer.h"
#include "nsIServiceManager.h" #include "nsIServiceManager.h"
@ -56,14 +56,7 @@ public:
PRBool aTakeOwnership); PRBool aTakeOwnership);
NS_DECL_ISUPPORTS NS_DECL_ISUPPORTS
NS_DECL_NSIUNICHARINPUTSTREAM
NS_IMETHOD Read(PRUnichar* aBuf,
PRUint32 aCount,
PRUint32 *aReadCount);
NS_IMETHOD ReadSegments(nsWriteUnicharSegmentFun aWriter,
void* aClosure,
PRUint32 aCount, PRUint32* aReadCount);
NS_IMETHOD Close();
const nsAString* mString; const nsAString* mString;
PRUint32 mPos; PRUint32 mPos;
@ -104,7 +97,6 @@ StringUnicharInputStream::Read(PRUnichar* aBuf,
nsAString::const_iterator iter; nsAString::const_iterator iter;
mString->BeginReading(iter); mString->BeginReading(iter);
const PRUnichar* us = iter.get(); const PRUnichar* us = iter.get();
NS_ASSERTION(mLen >= mPos, "unsigned madness");
PRUint32 amount = mLen - mPos; PRUint32 amount = mLen - mPos;
if (amount > aCount) { if (amount > aCount) {
amount = aCount; amount = aCount;
@ -148,6 +140,24 @@ StringUnicharInputStream::ReadSegments(nsWriteUnicharSegmentFun aWriter,
return NS_OK; return NS_OK;
} }
NS_IMETHODIMP
StringUnicharInputStream::ReadString(PRUint32 aCount, nsAString& aString,
PRUint32* aReadCount)
{
if (mPos >= mLen) {
*aReadCount = 0;
return NS_OK;
}
PRUint32 amount = mLen - mPos;
if (amount > aCount) {
amount = aCount;
}
aString = Substring(*mString, mPos, amount);
mPos += amount;
*aReadCount = amount;
return NS_OK;
}
nsresult StringUnicharInputStream::Close() nsresult StringUnicharInputStream::Close()
{ {
mPos = mLen; mPos = mLen;
@ -188,14 +198,7 @@ public:
nsresult Init(nsIInputStream* aStream, PRUint32 aBufSize); nsresult Init(nsIInputStream* aStream, PRUint32 aBufSize);
NS_DECL_ISUPPORTS NS_DECL_ISUPPORTS
NS_IMETHOD Read(PRUnichar* aBuf, NS_DECL_NSIUNICHARINPUTSTREAM
PRUint32 aCount,
PRUint32 *aReadCount);
NS_IMETHOD ReadSegments(nsWriteUnicharSegmentFun aWriter,
void* aClosure,
PRUint32 aCount,
PRUint32 *aReadCount);
NS_IMETHOD Close();
private: private:
~UTF8InputStream(); ~UTF8InputStream();
@ -259,23 +262,23 @@ nsresult UTF8InputStream::Read(PRUnichar* aBuf,
PRUint32 *aReadCount) PRUint32 *aReadCount)
{ {
NS_ASSERTION(mUnicharDataLength >= mUnicharDataOffset, "unsigned madness"); NS_ASSERTION(mUnicharDataLength >= mUnicharDataOffset, "unsigned madness");
PRUint32 rv = mUnicharDataLength - mUnicharDataOffset; PRUint32 readCount = mUnicharDataLength - mUnicharDataOffset;
nsresult errorCode; nsresult errorCode;
if (0 == rv) { if (0 == readCount) {
// Fill the unichar buffer // Fill the unichar buffer
rv = Fill(&errorCode); readCount = Fill(&errorCode);
if (rv <= 0) { if (readCount <= 0) {
*aReadCount = 0; *aReadCount = 0;
return errorCode; return errorCode;
} }
} }
if (rv > aCount) { if (readCount > aCount) {
rv = aCount; readCount = aCount;
} }
memcpy(aBuf, mUnicharData->GetBuffer() + mUnicharDataOffset, memcpy(aBuf, mUnicharData->GetBuffer() + mUnicharDataOffset,
rv * sizeof(PRUnichar)); readCount * sizeof(PRUnichar));
mUnicharDataOffset += rv; mUnicharDataOffset += readCount;
*aReadCount = rv; *aReadCount = readCount;
return NS_OK; return NS_OK;
} }
@ -322,6 +325,35 @@ UTF8InputStream::ReadSegments(nsWriteUnicharSegmentFun aWriter,
return NS_OK; return NS_OK;
} }
NS_IMETHODIMP
UTF8InputStream::ReadString(PRUint32 aCount, nsAString& aString,
PRUint32* aReadCount)
{
NS_ASSERTION(mUnicharDataLength >= mUnicharDataOffset, "unsigned madness");
PRUint32 readCount = mUnicharDataLength - mUnicharDataOffset;
nsresult errorCode;
if (0 == readCount) {
// Fill the unichar buffer
readCount = Fill(&errorCode);
if (readCount <= 0) {
*aReadCount = 0;
return errorCode;
}
}
if (readCount > aCount) {
readCount = aCount;
}
const PRUnichar* buf = NS_REINTERPRET_CAST(const PRUnichar*,
mUnicharData->GetBuffer() +
mUnicharDataOffset);
aString.Assign(buf, readCount);
mUnicharDataOffset += readCount;
*aReadCount = readCount;
return NS_OK;
}
PRInt32 UTF8InputStream::Fill(nsresult * aErrorCode) PRInt32 UTF8InputStream::Fill(nsresult * aErrorCode)
{ {
if (nsnull == mInput) { if (nsnull == mInput) {

Просмотреть файл

@ -87,8 +87,8 @@ int main(int argc, char** argv)
nsCOMPtr<nsIConverterInputStream> uin = nsCOMPtr<nsIConverterInputStream> uin =
do_CreateInstance("@mozilla.org/intl/converter-input-stream;1", &rv); do_CreateInstance("@mozilla.org/intl/converter-input-stream;1", &rv);
if (NS_SUCCEEDED(rv)) if (NS_SUCCEEDED(rv))
uin->Init(in, cset->get(), nsnull, PR_TRUE); rv = uin->Init(in, cset->get(), 4096);
if (NS_OK != rv) { if (NS_FAILED(rv)) {
printf("can't create converter input stream: %d\n", rv); printf("can't create converter input stream: %d\n", rv);
return -1; return -1;
} }