Switch package file accessor classes to use BPositionIO

* PackageFileHeap{Reader,Writer} as well as Package{Reader,Writer} and
  their implementation and super classes do now internally use a
  BPositionIO instead of a FD to access the package file. This provides
  more flexibility needed for features to come.
* BPackageReader has already grown a new Init() version with a
  BPositionIO* parameter.
This commit is contained in:
Ingo Weinhold
2014-07-12 15:40:22 +02:00
parent 01e6d687c0
commit e527b79631
21 changed files with 205 additions and 141 deletions
+6 -1
View File
@@ -9,6 +9,9 @@
#include <SupportDefs.h> #include <SupportDefs.h>
class BPositionIO;
namespace BPackageKit { namespace BPackageKit {
namespace BHPKG { namespace BHPKG {
@@ -34,12 +37,14 @@ public:
status_t Init(const char* fileName, uint32 flags = 0); status_t Init(const char* fileName, uint32 flags = 0);
status_t Init(int fd, bool keepFD, uint32 flags = 0); status_t Init(int fd, bool keepFD, uint32 flags = 0);
status_t Init(BPositionIO* file, bool keepFile,
uint32 flags = 0);
status_t ParseContent( status_t ParseContent(
BPackageContentHandler* contentHandler); BPackageContentHandler* contentHandler);
status_t ParseContent(BLowLevelPackageContentHandler* status_t ParseContent(BLowLevelPackageContentHandler*
contentHandler); contentHandler);
int PackageFileFD(); BPositionIO* PackageFile() const;
BAbstractBufferedDataReader* HeapReader() const; BAbstractBufferedDataReader* HeapReader() const;
// Only valid as long as the reader lives. // Only valid as long as the reader lives.
@@ -71,8 +71,8 @@ public:
public: public:
PackageFileHeapAccessorBase( PackageFileHeapAccessorBase(
BErrorOutput* errorOutput, int fd, BErrorOutput* errorOutput,
off_t heapOffset, BPositionIO* file, off_t heapOffset,
DecompressionAlgorithmOwner* DecompressionAlgorithmOwner*
decompressionAlgorithm); decompressionAlgorithm);
virtual ~PackageFileHeapAccessorBase(); virtual ~PackageFileHeapAccessorBase();
@@ -89,8 +89,8 @@ public:
// normally used after cloning a PackageFileHeapReader only // normally used after cloning a PackageFileHeapReader only
void SetErrorOutput(BErrorOutput* errorOutput) void SetErrorOutput(BErrorOutput* errorOutput)
{ fErrorOutput = errorOutput; } { fErrorOutput = errorOutput; }
void SetFD(int fd) void SetFile(BPositionIO* file)
{ fFD = fd; } { fFile = file; }
uint64 HeapOverhead(uint64 uncompressedSize) const; uint64 HeapOverhead(uint64 uncompressedSize) const;
// additional bytes needed when storing // additional bytes needed when storing
@@ -122,7 +122,7 @@ protected:
protected: protected:
BErrorOutput* fErrorOutput; BErrorOutput* fErrorOutput;
int fFD; BPositionIO* fFile;
off_t fHeapOffset; off_t fHeapOffset;
uint64 fCompressedHeapSize; uint64 fCompressedHeapSize;
uint64 fUncompressedHeapSize; uint64 fUncompressedHeapSize;
@@ -25,7 +25,7 @@ namespace BPrivate {
class PackageFileHeapReader : public PackageFileHeapAccessorBase { class PackageFileHeapReader : public PackageFileHeapAccessorBase {
public: public:
PackageFileHeapReader(BErrorOutput* errorOutput, PackageFileHeapReader(BErrorOutput* errorOutput,
int fd, off_t heapOffset, BPositionIO* file, off_t heapOffset,
off_t compressedHeapSize, off_t compressedHeapSize,
uint64 uncompressedHeapSize, uint64 uncompressedHeapSize,
DecompressionAlgorithmOwner* DecompressionAlgorithmOwner*
@@ -35,7 +35,7 @@ class PackageFileHeapReader;
class PackageFileHeapWriter : public PackageFileHeapAccessorBase { class PackageFileHeapWriter : public PackageFileHeapAccessorBase {
public: public:
PackageFileHeapWriter(BErrorOutput* errorOutput, PackageFileHeapWriter(BErrorOutput* errorOutput,
int fd, off_t heapOffset, BPositionIO* file, off_t heapOffset,
CompressionAlgorithmOwner* CompressionAlgorithmOwner*
compressionAlgorithm, compressionAlgorithm,
DecompressionAlgorithmOwner* DecompressionAlgorithmOwner*
@@ -33,12 +33,14 @@ public:
status_t Init(const char* fileName, uint32 flags); status_t Init(const char* fileName, uint32 flags);
status_t Init(int fd, bool keepFD, uint32 flags); status_t Init(int fd, bool keepFD, uint32 flags);
status_t Init(BPositionIO* file, bool keepFile,
uint32 flags);
status_t ParseContent( status_t ParseContent(
BPackageContentHandler* contentHandler); BPackageContentHandler* contentHandler);
status_t ParseContent(BLowLevelPackageContentHandler* status_t ParseContent(BLowLevelPackageContentHandler*
contentHandler); contentHandler);
int PackageFileFD() const; BPositionIO* PackageFile() const;
uint64 HeapOffset() const; uint64 HeapOffset() const;
uint64 HeapSize() const; uint64 HeapSize() const;
@@ -77,10 +79,10 @@ private:
}; };
inline int inline BPositionIO*
PackageReaderImpl::PackageFileFD() const PackageReaderImpl::PackageFile() const
{ {
return FD(); return File();
} }
+27 -26
View File
@@ -1,5 +1,5 @@
/* /*
* Copyright 2009-2013, Ingo Weinhold, [email protected]. * Copyright 2009-2014, Ingo Weinhold, [email protected].
* Copyright 2011, Oliver Tappe <[email protected]> * Copyright 2011, Oliver Tappe <[email protected]>
* Distributed under the terms of the MIT License. * Distributed under the terms of the MIT License.
*/ */
@@ -11,7 +11,7 @@
#include <sys/stat.h> #include <sys/stat.h>
#include <ByteOrder.h> #include <ByteOrder.h>
#include <SupportDefs.h> #include <DataIO.h>
#include <Array.h> #include <Array.h>
#include <util/SinglyLinkedList.h> #include <util/SinglyLinkedList.h>
@@ -77,7 +77,7 @@ protected:
BErrorOutput* errorOutput); BErrorOutput* errorOutput);
virtual ~ReaderImplBase(); virtual ~ReaderImplBase();
int FD() const; BPositionIO* File() const;
BErrorOutput* ErrorOutput() const; BErrorOutput* ErrorOutput() const;
@@ -93,14 +93,14 @@ protected:
// equals RawHeapReader(), if uncached // equals RawHeapReader(), if uncached
BAbstractBufferedDataReader* DetachHeapReader( BAbstractBufferedDataReader* DetachHeapReader(
PackageFileHeapReader** _rawHeapReader PackageFileHeapReader*& _rawHeapReader);
= NULL);
// Detaches both raw and (if applicable) // Detaches both raw and (if applicable)
// cached heap reader. The called gains // cached heap reader. The called gains
// ownership. The FD may need to be set on // ownership of both. The file may need to
// the raw heap reader, if it shall be used // be set on the raw heap reader, if it
// after destroying this object and Init() // shall be used after destroying this
// has been called with keepFD == true. // object and Init() has been called with
// keepFile == true.
protected: protected:
class AttributeHandlerContext; class AttributeHandlerContext;
@@ -122,8 +122,8 @@ protected:
protected: protected:
template<typename Header, uint32 kMagic, uint16 kVersion, template<typename Header, uint32 kMagic, uint16 kVersion,
uint16 kMinorVersion> uint16 kMinorVersion>
status_t Init(int fd, bool keepFD, Header& header, status_t Init(BPositionIO* file, bool keepFile,
uint32 flags); Header& header, uint32 flags);
status_t InitHeapReader(uint32 compression, status_t InitHeapReader(uint32 compression,
uint32 chunkSize, off_t offset, uint32 chunkSize, off_t offset,
uint64 compressedSize, uint64 compressedSize,
@@ -169,7 +169,7 @@ protected:
PackageFileSection fPackageAttributesSection; PackageFileSection fPackageAttributesSection;
private: private:
status_t _Init(int fd, bool keepFD); status_t _Init(BPositionIO* file, bool keepFile);
status_t _ParseAttributeTree( status_t _ParseAttributeTree(
AttributeHandlerContext* context); AttributeHandlerContext* context);
@@ -190,8 +190,8 @@ private:
private: private:
const char* fFileType; const char* fFileType;
BErrorOutput* fErrorOutput; BErrorOutput* fErrorOutput;
int fFD; BPositionIO* fFile;
bool fOwnsFD; bool fOwnsFile;
uint16 fMinorFormatVersion; uint16 fMinorFormatVersion;
uint16 fCurrentMinorFormatVersion; uint16 fCurrentMinorFormatVersion;
@@ -429,17 +429,18 @@ private:
template<typename Header, uint32 kMagic, uint16 kVersion, uint16 kMinorVersion> template<typename Header, uint32 kMagic, uint16 kVersion, uint16 kMinorVersion>
status_t status_t
ReaderImplBase::Init(int fd, bool keepFD, Header& header, uint32 flags) ReaderImplBase::Init(BPositionIO* file, bool keepFile, Header& header, uint32 flags)
{ {
status_t error = _Init(fd, keepFD); status_t error = _Init(file, keepFile);
if (error != B_OK) if (error != B_OK)
return error; return error;
// stat the file // get the file size
struct stat st; off_t fileSize;
if (fstat(FD(), &st) < 0) { error = fFile->GetSize(&fileSize);
ErrorOutput()->PrintError("Error: Failed to access %s file: %s\n", if (error != B_OK) {
fFileType, strerror(errno)); ErrorOutput()->PrintError("Error: Failed to get size of %s file: %s\n",
fFileType, strerror(error));
return errno; return errno;
} }
@@ -479,10 +480,10 @@ ReaderImplBase::Init(int fd, bool keepFD, Header& header, uint32 flags)
// total size // total size
uint64 totalSize = B_BENDIAN_TO_HOST_INT64(header.total_size); uint64 totalSize = B_BENDIAN_TO_HOST_INT64(header.total_size);
if (totalSize != (uint64)st.st_size) { if (totalSize != (uint64)fileSize) {
ErrorOutput()->PrintError("Error: Invalid %s file: Total size in " ErrorOutput()->PrintError("Error: Invalid %s file: Total size in "
"header (%" B_PRIu64 ") doesn't agree with total file size (%" "header (%" B_PRIu64 ") doesn't agree with total file size (%"
B_PRIdOFF ")\n", fFileType, totalSize, st.st_size); B_PRIdOFF ")\n", fFileType, totalSize, fileSize);
return B_BAD_DATA; return B_BAD_DATA;
} }
@@ -510,10 +511,10 @@ ReaderImplBase::Init(int fd, bool keepFD, Header& header, uint32 flags)
} }
inline int inline BPositionIO*
ReaderImplBase::FD() const ReaderImplBase::File() const
{ {
return fFD; return fFile;
} }
@@ -30,6 +30,7 @@ public:
status_t Init(const char* fileName); status_t Init(const char* fileName);
status_t Init(int fd, bool keepFD); status_t Init(int fd, bool keepFD);
status_t Init(BPositionIO* file, bool keepFile);
status_t GetRepositoryInfo( status_t GetRepositoryInfo(
BRepositoryInfo* _repositoryInfo) const; BRepositoryInfo* _repositoryInfo) const;
@@ -149,7 +149,7 @@ protected:
off_t offset); off_t offset);
// writes to the file directly // writes to the file directly
inline int FD() const; inline BPositionIO* File() const;
inline uint32 Flags() const; inline uint32 Flags() const;
inline const BPackageWriterParameters& Parameters() const; inline const BPackageWriterParameters& Parameters() const;
@@ -187,7 +187,7 @@ private:
BErrorOutput* fErrorOutput; BErrorOutput* fErrorOutput;
const char* fFileName; const char* fFileName;
BPackageWriterParameters fParameters; BPackageWriterParameters fParameters;
int fFD; BPositionIO* fFile;
bool fFinished; bool fFinished;
StringCache fPackageStringCache; StringCache fPackageStringCache;
@@ -217,10 +217,10 @@ WriterImplBase::WriteBuffer(const void* data, size_t size)
} }
inline int inline BPositionIO*
WriterImplBase::FD() const WriterImplBase::File() const
{ {
return fFD; return fFile;
} }
@@ -110,6 +110,10 @@ local libSharedSources =
NaturalCompare.cpp NaturalCompare.cpp
; ;
local storageKitSources =
FdIO.cpp
;
local supportKitSources = local supportKitSources =
CompressionAlgorithm.cpp CompressionAlgorithm.cpp
ZlibCompressionAlgorithm.cpp ZlibCompressionAlgorithm.cpp
@@ -122,6 +126,7 @@ KernelAddon packagefs
$(HAIKU_PACKAGE_FS_PACKAGE_READER_SOURCES) $(HAIKU_PACKAGE_FS_PACKAGE_READER_SOURCES)
$(HAIKU_PACKAGE_FS_PACKAGE_READER_SOURCES_V1) $(HAIKU_PACKAGE_FS_PACKAGE_READER_SOURCES_V1)
$(libSharedSources) $(libSharedSources)
$(storageKitSources)
$(supportKitSources) $(supportKitSources)
: $(TARGET_KERNEL_LIBSUPC++) kernel_libz.a : $(TARGET_KERNEL_LIBSUPC++) kernel_libz.a
@@ -136,5 +141,7 @@ SEARCH on [ FGristFiles $(HAIKU_PACKAGE_FS_PACKAGE_READER_SOURCES_V1) ]
+= [ FDirName $(HAIKU_TOP) src kits package hpkg v1 ] ; += [ FDirName $(HAIKU_TOP) src kits package hpkg v1 ] ;
SEARCH on [ FGristFiles $(libSharedSources) ] SEARCH on [ FGristFiles $(libSharedSources) ]
+= [ FDirName $(HAIKU_TOP) src kits shared ] ; += [ FDirName $(HAIKU_TOP) src kits shared ] ;
SEARCH on [ FGristFiles $(storageKitSources) ]
+= [ FDirName $(HAIKU_TOP) src kits storage ] ;
SEARCH on [ FGristFiles $(supportKitSources) ] SEARCH on [ FGristFiles $(supportKitSources) ]
+= [ FDirName $(HAIKU_TOP) src kits support ] ; += [ FDirName $(HAIKU_TOP) src kits support ] ;
@@ -20,6 +20,7 @@
#include <package/hpkg/v1/PackageEntryAttribute.h> #include <package/hpkg/v1/PackageEntryAttribute.h>
#include <AutoDeleter.h> #include <AutoDeleter.h>
#include <FdIO.h>
#include <package/hpkg/PackageFileHeapReader.h> #include <package/hpkg/PackageFileHeapReader.h>
#include <package/hpkg/PackageReaderImpl.h> #include <package/hpkg/PackageReaderImpl.h>
#include <package/hpkg/v1/PackageReaderImpl.h> #include <package/hpkg/v1/PackageReaderImpl.h>
@@ -687,7 +688,7 @@ private:
struct Package::HeapReaderV2 : public HeapReader, public CachedDataReader, struct Package::HeapReaderV2 : public HeapReader, public CachedDataReader,
private BErrorOutput { private BErrorOutput, private BFdIO {
public: public:
HeapReaderV2() HeapReaderV2()
: :
@@ -706,8 +707,10 @@ public:
if (fHeapReader == NULL) if (fHeapReader == NULL)
return B_NO_MEMORY; return B_NO_MEMORY;
BFdIO::SetTo(fd, false);
fHeapReader->SetErrorOutput(this); fHeapReader->SetErrorOutput(this);
fHeapReader->SetFD(fd); fHeapReader->SetFile(this);
status_t error = CachedDataReader::Init(fHeapReader, status_t error = CachedDataReader::Init(fHeapReader,
fHeapReader->UncompressedHeapSize()); fHeapReader->UncompressedHeapSize());
@@ -719,7 +722,7 @@ public:
virtual void UpdateFD(int fd) virtual void UpdateFD(int fd)
{ {
fHeapReader->SetFD(fd); BFdIO::SetTo(fd, false);
} }
virtual status_t CreateDataReader(const PackageData& data, virtual status_t CreateDataReader(const PackageData& data,
@@ -749,7 +752,8 @@ struct Package::CachingPackageReader : public PackageReaderImpl {
CachingPackageReader(BErrorOutput* errorOutput) CachingPackageReader(BErrorOutput* errorOutput)
: :
PackageReaderImpl(errorOutput), PackageReaderImpl(errorOutput),
fCachedHeapReader(NULL) fCachedHeapReader(NULL),
fFD(-1)
{ {
} }
@@ -757,6 +761,12 @@ struct Package::CachingPackageReader : public PackageReaderImpl {
{ {
} }
status_t Init(int fd, bool keepFD, uint32 flags)
{
fFD = fd;
return PackageReaderImpl::Init(fd, keepFD, flags);
}
virtual status_t CreateCachedHeapReader( virtual status_t CreateCachedHeapReader(
PackageFileHeapReader* rawHeapReader, PackageFileHeapReader* rawHeapReader,
BAbstractBufferedDataReader*& _cachedReader) BAbstractBufferedDataReader*& _cachedReader)
@@ -765,7 +775,7 @@ struct Package::CachingPackageReader : public PackageReaderImpl {
if (fCachedHeapReader == NULL) if (fCachedHeapReader == NULL)
RETURN_ERROR(B_NO_MEMORY); RETURN_ERROR(B_NO_MEMORY);
status_t error = fCachedHeapReader->Init(rawHeapReader, FD()); status_t error = fCachedHeapReader->Init(rawHeapReader, fFD);
if (error != B_OK) if (error != B_OK)
RETURN_ERROR(error); RETURN_ERROR(error);
@@ -775,7 +785,12 @@ struct Package::CachingPackageReader : public PackageReaderImpl {
HeapReaderV2* DetachCachedHeapReader() HeapReaderV2* DetachCachedHeapReader()
{ {
DetachHeapReader(); PackageFileHeapReader* rawHeapReader;
DetachHeapReader(rawHeapReader);
// We don't need the raw heap reader anymore, since the cached reader
// is not a wrapper around it, but completely independent from it.
delete rawHeapReader;
HeapReaderV2* cachedHeapReader = fCachedHeapReader; HeapReaderV2* cachedHeapReader = fCachedHeapReader;
fCachedHeapReader = NULL; fCachedHeapReader = NULL;
@@ -784,6 +799,7 @@ struct Package::CachingPackageReader : public PackageReaderImpl {
private: private:
HeapReaderV2* fCachedHeapReader; HeapReaderV2* fCachedHeapReader;
int fFD;
}; };
@@ -6,7 +6,6 @@
#include <package/hpkg/PackageFileHeapAccessorBase.h> #include <package/hpkg/PackageFileHeapAccessorBase.h>
#include <errno.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
@@ -122,11 +121,11 @@ PackageFileHeapAccessorBase::OffsetArray::Init(size_t totalChunkCount,
PackageFileHeapAccessorBase::PackageFileHeapAccessorBase( PackageFileHeapAccessorBase::PackageFileHeapAccessorBase(
BErrorOutput* errorOutput, int fd, off_t heapOffset, BErrorOutput* errorOutput, BPositionIO* file, off_t heapOffset,
DecompressionAlgorithmOwner* decompressionAlgorithm) DecompressionAlgorithmOwner* decompressionAlgorithm)
: :
fErrorOutput(errorOutput), fErrorOutput(errorOutput),
fFD(fd), fFile(file),
fHeapOffset(heapOffset), fHeapOffset(heapOffset),
fCompressedHeapSize(0), fCompressedHeapSize(0),
fUncompressedHeapSize(0), fUncompressedHeapSize(0),
@@ -252,16 +251,12 @@ status_t
PackageFileHeapAccessorBase::ReadFileData(uint64 offset, void* buffer, PackageFileHeapAccessorBase::ReadFileData(uint64 offset, void* buffer,
size_t size) size_t size)
{ {
ssize_t bytesRead = pread(fFD, buffer, size, fHeapOffset + (off_t)offset); status_t error = fFile->ReadAtExactly(fHeapOffset + (off_t)offset, buffer,
if (bytesRead < 0) { size);
if (error != B_OK) {
fErrorOutput->PrintError("ReadFileData(%" B_PRIu64 ", %p, %zu) failed " fErrorOutput->PrintError("ReadFileData(%" B_PRIu64 ", %p, %zu) failed "
"to read data: %s\n", offset, buffer, size, strerror(errno)); "to read data: %s\n", offset, buffer, size, strerror(error));
return errno; return error;
}
if ((size_t)bytesRead != size) {
fErrorOutput->PrintError("ReadFileData(%" B_PRIu64 ", %p, %zu) could "
"read only %zd bytes\n", offset, buffer, size, bytesRead);
return B_ERROR;
} }
return B_OK; return B_OK;
@@ -23,11 +23,12 @@ namespace BHPKG {
namespace BPrivate { namespace BPrivate {
PackageFileHeapReader::PackageFileHeapReader(BErrorOutput* errorOutput, int fd, PackageFileHeapReader::PackageFileHeapReader(BErrorOutput* errorOutput,
off_t heapOffset, off_t compressedHeapSize, uint64 uncompressedHeapSize, BPositionIO* file, off_t heapOffset, off_t compressedHeapSize,
uint64 uncompressedHeapSize,
DecompressionAlgorithmOwner* decompressionAlgorithm) DecompressionAlgorithmOwner* decompressionAlgorithm)
: :
PackageFileHeapAccessorBase(errorOutput, fd, heapOffset, PackageFileHeapAccessorBase(errorOutput, file, heapOffset,
decompressionAlgorithm), decompressionAlgorithm),
fOffsets() fOffsets()
{ {
@@ -118,7 +119,7 @@ PackageFileHeapReader*
PackageFileHeapReader::Clone() const PackageFileHeapReader::Clone() const
{ {
PackageFileHeapReader* clone = new(std::nothrow) PackageFileHeapReader( PackageFileHeapReader* clone = new(std::nothrow) PackageFileHeapReader(
fErrorOutput, fFD, fHeapOffset, fCompressedHeapSize, fErrorOutput, fFile, fHeapOffset, fCompressedHeapSize,
fUncompressedHeapSize, fDecompressionAlgorithm); fUncompressedHeapSize, fDecompressionAlgorithm);
if (clone == NULL) if (clone == NULL)
return NULL; return NULL;
+10 -15
View File
@@ -6,8 +6,6 @@
#include <package/hpkg/PackageFileHeapWriter.h> #include <package/hpkg/PackageFileHeapWriter.h>
#include <errno.h>
#include <algorithm> #include <algorithm>
#include <new> #include <new>
@@ -196,11 +194,12 @@ private:
}; };
PackageFileHeapWriter::PackageFileHeapWriter(BErrorOutput* errorOutput, int fd, PackageFileHeapWriter::PackageFileHeapWriter(BErrorOutput* errorOutput,
off_t heapOffset, CompressionAlgorithmOwner* compressionAlgorithm, BPositionIO* file, off_t heapOffset,
CompressionAlgorithmOwner* compressionAlgorithm,
DecompressionAlgorithmOwner* decompressionAlgorithm) DecompressionAlgorithmOwner* decompressionAlgorithm)
: :
PackageFileHeapAccessorBase(errorOutput, fd, heapOffset, PackageFileHeapAccessorBase(errorOutput, file, heapOffset,
decompressionAlgorithm), decompressionAlgorithm),
fPendingDataBuffer(NULL), fPendingDataBuffer(NULL),
fCompressedDataBuffer(NULL), fCompressedDataBuffer(NULL),
@@ -580,18 +579,14 @@ PackageFileHeapWriter::_WriteDataCompressed(const void* data, size_t size)
status_t status_t
PackageFileHeapWriter::_WriteDataUncompressed(const void* data, size_t size) PackageFileHeapWriter::_WriteDataUncompressed(const void* data, size_t size)
{ {
ssize_t bytesWritten = pwrite(fFD, data, size, status_t error = fFile->WriteAtExactly(
fHeapOffset + (off_t)fCompressedHeapSize); fHeapOffset + (off_t)fCompressedHeapSize, data, size);
if (bytesWritten < 0) { if (error != B_OK) {
fErrorOutput->PrintError("Failed to write data: %s\n", strerror(errno)); fErrorOutput->PrintError("Failed to write data: %s\n", strerror(error));
return errno; return error;
}
if ((size_t)bytesWritten != size) {
fErrorOutput->PrintError("Failed to write all data\n");
return B_ERROR;
} }
fCompressedHeapSize += bytesWritten; fCompressedHeapSize += size;
return B_OK; return B_OK;
} }
+14 -4
View File
@@ -52,6 +52,16 @@ BPackageReader::Init(int fd, bool keepFD, uint32 flags)
} }
status_t
BPackageReader::Init(BPositionIO* file, bool keepFile, uint32 flags)
{
if (fImpl == NULL)
return B_NO_INIT;
return fImpl->Init(file, keepFile, flags);
}
status_t status_t
BPackageReader::ParseContent(BPackageContentHandler* contentHandler) BPackageReader::ParseContent(BPackageContentHandler* contentHandler)
{ {
@@ -72,13 +82,13 @@ BPackageReader::ParseContent(BLowLevelPackageContentHandler* contentHandler)
} }
int BPositionIO*
BPackageReader::PackageFileFD() BPackageReader::PackageFile() const
{ {
if (fImpl == NULL) if (fImpl == NULL)
return -1; return NULL;
return fImpl->PackageFileFD(); return fImpl->PackageFile();
} }
+17 -1
View File
@@ -20,6 +20,8 @@
#include <ByteOrder.h> #include <ByteOrder.h>
#include <FdIO.h>
#include <package/hpkg/HPKGDefsPrivate.h> #include <package/hpkg/HPKGDefsPrivate.h>
#include <package/hpkg/PackageData.h> #include <package/hpkg/PackageData.h>
@@ -331,10 +333,24 @@ PackageReaderImpl::Init(const char* fileName, uint32 flags)
status_t status_t
PackageReaderImpl::Init(int fd, bool keepFD, uint32 flags) PackageReaderImpl::Init(int fd, bool keepFD, uint32 flags)
{
BFdIO* file = new(std::nothrow) BFdIO(fd, keepFD);
if (file == NULL) {
if (keepFD && fd >= 0)
close(fd);
return B_NO_MEMORY;
}
return Init(file, true, flags);
}
status_t
PackageReaderImpl::Init(BPositionIO* file, bool keepFile, uint32 flags)
{ {
hpkg_header header; hpkg_header header;
status_t error = inherited::Init<hpkg_header, B_HPKG_MAGIC, B_HPKG_VERSION, status_t error = inherited::Init<hpkg_header, B_HPKG_MAGIC, B_HPKG_VERSION,
B_HPKG_MINOR_VERSION>(fd, keepFD, header, flags); B_HPKG_MINOR_VERSION>(file, keepFile, header, flags);
if (error != B_OK) if (error != B_OK)
return error; return error;
fHeapSize = UncompressedHeapSize(); fHeapSize = UncompressedHeapSize();
+3 -2
View File
@@ -648,7 +648,7 @@ PackageWriterImpl::_Init(const char* fileName,
// in update mode, parse the TOC // in update mode, parse the TOC
if ((Flags() & B_HPKG_WRITER_UPDATE_PACKAGE) != 0) { if ((Flags() & B_HPKG_WRITER_UPDATE_PACKAGE) != 0) {
PackageReaderImpl packageReader(fListener); PackageReaderImpl packageReader(fListener);
result = packageReader.Init(FD(), false, 0); result = packageReader.Init(File(), false, 0);
if (result != B_OK) if (result != B_OK)
return result; return result;
@@ -716,7 +716,8 @@ PackageWriterImpl::_Finish()
// can be greater when one or more files are shrunk. In creation mode it // can be greater when one or more files are shrunk. In creation mode it
// should already have the correct size. // should already have the correct size.
off_t totalSize = fHeapWriter->HeapOffset() + (off_t)compressedHeapSize; off_t totalSize = fHeapWriter->HeapOffset() + (off_t)compressedHeapSize;
if (ftruncate(FD(), totalSize) != 0) { error = File()->SetSize(totalSize);
if (error != B_OK) {
fListener->PrintError("Failed to truncate package file to new " fListener->PrintError("Failed to truncate package file to new "
"size: %s\n", strerror(errno)); "size: %s\n", strerror(errno));
return errno; return errno;
+17 -24
View File
@@ -764,8 +764,8 @@ ReaderImplBase::ReaderImplBase(const char* fileType, BErrorOutput* errorOutput)
fPackageAttributesSection("package attributes"), fPackageAttributesSection("package attributes"),
fFileType(fileType), fFileType(fileType),
fErrorOutput(errorOutput), fErrorOutput(errorOutput),
fFD(-1), fFile(NULL),
fOwnsFD(false), fOwnsFile(false),
fRawHeapReader(NULL), fRawHeapReader(NULL),
fHeapReader(NULL), fHeapReader(NULL),
fCurrentSection(NULL) fCurrentSection(NULL)
@@ -779,8 +779,8 @@ ReaderImplBase::~ReaderImplBase()
if (fRawHeapReader != fHeapReader) if (fRawHeapReader != fHeapReader)
delete fRawHeapReader; delete fRawHeapReader;
if (fOwnsFD && fFD >= 0) if (fOwnsFile)
close(fFD); delete fFile;
} }
@@ -792,13 +792,11 @@ ReaderImplBase::UncompressedHeapSize() const
BAbstractBufferedDataReader* BAbstractBufferedDataReader*
ReaderImplBase::DetachHeapReader(PackageFileHeapReader** _rawHeapReader) ReaderImplBase::DetachHeapReader(PackageFileHeapReader*& _rawHeapReader)
{ {
BAbstractBufferedDataReader* heapReader = fHeapReader; BAbstractBufferedDataReader* heapReader = fHeapReader;
_rawHeapReader = fRawHeapReader;
fHeapReader = NULL; fHeapReader = NULL;
if (_rawHeapReader != NULL)
*_rawHeapReader = fRawHeapReader;
fRawHeapReader = NULL; fRawHeapReader = NULL;
return heapReader; return heapReader;
@@ -827,8 +825,9 @@ ReaderImplBase::InitHeapReader(uint32 compression, uint32 chunkSize,
return B_NO_MEMORY; return B_NO_MEMORY;
} }
fRawHeapReader = new(std::nothrow) PackageFileHeapReader(fErrorOutput, fFD, fRawHeapReader = new(std::nothrow) PackageFileHeapReader(fErrorOutput,
offset, compressedSize, uncompressedSize, decompressionAlgorithm); fFile, offset, compressedSize, uncompressedSize,
decompressionAlgorithm);
if (fRawHeapReader == NULL) if (fRawHeapReader == NULL)
return B_NO_MEMORY; return B_NO_MEMORY;
@@ -1059,12 +1058,11 @@ ReaderImplBase::ParseAttributeTree(AttributeHandlerContext* context,
status_t status_t
ReaderImplBase::_Init(int fd, bool keepFD) ReaderImplBase::_Init(BPositionIO* file, bool keepFile)
{ {
fFD = fd; fFile = file;
fOwnsFD = keepFD; fOwnsFile = keepFile;
return fFile != NULL ? B_OK : B_BAD_VALUE;
return B_OK;
} }
@@ -1341,16 +1339,11 @@ ReaderImplBase::_ReadSectionBuffer(void* buffer, size_t size)
status_t status_t
ReaderImplBase::ReadBuffer(off_t offset, void* buffer, size_t size) ReaderImplBase::ReadBuffer(off_t offset, void* buffer, size_t size)
{ {
ssize_t bytesRead = pread(fFD, buffer, size, offset); status_t error = fFile->ReadAtExactly(offset, buffer, size);
if (bytesRead < 0) { if (error != B_OK) {
fErrorOutput->PrintError("_ReadBuffer(%p, %lu) failed to read data: " fErrorOutput->PrintError("_ReadBuffer(%p, %lu) failed to read data: "
"%s\n", buffer, size, strerror(errno)); "%s\n", buffer, size, strerror(error));
return errno; return error;
}
if ((size_t)bytesRead != size) {
fErrorOutput->PrintError("_ReadBuffer(%p, %lu) failed to read all "
"data\n", buffer, size);
return B_ERROR;
} }
return B_OK; return B_OK;
+18 -1
View File
@@ -18,6 +18,8 @@
#include <ByteOrder.h> #include <ByteOrder.h>
#include <Message.h> #include <Message.h>
#include <FdIO.h>
#include <package/hpkg/HPKGDefsPrivate.h> #include <package/hpkg/HPKGDefsPrivate.h>
#include <package/hpkg/RepositoryContentHandler.h> #include <package/hpkg/RepositoryContentHandler.h>
@@ -196,10 +198,25 @@ RepositoryReaderImpl::Init(const char* fileName)
status_t status_t
RepositoryReaderImpl::Init(int fd, bool keepFD) RepositoryReaderImpl::Init(int fd, bool keepFD)
{
BFdIO* file = new(std::nothrow) BFdIO(fd, keepFD);
if (file == NULL) {
if (keepFD && fd >= 0)
close(fd);
return B_NO_MEMORY;
}
return Init(file, true);
}
status_t
RepositoryReaderImpl::Init(BPositionIO* file, bool keepFile)
{ {
hpkg_repo_header header; hpkg_repo_header header;
status_t error = inherited::Init<hpkg_repo_header, B_HPKG_REPO_MAGIC, status_t error = inherited::Init<hpkg_repo_header, B_HPKG_REPO_MAGIC,
B_HPKG_REPO_VERSION, B_HPKG_REPO_MINOR_VERSION>(fd, keepFD, header, 0); B_HPKG_REPO_VERSION, B_HPKG_REPO_MINOR_VERSION>(file, keepFile, header,
0);
if (error != B_OK) if (error != B_OK)
return error; return error;
+14 -16
View File
@@ -16,6 +16,7 @@
#include <new> #include <new>
#include <ByteOrder.h> #include <ByteOrder.h>
#include <File.h>
#include <AutoDeleter.h> #include <AutoDeleter.h>
#include <ZlibCompressionAlgorithm.h> #include <ZlibCompressionAlgorithm.h>
@@ -226,7 +227,7 @@ WriterImplBase::WriterImplBase(const char* fileType, BErrorOutput* errorOutput)
fErrorOutput(errorOutput), fErrorOutput(errorOutput),
fFileName(NULL), fFileName(NULL),
fParameters(), fParameters(),
fFD(-1), fFile(NULL),
fFinished(false) fFinished(false)
{ {
} }
@@ -240,8 +241,7 @@ WriterImplBase::~WriterImplBase()
delete fDecompressionAlgorithm; delete fDecompressionAlgorithm;
delete fDecompressionParameters; delete fDecompressionParameters;
if (fFD >= 0) delete fFile;
close(fFD);
if (!fFinished && fFileName != NULL if (!fFinished && fFileName != NULL
&& (Flags() & B_HPKG_WRITER_UPDATE_PACKAGE) == 0) { && (Flags() & B_HPKG_WRITER_UPDATE_PACKAGE) == 0) {
@@ -264,13 +264,16 @@ WriterImplBase::Init(const char* fileName, size_t headerSize,
if ((Flags() & B_HPKG_WRITER_UPDATE_PACKAGE) == 0) if ((Flags() & B_HPKG_WRITER_UPDATE_PACKAGE) == 0)
openMode |= O_CREAT | O_TRUNC; openMode |= O_CREAT | O_TRUNC;
fFD = open(fileName, openMode, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); BFile* file = new BFile;
if (fFD < 0) { status_t error = file->SetTo(fileName, openMode);
if (error != B_OK) {
fErrorOutput->PrintError("Failed to open %s file \"%s\": %s\n", fErrorOutput->PrintError("Failed to open %s file \"%s\": %s\n",
fFileType, fileName, strerror(errno)); fFileType, fileName, strerror(errno));
return errno; delete file;
return error;
} }
fFile = file;
fFileName = fileName; fFileName = fileName;
DecompressionAlgorithmOwner* decompressionAlgorithm DecompressionAlgorithmOwner* decompressionAlgorithm
@@ -305,7 +308,7 @@ WriterImplBase::Init(const char* fileName, size_t headerSize,
compressionAlgorithm, true); compressionAlgorithm, true);
// create heap writer // create heap writer
fHeapWriter = new PackageFileHeapWriter(fErrorOutput, FD(), headerSize, fHeapWriter = new PackageFileHeapWriter(fErrorOutput, fFile, headerSize,
compressionAlgorithm, decompressionAlgorithm); compressionAlgorithm, decompressionAlgorithm);
fHeapWriter->Init(); fHeapWriter->Init();
@@ -717,17 +720,12 @@ WriterImplBase::WriteUnsignedLEB128(uint64 value)
void void
WriterImplBase::RawWriteBuffer(const void* buffer, size_t size, off_t offset) WriterImplBase::RawWriteBuffer(const void* buffer, size_t size, off_t offset)
{ {
ssize_t bytesWritten = pwrite(fFD, buffer, size, offset); status_t error = fFile->WriteAtExactly(offset, buffer, size);
if (bytesWritten < 0) { if (error != B_OK) {
fErrorOutput->PrintError( fErrorOutput->PrintError(
"RawWriteBuffer(%p, %lu) failed to write data: %s\n", buffer, size, "RawWriteBuffer(%p, %lu) failed to write data: %s\n", buffer, size,
strerror(errno)); strerror(error));
throw status_t(errno); throw error;
}
if ((size_t)bytesWritten != size) {
fErrorOutput->PrintError(
"RawWriteBuffer(%p, %lu) failed to write all data\n", buffer, size);
throw status_t(B_ERROR);
} }
} }
@@ -1,7 +1,7 @@
SubDir HAIKU_TOP src system boot loader file_systems packagefs ; SubDir HAIKU_TOP src system boot loader file_systems packagefs ;
UsePrivateHeaders [ FDirName kernel boot platform $(TARGET_BOOT_PLATFORM) ] ; UsePrivateHeaders [ FDirName kernel boot platform $(TARGET_BOOT_PLATFORM) ] ;
UsePrivateHeaders kernel shared support ; UsePrivateHeaders kernel shared storage support ;
UseBuildFeatureHeaders zlib ; UseBuildFeatureHeaders zlib ;
DEFINES += _BOOT_MODE ; DEFINES += _BOOT_MODE ;
@@ -13,6 +13,7 @@ SubDirC++Flags -fno-rtti -include $(kernelC++Header) ;
SEARCH_SOURCE += [ FDirName $(HAIKU_TOP) src kits package ] ; SEARCH_SOURCE += [ FDirName $(HAIKU_TOP) src kits package ] ;
SEARCH_SOURCE += [ FDirName $(HAIKU_TOP) src kits package hpkg ] ; SEARCH_SOURCE += [ FDirName $(HAIKU_TOP) src kits package hpkg ] ;
SEARCH_SOURCE += [ FDirName $(HAIKU_TOP) src kits storage ] ;
SEARCH_SOURCE += [ FDirName $(HAIKU_TOP) src kits support ] ; SEARCH_SOURCE += [ FDirName $(HAIKU_TOP) src kits support ] ;
@@ -20,8 +21,6 @@ BootStaticLibrary boot_packagefs :
packagefs.cpp packagefs.cpp
PackageSettingsItem.cpp PackageSettingsItem.cpp
# package kit
# package kit/hpkg # package kit/hpkg
BlockBufferPool.cpp BlockBufferPool.cpp
BlockBufferPoolImpl.cpp BlockBufferPoolImpl.cpp
@@ -41,8 +40,10 @@ BootStaticLibrary boot_packagefs :
PackageReaderImpl.cpp PackageReaderImpl.cpp
ReaderImplBase.cpp ReaderImplBase.cpp
# support kit # storage kit
FdIO.cpp
# support kit
CompressionAlgorithm.cpp CompressionAlgorithm.cpp
ZlibCompressionAlgorithm.cpp ZlibCompressionAlgorithm.cpp
@@ -1,5 +1,5 @@
/* /*
* Copyright 2011-2013, Ingo Weinhold, ingo_weinhold@gmx.de. * Copyright 2011-2014, Ingo Weinhold, ingo_weinhold@gmx.de.
* Distributed under the terms of the MIT License. * Distributed under the terms of the MIT License.
*/ */
@@ -18,6 +18,7 @@
#include <package/hpkg/PackageReaderImpl.h> #include <package/hpkg/PackageReaderImpl.h>
#include <AutoDeleter.h> #include <AutoDeleter.h>
#include <FdIO.h>
#include <util/DoublyLinkedList.h> #include <util/DoublyLinkedList.h>
@@ -299,16 +300,14 @@ struct PackageVolume : BReferenceable, private PackageLoaderErrorOutput {
fNextNodeID(1), fNextNodeID(1),
fRootDirectory(this, S_IFDIR), fRootDirectory(this, S_IFDIR),
fHeapReader(NULL), fHeapReader(NULL),
fFD(-1) fFile(NULL)
{ {
} }
~PackageVolume() ~PackageVolume()
{ {
delete fHeapReader; delete fHeapReader;
delete fFile;
if (fFD >= 0)
close(fFD);
} }
status_t Init(int fd, const PackageFileHeapReader* heapReader) status_t Init(int fd, const PackageFileHeapReader* heapReader)
@@ -318,17 +317,23 @@ struct PackageVolume : BReferenceable, private PackageLoaderErrorOutput {
if (error != B_OK) if (error != B_OK)
return error; return error;
fFD = dup(fd); fd = dup(fd);
if (fFD < 0) if (fd < 0)
return errno; return errno;
fFile = new(std::nothrow) BFdIO(fd, true);
if (fFile == NULL) {
close(fd);
return B_NO_MEMORY;
}
// clone a heap reader and adjust it for our use // clone a heap reader and adjust it for our use
fHeapReader = heapReader->Clone(); fHeapReader = heapReader->Clone();
if (fHeapReader == NULL) if (fHeapReader == NULL)
return B_NO_MEMORY; return B_NO_MEMORY;
fHeapReader->SetErrorOutput(this); fHeapReader->SetErrorOutput(this);
fHeapReader->SetFD(fFD); fHeapReader->SetFile(fFile);
return B_OK; return B_OK;
} }
@@ -354,7 +359,7 @@ private:
ino_t fNextNodeID; ino_t fNextNodeID;
PackageDirectory fRootDirectory; PackageDirectory fRootDirectory;
PackageFileHeapReader* fHeapReader; PackageFileHeapReader* fHeapReader;
int fFD; BPositionIO* fFile;
}; };