зеркало из https://github.com/mozilla/gecko-dev.git
Backed out changeset 22c00a19e267 (bug 1534712) for causing test_bug536567_perwindowpb.html, browser_jsonview_save_json.js, browser_bookmark_backup_export_import.js to perma fail CLOSED TREE
This commit is contained in:
Родитель
add7a3fb9e
Коммит
d13f7bbf24
|
@ -22,9 +22,8 @@ FileBlobImpl::FileBlobImpl(nsIFile* aFile)
|
|||
: BaseBlobImpl(NS_LITERAL_STRING("FileBlobImpl"), EmptyString(),
|
||||
EmptyString(), UINT64_MAX, INT64_MAX),
|
||||
mFile(aFile),
|
||||
mFileId(-1),
|
||||
mWholeFile(true),
|
||||
mHasEmptyMozFullPath(false) {
|
||||
mFileId(-1) {
|
||||
MOZ_ASSERT(mFile, "must have file");
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
// Lazily get the content type and size
|
||||
|
@ -38,9 +37,8 @@ FileBlobImpl::FileBlobImpl(const nsAString& aName,
|
|||
: BaseBlobImpl(NS_LITERAL_STRING("FileBlobImpl"), aName, aContentType,
|
||||
aLength, UINT64_MAX),
|
||||
mFile(aFile),
|
||||
mFileId(-1),
|
||||
mWholeFile(true),
|
||||
mHasEmptyMozFullPath(false) {
|
||||
mFileId(-1) {
|
||||
MOZ_ASSERT(mFile, "must have file");
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
}
|
||||
|
@ -51,9 +49,8 @@ FileBlobImpl::FileBlobImpl(const nsAString& aName,
|
|||
: BaseBlobImpl(NS_LITERAL_STRING("FileBlobImpl"), aName, aContentType,
|
||||
aLength, aLastModificationDate),
|
||||
mFile(aFile),
|
||||
mFileId(-1),
|
||||
mWholeFile(true),
|
||||
mHasEmptyMozFullPath(false) {
|
||||
mFileId(-1) {
|
||||
MOZ_ASSERT(mFile, "must have file");
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
}
|
||||
|
@ -63,9 +60,8 @@ FileBlobImpl::FileBlobImpl(nsIFile* aFile, const nsAString& aName,
|
|||
const nsAString& aBlobImplType)
|
||||
: BaseBlobImpl(aBlobImplType, aName, aContentType, UINT64_MAX, INT64_MAX),
|
||||
mFile(aFile),
|
||||
mFileId(-1),
|
||||
mWholeFile(true),
|
||||
mHasEmptyMozFullPath(false) {
|
||||
mFileId(-1) {
|
||||
MOZ_ASSERT(mFile, "must have file");
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
if (aContentType.IsEmpty()) {
|
||||
|
@ -79,9 +75,8 @@ FileBlobImpl::FileBlobImpl(const FileBlobImpl* aOther, uint64_t aStart,
|
|||
: BaseBlobImpl(NS_LITERAL_STRING("FileBlobImpl"), aContentType,
|
||||
aOther->mStart + aStart, aLength),
|
||||
mFile(aOther->mFile),
|
||||
mFileId(-1),
|
||||
mWholeFile(false),
|
||||
mHasEmptyMozFullPath(false) {
|
||||
mFileId(-1) {
|
||||
MOZ_ASSERT(mFile, "must have file");
|
||||
MOZ_ASSERT(XRE_IsParentProcess());
|
||||
mImmutable = aOther->mImmutable;
|
||||
|
@ -97,12 +92,6 @@ already_AddRefed<BlobImpl> FileBlobImpl::CreateSlice(
|
|||
void FileBlobImpl::GetMozFullPathInternal(nsAString& aFilename,
|
||||
ErrorResult& aRv) const {
|
||||
MOZ_ASSERT(mIsFile, "Should only be called on files");
|
||||
|
||||
if (mHasEmptyMozFullPath) {
|
||||
aFilename.Truncate();
|
||||
return;
|
||||
}
|
||||
|
||||
aRv = mFile->GetPath(aFilename);
|
||||
}
|
||||
|
||||
|
@ -216,6 +205,10 @@ int64_t FileBlobImpl::GetLastModified(ErrorResult& aRv) {
|
|||
return mLastModificationDate;
|
||||
}
|
||||
|
||||
void FileBlobImpl::SetLastModified(int64_t aLastModified) {
|
||||
MOZ_CRASH("SetLastModified of a real file is not allowed!");
|
||||
}
|
||||
|
||||
const uint32_t sFileStreamFlags =
|
||||
nsIFileInputStream::CLOSE_ON_EOF | nsIFileInputStream::REOPEN_ON_REWIND |
|
||||
nsIFileInputStream::DEFER_OPEN | nsIFileInputStream::SHARE_DELETE;
|
||||
|
|
|
@ -37,6 +37,7 @@ class FileBlobImpl : public BaseBlobImpl {
|
|||
virtual uint64_t GetSize(ErrorResult& aRv) override;
|
||||
virtual void GetType(nsAString& aType) override;
|
||||
virtual int64_t GetLastModified(ErrorResult& aRv) override;
|
||||
virtual void SetLastModified(int64_t aLastModified) override;
|
||||
virtual void GetMozFullPathInternal(nsAString& aFullPath,
|
||||
ErrorResult& aRv) const override;
|
||||
virtual void CreateInputStream(nsIInputStream** aInputStream,
|
||||
|
@ -56,8 +57,6 @@ class FileBlobImpl : public BaseBlobImpl {
|
|||
|
||||
void SetFileId(int64_t aFileId) { mFileId = aFileId; }
|
||||
|
||||
void SetEmptyMozFullPath() { mHasEmptyMozFullPath = true; }
|
||||
|
||||
protected:
|
||||
virtual ~FileBlobImpl() = default;
|
||||
|
||||
|
@ -71,13 +70,8 @@ class FileBlobImpl : public BaseBlobImpl {
|
|||
ErrorResult& aRv) override;
|
||||
|
||||
nsCOMPtr<nsIFile> mFile;
|
||||
int64_t mFileId;
|
||||
bool mWholeFile;
|
||||
|
||||
// When this is set to true, mozFullPath is returned as an empty string. This
|
||||
// is useful in case the file doesn't exist (yet). See:
|
||||
// FileCreatorHelper::CreateFile and aExistenceCheck.
|
||||
bool mHasEmptyMozFullPath;
|
||||
int64_t mFileId;
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
|
|
|
@ -7,16 +7,13 @@
|
|||
#include "FileCreatorHelper.h"
|
||||
|
||||
#include "mozilla/dom/BindingDeclarations.h"
|
||||
#include "mozilla/dom/ContentChild.h"
|
||||
#include "mozilla/dom/ContentParent.h"
|
||||
#include "mozilla/dom/FileBinding.h"
|
||||
#include "mozilla/dom/ipc/FileCreatorChild.h"
|
||||
#include "mozilla/ipc/BackgroundChild.h"
|
||||
#include "mozilla/ipc/PBackgroundChild.h"
|
||||
#include "mozilla/dom/File.h"
|
||||
#include "mozilla/dom/Promise.h"
|
||||
#include "mozilla/StaticPrefs.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsPIDOMWindow.h"
|
||||
#include "nsProxyRelease.h"
|
||||
#include "nsIFile.h"
|
||||
|
||||
// Undefine the macro of CreateFile to avoid FileCreatorHelper#CreateFile being
|
||||
|
@ -39,32 +36,167 @@ already_AddRefed<Promise> FileCreatorHelper::CreateFile(
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
nsAutoString path;
|
||||
aRv = aFile->GetPath(path);
|
||||
nsCOMPtr<nsPIDOMWindowInner> window = do_QueryInterface(aGlobalObject);
|
||||
|
||||
// Parent process
|
||||
|
||||
if (XRE_IsParentProcess()) {
|
||||
RefPtr<File> file =
|
||||
CreateFileInternal(window, aFile, aBag, aIsFromNsIFile, aRv);
|
||||
if (aRv.Failed()) {
|
||||
return nullptr;
|
||||
}
|
||||
promise->MaybeResolve(file);
|
||||
return promise.forget();
|
||||
}
|
||||
|
||||
// Content process.
|
||||
|
||||
ContentChild* cc = ContentChild::GetSingleton();
|
||||
if (!cc) {
|
||||
promise->MaybeReject(NS_ERROR_DOM_INVALID_STATE_ERR);
|
||||
return promise.forget();
|
||||
}
|
||||
|
||||
if (!cc->GetRemoteType().EqualsLiteral(FILE_REMOTE_TYPE) &&
|
||||
!Preferences::GetBool("dom.file.createInChild", false)) {
|
||||
// If this pref is not set and the request is received by the parent
|
||||
// process, this child is killed for security reason.
|
||||
promise->MaybeReject(NS_ERROR_DOM_INVALID_STATE_ERR);
|
||||
return promise.forget();
|
||||
}
|
||||
|
||||
RefPtr<FileCreatorHelper> helper = new FileCreatorHelper(promise, window);
|
||||
|
||||
// The request is sent to the parent process and it's kept alive by
|
||||
// ContentChild.
|
||||
helper->SendRequest(aFile, aBag, aIsFromNsIFile, aRv);
|
||||
if (NS_WARN_IF(aRv.Failed())) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// Register this component to PBackground.
|
||||
mozilla::ipc::PBackgroundChild* actorChild =
|
||||
mozilla::ipc::BackgroundChild::GetOrCreateForCurrentThread();
|
||||
if (NS_WARN_IF(!actorChild)) {
|
||||
aRv.Throw(NS_ERROR_FAILURE);
|
||||
return promise.forget();
|
||||
}
|
||||
|
||||
/* static */
|
||||
already_AddRefed<File> FileCreatorHelper::CreateFileInternal(
|
||||
nsPIDOMWindowInner* aWindow, nsIFile* aFile,
|
||||
const ChromeFilePropertyBag& aBag, bool aIsFromNsIFile, ErrorResult& aRv) {
|
||||
bool lastModifiedPassed = false;
|
||||
int64_t lastModified = 0;
|
||||
if (aBag.mLastModified.WasPassed()) {
|
||||
lastModifiedPassed = true;
|
||||
lastModified = aBag.mLastModified.Value();
|
||||
}
|
||||
|
||||
RefPtr<BlobImpl> blobImpl;
|
||||
aRv = CreateBlobImpl(aFile, aBag.mType, aBag.mName, lastModifiedPassed,
|
||||
lastModified, aBag.mExistenceCheck, aIsFromNsIFile,
|
||||
getter_AddRefs(blobImpl));
|
||||
if (aRv.Failed()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Maybe<int64_t> lastModified;
|
||||
if (aBag.mLastModified.WasPassed()) {
|
||||
lastModified.emplace(aBag.mLastModified.Value());
|
||||
RefPtr<File> file = File::Create(aWindow, blobImpl);
|
||||
return file.forget();
|
||||
}
|
||||
|
||||
FileCreatorHelper::FileCreatorHelper(Promise* aPromise,
|
||||
nsPIDOMWindowInner* aWindow)
|
||||
: mPromise(aPromise), mWindow(aWindow) {
|
||||
MOZ_ASSERT(aPromise);
|
||||
}
|
||||
|
||||
FileCreatorHelper::~FileCreatorHelper() {}
|
||||
|
||||
void FileCreatorHelper::SendRequest(nsIFile* aFile,
|
||||
const ChromeFilePropertyBag& aBag,
|
||||
bool aIsFromNsIFile, ErrorResult& aRv) {
|
||||
MOZ_ASSERT(aFile);
|
||||
|
||||
ContentChild* cc = ContentChild::GetSingleton();
|
||||
if (NS_WARN_IF(!cc)) {
|
||||
aRv.Throw(NS_ERROR_FAILURE);
|
||||
return;
|
||||
}
|
||||
|
||||
mozilla::ipc::PFileCreatorChild* actor =
|
||||
actorChild->SendPFileCreatorConstructor(
|
||||
path, aBag.mType, aBag.mName, lastModified, aBag.mExistenceCheck,
|
||||
aIsFromNsIFile);
|
||||
nsID uuid;
|
||||
aRv = nsContentUtils::GenerateUUIDInPlace(uuid);
|
||||
if (NS_WARN_IF(aRv.Failed())) {
|
||||
return;
|
||||
}
|
||||
|
||||
static_cast<FileCreatorChild*>(actor)->SetPromise(promise);
|
||||
return promise.forget();
|
||||
nsAutoString path;
|
||||
aRv = aFile->GetPath(path);
|
||||
if (NS_WARN_IF(aRv.Failed())) {
|
||||
return;
|
||||
}
|
||||
|
||||
cc->FileCreationRequest(uuid, this, path, aBag.mType, aBag.mName,
|
||||
aBag.mLastModified, aBag.mExistenceCheck,
|
||||
aIsFromNsIFile);
|
||||
}
|
||||
|
||||
void FileCreatorHelper::ResponseReceived(BlobImpl* aBlobImpl, nsresult aRv) {
|
||||
if (NS_FAILED(aRv)) {
|
||||
mPromise->MaybeReject(aRv);
|
||||
return;
|
||||
}
|
||||
|
||||
RefPtr<File> file = File::Create(mWindow, aBlobImpl);
|
||||
mPromise->MaybeResolve(file);
|
||||
}
|
||||
|
||||
/* static */
|
||||
nsresult FileCreatorHelper::CreateBlobImplForIPC(
|
||||
const nsAString& aPath, const nsAString& aType, const nsAString& aName,
|
||||
bool aLastModifiedPassed, int64_t aLastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile, BlobImpl** aBlobImpl) {
|
||||
nsCOMPtr<nsIFile> file;
|
||||
nsresult rv = NS_NewLocalFile(aPath, true, getter_AddRefs(file));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
return CreateBlobImpl(file, aType, aName, aLastModifiedPassed, aLastModified,
|
||||
aExistenceCheck, aIsFromNsIFile, aBlobImpl);
|
||||
}
|
||||
|
||||
/* static */
|
||||
nsresult FileCreatorHelper::CreateBlobImpl(
|
||||
nsIFile* aFile, const nsAString& aType, const nsAString& aName,
|
||||
bool aLastModifiedPassed, int64_t aLastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile, BlobImpl** aBlobImpl) {
|
||||
if (!aExistenceCheck) {
|
||||
RefPtr<FileBlobImpl> impl = new FileBlobImpl(aFile);
|
||||
|
||||
if (!aName.IsEmpty()) {
|
||||
impl->SetName(aName);
|
||||
}
|
||||
|
||||
if (!aType.IsEmpty()) {
|
||||
impl->SetType(aType);
|
||||
}
|
||||
|
||||
if (aLastModifiedPassed) {
|
||||
impl->SetLastModified(aLastModified);
|
||||
}
|
||||
|
||||
impl.forget(aBlobImpl);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
RefPtr<MultipartBlobImpl> impl = new MultipartBlobImpl(EmptyString());
|
||||
nsresult rv = impl->InitializeChromeFile(
|
||||
aFile, aType, aName, aLastModifiedPassed, aLastModified, aIsFromNsIFile);
|
||||
if (NS_FAILED(rv)) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
MOZ_ASSERT(impl->IsFile());
|
||||
|
||||
impl.forget(aBlobImpl);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
} // namespace dom
|
||||
|
|
|
@ -20,20 +20,52 @@
|
|||
|
||||
class nsIFile;
|
||||
class nsIGlobalObject;
|
||||
class nsPIDOMWindowInner;
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
struct ChromeFilePropertyBag;
|
||||
class Promise;
|
||||
class File;
|
||||
|
||||
class FileCreatorHelper final {
|
||||
public:
|
||||
NS_INLINE_DECL_REFCOUNTING(FileCreatorHelper);
|
||||
|
||||
static already_AddRefed<Promise> CreateFile(nsIGlobalObject* aGlobalObject,
|
||||
nsIFile* aFile,
|
||||
const ChromeFilePropertyBag& aBag,
|
||||
bool aIsFromNsIFile,
|
||||
ErrorResult& aRv);
|
||||
|
||||
void ResponseReceived(BlobImpl* aBlobImpl, nsresult aRv);
|
||||
|
||||
// For IPC only
|
||||
static nsresult CreateBlobImplForIPC(
|
||||
const nsAString& aPath, const nsAString& aType, const nsAString& aName,
|
||||
bool aLastModifiedPassed, int64_t aLastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile, BlobImpl** aBlobImpl);
|
||||
|
||||
private:
|
||||
static already_AddRefed<File> CreateFileInternal(
|
||||
nsPIDOMWindowInner* aWindow, nsIFile* aFile,
|
||||
const ChromeFilePropertyBag& aBag, bool aIsFromNsIFile, ErrorResult& aRv);
|
||||
|
||||
static nsresult CreateBlobImpl(nsIFile* aFile, const nsAString& aType,
|
||||
const nsAString& aName,
|
||||
bool aLastModifiedPassed,
|
||||
int64_t aLastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile, BlobImpl** aBlobImpl);
|
||||
|
||||
FileCreatorHelper(Promise* aPromise, nsPIDOMWindowInner* aWindow);
|
||||
~FileCreatorHelper();
|
||||
|
||||
void SendRequest(nsIFile* aFile, const ChromeFilePropertyBag& aBag,
|
||||
bool aIsFromNsIFile, ErrorResult& aRv);
|
||||
|
||||
RefPtr<Promise> mPromise;
|
||||
nsCOMPtr<nsPIDOMWindowInner> mWindow;
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
|
|
|
@ -274,6 +274,22 @@ void MultipartBlobImpl::SetLengthAndModifiedDate(ErrorResult& aRv) {
|
|||
}
|
||||
}
|
||||
|
||||
void MultipartBlobImpl::GetMozFullPathInternal(nsAString& aFilename,
|
||||
ErrorResult& aRv) const {
|
||||
if (!mIsFromNsIFile || mBlobImpls.Length() == 0) {
|
||||
BaseBlobImpl::GetMozFullPathInternal(aFilename, aRv);
|
||||
return;
|
||||
}
|
||||
|
||||
BlobImpl* blobImpl = mBlobImpls.ElementAt(0).get();
|
||||
if (!blobImpl) {
|
||||
BaseBlobImpl::GetMozFullPathInternal(aFilename, aRv);
|
||||
return;
|
||||
}
|
||||
|
||||
blobImpl->GetMozFullPathInternal(aFilename, aRv);
|
||||
}
|
||||
|
||||
nsresult MultipartBlobImpl::SetMutable(bool aMutable) {
|
||||
nsresult rv;
|
||||
|
||||
|
@ -301,6 +317,82 @@ nsresult MultipartBlobImpl::SetMutable(bool aMutable) {
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult MultipartBlobImpl::InitializeChromeFile(
|
||||
nsIFile* aFile, const nsAString& aType, const nsAString& aName,
|
||||
bool aLastModifiedPassed, int64_t aLastModified, bool aIsFromNsIFile) {
|
||||
MOZ_ASSERT(!mImmutable, "Something went wrong ...");
|
||||
if (mImmutable) {
|
||||
return NS_ERROR_UNEXPECTED;
|
||||
}
|
||||
|
||||
mName = aName;
|
||||
mContentType = aType;
|
||||
mIsFromNsIFile = aIsFromNsIFile;
|
||||
|
||||
bool exists;
|
||||
nsresult rv = aFile->Exists(&exists);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (!exists) {
|
||||
return NS_ERROR_FILE_NOT_FOUND;
|
||||
}
|
||||
|
||||
bool isDir;
|
||||
rv = aFile->IsDirectory(&isDir);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (isDir) {
|
||||
return NS_ERROR_FILE_IS_DIRECTORY;
|
||||
}
|
||||
|
||||
if (mName.IsEmpty()) {
|
||||
aFile->GetLeafName(mName);
|
||||
}
|
||||
|
||||
RefPtr<File> blob = File::CreateFromFile(nullptr, aFile);
|
||||
|
||||
// Pre-cache size.
|
||||
ErrorResult error;
|
||||
blob->GetSize(error);
|
||||
if (NS_WARN_IF(error.Failed())) {
|
||||
return error.StealNSResult();
|
||||
}
|
||||
|
||||
// Pre-cache modified date.
|
||||
blob->GetLastModified(error);
|
||||
if (NS_WARN_IF(error.Failed())) {
|
||||
return error.StealNSResult();
|
||||
}
|
||||
|
||||
// XXXkhuey this is terrible
|
||||
if (mContentType.IsEmpty()) {
|
||||
blob->GetType(mContentType);
|
||||
}
|
||||
|
||||
BlobSet blobSet;
|
||||
rv = blobSet.AppendBlobImpl(static_cast<File*>(blob.get())->Impl());
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
mBlobImpls = blobSet.GetBlobImpls();
|
||||
|
||||
SetLengthAndModifiedDate(error);
|
||||
if (NS_WARN_IF(error.Failed())) {
|
||||
return error.StealNSResult();
|
||||
}
|
||||
|
||||
if (aLastModifiedPassed) {
|
||||
SetLastModified(aLastModified);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
bool MultipartBlobImpl::MayBeClonedToOtherThreads() const {
|
||||
for (uint32_t i = 0; i < mBlobImpls.Length(); ++i) {
|
||||
if (!mBlobImpls[i]->MayBeClonedToOtherThreads()) {
|
||||
|
|
|
@ -32,12 +32,14 @@ class MultipartBlobImpl final : public BaseBlobImpl {
|
|||
// Create as a file to be later initialized
|
||||
explicit MultipartBlobImpl(const nsAString& aName)
|
||||
: BaseBlobImpl(NS_LITERAL_STRING("MultipartBlobImpl"), aName,
|
||||
EmptyString(), UINT64_MAX) {}
|
||||
EmptyString(), UINT64_MAX),
|
||||
mIsFromNsIFile(false) {}
|
||||
|
||||
// Create as a blob to be later initialized
|
||||
MultipartBlobImpl()
|
||||
: BaseBlobImpl(NS_LITERAL_STRING("MultipartBlobImpl"), EmptyString(),
|
||||
UINT64_MAX) {}
|
||||
UINT64_MAX),
|
||||
mIsFromNsIFile(false) {}
|
||||
|
||||
void InitializeBlob(ErrorResult& aRv);
|
||||
|
||||
|
@ -45,6 +47,11 @@ class MultipartBlobImpl final : public BaseBlobImpl {
|
|||
const nsAString& aContentType, bool aNativeEOL,
|
||||
ErrorResult& aRv);
|
||||
|
||||
nsresult InitializeChromeFile(nsIFile* aData, const nsAString& aType,
|
||||
const nsAString& aName,
|
||||
bool aLastModifiedPassed, int64_t aLastModified,
|
||||
bool aIsFromNsIFile);
|
||||
|
||||
virtual already_AddRefed<BlobImpl> CreateSlice(uint64_t aStart,
|
||||
uint64_t aLength,
|
||||
const nsAString& aContentType,
|
||||
|
@ -59,6 +66,9 @@ class MultipartBlobImpl final : public BaseBlobImpl {
|
|||
return mBlobImpls.Length() ? &mBlobImpls : nullptr;
|
||||
}
|
||||
|
||||
virtual void GetMozFullPathInternal(nsAString& aFullPath,
|
||||
ErrorResult& aRv) const override;
|
||||
|
||||
virtual nsresult SetMutable(bool aMutable) override;
|
||||
|
||||
void SetName(const nsAString& aName) { mName = aName; }
|
||||
|
@ -76,19 +86,22 @@ class MultipartBlobImpl final : public BaseBlobImpl {
|
|||
const nsAString& aName, const nsAString& aContentType)
|
||||
: BaseBlobImpl(NS_LITERAL_STRING("MultipartBlobImpl"), aName,
|
||||
aContentType, UINT64_MAX),
|
||||
mBlobImpls(std::move(aBlobImpls)) {}
|
||||
mBlobImpls(std::move(aBlobImpls)),
|
||||
mIsFromNsIFile(false) {}
|
||||
|
||||
MultipartBlobImpl(nsTArray<RefPtr<BlobImpl>>&& aBlobImpls,
|
||||
const nsAString& aContentType)
|
||||
: BaseBlobImpl(NS_LITERAL_STRING("MultipartBlobImpl"), aContentType,
|
||||
UINT64_MAX),
|
||||
mBlobImpls(std::move(aBlobImpls)) {}
|
||||
mBlobImpls(std::move(aBlobImpls)),
|
||||
mIsFromNsIFile(false) {}
|
||||
|
||||
virtual ~MultipartBlobImpl() {}
|
||||
|
||||
void SetLengthAndModifiedDate(ErrorResult& aRv);
|
||||
|
||||
nsTArray<RefPtr<BlobImpl>> mBlobImpls;
|
||||
bool mIsFromNsIFile;
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
|
|
|
@ -1,55 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "FileCreatorChild.h"
|
||||
#include "mozilla/dom/Promise.h"
|
||||
#include "mozilla/dom/IPCBlobUtils.h"
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
FileCreatorChild::FileCreatorChild() = default;
|
||||
|
||||
FileCreatorChild::~FileCreatorChild() { MOZ_ASSERT(!mPromise); }
|
||||
|
||||
void FileCreatorChild::SetPromise(Promise* aPromise) {
|
||||
MOZ_ASSERT(aPromise);
|
||||
MOZ_ASSERT(!mPromise);
|
||||
|
||||
mPromise = aPromise;
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult FileCreatorChild::Recv__delete__(
|
||||
const FileCreationResult& aResult) {
|
||||
MOZ_ASSERT(mPromise);
|
||||
|
||||
RefPtr<Promise> promise;
|
||||
promise.swap(mPromise);
|
||||
|
||||
if (aResult.type() == FileCreationResult::TFileCreationErrorResult) {
|
||||
promise->MaybeReject(aResult.get_FileCreationErrorResult().errorCode());
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
MOZ_ASSERT(aResult.type() == FileCreationResult::TFileCreationSuccessResult);
|
||||
|
||||
RefPtr<dom::BlobImpl> impl = dom::IPCBlobUtils::Deserialize(
|
||||
aResult.get_FileCreationSuccessResult().blob());
|
||||
|
||||
RefPtr<File> file = File::Create(promise->GetParentObject(), impl);
|
||||
promise->MaybeResolve(file);
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
void FileCreatorChild::ActorDestroy(ActorDestroyReason aWhy) {
|
||||
if (mPromise) {
|
||||
mPromise->MaybeReject(NS_ERROR_FAILURE);
|
||||
mPromise = nullptr;
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
|
@ -1,36 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef mozilla_dom_ipc_FileCreatorChild_h
|
||||
#define mozilla_dom_ipc_FileCreatorChild_h
|
||||
|
||||
#include "mozilla/ipc/PFileCreatorChild.h"
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
class FileCreatorChild final : public mozilla::ipc::PFileCreatorChild {
|
||||
friend class mozilla::ipc::PFileCreatorChild;
|
||||
|
||||
public:
|
||||
FileCreatorChild();
|
||||
~FileCreatorChild();
|
||||
|
||||
void SetPromise(Promise* aPromise);
|
||||
|
||||
private:
|
||||
mozilla::ipc::IPCResult Recv__delete__(
|
||||
const FileCreationResult& aResult) override;
|
||||
|
||||
void ActorDestroy(ActorDestroyReason aWhy) override;
|
||||
|
||||
RefPtr<Promise> mPromise;
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
||||
|
||||
#endif // mozilla_dom_ipc_FileCreatorChild_h
|
|
@ -1,128 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "FileCreatorParent.h"
|
||||
#include "mozilla/dom/FileBlobImpl.h"
|
||||
#include "mozilla/dom/IPCBlobUtils.h"
|
||||
#include "mozilla/dom/MultipartBlobImpl.h"
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
FileCreatorParent::FileCreatorParent()
|
||||
: mBackgroundEventTarget(GetCurrentThreadEventTarget()), mIPCActive(true) {}
|
||||
|
||||
FileCreatorParent::~FileCreatorParent() = default;
|
||||
|
||||
mozilla::ipc::IPCResult FileCreatorParent::CreateAndShareFile(
|
||||
const nsString& aFullPath, const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) {
|
||||
RefPtr<dom::BlobImpl> blobImpl;
|
||||
nsresult rv =
|
||||
CreateBlobImpl(aFullPath, aType, aName, aLastModified.isSome(),
|
||||
aLastModified.isSome() ? aLastModified.value() : 0,
|
||||
aExistenceCheck, aIsFromNsIFile, getter_AddRefs(blobImpl));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
Unused << Send__delete__(this, FileCreationErrorResult(rv));
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
MOZ_ASSERT(blobImpl);
|
||||
|
||||
// FileBlobImpl is unable to return the correct type on this thread because
|
||||
// nsIMIMEService is not thread-safe. We must exec the 'type' getter on
|
||||
// main-thread before send the blob to the child actor.
|
||||
|
||||
RefPtr<FileCreatorParent> self = this;
|
||||
NS_DispatchToMainThread(NS_NewRunnableFunction(
|
||||
"FileCreatorParent::CreateAndShareFile", [self, blobImpl]() {
|
||||
nsAutoString type;
|
||||
blobImpl->GetType(type);
|
||||
|
||||
self->mBackgroundEventTarget->Dispatch(NS_NewRunnableFunction(
|
||||
"FileCreatorParent::CreateAndShareFile return", [self, blobImpl]() {
|
||||
if (self->mIPCActive) {
|
||||
IPCBlob ipcBlob;
|
||||
nsresult rv = dom::IPCBlobUtils::Serialize(
|
||||
blobImpl, self->Manager(), ipcBlob);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
Unused << Send__delete__(self, FileCreationErrorResult(rv));
|
||||
return;
|
||||
}
|
||||
|
||||
Unused << Send__delete__(self,
|
||||
FileCreationSuccessResult(ipcBlob));
|
||||
}
|
||||
}));
|
||||
}));
|
||||
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
void FileCreatorParent::ActorDestroy(ActorDestroyReason aWhy) {
|
||||
mIPCActive = false;
|
||||
}
|
||||
|
||||
/* static */
|
||||
nsresult FileCreatorParent::CreateBlobImpl(
|
||||
const nsAString& aPath, const nsAString& aType, const nsAString& aName,
|
||||
bool aLastModifiedPassed, int64_t aLastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile, BlobImpl** aBlobImpl) {
|
||||
MOZ_ASSERT(!NS_IsMainThread());
|
||||
|
||||
nsCOMPtr<nsIFile> file;
|
||||
nsresult rv = NS_NewLocalFile(aPath, true, getter_AddRefs(file));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (aExistenceCheck) {
|
||||
bool exists;
|
||||
nsresult rv = file->Exists(&exists);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (!exists) {
|
||||
return NS_ERROR_FILE_NOT_FOUND;
|
||||
}
|
||||
|
||||
bool isDir;
|
||||
rv = file->IsDirectory(&isDir);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
return rv;
|
||||
}
|
||||
|
||||
if (isDir) {
|
||||
return NS_ERROR_FILE_IS_DIRECTORY;
|
||||
}
|
||||
}
|
||||
|
||||
RefPtr<FileBlobImpl> impl = new FileBlobImpl(file);
|
||||
|
||||
if (!aName.IsEmpty()) {
|
||||
impl->SetName(aName);
|
||||
}
|
||||
|
||||
if (!aType.IsEmpty()) {
|
||||
impl->SetType(aType);
|
||||
}
|
||||
|
||||
if (aLastModifiedPassed) {
|
||||
impl->SetLastModified(aLastModified);
|
||||
}
|
||||
|
||||
if (!aIsFromNsIFile) {
|
||||
impl->SetEmptyMozFullPath();
|
||||
}
|
||||
|
||||
impl.forget(aBlobImpl);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
|
@ -1,47 +0,0 @@
|
|||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef mozilla_dom_ipc_FileCreatorParent_h
|
||||
#define mozilla_dom_ipc_FileCreatorParent_h
|
||||
|
||||
#include "mozilla/ipc/PFileCreatorParent.h"
|
||||
|
||||
class nsIFile;
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
class BlobImpl;
|
||||
|
||||
class FileCreatorParent final : public mozilla::ipc::PFileCreatorParent {
|
||||
public:
|
||||
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(FileCreatorParent)
|
||||
|
||||
FileCreatorParent();
|
||||
|
||||
mozilla::ipc::IPCResult CreateAndShareFile(
|
||||
const nsString& aFullPath, const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile);
|
||||
|
||||
private:
|
||||
~FileCreatorParent();
|
||||
|
||||
void ActorDestroy(ActorDestroyReason aWhy) override;
|
||||
|
||||
nsresult CreateBlobImpl(const nsAString& aPath, const nsAString& aType,
|
||||
const nsAString& aName, bool aLastModifiedPassed,
|
||||
int64_t aLastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile, BlobImpl** aBlobImpl);
|
||||
|
||||
nsCOMPtr<nsIEventTarget> mBackgroundEventTarget;
|
||||
bool mIPCActive;
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
||||
|
||||
#endif // mozilla_dom_ipc_FileCreatorParent_h
|
|
@ -1,41 +0,0 @@
|
|||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
include protocol PBackground;
|
||||
include protocol PChildToParentStream;
|
||||
include protocol PFileDescriptorSet;
|
||||
include protocol PIPCBlobInputStream;
|
||||
include protocol PParentToChildStream;
|
||||
|
||||
include IPCBlob;
|
||||
|
||||
namespace mozilla {
|
||||
namespace ipc {
|
||||
|
||||
struct FileCreationSuccessResult
|
||||
{
|
||||
IPCBlob blob;
|
||||
};
|
||||
|
||||
struct FileCreationErrorResult
|
||||
{
|
||||
nsresult errorCode;
|
||||
};
|
||||
|
||||
union FileCreationResult
|
||||
{
|
||||
FileCreationSuccessResult;
|
||||
FileCreationErrorResult;
|
||||
};
|
||||
|
||||
protocol PFileCreator
|
||||
{
|
||||
manager PBackground;
|
||||
|
||||
child:
|
||||
async __delete__(FileCreationResult aResult);
|
||||
};
|
||||
|
||||
} // namespace ipc
|
||||
} // namespace mozilla
|
|
@ -39,5 +39,5 @@ parent:
|
|||
async OperationDone(nsCString aContentType, FileDescriptor aFD);
|
||||
};
|
||||
|
||||
} // namespace ipc
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
||||
|
|
|
@ -8,8 +8,6 @@ with Files("**"):
|
|||
BUG_COMPONENT = ("Core", "DOM: File")
|
||||
|
||||
EXPORTS.mozilla.dom.ipc += [
|
||||
'FileCreatorChild.h',
|
||||
'FileCreatorParent.h',
|
||||
'IPCBlobInputStream.h',
|
||||
'IPCBlobInputStreamChild.h',
|
||||
'IPCBlobInputStreamParent.h',
|
||||
|
@ -25,8 +23,6 @@ EXPORTS.mozilla.dom += [
|
|||
]
|
||||
|
||||
UNIFIED_SOURCES += [
|
||||
'FileCreatorChild.cpp',
|
||||
'FileCreatorParent.cpp',
|
||||
'IPCBlobInputStream.cpp',
|
||||
'IPCBlobInputStreamChild.cpp',
|
||||
'IPCBlobInputStreamParent.cpp',
|
||||
|
@ -42,7 +38,6 @@ UNIFIED_SOURCES += [
|
|||
IPDL_SOURCES += [
|
||||
'BlobTypes.ipdlh',
|
||||
'IPCBlob.ipdlh',
|
||||
'PFileCreator.ipdl',
|
||||
'PIPCBlobInputStream.ipdl',
|
||||
'PPendingIPCBlob.ipdl',
|
||||
'PTemporaryIPCBlob.ipdl',
|
||||
|
|
|
@ -39,6 +39,7 @@
|
|||
#include "mozilla/dom/DataTransfer.h"
|
||||
#include "mozilla/dom/DocGroup.h"
|
||||
#include "mozilla/dom/ExternalHelperAppChild.h"
|
||||
#include "mozilla/dom/FileCreatorHelper.h"
|
||||
#include "mozilla/dom/GetFilesHelper.h"
|
||||
#include "mozilla/dom/IPCBlobUtils.h"
|
||||
#include "mozilla/dom/JSWindowActorService.h"
|
||||
|
@ -3387,6 +3388,51 @@ bool ContentChild::DeallocPSessionStorageObserverChild(
|
|||
return true;
|
||||
}
|
||||
|
||||
void ContentChild::FileCreationRequest(nsID& aUUID, FileCreatorHelper* aHelper,
|
||||
const nsAString& aFullPath,
|
||||
const nsAString& aType,
|
||||
const nsAString& aName,
|
||||
const Optional<int64_t>& aLastModified,
|
||||
bool aExistenceCheck,
|
||||
bool aIsFromNsIFile) {
|
||||
MOZ_ASSERT(aHelper);
|
||||
|
||||
bool lastModifiedPassed = false;
|
||||
int64_t lastModified = 0;
|
||||
if (aLastModified.WasPassed()) {
|
||||
lastModifiedPassed = true;
|
||||
lastModified = aLastModified.Value();
|
||||
}
|
||||
|
||||
Unused << SendFileCreationRequest(
|
||||
aUUID, nsString(aFullPath), nsString(aType), nsString(aName),
|
||||
lastModifiedPassed, lastModified, aExistenceCheck, aIsFromNsIFile);
|
||||
mFileCreationPending.Put(aUUID, aHelper);
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult ContentChild::RecvFileCreationResponse(
|
||||
const nsID& aUUID, const FileCreationResult& aResult) {
|
||||
FileCreatorHelper* helper = mFileCreationPending.GetWeak(aUUID);
|
||||
if (!helper) {
|
||||
return IPC_FAIL_NO_REASON(this);
|
||||
}
|
||||
|
||||
if (aResult.type() == FileCreationResult::TFileCreationErrorResult) {
|
||||
helper->ResponseReceived(nullptr,
|
||||
aResult.get_FileCreationErrorResult().errorCode());
|
||||
} else {
|
||||
MOZ_ASSERT(aResult.type() ==
|
||||
FileCreationResult::TFileCreationSuccessResult);
|
||||
|
||||
RefPtr<BlobImpl> impl = IPCBlobUtils::Deserialize(
|
||||
aResult.get_FileCreationSuccessResult().blob());
|
||||
helper->ResponseReceived(impl, NS_OK);
|
||||
}
|
||||
|
||||
mFileCreationPending.Remove(aUUID);
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult ContentChild::RecvActivate(PBrowserChild* aTab) {
|
||||
TabChild* tab = static_cast<TabChild*>(aTab);
|
||||
return tab->RecvActivate();
|
||||
|
|
|
@ -77,6 +77,7 @@ class ConsoleListener;
|
|||
class ClonedMessageData;
|
||||
class TabChild;
|
||||
class GetFilesHelperChild;
|
||||
class FileCreatorHelper;
|
||||
|
||||
class ContentChild final : public PContentChild,
|
||||
public nsIWindowProvider,
|
||||
|
@ -563,6 +564,9 @@ class ContentChild final : public PContentChild,
|
|||
|
||||
mozilla::ipc::IPCResult RecvBlobURLUnregistration(const nsCString& aURI);
|
||||
|
||||
mozilla::ipc::IPCResult RecvFileCreationResponse(
|
||||
const nsID& aUUID, const FileCreationResult& aResult);
|
||||
|
||||
mozilla::ipc::IPCResult RecvRequestMemoryReport(
|
||||
const uint32_t& generation, const bool& anonymize,
|
||||
const bool& minimizeMemoryUsage, const Maybe<FileDescriptor>& DMDFile);
|
||||
|
@ -641,6 +645,13 @@ class ContentChild final : public PContentChild,
|
|||
static void FatalErrorIfNotUsingGPUProcess(const char* const aErrorMsg,
|
||||
base::ProcessId aOtherPid);
|
||||
|
||||
// This method is used by FileCreatorHelper for the creation of a BlobImpl.
|
||||
void FileCreationRequest(nsID& aUUID, FileCreatorHelper* aHelper,
|
||||
const nsAString& aFullPath, const nsAString& aType,
|
||||
const nsAString& aName,
|
||||
const Optional<int64_t>& aLastModified,
|
||||
bool aExistenceCheck, bool aIsFromNsIFile);
|
||||
|
||||
typedef std::function<void(PRFileDesc*)> AnonymousTemporaryFileCallback;
|
||||
nsresult AsyncOpenAnonymousTemporaryFile(
|
||||
const AnonymousTemporaryFileCallback& aCallback);
|
||||
|
@ -792,6 +803,10 @@ class ContentChild final : public PContentChild,
|
|||
// received.
|
||||
nsRefPtrHashtable<nsIDHashKey, GetFilesHelperChild> mGetFilesPendingRequests;
|
||||
|
||||
// Hashtable to keep track of the pending file creation.
|
||||
// These items are removed when RecvFileCreationResponse is received.
|
||||
nsRefPtrHashtable<nsIDHashKey, FileCreatorHelper> mFileCreationPending;
|
||||
|
||||
nsClassHashtable<nsUint64HashKey, AnonymousTemporaryFileCallback>
|
||||
mPendingAnonymousTemporaryFiles;
|
||||
|
||||
|
|
|
@ -47,6 +47,7 @@
|
|||
#include "mozilla/dom/DataTransfer.h"
|
||||
#include "mozilla/dom/Element.h"
|
||||
#include "mozilla/dom/File.h"
|
||||
#include "mozilla/dom/FileCreatorHelper.h"
|
||||
#include "mozilla/dom/FileSystemSecurity.h"
|
||||
#include "mozilla/dom/IPCBlobUtils.h"
|
||||
#include "mozilla/dom/ExternalHelperAppParent.h"
|
||||
|
@ -5532,6 +5533,49 @@ bool ContentParent::DeallocPSessionStorageObserverParent(
|
|||
return mozilla::dom::DeallocPSessionStorageObserverParent(aActor);
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult ContentParent::RecvFileCreationRequest(
|
||||
const nsID& aID, const nsString& aFullPath, const nsString& aType,
|
||||
const nsString& aName, const bool& aLastModifiedPassed,
|
||||
const int64_t& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) {
|
||||
// We allow the creation of File via this IPC call only for the 'file' process
|
||||
// or for testing.
|
||||
if (!mRemoteType.EqualsLiteral(FILE_REMOTE_TYPE) &&
|
||||
!Preferences::GetBool("dom.file.createInChild", false)) {
|
||||
return IPC_FAIL_NO_REASON(this);
|
||||
}
|
||||
|
||||
RefPtr<BlobImpl> blobImpl;
|
||||
nsresult rv = FileCreatorHelper::CreateBlobImplForIPC(
|
||||
aFullPath, aType, aName, aLastModifiedPassed, aLastModified,
|
||||
aExistenceCheck, aIsFromNsIFile, getter_AddRefs(blobImpl));
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
if (!SendFileCreationResponse(aID, FileCreationErrorResult(rv))) {
|
||||
return IPC_FAIL_NO_REASON(this);
|
||||
}
|
||||
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
MOZ_ASSERT(blobImpl);
|
||||
|
||||
IPCBlob ipcBlob;
|
||||
rv = IPCBlobUtils::Serialize(blobImpl, this, ipcBlob);
|
||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
||||
if (!SendFileCreationResponse(aID, FileCreationErrorResult(rv))) {
|
||||
return IPC_FAIL_NO_REASON(this);
|
||||
}
|
||||
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
if (!SendFileCreationResponse(aID, FileCreationSuccessResult(ipcBlob))) {
|
||||
return IPC_FAIL_NO_REASON(this);
|
||||
}
|
||||
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
nsresult ContentParent::SaveRecording(nsIFile* aFile, bool* aRetval) {
|
||||
if (mRecordReplayState != eRecording) {
|
||||
*aRetval = false;
|
||||
|
|
|
@ -1127,6 +1127,12 @@ class ContentParent final : public PContentParent,
|
|||
|
||||
mozilla::ipc::IPCResult RecvDeleteGetFilesRequest(const nsID& aID);
|
||||
|
||||
mozilla::ipc::IPCResult RecvFileCreationRequest(
|
||||
const nsID& aID, const nsString& aFullPath, const nsString& aType,
|
||||
const nsString& aName, const bool& aLastModifiedPassed,
|
||||
const int64_t& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile);
|
||||
|
||||
mozilla::ipc::IPCResult RecvAccumulateChildHistograms(
|
||||
InfallibleTArray<HistogramAccumulation>&& aAccumulations);
|
||||
mozilla::ipc::IPCResult RecvAccumulateChildKeyedHistograms(
|
||||
|
|
|
@ -203,6 +203,22 @@ union GetFilesResponseResult
|
|||
GetFilesResponseFailure;
|
||||
};
|
||||
|
||||
struct FileCreationSuccessResult
|
||||
{
|
||||
IPCBlob blob;
|
||||
};
|
||||
|
||||
struct FileCreationErrorResult
|
||||
{
|
||||
nsresult errorCode;
|
||||
};
|
||||
|
||||
union FileCreationResult
|
||||
{
|
||||
FileCreationSuccessResult;
|
||||
FileCreationErrorResult;
|
||||
};
|
||||
|
||||
struct BlobURLRegistrationData
|
||||
{
|
||||
nsCString url;
|
||||
|
@ -654,6 +670,8 @@ child:
|
|||
async GMPsChanged(GMPCapabilityData[] capabilities);
|
||||
|
||||
|
||||
async FileCreationResponse(nsID aID, FileCreationResult aResult);
|
||||
|
||||
/**
|
||||
* Sending an activate message moves focus to the child.
|
||||
*/
|
||||
|
@ -1188,6 +1206,11 @@ parent:
|
|||
async GetFilesRequest(nsID aID, nsString aDirectory, bool aRecursiveFlag);
|
||||
async DeleteGetFilesRequest(nsID aID);
|
||||
|
||||
async FileCreationRequest(nsID aID, nsString aFullPath, nsString aType,
|
||||
nsString aName, bool lastModifiedPassed,
|
||||
int64_t lastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile);
|
||||
|
||||
async StoreAndBroadcastBlobURLRegistration(nsCString url, IPCBlob blob,
|
||||
Principal principal);
|
||||
|
||||
|
|
|
@ -27,11 +27,9 @@
|
|||
#include "mozilla/dom/cache/ActorUtils.h"
|
||||
#include "mozilla/dom/indexedDB/PBackgroundIDBFactoryChild.h"
|
||||
#include "mozilla/dom/indexedDB/PBackgroundIndexedDBUtilsChild.h"
|
||||
#include "mozilla/dom/ipc/FileCreatorChild.h"
|
||||
#include "mozilla/dom/ipc/IPCBlobInputStreamChild.h"
|
||||
#include "mozilla/dom/ipc/PendingIPCBlobChild.h"
|
||||
#include "mozilla/dom/ipc/TemporaryIPCBlobChild.h"
|
||||
#include "mozilla/dom/IPCBlobUtils.h"
|
||||
#include "mozilla/dom/quota/PQuotaChild.h"
|
||||
#include "mozilla/dom/RemoteWorkerChild.h"
|
||||
#include "mozilla/dom/RemoteWorkerServiceChild.h"
|
||||
|
@ -381,18 +379,6 @@ bool BackgroundChildImpl::DeallocPTemporaryIPCBlobChild(
|
|||
return true;
|
||||
}
|
||||
|
||||
PFileCreatorChild* BackgroundChildImpl::AllocPFileCreatorChild(
|
||||
const nsString& aFullPath, const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) {
|
||||
return new mozilla::dom::FileCreatorChild();
|
||||
}
|
||||
|
||||
bool BackgroundChildImpl::DeallocPFileCreatorChild(PFileCreatorChild* aActor) {
|
||||
delete static_cast<mozilla::dom::FileCreatorChild*>(aActor);
|
||||
return true;
|
||||
}
|
||||
|
||||
PIPCBlobInputStreamChild* BackgroundChildImpl::AllocPIPCBlobInputStreamChild(
|
||||
const nsID& aID, const uint64_t& aSize) {
|
||||
// IPCBlobInputStreamChild is refcounted. Here it's created and in
|
||||
|
|
|
@ -9,7 +9,6 @@
|
|||
|
||||
#include "mozilla/Attributes.h"
|
||||
#include "mozilla/ipc/PBackgroundChild.h"
|
||||
#include "nsRefPtrHashtable.h"
|
||||
#include "nsAutoPtr.h"
|
||||
|
||||
namespace mozilla {
|
||||
|
@ -127,13 +126,6 @@ class BackgroundChildImpl : public PBackgroundChild {
|
|||
virtual bool DeallocPTemporaryIPCBlobChild(
|
||||
PTemporaryIPCBlobChild* aActor) override;
|
||||
|
||||
virtual PFileCreatorChild* AllocPFileCreatorChild(
|
||||
const nsString& aFullPath, const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) override;
|
||||
|
||||
virtual bool DeallocPFileCreatorChild(PFileCreatorChild* aActor) override;
|
||||
|
||||
virtual mozilla::dom::PRemoteWorkerChild* AllocPRemoteWorkerChild(
|
||||
const RemoteWorkerData& aData) override;
|
||||
|
||||
|
|
|
@ -30,11 +30,9 @@
|
|||
#include "mozilla/dom/StorageActivityService.h"
|
||||
#include "mozilla/dom/cache/ActorUtils.h"
|
||||
#include "mozilla/dom/indexedDB/ActorsParent.h"
|
||||
#include "mozilla/dom/ipc/FileCreatorParent.h"
|
||||
#include "mozilla/dom/ipc/IPCBlobInputStreamParent.h"
|
||||
#include "mozilla/dom/ipc/PendingIPCBlobParent.h"
|
||||
#include "mozilla/dom/ipc/TemporaryIPCBlobParent.h"
|
||||
#include "mozilla/dom/IPCBlobUtils.h"
|
||||
#include "mozilla/dom/localstorage/ActorsParent.h"
|
||||
#include "mozilla/dom/quota/ActorsParent.h"
|
||||
#include "mozilla/dom/simpledb/ActorsParent.h"
|
||||
|
@ -58,7 +56,6 @@
|
|||
#include "mozilla/dom/network/UDPSocketParent.h"
|
||||
#include "mozilla/dom/WebAuthnTransactionParent.h"
|
||||
#include "mozilla/Preferences.h"
|
||||
#include "mozilla/StaticPrefs.h"
|
||||
#include "nsNetUtil.h"
|
||||
#include "nsIScriptSecurityManager.h"
|
||||
#include "nsProxyRelease.h"
|
||||
|
@ -541,53 +538,6 @@ bool BackgroundParentImpl::DeallocPSharedWorkerParent(
|
|||
return true;
|
||||
}
|
||||
|
||||
PFileCreatorParent* BackgroundParentImpl::AllocPFileCreatorParent(
|
||||
const nsString& aFullPath, const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) {
|
||||
RefPtr<mozilla::dom::FileCreatorParent> actor =
|
||||
new mozilla::dom::FileCreatorParent();
|
||||
return actor.forget().take();
|
||||
}
|
||||
|
||||
mozilla::ipc::IPCResult BackgroundParentImpl::RecvPFileCreatorConstructor(
|
||||
PFileCreatorParent* aActor, const nsString& aFullPath,
|
||||
const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) {
|
||||
bool isFileRemoteType = false;
|
||||
|
||||
// If the ContentParent is null we are dealing with a same-process actor.
|
||||
RefPtr<ContentParent> parent = BackgroundParent::GetContentParent(this);
|
||||
if (!parent) {
|
||||
isFileRemoteType = true;
|
||||
} else {
|
||||
isFileRemoteType = parent->GetRemoteType().EqualsLiteral(FILE_REMOTE_TYPE);
|
||||
NS_ReleaseOnMainThreadSystemGroup("ContentParent release", parent.forget());
|
||||
}
|
||||
|
||||
mozilla::dom::FileCreatorParent* actor =
|
||||
static_cast<mozilla::dom::FileCreatorParent*>(aActor);
|
||||
|
||||
// We allow the creation of File via this IPC call only for the 'file' process
|
||||
// or for testing.
|
||||
if (!isFileRemoteType && !StaticPrefs::dom_file_createInChild()) {
|
||||
Unused << mozilla::dom::FileCreatorParent::Send__delete__(
|
||||
actor, FileCreationErrorResult(NS_ERROR_DOM_INVALID_STATE_ERR));
|
||||
return IPC_OK();
|
||||
}
|
||||
|
||||
return actor->CreateAndShareFile(aFullPath, aType, aName, aLastModified,
|
||||
aExistenceCheck, aIsFromNsIFile);
|
||||
}
|
||||
|
||||
bool BackgroundParentImpl::DeallocPFileCreatorParent(
|
||||
PFileCreatorParent* aActor) {
|
||||
RefPtr<mozilla::dom::FileCreatorParent> actor =
|
||||
dont_AddRef(static_cast<mozilla::dom::FileCreatorParent*>(aActor));
|
||||
return true;
|
||||
}
|
||||
|
||||
PTemporaryIPCBlobParent* BackgroundParentImpl::AllocPTemporaryIPCBlobParent() {
|
||||
return new mozilla::dom::TemporaryIPCBlobParent();
|
||||
}
|
||||
|
|
|
@ -155,19 +155,6 @@ class BackgroundParentImpl : public PBackgroundParent {
|
|||
virtual bool DeallocPTemporaryIPCBlobParent(
|
||||
PTemporaryIPCBlobParent* aActor) override;
|
||||
|
||||
virtual PFileCreatorParent* AllocPFileCreatorParent(
|
||||
const nsString& aFullPath, const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) override;
|
||||
|
||||
virtual mozilla::ipc::IPCResult RecvPFileCreatorConstructor(
|
||||
PFileCreatorParent* actor, const nsString& aFullPath,
|
||||
const nsString& aType, const nsString& aName,
|
||||
const Maybe<int64_t>& aLastModified, const bool& aExistenceCheck,
|
||||
const bool& aIsFromNsIFile) override;
|
||||
|
||||
virtual bool DeallocPFileCreatorParent(PFileCreatorParent* aActor) override;
|
||||
|
||||
virtual mozilla::dom::PRemoteWorkerParent* AllocPRemoteWorkerParent(
|
||||
const RemoteWorkerData& aData) override;
|
||||
|
||||
|
|
|
@ -29,7 +29,6 @@ include protocol PRemoteWorker;
|
|||
include protocol PRemoteWorkerService;
|
||||
include protocol PSharedWorker;
|
||||
include protocol PTemporaryIPCBlob;
|
||||
include protocol PFileCreator;
|
||||
include protocol PMessagePort;
|
||||
include protocol PCameras;
|
||||
include protocol PMIDIManager;
|
||||
|
@ -95,7 +94,6 @@ sync protocol PBackground
|
|||
manages PRemoteWorkerService;
|
||||
manages PSharedWorker;
|
||||
manages PTemporaryIPCBlob;
|
||||
manages PFileCreator;
|
||||
manages PMessagePort;
|
||||
manages PCameras;
|
||||
manages PMIDIManager;
|
||||
|
@ -199,10 +197,6 @@ parent:
|
|||
|
||||
async PTemporaryIPCBlob();
|
||||
|
||||
async PFileCreator(nsString aFullPath, nsString aType, nsString aName,
|
||||
int64_t? lastModified, bool aExistenceCheck,
|
||||
bool aIsFromNsIFile);
|
||||
|
||||
async PClientManager();
|
||||
|
||||
async PMIDIManager();
|
||||
|
@ -234,7 +228,6 @@ child:
|
|||
async PPendingIPCBlob(IPCBlob blob);
|
||||
|
||||
async PRemoteWorker(RemoteWorkerData data);
|
||||
|
||||
both:
|
||||
// PIPCBlobInputStream is created on the parent side only if the child starts
|
||||
// a migration.
|
||||
|
|
|
@ -29,13 +29,6 @@ DIRECT_CALL_OVERRIDES = {
|
|||
"RemotePermissionRequest", "nsContentPermissionHelper.h"
|
||||
),
|
||||
|
||||
("PFileCreator", "child"): (
|
||||
"mozilla::dom::FileCreatorChild", "mozilla/dom/ipc/FileCreatorChild.h"
|
||||
),
|
||||
("PFileCreator", "parent"): (
|
||||
"mozilla::dom::FileCreatorParent", "mozilla/dom/ipc/FileCreatorParent.h"
|
||||
),
|
||||
|
||||
("PFileSystemRequest", "child"): (
|
||||
"FileSystemTaskChildBase", "mozilla/dom/FileSystemTaskBase.h"
|
||||
),
|
||||
|
|
|
@ -572,14 +572,6 @@ VARCACHE_PREF(
|
|||
bool, true
|
||||
)
|
||||
|
||||
// Allow the content process to create a File from a path. This is allowed just
|
||||
// on parent process, on 'file' Content process, or for testing.
|
||||
VARCACHE_PREF(
|
||||
"dom.file.createInChild",
|
||||
dom_file_createInChild,
|
||||
RelaxedAtomicBool, false
|
||||
)
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
// Extension prefs
|
||||
//---------------------------------------------------------------------------
|
||||
|
|
Загрузка…
Ссылка в новой задаче