# HG changeset patch # User Jonathan Watt # Parent 11e1a66a6f9ce6d00b4b45cd6a8a7830c8144c41 diff --git a/dom/base/File.cpp b/dom/base/File.cpp --- a/dom/base/File.cpp +++ b/dom/base/File.cpp @@ -422,20 +422,21 @@ File::Create(nsISupports* aParent, BlobI MOZ_ASSERT(aImpl->IsFile()); return new File(aParent, aImpl); } /* static */ already_AddRefed File::Create(nsISupports* aParent, const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aLastModifiedDate) + int64_t aLastModifiedDate, bool aIsDirectory) { nsRefPtr file = new File(aParent, - new BlobImplBase(aName, aContentType, aLength, aLastModifiedDate)); + new BlobImplBase(aName, aContentType, aLength, aLastModifiedDate, + aIsDirectory)); return file.forget(); } /* static */ already_AddRefed File::Create(nsISupports* aParent, const nsAString& aName, const nsAString& aContentType, uint64_t aLength) { nsRefPtr file = new File(aParent, diff --git a/dom/base/File.h b/dom/base/File.h --- a/dom/base/File.h +++ b/dom/base/File.h @@ -188,17 +188,17 @@ public: // Note: BlobImpl must be a File in order to use this method. // Check impl->IsFile(). static File* Create(nsISupports* aParent, BlobImpl* aImpl); static already_AddRefed Create(nsISupports* aParent, const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aLastModifiedDate); + int64_t aLastModifiedDate, bool aIsDirectory); static already_AddRefed Create(nsISupports* aParent, const nsAString& aName, const nsAString& aContentType, uint64_t aLength); // The returned File takes ownership of aMemoryBuffer. aMemoryBuffer will be // freed by free so it must be allocated by malloc or something // compatible with it. @@ -346,26 +346,26 @@ public: virtual nsresult GetMutable(bool* aMutable) const = 0; virtual nsresult SetMutable(bool aMutable) = 0; virtual void SetLazyData(const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aLastModifiedDate) = 0; + int64_t aLastModifiedDate, + bool aIsDirectory) = 0; virtual bool IsMemoryFile() const = 0; virtual bool IsSizeUnknown() const = 0; virtual bool IsDateUnknown() const = 0; virtual bool IsFile() const = 0; - virtual void SetIsDirectory() = 0; virtual bool IsDirectory() const = 0; // True if this implementation can be sent to other threads. virtual bool MayBeClonedToOtherThreads() const { return true; } @@ -374,19 +374,19 @@ protected: }; NS_DEFINE_STATIC_IID_ACCESSOR(BlobImpl, FILEIMPL_IID) class BlobImplBase : public BlobImpl { public: BlobImplBase(const nsAString& aName, const nsAString& aContentType, - uint64_t aLength, int64_t aLastModifiedDate) + uint64_t aLength, int64_t aLastModifiedDate, bool aIsDirectory) : mIsFile(true) - , mIsDirectory(false) + , mIsDirectory(aIsDirectory) , mImmutable(false) , mContentType(aContentType) , mName(aName) , mStart(0) , mLength(aLength) , mLastModificationDate(aLastModifiedDate) , mSerialNumber(NextSerialNumber()) { @@ -495,17 +495,18 @@ public: nsACString& aCharset) override; virtual nsresult GetMutable(bool* aMutable) const override; virtual nsresult SetMutable(bool aMutable) override; virtual void SetLazyData(const nsAString& aName, const nsAString& aContentType, - uint64_t aLength, int64_t aLastModifiedDate) override + uint64_t aLength, int64_t aLastModifiedDate, + bool aIsDirectory) override { NS_ASSERTION(aLength, "must have length"); mName = aName; mContentType = aContentType; mLength = aLength; mLastModificationDate = aLastModifiedDate; mIsFile = !aName.IsVoid(); @@ -521,24 +522,16 @@ public: return mIsFile && mLastModificationDate == INT64_MAX; } virtual bool IsFile() const override { return mIsFile; } - virtual void SetIsDirectory() override - { - MOZ_ASSERT(mIsFile, - "This should only be called when this object has been created " - "from an nsIFile to note that the nsIFile is a directory"); - mIsDirectory = true; - } - /** * Returns true if the nsIFile that this object wraps is a directory. */ virtual bool IsDirectory() const override { return mIsDirectory; } @@ -606,17 +599,17 @@ protected: */ class BlobImplMemory final : public BlobImplBase { public: NS_DECL_ISUPPORTS_INHERITED BlobImplMemory(void* aMemoryBuffer, uint64_t aLength, const nsAString& aName, const nsAString& aContentType, int64_t aLastModifiedDate) - : BlobImplBase(aName, aContentType, aLength, aLastModifiedDate) + : BlobImplBase(aName, aContentType, aLength, aLastModifiedDate, false) , mDataOwner(new DataOwner(aMemoryBuffer, aLength)) { NS_ASSERTION(mDataOwner && mDataOwner->mData, "must have data"); } BlobImplMemory(void* aMemoryBuffer, uint64_t aLength, const nsAString& aContentType) : BlobImplBase(aContentType, aLength) @@ -736,114 +729,121 @@ private: class BlobImplFile : public BlobImplBase { public: NS_DECL_ISUPPORTS_INHERITED // Create as a file explicit BlobImplFile(nsIFile* aFile, bool aTemporary = false) - : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX) + : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX, false) , mFile(aFile) , mWholeFile(true) , mStoredFile(false) , mIsTemporary(aTemporary) { NS_ASSERTION(mFile, "must have file"); // Lazily get the content type and size mContentType.SetIsVoid(true); mFile->GetLeafName(mName); + mFile->IsDirectory(&mIsDirectory); } BlobImplFile(nsIFile* aFile, indexedDB::FileInfo* aFileInfo) - : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX) + : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX, false) , mFile(aFile) , mWholeFile(true) , mStoredFile(true) , mIsTemporary(false) { NS_ASSERTION(mFile, "must have file"); NS_ASSERTION(aFileInfo, "must have file info"); // Lazily get the content type and size mContentType.SetIsVoid(true); mFile->GetLeafName(mName); + mFile->IsDirectory(&mIsDirectory); mFileInfos.AppendElement(aFileInfo); } // Create as a file BlobImplFile(const nsAString& aName, const nsAString& aContentType, uint64_t aLength, nsIFile* aFile) - : BlobImplBase(aName, aContentType, aLength, UINT64_MAX) + : BlobImplBase(aName, aContentType, aLength, UINT64_MAX, false) , mFile(aFile) , mWholeFile(true) , mStoredFile(false) , mIsTemporary(false) { NS_ASSERTION(mFile, "must have file"); + mFile->IsDirectory(&mIsDirectory); } BlobImplFile(const nsAString& aName, const nsAString& aContentType, uint64_t aLength, nsIFile* aFile, int64_t aLastModificationDate) - : BlobImplBase(aName, aContentType, aLength, aLastModificationDate) + : BlobImplBase(aName, aContentType, aLength, aLastModificationDate, false) , mFile(aFile) , mWholeFile(true) , mStoredFile(false) , mIsTemporary(false) { NS_ASSERTION(mFile, "must have file"); + mFile->IsDirectory(&mIsDirectory); } // Create as a file with custom name BlobImplFile(nsIFile* aFile, const nsAString& aName, const nsAString& aContentType) - : BlobImplBase(aName, aContentType, UINT64_MAX, INT64_MAX) + : BlobImplBase(aName, aContentType, UINT64_MAX, INT64_MAX, false) , mFile(aFile) , mWholeFile(true) , mStoredFile(false) , mIsTemporary(false) { NS_ASSERTION(mFile, "must have file"); + mFile->IsDirectory(&mIsDirectory); if (aContentType.IsEmpty()) { // Lazily get the content type and size mContentType.SetIsVoid(true); } } // Create as a stored file BlobImplFile(const nsAString& aName, const nsAString& aContentType, uint64_t aLength, nsIFile* aFile, indexedDB::FileInfo* aFileInfo) - : BlobImplBase(aName, aContentType, aLength, UINT64_MAX) + : BlobImplBase(aName, aContentType, aLength, UINT64_MAX, false) , mFile(aFile) , mWholeFile(true) , mStoredFile(true) , mIsTemporary(false) { NS_ASSERTION(mFile, "must have file"); + mFile->IsDirectory(&mIsDirectory); mFileInfos.AppendElement(aFileInfo); } // Create as a stored blob BlobImplFile(const nsAString& aContentType, uint64_t aLength, nsIFile* aFile, indexedDB::FileInfo* aFileInfo) : BlobImplBase(aContentType, aLength) , mFile(aFile) , mWholeFile(true) , mStoredFile(true) , mIsTemporary(false) { NS_ASSERTION(mFile, "must have file"); + mFile->IsDirectory(&mIsDirectory); mFileInfos.AppendElement(aFileInfo); } // Create as a file to be later initialized BlobImplFile() - : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX) + : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX, false) , mWholeFile(true) , mStoredFile(false) , mIsTemporary(false) { // Lazily get the content type and size mContentType.SetIsVoid(true); mName.SetIsVoid(true); } diff --git a/dom/indexedDB/FileSnapshot.cpp b/dom/indexedDB/FileSnapshot.cpp --- a/dom/indexedDB/FileSnapshot.cpp +++ b/dom/indexedDB/FileSnapshot.cpp @@ -24,17 +24,18 @@ BlobImplSnapshot::BlobImplSnapshot(const const nsAString& aContentType, MetadataParameters* aMetadataParams, nsIFile* aFile, IDBFileHandle* aFileHandle, FileInfo* aFileInfo) : BlobImplBase(aName, aContentType, aMetadataParams->Size(), - aMetadataParams->LastModified()) + aMetadataParams->LastModified(), + false) , mFile(aFile) , mWholeFile(true) { AssertSanity(); MOZ_ASSERT(aMetadataParams); MOZ_ASSERT(aMetadataParams->Size() != UINT64_MAX); MOZ_ASSERT(aMetadataParams->LastModified() != INT64_MAX); MOZ_ASSERT(aFile); diff --git a/dom/indexedDB/IDBObjectStore.cpp b/dom/indexedDB/IDBObjectStore.cpp --- a/dom/indexedDB/IDBObjectStore.cpp +++ b/dom/indexedDB/IDBObjectStore.cpp @@ -434,17 +434,18 @@ ResolveMysteryFile(BlobImpl* aImpl, const nsString& aName, const nsString& aContentType, uint64_t aSize, uint64_t aLastModifiedDate) { BlobChild* actor = ActorFromRemoteBlobImpl(aImpl); if (actor) { return actor->SetMysteryBlobInfo(aName, aContentType, - aSize, aLastModifiedDate); + aSize, aLastModifiedDate, + false); } return true; } bool ResolveMysteryBlob(BlobImpl* aImpl, const nsString& aContentType, uint64_t aSize) diff --git a/dom/ipc/Blob.cpp b/dom/ipc/Blob.cpp --- a/dom/ipc/Blob.cpp +++ b/dom/ipc/Blob.cpp @@ -665,17 +665,17 @@ public: : BlobImplBase(aContentType, 0) { mImmutable = true; } EmptyBlobImpl(const nsAString& aName, const nsAString& aContentType, int64_t aLastModifiedDate) - : BlobImplBase(aName, aContentType, 0, aLastModifiedDate) + : BlobImplBase(aName, aContentType, 0, aLastModifiedDate, false) { mImmutable = true; } private: virtual already_AddRefed CreateSlice(uint64_t /* aStart */, uint64_t aLength, @@ -728,17 +728,17 @@ public: mImmutable = true; } SameProcessInputStreamBlobImpl(const nsAString& aName, const nsAString& aContentType, uint64_t aLength, int64_t aLastModifiedDate, nsIInputStream* aInputStream) - : BlobImplBase(aName, aContentType, aLength, aLastModifiedDate) + : BlobImplBase(aName, aContentType, aLength, aLastModifiedDate, false) , mInputStream(aInputStream) { MOZ_ASSERT(aLength != UINT64_MAX); MOZ_ASSERT(aLastModifiedDate != INT64_MAX); MOZ_ASSERT(aInputStream); mImmutable = true; } @@ -767,22 +767,24 @@ private: }; struct MOZ_STACK_CLASS CreateBlobImplMetadata final { nsString mContentType; nsString mName; uint64_t mLength; int64_t mLastModifiedDate; + bool mIsDirectory; bool mHasRecursed; const bool mIsSameProcessActor; explicit CreateBlobImplMetadata(bool aIsSameProcessActor) : mLength(0) , mLastModifiedDate(0) + , mIsDirectory(false) , mHasRecursed(false) , mIsSameProcessActor(aIsSameProcessActor) { MOZ_COUNT_CTOR(CreateBlobImplMetadata); mName.SetIsVoid(true); } @@ -1049,16 +1051,17 @@ CreateBlobImpl(const ParentBlobConstruct ASSERT_UNLESS_FUZZING(); return nullptr; } metadata.mContentType = params.contentType(); metadata.mName = params.name(); metadata.mLength = params.length(); metadata.mLastModifiedDate = params.modDate(); + metadata.mIsDirectory = params.isDirectory(); } nsRefPtr blobImpl = CreateBlobImplFromBlobData(aBlobData, metadata); return blobImpl.forget(); } void @@ -1850,30 +1853,32 @@ protected: const bool mIsSlice; public: // For File. RemoteBlobImpl(BlobChild* aActor, const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aModDate); + int64_t aModDate, + bool aIsDirectory); // For Blob. RemoteBlobImpl(BlobChild* aActor, const nsAString& aContentType, uint64_t aLength); // For same-process blobs. RemoteBlobImpl(BlobChild* aActor, BlobImpl* aSameProcessBlobImpl, const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aModDate); + int64_t aModDate, + bool aIsDirectory); // For same-process blobs. RemoteBlobImpl(BlobChild* aActor, BlobImpl* aSameProcessBlobImpl, const nsAString& aContentType, uint64_t aLength); // For mystery blobs. @@ -2124,33 +2129,31 @@ public: virtual nsresult SetMutable(bool aMutable) override; virtual void SetLazyData(const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aLastModifiedDate) override; + int64_t aLastModifiedDate, + bool aIsDirectory) override; virtual bool IsMemoryFile() const override; virtual bool IsSizeUnknown() const override; virtual bool IsDateUnknown() const override; virtual bool IsFile() const override; - virtual void - SetIsDirectory() override; - virtual bool IsDirectory() const override; virtual bool MayBeClonedToOtherThreads() const override; virtual BlobChild* GetBlobChild() override; @@ -2173,18 +2176,19 @@ private: * BlobChild::RemoteBlobImpl ******************************************************************************/ BlobChild:: RemoteBlobImpl::RemoteBlobImpl(BlobChild* aActor, const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aModDate) - : BlobImplBase(aName, aContentType, aLength, aModDate) + int64_t aModDate, + bool aIsDirectory) + : BlobImplBase(aName, aContentType, aLength, aModDate, aIsDirectory) , mIsSlice(false) { CommonInit(aActor); } BlobChild:: RemoteBlobImpl::RemoteBlobImpl(BlobChild* aActor, const nsAString& aContentType, @@ -2196,18 +2200,19 @@ RemoteBlobImpl::RemoteBlobImpl(BlobChild } BlobChild:: RemoteBlobImpl::RemoteBlobImpl(BlobChild* aActor, BlobImpl* aSameProcessBlobImpl, const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aModDate) - : BlobImplBase(aName, aContentType, aLength, aModDate) + int64_t aModDate, + bool aIsDirectory) + : BlobImplBase(aName, aContentType, aLength, aModDate, aIsDirectory) , mSameProcessBlobImpl(aSameProcessBlobImpl) , mIsSlice(false) { MOZ_ASSERT(aSameProcessBlobImpl); MOZ_ASSERT(gProcessType == GeckoProcessType_Default); CommonInit(aActor); } @@ -2224,17 +2229,17 @@ RemoteBlobImpl::RemoteBlobImpl(BlobChild MOZ_ASSERT(aSameProcessBlobImpl); MOZ_ASSERT(gProcessType == GeckoProcessType_Default); CommonInit(aActor); } BlobChild:: RemoteBlobImpl::RemoteBlobImpl(BlobChild* aActor) - : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX) + : BlobImplBase(EmptyString(), EmptyString(), UINT64_MAX, INT64_MAX, false) , mIsSlice(false) { CommonInit(aActor); } BlobChild:: RemoteBlobImpl::RemoteBlobImpl(const nsAString& aContentType, uint64_t aLength) : BlobImplBase(aContentType, aLength) @@ -2885,17 +2890,18 @@ RemoteBlobImpl::SetMutable(bool aMutable return mBlobImpl->SetMutable(aMutable); } void BlobParent:: RemoteBlobImpl::SetLazyData(const nsAString& aName, const nsAString& aContentType, uint64_t aLength, - int64_t aLastModifiedDate) + int64_t aLastModifiedDate, + bool aIsDirectory) { MOZ_CRASH("This should never be called!"); } bool BlobParent:: RemoteBlobImpl::IsMemoryFile() const { @@ -2918,23 +2924,16 @@ RemoteBlobImpl::IsDateUnknown() const bool BlobParent:: RemoteBlobImpl::IsFile() const { return mBlobImpl->IsFile(); } -void -BlobParent:: -RemoteBlobImpl::SetIsDirectory() -{ - return mBlobImpl->SetIsDirectory(); -} - bool BlobParent:: RemoteBlobImpl::IsDirectory() const { return mBlobImpl->IsDirectory(); } bool @@ -3122,17 +3121,18 @@ BlobChild::CommonInit(BlobChild* aOther, nsRefPtr remoteBlob; if (otherImpl->IsFile()) { nsString name; otherImpl->GetName(name); int64_t modDate = otherImpl->GetLastModified(rv); MOZ_ASSERT(!rv.Failed()); - remoteBlob = new RemoteBlobImpl(this, name, contentType, length, modDate); + remoteBlob = new RemoteBlobImpl(this, name, contentType, length, modDate, + otherImpl->IsDirectory()); } else { remoteBlob = new RemoteBlobImpl(this, contentType, length); } CommonInit(aOther->ParentID(), remoteBlob); } void @@ -3164,17 +3164,18 @@ BlobChild::CommonInit(const ChildBlobCon case AnyBlobConstructorParams::TFileBlobConstructorParams: { const FileBlobConstructorParams& params = blobParams.get_FileBlobConstructorParams(); remoteBlob = new RemoteBlobImpl(this, params.name(), params.contentType(), params.length(), - params.modDate()); + params.modDate(), + params.isDirectory()); break; } case AnyBlobConstructorParams::TSameProcessBlobConstructorParams: { MOZ_ASSERT(gProcessType == GeckoProcessType_Default); const SameProcessBlobConstructorParams& params = blobParams.get_SameProcessBlobConstructorParams(); @@ -3198,17 +3199,18 @@ BlobChild::CommonInit(const ChildBlobCon MOZ_ASSERT(!rv.Failed()); remoteBlob = new RemoteBlobImpl(this, blobImpl, name, contentType, size, - lastModifiedDate); + lastModifiedDate, + blobImpl->IsDirectory()); } else { remoteBlob = new RemoteBlobImpl(this, blobImpl, contentType, size); } break; } case AnyBlobConstructorParams::TMysteryBlobConstructorParams: { @@ -3383,17 +3385,18 @@ BlobChild::GetOrCreateFromImpl(ChildMana if (aBlobImpl->IsFile()) { nsString name; aBlobImpl->GetName(name); int64_t modDate = aBlobImpl->GetLastModified(rv); MOZ_ASSERT(!rv.Failed()); blobParams = - FileBlobConstructorParams(name, contentType, length, modDate, blobData); + FileBlobConstructorParams(name, contentType, length, modDate, + aBlobImpl->IsDirectory(), blobData); } else { blobParams = NormalBlobConstructorParams(contentType, length, blobData); } } BlobChild* actor = new BlobChild(aManager, aBlobImpl); ParentBlobConstructorParams params(blobParams); @@ -3556,44 +3559,47 @@ BlobChild::GetBlobImpl() return blobImpl.forget(); } bool BlobChild::SetMysteryBlobInfo(const nsString& aName, const nsString& aContentType, uint64_t aLength, - int64_t aLastModifiedDate) + int64_t aLastModifiedDate, + bool aIsDirectory) { AssertIsOnOwningThread(); MOZ_ASSERT(mBlobImpl); MOZ_ASSERT(mRemoteBlobImpl); MOZ_ASSERT(aLastModifiedDate != INT64_MAX); - mBlobImpl->SetLazyData(aName, aContentType, aLength, aLastModifiedDate); + mBlobImpl->SetLazyData(aName, aContentType, aLength, aLastModifiedDate, + aIsDirectory); FileBlobConstructorParams params(aName, aContentType, aLength, aLastModifiedDate, + aIsDirectory, void_t() /* optionalBlobData */); return SendResolveMystery(params); } bool BlobChild::SetMysteryBlobInfo(const nsString& aContentType, uint64_t aLength) { AssertIsOnOwningThread(); MOZ_ASSERT(mBlobImpl); MOZ_ASSERT(mRemoteBlobImpl); nsString voidString; voidString.SetIsVoid(true); - mBlobImpl->SetLazyData(voidString, aContentType, aLength, INT64_MAX); + mBlobImpl->SetLazyData(voidString, aContentType, aLength, INT64_MAX, false); NormalBlobConstructorParams params(aContentType, aLength, void_t() /* optionalBlobData */); return SendResolveMystery(params); } void @@ -3925,17 +3931,18 @@ BlobParent::GetOrCreateFromImpl(ParentMa if (aBlobImpl->IsFile()) { nsString name; aBlobImpl->GetName(name); int64_t modDate = aBlobImpl->GetLastModified(rv); MOZ_ASSERT(!rv.Failed()); blobParams = - FileBlobConstructorParams(name, contentType, length, modDate, void_t()); + FileBlobConstructorParams(name, contentType, length, modDate, + aBlobImpl->IsDirectory(), void_t()); } else { blobParams = NormalBlobConstructorParams(contentType, length, void_t()); } } } nsID id; MOZ_ALWAYS_TRUE(NS_SUCCEEDED(gUUIDGenerator->GenerateUUIDInPlace(&id))); @@ -4403,17 +4410,18 @@ BlobParent::RecvResolveMystery(const Res } nsString voidString; voidString.SetIsVoid(true); mBlobImpl->SetLazyData(voidString, params.contentType(), params.length(), - INT64_MAX); + INT64_MAX, + false); return true; } case ResolveMysteryParams::TFileBlobConstructorParams: { const FileBlobConstructorParams& params = aParams.get_FileBlobConstructorParams(); if (NS_WARN_IF(params.name().IsVoid())) { ASSERT_UNLESS_FUZZING(); @@ -4428,17 +4436,18 @@ BlobParent::RecvResolveMystery(const Res if (NS_WARN_IF(params.modDate() == INT64_MAX)) { ASSERT_UNLESS_FUZZING(); return false; } mBlobImpl->SetLazyData(params.name(), params.contentType(), params.length(), - params.modDate()); + params.modDate(), + params.isDirectory()); return true; } default: MOZ_CRASH("Unknown params!"); } MOZ_CRASH("Should never get here!"); diff --git a/dom/ipc/BlobChild.h b/dom/ipc/BlobChild.h --- a/dom/ipc/BlobChild.h +++ b/dom/ipc/BlobChild.h @@ -109,17 +109,18 @@ public: already_AddRefed GetBlobImpl(); // Use this for files. bool SetMysteryBlobInfo(const nsString& aName, const nsString& aContentType, uint64_t aLength, - int64_t aLastModifiedDate); + int64_t aLastModifiedDate, + bool aIsDirectory); // Use this for non-file blobs. bool SetMysteryBlobInfo(const nsString& aContentType, uint64_t aLength); void AssertIsOnOwningThread() const #ifdef DEBUG diff --git a/dom/ipc/DOMTypes.ipdlh b/dom/ipc/DOMTypes.ipdlh --- a/dom/ipc/DOMTypes.ipdlh +++ b/dom/ipc/DOMTypes.ipdlh @@ -62,16 +62,17 @@ struct NormalBlobConstructorParams }; struct FileBlobConstructorParams { nsString name; nsString contentType; uint64_t length; int64_t modDate; + bool isDirectory; // This must be of type BlobData in a child->parent message, and will always // be of type void_t in a parent->child message. OptionalBlobData optionalBlobData; }; struct SlicedBlobConstructorParams {