mirror of
https://github.com/gnustep/libs-base.git
synced 2025-04-23 09:04:13 +00:00
Implemented experimental library resource bundle versioning
git-svn-id: svn+ssh://svn.gna.org/svn/gnustep/libs/base/trunk@24841 72102866-910b-0410-8b05-ffd578937521
This commit is contained in:
parent
c2d8270d8c
commit
c641207ab8
8 changed files with 177 additions and 41 deletions
39
ChangeLog
39
ChangeLog
|
@ -1,3 +1,42 @@
|
|||
2007-03-09 Nicola Pero <nicola.pero@meta-innovation.com>
|
||||
|
||||
Implemented library resource bundle versioning. Updated
|
||||
gnustep-base to use versioned resources.
|
||||
* Source/NSBundle ([+bundleForLibrary:version]): New method.
|
||||
Allow to request the resource bundle for a specific version.
|
||||
Changed bundle resource location to be
|
||||
GNUSTEP_LIBRARY/Libraries/<libraryName>/Versions/<interfaceVersion>/Resources
|
||||
to allow versioned resources and be similar to framework resources
|
||||
- will be handy in the future. Fall back to the old unversioned
|
||||
bundle at GNUSTEP_LIBRARY/Libraries/Resources/<libraryName> if no
|
||||
specific version is required and no versioned bundle can be found.
|
||||
([+bundleForLibrary:]): Implemented in terms of
|
||||
+bundleForLibrary:version:. Should be backwards compatible if
|
||||
you're not using resource versioning yet.
|
||||
([+initialize]): When creating _gnustep_bundle, use
|
||||
[+bundleForLibrary:version:] to get the appropriate version of the
|
||||
bundle.
|
||||
|
||||
* Headers/Foundation/NSBundle.h ([+bundleForLibrary:version:]):
|
||||
New method; updated documentation for this method and for
|
||||
[+bundleForLibrary:].
|
||||
|
||||
* Resources/GNUmakefile: Include ../Version and install into the
|
||||
new versioned directory.
|
||||
* NSTimeZones/GNUmakefile: Same changes.
|
||||
* Source/GNUmakefile: Same changes.
|
||||
|
||||
* Source/NSBundle.m ([+bundleForClass:]): If we are asked for the
|
||||
bundle for NSObject, return _gnustep_bundle (prepared during
|
||||
+initialize) immediately.
|
||||
* Source/NSTimeZone.m (_time_zone_path): Use bundleForClass:
|
||||
NSObject to get the gnustep-base bundle immediately and safely.
|
||||
* Source/NSUserDefaults.m ([+standardUserDefaults]): Same change.
|
||||
|
||||
* Source/GNUmakefile (libgnustep-base_INTERFACE_VERSION,
|
||||
libgnustep-baseadd_INTERFACE_VERSION): Use more standard makefile
|
||||
syntax.
|
||||
|
||||
2007-03-09 Richard Frith-Macdonald <rfm@gnu.org>
|
||||
|
||||
* Source/NSProcessInfo.m: On mswindows, don't count a '.exe'
|
||||
|
|
|
@ -387,11 +387,17 @@ GS_EXPORT NSString* const NSLoadedClasses;
|
|||
@interface NSBundle (GNUstep)
|
||||
|
||||
/** This method is an experimental GNUstep extension, and might change.
|
||||
* <p>Return a bundle which accesses the first existing directory from
|
||||
* the standard libraries directories whose Resources subdirectory
|
||||
* contains libraryName.
|
||||
* Where libraryName is the name of a library without the <em>lib</em>
|
||||
* prefix or any extensions.
|
||||
* <p>Return a bundle to access the resources for the (static or shared) library
|
||||
* libraryName, with interface version interfaceVersion.
|
||||
* </p>
|
||||
* <p>Resources for shared libraries are stored into
|
||||
* GNUSTEP_LIBRARY/Libraries/libraryName/Versions/interfaceVersion/Resources/;
|
||||
* this method will search for the first such existing directory and return it.
|
||||
*</p>
|
||||
* <p>libraryName should be the name of a library without the
|
||||
* <em>lib</em> prefix or any extensions; interfaceVersion is the
|
||||
* interface version of the library (eg, it's 1.13 in libgnustep-base.so.1.13;
|
||||
* see library.make on how to control it).
|
||||
* </p>
|
||||
* <p>This method exists to provide resource bundles for libraries and has no
|
||||
* particular relationship to the library code itsself. The named library
|
||||
|
@ -409,8 +415,16 @@ GS_EXPORT NSString* const NSLoadedClasses;
|
|||
* not exist on disk.
|
||||
* </p>
|
||||
*/
|
||||
+ (NSBundle *) bundleForLibrary: (NSString *)libraryName
|
||||
version: (NSString *)interfaceVersion;
|
||||
|
||||
/** This method is a equivalent to bundleForLibrary:version: with a nil
|
||||
* version.
|
||||
*/
|
||||
+ (NSBundle *) bundleForLibrary: (NSString *)libraryName;
|
||||
|
||||
|
||||
|
||||
/** Find a resource in the "Library" directory. */
|
||||
+ (NSString*) pathForLibraryResource: (NSString*)name
|
||||
ofType: (NSString*)ext
|
||||
|
|
|
@ -39,7 +39,9 @@ include $(GNUSTEP_MAKEFILES)/common.make
|
|||
include ../Version
|
||||
include ../config.mak
|
||||
|
||||
resourcedir = $(GNUSTEP_RESOURCES)/gnustep-base
|
||||
libgnustep-base_INTERFACE_VERSION=$(MAJOR_VERSION).$(MINOR_VERSION)
|
||||
|
||||
resourcedir = $(GNUSTEP_LIBRARY)/Libraries/gnustep-base/Versions/$(libgnustep-base_INTERFACE_VERSION)/Resources
|
||||
|
||||
TIMEZONE_ARCHIVE = \
|
||||
NSTimeZones.tar
|
||||
|
|
|
@ -36,9 +36,12 @@ GNUSTEP_LOCAL_ADDITIONAL_MAKEFILES=../base.make
|
|||
|
||||
include $(GNUSTEP_MAKEFILES)/common.make
|
||||
|
||||
include ../Version
|
||||
libgnustep-base_INTERFACE_VERSION=$(MAJOR_VERSION).$(MINOR_VERSION)
|
||||
|
||||
RESOURCE_SET_NAME = base-resources
|
||||
# This is for gnustep-make >= 14-02-2007
|
||||
base-resources_INSTALL_DIR = $(GNUSTEP_RESOURCES)/gnustep-base
|
||||
base-resources_INSTALL_DIR = $(GNUSTEP_LIBRARY)/Libraries/gnustep-base/Versions/$(libgnustep-base_INTERFACE_VERSION)/Resources
|
||||
# This is kept temporarily for gnustep-make < 14-02-2007
|
||||
base-resources_RESOURCE_FILES_INSTALL_DIR = /Library/Libraries/Resources/gnustep-base
|
||||
base-resources_LANGUAGES = English German French Italian TraditionalChinese \
|
||||
|
|
|
@ -42,8 +42,8 @@ include ../Version
|
|||
include ../config.mak
|
||||
|
||||
# Interface version changes with each minor release
|
||||
libgnustep-base_INTERFACE_VERSION=${MAJOR_VERSION}.${MINOR_VERSION}
|
||||
libgnustep-baseadd_INTERFACE_VERSION=${MAJOR_VERSION}.${MINOR_VERSION}
|
||||
libgnustep-base_INTERFACE_VERSION=$(MAJOR_VERSION).$(MINOR_VERSION)
|
||||
libgnustep-baseadd_INTERFACE_VERSION=$(MAJOR_VERSION).$(MINOR_VERSION)
|
||||
|
||||
PACKAGE_NAME = gnustep-base
|
||||
|
||||
|
@ -421,7 +421,7 @@ libgnustep-base_HEADER_FILES = $(FOUNDATION_HEADERS)
|
|||
RESOURCE_SET_NAME = libbase-resources
|
||||
|
||||
# This is for gnustep-make >= 14-02-2007
|
||||
libbase-resources_INSTALL_DIR = $(GNUSTEP_LIBRARY)/Libraries/Resources/gnustep-base
|
||||
libbase-resources_INSTALL_DIR = $(GNUSTEP_LIBRARY)/Libraries/gnustep-base/Versions/$(libgnustep-base_INTERFACE_VERSION)/Resources
|
||||
# This is kept temporarily for gnustep-make < 14-02-2007
|
||||
libbase-resources_RESOURCE_FILES_INSTALL_DIR = /Library/Libraries/Resources/gnustep-base
|
||||
|
||||
|
|
|
@ -806,7 +806,8 @@ _bundle_load_callback(Class theClass, struct objc_category *theCategory)
|
|||
_launchDirectory = RETAIN([[NSFileManager defaultManager]
|
||||
currentDirectoryPath]);
|
||||
|
||||
_gnustep_bundle = RETAIN([self bundleForLibrary: @"gnustep-base"]);
|
||||
_gnustep_bundle = RETAIN([self bundleForLibrary: @"gnustep-base"
|
||||
version: OBJC_STRINGIFY(GNUSTEP_BASE_MAJOR_VERSION.GNUSTEP_BASE_MINOR_VERSION)]);
|
||||
|
||||
#if 0
|
||||
_loadingBundle = [self mainBundle];
|
||||
|
@ -1095,6 +1096,14 @@ _bundle_load_callback(Class theClass, struct objc_category *theCategory)
|
|||
if (!aClass)
|
||||
return nil;
|
||||
|
||||
/* This is asked relatively frequently inside gnustep-base itself;
|
||||
* shortcut it.
|
||||
*/
|
||||
if (aClass == [NSObject class])
|
||||
{
|
||||
return _gnustep_bundle;
|
||||
}
|
||||
|
||||
[load_lock lock];
|
||||
bundle = nil;
|
||||
enumerate = NSEnumerateMapTable(_bundles);
|
||||
|
@ -1127,8 +1136,8 @@ _bundle_load_callback(Class theClass, struct objc_category *theCategory)
|
|||
|
||||
/*
|
||||
* Take the path to the binary containing the class and
|
||||
* convert it to the format for a library name as used
|
||||
* for obtaining a library resource bundle.
|
||||
* convert it to the format for a library name as used for
|
||||
* obtaining a library resource bundle.
|
||||
*/
|
||||
lib = GSPrivateSymbolPath (aClass, NULL);
|
||||
if ([lib isEqual: GSPrivateExecutablePath()] == YES)
|
||||
|
@ -1137,9 +1146,13 @@ _bundle_load_callback(Class theClass, struct objc_category *theCategory)
|
|||
}
|
||||
|
||||
/*
|
||||
* Get the library bundle ... if there wasn't one
|
||||
* then we will assume the class was in the program
|
||||
* executable and return the mainBundle instead.
|
||||
* Get the library bundle ... if there wasn't one then we
|
||||
* will assume the class was in the program executable and
|
||||
* return the mainBundle instead.
|
||||
*
|
||||
* FIXME: This will not work well with versioned library
|
||||
* resources. It used to work fine (maybe) with unversioned
|
||||
* library resources.
|
||||
*/
|
||||
bundle = [NSBundle bundleForLibrary: lib];
|
||||
if (bundle == nil)
|
||||
|
@ -1148,9 +1161,9 @@ _bundle_load_callback(Class theClass, struct objc_category *theCategory)
|
|||
}
|
||||
|
||||
/*
|
||||
* Add the class to the list of classes known to be in
|
||||
* the library or executable. We didn't find it there
|
||||
* to start with, so we know it's safe to add now.
|
||||
* Add the class to the list of classes known to be in the
|
||||
* library or executable. We didn't find it there to start
|
||||
* with, so we know it's safe to add now.
|
||||
*/
|
||||
if (bundle->_bundleClasses == nil)
|
||||
{
|
||||
|
@ -2176,11 +2189,16 @@ _bundle_load_callback(Class theClass, struct objc_category *theCategory)
|
|||
@implementation NSBundle (GNUstep)
|
||||
|
||||
+ (NSBundle *) bundleForLibrary: (NSString *)libraryName
|
||||
{
|
||||
return [self bundleForLibrary: libraryName version: nil];
|
||||
}
|
||||
|
||||
+ (NSBundle *) bundleForLibrary: (NSString *)libraryName
|
||||
version: (NSString *)interfaceVersion
|
||||
{
|
||||
NSArray *paths;
|
||||
NSEnumerator *enumerator;
|
||||
NSString *path;
|
||||
NSString *tail;
|
||||
NSFileManager *fm = [NSFileManager defaultManager];
|
||||
|
||||
/*
|
||||
|
@ -2199,41 +2217,101 @@ _bundle_load_callback(Class theClass, struct objc_category *theCategory)
|
|||
{
|
||||
libraryName = [libraryName substringFromIndex: 3];
|
||||
}
|
||||
/*
|
||||
* Discard debug/profile library suffix
|
||||
*/
|
||||
if ([libraryName hasSuffix: @"_d"] == YES
|
||||
|| [libraryName hasSuffix: @"_p"] == YES)
|
||||
{
|
||||
libraryName = [libraryName substringToIndex: [libraryName length] - 3];
|
||||
}
|
||||
|
||||
if ([libraryName length] == 0)
|
||||
{
|
||||
return nil;
|
||||
}
|
||||
|
||||
tail = [@"Libraries" stringByAppendingPathComponent:
|
||||
[@"Resources" stringByAppendingPathComponent: libraryName]];
|
||||
|
||||
/*
|
||||
* We expect to find the library resources into:
|
||||
*
|
||||
* GNUSTEP_LIBRARY/Libraries/<libraryName>/Versions/<interfaceVersion>/Resources/
|
||||
*
|
||||
* if no <interfaceVersion> is specified, and if can't find any versioned
|
||||
* resources in those directories, we'll also accept the old unversioned format
|
||||
*
|
||||
* GNUSTEP_LIBRARY/Libraries/Resources/<libraryName>/
|
||||
*
|
||||
*/
|
||||
paths = NSSearchPathForDirectoriesInDomains (NSLibraryDirectory,
|
||||
NSAllDomainsMask, YES);
|
||||
|
||||
|
||||
enumerator = [paths objectEnumerator];
|
||||
while ((path = [enumerator nextObject]))
|
||||
while ((path = [enumerator nextObject]) != nil)
|
||||
{
|
||||
NSBundle *b;
|
||||
BOOL isDir;
|
||||
path = [path stringByAppendingPathComponent: tail];
|
||||
path = [path stringByAppendingPathComponent: @"Libraries"];
|
||||
|
||||
if ([fm fileExistsAtPath: path isDirectory: &isDir] && isDir)
|
||||
{
|
||||
NSBundle *b = [self bundleWithPath: path];
|
||||
|
||||
if (b != nil && b->_bundleType == NSBUNDLE_BUNDLE)
|
||||
if (interfaceVersion != nil)
|
||||
{
|
||||
b->_bundleType = NSBUNDLE_LIBRARY;
|
||||
/* We're looking for a specific version. */
|
||||
path = [[[[path stringByAppendingPathComponent: libraryName]
|
||||
stringByAppendingPathComponent: @"Versions"]
|
||||
stringByAppendingPathComponent: interfaceVersion]
|
||||
stringByAppendingPathComponent: @"Resources"];
|
||||
if ([fm fileExistsAtPath: path isDirectory: &isDir] && isDir)
|
||||
{
|
||||
b = [self bundleWithPath: path];
|
||||
|
||||
if (b != nil && b->_bundleType == NSBUNDLE_BUNDLE)
|
||||
{
|
||||
b->_bundleType = NSBUNDLE_LIBRARY;
|
||||
}
|
||||
return b;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Any version will do. */
|
||||
NSString *versionsPath = [[path stringByAppendingPathComponent: libraryName]
|
||||
stringByAppendingPathComponent: @"Versions"];
|
||||
if ([fm fileExistsAtPath: versionsPath isDirectory: &isDir] && isDir)
|
||||
{
|
||||
NSEnumerator *fileEnumerator = [fm enumeratorAtPath: versionsPath];
|
||||
NSString *potentialPath;
|
||||
|
||||
while ((potentialPath = [fileEnumerator nextObject]) != nil)
|
||||
{
|
||||
potentialPath = [potentialPath stringByAppendingPathComponent: @"Resources"];
|
||||
if ([fm fileExistsAtPath: potentialPath isDirectory: &isDir] && isDir)
|
||||
{
|
||||
b = [self bundleWithPath: potentialPath];
|
||||
|
||||
if (b != nil && b->_bundleType == NSBUNDLE_BUNDLE)
|
||||
{
|
||||
b->_bundleType = NSBUNDLE_LIBRARY;
|
||||
}
|
||||
return b;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* We didn't find anything! For backwards
|
||||
* compatibility, try the unversioned directory itself:
|
||||
* we used to put library resources directly in
|
||||
* unversioned directories such as
|
||||
* GNUSTEP_LIBRARY/Libraries/Resources/gnustep-base/{resources
|
||||
* here}. This was deprecated/obsoleted on 9 March 2007
|
||||
* when we added library resource versioning.
|
||||
*/
|
||||
{
|
||||
NSString *oldResourcesPath = [[path stringByAppendingPathComponent: @"Resources"]
|
||||
stringByAppendingPathComponent: libraryName];
|
||||
if ([fm fileExistsAtPath: oldResourcesPath isDirectory: &isDir] && isDir)
|
||||
{
|
||||
b = [self bundleWithPath: oldResourcesPath];
|
||||
if (b != nil && b->_bundleType == NSBUNDLE_BUNDLE)
|
||||
{
|
||||
b->_bundleType = NSBUNDLE_LIBRARY;
|
||||
}
|
||||
return b;
|
||||
}
|
||||
}
|
||||
}
|
||||
return b;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -273,7 +273,7 @@ static NSString *_time_zone_path(NSString *subpath, NSString *type)
|
|||
NSBundle *gbundle;
|
||||
if (type == nil)
|
||||
type = @"";
|
||||
gbundle = [NSBundle bundleForLibrary: @"gnustep-base"];
|
||||
gbundle = [NSBundle bundleForClass: [NSObject class]];
|
||||
return [gbundle pathForResource: subpath
|
||||
ofType: type
|
||||
inDirectory: TIME_ZONE_DIR];
|
||||
|
|
|
@ -502,7 +502,7 @@ static BOOL setSharedDefaults = NO; /* Flag to prevent infinite recursion */
|
|||
NSDictionary *dict;
|
||||
NSBundle *gbundle;
|
||||
|
||||
gbundle = [NSBundle bundleForLibrary: @"gnustep-base"];
|
||||
gbundle = [NSBundle bundleForClass: [NSObject class]];
|
||||
path = [gbundle pathForResource: lang
|
||||
ofType: nil
|
||||
inDirectory: @"Languages"];
|
||||
|
|
Loading…
Reference in a new issue