diff --git a/src/add-ons/kernel/file_systems/packagefs/package/Package.cpp b/src/add-ons/kernel/file_systems/packagefs/package/Package.cpp index 318ea90138..8f881c74eb 100644 --- a/src/add-ons/kernel/file_systems/packagefs/package/Package.cpp +++ b/src/add-ons/kernel/file_systems/packagefs/package/Package.cpp @@ -761,6 +761,7 @@ Package::Package(::Volume* volume, dev_t deviceID, ino_t nodeID) fFileName(), fName(), fInstallPath(), + fVersionedName(), fVersion(NULL), fArchitecture(B_PACKAGE_ARCHITECTURE_ENUM_COUNT), fLinkDirectory(NULL), @@ -806,59 +807,11 @@ Package::Init(const char* fileName) status_t Package::Load() { - // open package file - int fd = Open(); - if (fd < 0) - RETURN_ERROR(fd); - PackageCloser packageCloser(this); - - // initialize package reader - LoaderErrorOutput errorOutput(this); - - // try current package file format version - { - CachingPackageReader packageReader(&errorOutput); - status_t error = packageReader.Init(fd, false, - BHPKG::B_HPKG_READER_DONT_PRINT_VERSION_MISMATCH_MESSAGE); - if (error == B_OK) { - // parse content - LoaderContentHandler handler(this); - error = handler.Init(); - if (error != B_OK) - RETURN_ERROR(error); - - error = packageReader.ParseContent(&handler); - if (error != B_OK) - RETURN_ERROR(error); - - // get the heap reader - fHeapReader = packageReader.DetachCachedHeapReader(); - return B_OK; - } - - if (error != B_MISMATCHED_VALUES) - RETURN_ERROR(error); - } - - // try package file format version 1 - PackageReaderImplV1 packageReader(&errorOutput); - status_t error = packageReader.Init(fd, false); + status_t error = _Load(); if (error != B_OK) - RETURN_ERROR(error); + return error; - // parse content - LoaderContentHandlerV1 handler(this); - error = handler.Init(); - if (error != B_OK) - RETURN_ERROR(error); - - error = packageReader.ParseContent(&handler); - if (error != B_OK) - RETURN_ERROR(error); - - // create a heap reader - fHeapReader = new(std::nothrow) HeapReaderV1(fd); - if (fHeapReader == NULL) + if (!_InitVersionedName()) RETURN_ERROR(B_NO_MEMORY); return B_OK; @@ -991,3 +944,93 @@ Package::CreateDataReader(const PackageData& data, return fHeapReader->CreateDataReader(data, _reader); } + + +status_t +Package::_Load() +{ + // open package file + int fd = Open(); + if (fd < 0) + RETURN_ERROR(fd); + PackageCloser packageCloser(this); + + // initialize package reader + LoaderErrorOutput errorOutput(this); + + // try current package file format version + { + CachingPackageReader packageReader(&errorOutput); + status_t error = packageReader.Init(fd, false, + BHPKG::B_HPKG_READER_DONT_PRINT_VERSION_MISMATCH_MESSAGE); + if (error == B_OK) { + // parse content + LoaderContentHandler handler(this); + error = handler.Init(); + if (error != B_OK) + RETURN_ERROR(error); + + error = packageReader.ParseContent(&handler); + if (error != B_OK) + RETURN_ERROR(error); + + // get the heap reader + fHeapReader = packageReader.DetachCachedHeapReader(); + return B_OK; + } + + if (error != B_MISMATCHED_VALUES) + RETURN_ERROR(error); + } + + // try package file format version 1 + PackageReaderImplV1 packageReader(&errorOutput); + status_t error = packageReader.Init(fd, false); + if (error != B_OK) + RETURN_ERROR(error); + + // parse content + LoaderContentHandlerV1 handler(this); + error = handler.Init(); + if (error != B_OK) + RETURN_ERROR(error); + + error = packageReader.ParseContent(&handler); + if (error != B_OK) + RETURN_ERROR(error); + + // create a heap reader + fHeapReader = new(std::nothrow) HeapReaderV1(fd); + if (fHeapReader == NULL) + RETURN_ERROR(B_NO_MEMORY); + + return B_OK; +} + + +bool +Package::_InitVersionedName() +{ + // compute the allocation size needed for the versioned name + size_t nameLength = strlen(fName); + size_t size = nameLength + 1; + + if (fVersion != NULL) { + size += 1 + fVersion->ToString(NULL, 0); + // + 1 for the '-' + } + + // allocate the name and compose it + char* name = (char*)malloc(size); + if (name == NULL) + return false; + MemoryDeleter nameDeleter(name); + + memcpy(name, fName, nameLength + 1); + if (fVersion != NULL) { + name[nameLength] = '-'; + fVersion->ToString(name + nameLength + 1, size - nameLength - 1); + } + + return fVersionedName.SetTo(name); +} diff --git a/src/add-ons/kernel/file_systems/packagefs/package/Package.h b/src/add-ons/kernel/file_systems/packagefs/package/Package.h index caf2fb4097..210264ed5f 100644 --- a/src/add-ons/kernel/file_systems/packagefs/package/Package.h +++ b/src/add-ons/kernel/file_systems/packagefs/package/Package.h @@ -48,6 +48,9 @@ public: void SetName(const String& name); const String& Name() const { return fName; } + const String& VersionedName() const + { return fVersionedName; } + dev_t DeviceID() const { return fDeviceID; } ino_t NodeID() const @@ -102,12 +105,17 @@ private: struct HeapReaderV2; struct CachingPackageReader; +private: + status_t _Load(); + bool _InitVersionedName(); + private: mutex fLock; ::Volume* fVolume; String fFileName; String fName; String fInstallPath; + String fVersionedName; ::Version* fVersion; BPackageArchitecture fArchitecture; PackageLinkDirectory* fLinkDirectory; diff --git a/src/add-ons/kernel/file_systems/packagefs/package_links/PackageLinkDirectory.cpp b/src/add-ons/kernel/file_systems/packagefs/package_links/PackageLinkDirectory.cpp index ae2d171127..d23792761a 100644 --- a/src/add-ons/kernel/file_systems/packagefs/package_links/PackageLinkDirectory.cpp +++ b/src/add-ons/kernel/file_systems/packagefs/package_links/PackageLinkDirectory.cpp @@ -46,34 +46,8 @@ PackageLinkDirectory::~PackageLinkDirectory() status_t PackageLinkDirectory::Init(Directory* parent, Package* package) { - // compute the allocation size needed for the versioned name - size_t nameLength = strlen(package->Name()); - size_t size = nameLength + 1; - - Version* version = package->Version(); - if (version != NULL) { - size += 1 + version->ToString(NULL, 0); - // + 1 for the '-' - } - - // allocate the name and compose it - char* name = (char*)malloc(size); - if (name == NULL) - return B_NO_MEMORY; - MemoryDeleter nameDeleter(name); - - memcpy(name, package->Name(), nameLength + 1); - if (version != NULL) { - name[nameLength] = '-'; - version->ToString(name + nameLength + 1, size - nameLength - 1); - } - - String nameString; - if (!nameString.SetTo(name)) - return B_NO_MEMORY; - // init the directory/node - status_t error = Init(parent, nameString); + status_t error = Init(parent, package->VersionedName()); if (error != B_OK) RETURN_ERROR(error);